Mercurial > vim
changeset 36211:57a9f3d2ea2b v9.1.0748
patch 9.1.0748: :keep* commmands are sometimes misidentified as :k
Commit: https://github.com/vim/vim/commit/ea84202372061be9b5a9d16b360d5a17d93ccf7e
Author: Doug Kearns <dougkearns@gmail.com>
Date: Sun Sep 29 17:17:41 2024 +0200
patch 9.1.0748: :keep* commmands are sometimes misidentified as :k
Problem: The :keep{alt,jumps,marks,patterns} commmands are sometimes
misidentified as :k.
Solution: Make sure one_letter_cmd() only returns true for :k and not
other :keep* commands (Doug Kearns).
This currently manifests as missing completion for :keep* commands and
incorrect results from fullcommand().
E.g., fullcommand("keepmarks") returns "k" rather than "keepmarks".
The correct command, however, is executed as command modifiers are
handled specially in do_one_cmd() rather than using find_ex_command().
Fix exists(':k') so that it returns 2 for a full match.
closes: #15742
Signed-off-by: Doug Kearns <dougkearns@gmail.com>
Signed-off-by: Christian Brabandt <cb@256bit.org>
author | Christian Brabandt <cb@256bit.org> |
---|---|
date | Sun, 29 Sep 2024 17:30:03 +0200 |
parents | 382b2b7da177 |
children | 91e684beb001 |
files | src/ex_docmd.c src/testdir/test_cmdline.vim src/testdir/test_cmdmods.vim src/testdir/test_exists.vim src/version.c |
diffstat | 5 files changed, 59 insertions(+), 3 deletions(-) [+] |
line wrap: on
line diff
--- a/src/ex_docmd.c +++ b/src/ex_docmd.c @@ -3584,7 +3584,9 @@ skip_option_env_lead(char_u *start) /* * Return TRUE and set "*idx" if "p" points to a one letter command. * If not in Vim9 script: - * - The 'k' command can directly be followed by any character. + * - The 'k' command can directly be followed by any character + * but :keepa[lt] is another command, as are :keepj[umps], + * :kee[pmarks] and :keepp[atterns]. * - The 's' command can be followed directly by 'c', 'g', 'i', 'I' or 'r' * but :sre[wind] is another command, as are :scr[iptnames], * :scs[cope], :sim[alt], :sig[ns] and :sil[ent]. @@ -3594,7 +3596,8 @@ one_letter_cmd(char_u *p, cmdidx_T *idx) { if (in_vim9script()) return FALSE; - if (*p == 'k') + if (p[0] == 'k' + && (p[1] != 'e' || (p[1] == 'e' && p[2] != 'e'))) { *idx = CMD_k; return TRUE; @@ -3880,6 +3883,8 @@ find_ex_command( if (one_letter_cmd(p, &eap->cmdidx)) { ++p; + if (full != NULL) + *full = TRUE; } else {
--- a/src/testdir/test_cmdline.vim +++ b/src/testdir/test_cmdline.vim @@ -1195,6 +1195,10 @@ func Test_cmdline_complete_various() call feedkeys(":ka\<C-A>\<C-B>\"\<CR>", 'xt') call assert_equal("\"ka\<C-A>", @:) + " completion for :keepmarks command + call feedkeys(":kee edi\<C-A>\<C-B>\"\<CR>", 'xt') + call assert_equal("\"kee edit", @:) + " completion for short version of the :s command call feedkeys(":sI \<C-A>\<C-B>\"\<CR>", 'xt') call assert_equal("\"sI \<C-A>", @:) @@ -3901,7 +3905,7 @@ func Test_ex_command_completion() let list = filter(getcompletion('', 'command'), 'exists(":" . v:val) == 0') " :++ and :-- are only valid in Vim9 Script context, so they can be ignored call assert_equal(['++', '--'], sort(list)) - call assert_equal(1, exists(':k')) + call assert_equal(2, exists(':k')) call assert_equal(0, exists(':ke')) call assert_equal(1, exists(':kee')) call assert_equal(1, exists(':keep'))
--- a/src/testdir/test_cmdmods.vim +++ b/src/testdir/test_cmdmods.vim @@ -40,6 +40,44 @@ def Test_cmdmods_array() bwipe! enddef +def Test_keep_cmdmods_names() + # :k only available in legacy script + legacy call assert_equal('k', fullcommand(':k')) + legacy call assert_equal('k', fullcommand(':ke')) + # single character commands not supported in Vim9 + assert_equal('', fullcommand(':k')) + assert_equal('keepmarks', fullcommand(':ke')) + assert_equal('keepmarks', fullcommand(':kee')) + assert_equal('keepmarks', fullcommand(':keep')) + assert_equal('keepmarks', fullcommand(':keepm')) + assert_equal('keepmarks', fullcommand(':keepma')) + assert_equal('keepmarks', fullcommand(':keepmar')) + assert_equal('keepmarks', fullcommand(':keepmark')) + assert_equal('keepmarks', fullcommand(':keepmarks')) + assert_equal('keepalt', fullcommand(':keepa')) + assert_equal('keepalt', fullcommand(':keepal')) + assert_equal('keepalt', fullcommand(':keepalt')) + assert_equal('keepjumps', fullcommand(':keepj')) + assert_equal('keepjumps', fullcommand(':keepju')) + assert_equal('keepjumps', fullcommand(':keepjum')) + assert_equal('keepjumps', fullcommand(':keepjump')) + assert_equal('keepjumps', fullcommand(':keepjumps')) + assert_equal('keeppatterns', fullcommand(':keepp')) + assert_equal('keeppatterns', fullcommand(':keeppa')) + assert_equal('keeppatterns', fullcommand(':keeppat')) + assert_equal('keeppatterns', fullcommand(':keeppatt')) + assert_equal('keeppatterns', fullcommand(':keeppatte')) + assert_equal('keeppatterns', fullcommand(':keeppatter')) + assert_equal('keeppatterns', fullcommand(':keeppattern')) + assert_equal('keeppatterns', fullcommand(':keeppatterns')) +enddef + +def Test_cmdmod_completion() + assert_equal('edit', getcompletion('keepalt ed', 'cmdline')[0]) + assert_equal('edit', getcompletion('keepjumps ed', 'cmdline')[0]) + assert_equal('edit', getcompletion('keepmarks ed', 'cmdline')[0]) + assert_equal('edit', getcompletion('keeppatterns ed', 'cmdline')[0]) +enddef " vim: shiftwidth=2 sts=2 expandtab
--- a/src/testdir/test_exists.vim +++ b/src/testdir/test_exists.vim @@ -113,6 +113,13 @@ func Test_exists() " Internal command with a count call assert_equal(0, exists(':3buffer')) + " Valid internal command (full match) + call assert_equal(2, exists(':k')) + " Non-existing internal command (':k' with arg 'e') + call assert_equal(0, exists(':ke')) + " Valid internal command (partial match) + call assert_equal(1, exists(':kee')) + " User defined command (full match) command! MyCmd :echo 'My command' call assert_equal(2, exists(':MyCmd'))