]> granicus.if.org Git - vim/commitdiff
patch 8.2.1653: expand('<stack>') does not include the final line number v8.2.1653
authorBram Moolenaar <Bram@vim.org>
Thu, 10 Sep 2020 17:25:05 +0000 (19:25 +0200)
committerBram Moolenaar <Bram@vim.org>
Thu, 10 Sep 2020 17:25:05 +0000 (19:25 +0200)
Problem:    Expand('<stack>') does not include the final line number.
Solution:   Add the line nuber. (closes #6927)

src/debugger.c
src/ex_docmd.c
src/ex_eval.c
src/message.c
src/proto/scriptfile.pro
src/scriptfile.c
src/testdir/test_expand_func.vim
src/testing.c
src/version.c
src/vim.h

index 00fb9c8f8bc09d42a529560428e61b6e949fde72..f745761f10e4854115da5244696f1c6820dd3375 100644 (file)
@@ -105,7 +105,7 @@ do_debug(char_u *cmd)
        vim_free(debug_newval);
        debug_newval = NULL;
     }
-    sname = estack_sfile(FALSE);
+    sname = estack_sfile(ESTACK_NONE);
     if (sname != NULL)
        msg((char *)sname);
     vim_free(sname);
@@ -344,7 +344,7 @@ do_checkbacktracelevel(void)
     }
     else
     {
-       char_u  *sname = estack_sfile(FALSE);
+       char_u  *sname = estack_sfile(ESTACK_NONE);
        int     max = get_maxbacktrace_level(sname);
 
        if (debug_backtrace_level > max)
@@ -365,7 +365,7 @@ do_showbacktrace(char_u *cmd)
     int            i = 0;
     int            max;
 
-    sname = estack_sfile(FALSE);
+    sname = estack_sfile(ESTACK_NONE);
     max = get_maxbacktrace_level(sname);
     if (sname != NULL)
     {
index 1d3cfcdcd078e5f8b5c98a0887b8397cd3ee4009..6495db6e833e8cc8f55321bb9e4038a67aeb03de 100644 (file)
@@ -8389,6 +8389,7 @@ find_cmdline_var(char_u *src, int *usedlen)
  *       '<cexpr>' to C-expression under the cursor
  *       '<cfile>' to path name under the cursor
  *       '<sfile>' to sourced file name
+ *       '<stack>' to call stack
  *       '<slnum>' to sourced file line number
  *       '<afile>' to file name for autocommand
  *       '<abuf>'  to buffer number for autocommand
@@ -8606,7 +8607,8 @@ eval_vars(
 
        case SPEC_SFILE:        // file name for ":so" command
        case SPEC_STACK:        // call stack
-               result = estack_sfile(spec_idx == SPEC_SFILE);
+               result = estack_sfile(spec_idx == SPEC_SFILE
+                                               ? ESTACK_SFILE : ESTACK_STACK);
                if (result == NULL)
                {
                    *errormsg = spec_idx == SPEC_SFILE
index 58088a0706f43be41b53826aa030e802dbbaf47e..cbdf82e893183f6bee1b4f973079eb2a5de1085a 100644 (file)
@@ -290,7 +290,7 @@ cause_errthrow(
 
                    // Get the source name and lnum now, it may change before
                    // reaching do_errthrow().
-                   elem->sfile = estack_sfile(FALSE);
+                   elem->sfile = estack_sfile(ESTACK_NONE);
                    elem->slnum = SOURCING_LNUM;
                }
            }
@@ -549,7 +549,7 @@ throw_exception(void *value, except_type_T type, char_u *cmdname)
     }
     else
     {
-       excp->throw_name = estack_sfile(FALSE);
+       excp->throw_name = estack_sfile(ESTACK_NONE);
        if (excp->throw_name == NULL)
            excp->throw_name = vim_strsave((char_u *)"");
        if (excp->throw_name == NULL)
index a9851efab0c9b87c18b30989cf9af55c30ef667c..059835af0daaa5f480b5c715cbfba092daae2c10 100644 (file)
@@ -461,7 +461,7 @@ get_emsg_source(void)
 
     if (SOURCING_NAME != NULL && other_sourcing_name())
     {
-       char_u      *sname = estack_sfile(FALSE);
+       char_u      *sname = estack_sfile(ESTACK_NONE);
        char_u      *tofree = sname;
 
        if (sname == NULL)
index 52df2ca82ebcf356b41ca2af261b669dcc0ee525..cbb9253c5228ab69625b58640c124d5314fc25cf 100644 (file)
@@ -4,7 +4,7 @@ estack_T *estack_push(etype_T type, char_u *name, long lnum);
 estack_T *estack_push_ufunc(ufunc_T *ufunc, long lnum);
 int estack_top_is_ufunc(ufunc_T *ufunc, long lnum);
 estack_T *estack_pop(void);
-char_u *estack_sfile(int is_sfile);
+char_u *estack_sfile(estack_arg_T which);
 void ex_runtime(exarg_T *eap);
 int do_in_path(char_u *path, char_u *name, int flags, void (*callback)(char_u *fname, void *ck), void *cookie);
 int do_in_runtimepath(char_u *name, int flags, void (*callback)(char_u *fname, void *ck), void *cookie);
index e07523695306bd2782bd610748724ba5d2e0bc80..75182ca511487322186de6ff54c053942b671c31 100644 (file)
@@ -111,10 +111,10 @@ estack_pop(void)
 
 /*
  * Get the current value for <sfile> in allocated memory.
- * "is_sfile" is TRUE for <sfile> itself.
+ * "which" is ESTACK_SFILE for <sfile> and ESTACK_STACK for <stack>.
  */
     char_u *
-estack_sfile(int is_sfile UNUSED)
+estack_sfile(estack_arg_T which UNUSED)
 {
     estack_T   *entry;
 #ifdef FEAT_EVAL
@@ -127,7 +127,7 @@ estack_sfile(int is_sfile UNUSED)
 
     entry = ((estack_T *)exestack.ga_data) + exestack.ga_len - 1;
 #ifdef FEAT_EVAL
-    if (is_sfile && entry->es_type != ETYPE_UFUNC)
+    if (which == ESTACK_SFILE && entry->es_type != ETYPE_UFUNC)
 #endif
     {
        if (entry->es_name == NULL)
@@ -144,6 +144,8 @@ estack_sfile(int is_sfile UNUSED)
        entry = ((estack_T *)exestack.ga_data) + idx;
        if (entry->es_name != NULL)
        {
+           long lnum = 0;
+
            len = STRLEN(entry->es_name) + 15;
            type_name = "";
            if (entry->es_type != last_type)
@@ -159,15 +161,20 @@ estack_sfile(int is_sfile UNUSED)
            len += STRLEN(type_name);
            if (ga_grow(&ga, (int)len) == FAIL)
                break;
-           if (idx == exestack.ga_len - 1 || entry->es_lnum == 0)
-               // For the bottom entry: do not add the line number, it is used
-               // in <slnum>.  Also leave it out when the number is not set.
+           if (idx == exestack.ga_len - 1)
+               lnum = which == ESTACK_STACK ? SOURCING_LNUM : 0;
+           else
+               lnum = entry->es_lnum;
+           if (lnum == 0)
+               // For the bottom entry of <sfile>: do not add the line number,
+               // it is used in <slnum>.  Also leave it out when the number is
+               // not set.
                vim_snprintf((char *)ga.ga_data + ga.ga_len, len, "%s%s%s",
                                type_name, entry->es_name,
                                idx == exestack.ga_len - 1 ? "" : "..");
            else
                vim_snprintf((char *)ga.ga_data + ga.ga_len, len, "%s%s[%ld]..",
-                                   type_name, entry->es_name, entry->es_lnum);
+                                   type_name, entry->es_name, lnum);
            ga.ga_len += (int)STRLEN((char *)ga.ga_data + ga.ga_len);
        }
     }
index 42aa8e01bcd540e5a2b48cee3e9293a16994f595..a63cc04e1f97faae12dd354b704388dba8972589 100644 (file)
@@ -39,9 +39,9 @@ endfunc
 
 func Test_expand_sfile_and_stack()
   call assert_match('test_expand_func\.vim$', s:sfile)
-  let expected = 'script .*testdir/runtest.vim\[\d\+\]\.\.function RunTheTest\[\d\+\]\.\.Test_expand_sfile_and_stack$'
-  call assert_match(expected , expand('<sfile>'))
-  call assert_match(expected , expand('<stack>'))
+  let expected = 'script .*testdir/runtest.vim\[\d\+\]\.\.function RunTheTest\[\d\+\]\.\.Test_expand_sfile_and_stack'
+  call assert_match(expected .. '$', expand('<sfile>'))
+  call assert_match(expected .. '\[4\]' , expand('<stack>'))
 
   " Call in script-local function
   call assert_match('script .*testdir/runtest.vim\[\d\+\]\.\.function RunTheTest\[\d\+\]\.\.Test_expand_sfile_and_stack\[7\]\.\.<SNR>\d\+_expand_sfile$', s:expand_sfile())
@@ -53,11 +53,12 @@ func Test_expand_sfile_and_stack()
 
   " Use <stack> from sourced script.
   let lines =<< trim END
+    " comment here
     let g:stack_value = expand('<stack>')
   END
   call writefile(lines, 'Xstack')
   source Xstack
-  call assert_match('\<Xstack$', g:stack_value)
+  call assert_match('\<Xstack\[2\]', g:stack_value)
   call delete('Xstack')
 endfunc
 
index 8db7d62ed415d3ec97a693a00b063fea0f803449..8115441033bf9a38a7b4f0ace5faa87a1e2a0f96 100644 (file)
@@ -22,7 +22,7 @@
 prepare_assert_error(garray_T *gap)
 {
     char    buf[NUMBUFLEN];
-    char_u  *sname = estack_sfile(FALSE);
+    char_u  *sname = estack_sfile(ESTACK_NONE);
 
     ga_init2(gap, 1, 100);
     if (sname != NULL)
index 9159209f38822d2c9f4dbb4b7f47dad0f33a8598..c22ec480cf46a7ec88089b435e862876e4c7ff22 100644 (file)
@@ -750,6 +750,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1653,
 /**/
     1652,
 /**/
index 7bcc488c81becf23b01c8c1f338dae7fa2d72769..60a565b0a56a3514d051d5177efd36aba30ec04b 100644 (file)
--- a/src/vim.h
+++ b/src/vim.h
@@ -2097,8 +2097,7 @@ typedef struct stat stat_T;
 # define USE_PRINTF_FORMAT_ATTRIBUTE
 #endif
 
-typedef enum
-{
+typedef enum {
     ASSERT_EQUAL,
     ASSERT_NOTEQUAL,
     ASSERT_MATCH,
@@ -2128,6 +2127,13 @@ typedef enum {
     USEPOPUP_HIDDEN    // use info popup initially hidden
 } use_popup_T;
 
+// Argument for estack_sfile().
+typedef enum {
+    ESTACK_NONE,
+    ESTACK_SFILE,
+    ESTACK_STACK
+} estack_arg_T;
+
 // Flags for assignment functions.
 #define LET_IS_CONST   1   // ":const"
 #define LET_NO_COMMAND 2   // "var = expr" without ":let" or ":const"