]> granicus.if.org Git - vim/commitdiff
patch 8.2.2228: Vim9: cannot use ":e #" because # starts a comment v8.2.2228
authorBram Moolenaar <Bram@vim.org>
Sun, 27 Dec 2020 15:55:11 +0000 (16:55 +0100)
committerBram Moolenaar <Bram@vim.org>
Sun, 27 Dec 2020 15:55:11 +0000 (16:55 +0100)
Problem:    Vim9: cannot use ":e #" because # starts a comment.
Solution:   Support using %% instead of #.

src/ex_docmd.c
src/testdir/test_vim9_cmd.vim
src/version.c

index 156f0df16a302b2c727940e5f7498b9f86949e34..5e90ad16a3f535b9bb32349ed893d93a2c1144f8 100644 (file)
@@ -8535,18 +8535,19 @@ find_cmdline_var(char_u *src, int *usedlen)
 /*
  * Evaluate cmdline variables.
  *
- * change '%'      to curbuf->b_ffname
- *       '#'       to curwin->w_alt_fnum
- *       '<cword>' to word under the cursor
- *       '<cWORD>' to WORD under the cursor
- *       '<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
- *       '<amatch>' to matching name for autocommand
+ * change "%"      to curbuf->b_ffname
+ *       "#"       to curwin->w_alt_fnum
+ *       "%%"      to curwin->w_alt_fnum in Vim9 script
+ *       "<cword>" to word under the cursor
+ *       "<cWORD>" to WORD under the cursor
+ *       "<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
+ *       "<amatch>" to matching name for autocommand
  *
  * When an error is detected, "errormsg" is set to a non-NULL pointer (may be
  * "" for error without a message) and NULL is returned.
@@ -8627,47 +8628,57 @@ eval_vars(
      */
     else
     {
+       int off = 0;
+
        switch (spec_idx)
        {
-       case SPEC_PERC:         // '%': current file
-               if (curbuf->b_fname == NULL)
-               {
-                   result = (char_u *)"";
-                   valid = 0;      // Must have ":p:h" to be valid
-               }
-               else
+       case SPEC_PERC:
+               if (!in_vim9script() || src[1] != '%')
                {
-                   result = curbuf->b_fname;
-                   tilde_file = STRCMP(result, "~") == 0;
+                   // '%': current file
+                   if (curbuf->b_fname == NULL)
+                   {
+                       result = (char_u *)"";
+                       valid = 0;          // Must have ":p:h" to be valid
+                   }
+                   else
+                   {
+                       result = curbuf->b_fname;
+                       tilde_file = STRCMP(result, "~") == 0;
+                   }
+                   break;
                }
-               break;
+               // "%%" alternate file
+               off = 1;
+               // FALLTHROUGH
 
        case SPEC_HASH:         // '#' or "#99": alternate file
-               if (src[1] == '#')  // "##": the argument list
+               if (off == 0 ? src[1] == '#' : src[2] == '%')
                {
+                   // "##" or "%%%": the argument list
                    result = arg_all();
                    resultbuf = result;
-                   *usedlen = 2;
+                   *usedlen = off + 2;
                    if (escaped != NULL)
                        *escaped = TRUE;
                    skip_mod = TRUE;
                    break;
                }
-               s = src + 1;
+               s = src + off + 1;
                if (*s == '<')          // "#<99" uses v:oldfiles
                    ++s;
                i = (int)getdigits(&s);
-               if (s == src + 2 && src[1] == '-')
+               if (s == src + off + 2 && src[off + 1] == '-')
                    // just a minus sign, don't skip over it
                    s--;
                *usedlen = (int)(s - src); // length of what we expand
 
-               if (src[1] == '<' && i != 0)
+               if (src[off + 1] == '<' && i != 0)
                {
-                   if (*usedlen < 2)
+                   if (*usedlen < off + 2)
                    {
                        // Should we give an error message for #<text?
-                       *usedlen = 1;
+                       *usedlen = off + 1;
                        return NULL;
                    }
 #ifdef FEAT_EVAL
@@ -8685,8 +8696,8 @@ eval_vars(
                }
                else
                {
-                   if (i == 0 && src[1] == '<' && *usedlen > 1)
-                       *usedlen = 1;
+                   if (i == 0 && src[off + 1] == '<' && *usedlen > off + 1)
+                       *usedlen = off + 1;
                    buf = buflist_findnr(i);
                    if (buf == NULL)
                    {
index f5619b488d1ec1a49b44bb3d50034a877e90f3e3..b6644e394b83624a6f63a9c5e2655310f84d5b56 100644 (file)
@@ -25,6 +25,53 @@ def Test_edit_wildcards()
   CheckDefFailure(['edit `="foo"'], 'E1083:')
 enddef
 
+def Test_expand_alternate_file()
+  var lines =<< trim END
+    edit Xfileone
+    var bone = bufnr()
+    edit Xfiletwo
+    var btwo = bufnr()
+    edit Xfilethree
+    var bthree = bufnr()
+
+    edit #
+    assert_equal(bthree, bufnr())
+    edit %%
+    assert_equal(btwo, bufnr())
+    edit %% # comment
+    assert_equal(bthree, bufnr())
+    edit %%yy
+    assert_equal('Xfiletwoyy', bufname())
+
+    exe "edit %%" .. bone
+    assert_equal(bone, bufnr())
+    exe "edit %%" .. btwo .. "xx"
+    assert_equal('Xfiletwoxx', bufname())
+
+    next Xfileone Xfiletwo Xfilethree
+    assert_equal('Xfileone', argv(0))
+    assert_equal('Xfiletwo', argv(1))
+    assert_equal('Xfilethree', argv(2))
+    next %%%zz
+    assert_equal('Xfileone', argv(0))
+    assert_equal('Xfiletwo', argv(1))
+    assert_equal('Xfilethreezz', argv(2))
+
+    v:oldfiles = ['Xonefile', 'Xtwofile']
+    edit %%<1
+    assert_equal('Xonefile', bufname())
+    edit %%<2
+    assert_equal('Xtwofile', bufname())
+    assert_fails('edit %%<3', 'E684:')
+
+    edit Xfileone.vim
+    edit Xfiletwo
+    edit %%:r
+    assert_equal('Xfileone', bufname())
+  END
+  CheckDefAndScriptSuccess(lines)
+enddef
+
 def Test_global_backtick_expansion()
   new
   setline(1, 'xx')
index f9216ced87c1fd4c3b3a65ad941e41b5d2d0f1f8..985e48e6b07932a1cc7ac0376738ec4098912615 100644 (file)
@@ -750,6 +750,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    2228,
 /**/
     2227,
 /**/