mirror of
https://github.com/neovim/neovim.git
synced 2024-12-19 18:55:14 -07:00
vim-patch:8.1.1241: Ex command info contains confusing information
Problem: Ex command info contains confusing information. Solution: When using the NOTADR flag use ADDR_OTHER for the address type. Cleanup code using NOTADR. Check for errors in create_cmdidxs.vim. Adjust Makefile to see the errors.b731689e85
Use Lua's "assert()" to make an invalid command definition a compilation error. Misc changes: Remove 'RESTRICT' flag. Neovim does not support "restricted" mode since commit7777532ceb
. TODO: Do not generate files before Lua assertions so that CMake always runs the generator script if the previous build has an invalid command definition.
This commit is contained in:
parent
cf3a861017
commit
f3c242c13c
@ -55,7 +55,7 @@ end
|
||||
vimcmd_start = 'syn keyword vimCommand contained '
|
||||
w(vimcmd_start)
|
||||
local prev_cmd = nil
|
||||
for _, cmd_desc in ipairs(ex_cmds) do
|
||||
for _, cmd_desc in ipairs(ex_cmds.cmds) do
|
||||
if lld.line_length > 850 then
|
||||
w('\n' .. vimcmd_start)
|
||||
end
|
||||
|
@ -1032,14 +1032,15 @@ void free_prev_shellcmd(void)
|
||||
* Bangs in the argument are replaced with the previously entered command.
|
||||
* Remember the argument.
|
||||
*/
|
||||
void do_bang(int addr_count, exarg_T *eap, int forceit, int do_in, int do_out)
|
||||
void do_bang(int addr_count, exarg_T *eap, bool forceit,
|
||||
bool do_in, bool do_out)
|
||||
FUNC_ATTR_NONNULL_ALL
|
||||
{
|
||||
char_u *arg = eap->arg; /* command */
|
||||
linenr_T line1 = eap->line1; /* start of range */
|
||||
linenr_T line2 = eap->line2; /* end of range */
|
||||
char_u *newcmd = NULL; /* the new command */
|
||||
int free_newcmd = FALSE; /* need to free() newcmd */
|
||||
int ins_prevcmd;
|
||||
char_u *arg = eap->arg; // command
|
||||
linenr_T line1 = eap->line1; // start of range
|
||||
linenr_T line2 = eap->line2; // end of range
|
||||
char_u *newcmd = NULL; // the new command
|
||||
bool free_newcmd = false; // need to free() newcmd
|
||||
char_u *t;
|
||||
char_u *p;
|
||||
char_u *trailarg;
|
||||
@ -1064,7 +1065,7 @@ void do_bang(int addr_count, exarg_T *eap, int forceit, int do_in, int do_out)
|
||||
* Try to find an embedded bang, like in :!<cmd> ! [args]
|
||||
* (:!! is indicated by the 'forceit' variable)
|
||||
*/
|
||||
ins_prevcmd = forceit;
|
||||
bool ins_prevcmd = forceit;
|
||||
trailarg = arg;
|
||||
do {
|
||||
len = (int)STRLEN(trailarg) + 1;
|
||||
@ -1101,7 +1102,7 @@ void do_bang(int addr_count, exarg_T *eap, int forceit, int do_in, int do_out)
|
||||
else {
|
||||
trailarg = p;
|
||||
*trailarg++ = NUL;
|
||||
ins_prevcmd = TRUE;
|
||||
ins_prevcmd = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -1131,7 +1132,7 @@ void do_bang(int addr_count, exarg_T *eap, int forceit, int do_in, int do_out)
|
||||
STRCPY(newcmd, p_shq);
|
||||
STRCAT(newcmd, prevcmd);
|
||||
STRCAT(newcmd, p_shq);
|
||||
free_newcmd = TRUE;
|
||||
free_newcmd = true;
|
||||
}
|
||||
if (addr_count == 0) { /* :! */
|
||||
/* echo the command */
|
||||
@ -1164,15 +1165,15 @@ void do_bang(int addr_count, exarg_T *eap, int forceit, int do_in, int do_out)
|
||||
// do this.
|
||||
// Alternatively, if on Unix and redirecting input or output, but not both,
|
||||
// and the 'shelltemp' option isn't set, use pipes.
|
||||
// We use input redirection if do_in is TRUE.
|
||||
// We use output redirection if do_out is TRUE.
|
||||
// We use input redirection if do_in is true.
|
||||
// We use output redirection if do_out is true.
|
||||
static void do_filter(
|
||||
linenr_T line1,
|
||||
linenr_T line2,
|
||||
exarg_T *eap, /* for forced 'ff' and 'fenc' */
|
||||
char_u *cmd,
|
||||
int do_in,
|
||||
int do_out)
|
||||
bool do_in,
|
||||
bool do_out)
|
||||
{
|
||||
char_u *itmp = NULL;
|
||||
char_u *otmp = NULL;
|
||||
@ -1669,10 +1670,17 @@ void ex_update(exarg_T *eap)
|
||||
*/
|
||||
void ex_write(exarg_T *eap)
|
||||
{
|
||||
if (eap->usefilter) /* input lines to shell command */
|
||||
do_bang(1, eap, FALSE, TRUE, FALSE);
|
||||
else
|
||||
if (eap->cmdidx == CMD_saveas) {
|
||||
// :saveas does not take a range, uses all lines.
|
||||
eap->line1 = 1;
|
||||
eap->line2 = curbuf->b_ml.ml_line_count;
|
||||
}
|
||||
|
||||
if (eap->usefilter) { // input lines to shell command
|
||||
do_bang(1, eap, false, true, false);
|
||||
} else {
|
||||
(void)do_write(eap);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
1243
src/nvim/ex_cmds.lua
1243
src/nvim/ex_cmds.lua
File diff suppressed because it is too large
Load Diff
@ -51,17 +51,16 @@
|
||||
#define NOTRLCOM 0x800 // no trailing comment allowed
|
||||
#define ZEROR 0x1000 // zero line number allowed
|
||||
#define USECTRLV 0x2000 // do not remove CTRL-V from argument
|
||||
#define NOTADR 0x4000 // number before command is not an address
|
||||
#define EDITCMD 0x8000 // allow "+command" argument
|
||||
#define BUFNAME 0x10000 // accepts buffer name
|
||||
#define BUFUNL 0x20000 // accepts unlisted buffer too
|
||||
#define ARGOPT 0x40000 // allow "++opt=val" argument
|
||||
#define SBOXOK 0x80000 // allowed in the sandbox
|
||||
#define CMDWIN 0x100000 // allowed in cmdline window; when missing
|
||||
#define EDITCMD 0x4000 // allow "+command" argument
|
||||
#define BUFNAME 0x8000 // accepts buffer name
|
||||
#define BUFUNL 0x10000L // accepts unlisted buffer too
|
||||
#define ARGOPT 0x20000L // allow "++opt=val" argument
|
||||
#define SBOXOK 0x40000L // allowed in the sandbox
|
||||
#define CMDWIN 0x80000L // allowed in cmdline window; when missing
|
||||
// disallows editing another buffer when
|
||||
// curbuf_lock is set
|
||||
#define MODIFY 0x200000 // forbidden in non-'modifiable' buffer
|
||||
#define EXFLAGS 0x400000 // allow flags after count in argument
|
||||
#define MODIFY 0x100000L // forbidden in non-'modifiable' buffer
|
||||
#define EXFLAGS 0x200000L // allow flags after count in argument
|
||||
#define FILES (XFILE | EXTRA) // multiple extra files allowed
|
||||
#define WORD1 (EXTRA | NOSPC) // one extra word allowed
|
||||
#define FILE1 (FILES | NOSPC) // 1 file allowed, defaults to current file
|
||||
@ -153,7 +152,7 @@ struct exarg {
|
||||
int addr_count; ///< the number of addresses given
|
||||
linenr_T line1; ///< the first line number
|
||||
linenr_T line2; ///< the second line number or count
|
||||
int addr_type; ///< type of the count/range
|
||||
cmd_addr_T addr_type; ///< type of the count/range
|
||||
int flags; ///< extra flags after count: EXFLAG_
|
||||
char_u *do_ecmd_cmd; ///< +command arg to be used in edited file
|
||||
linenr_T do_ecmd_lnum; ///< the line number in an edited file
|
||||
|
@ -1086,7 +1086,10 @@ static int compute_buffer_local_count(int addr_type, int lnum, int offset)
|
||||
return buf->b_fnum;
|
||||
}
|
||||
|
||||
static int current_win_nr(win_T *win)
|
||||
// Return the window number of "win".
|
||||
// When "win" is NULL return the number of windows.
|
||||
static int current_win_nr(const win_T *win)
|
||||
FUNC_ATTR_PURE FUNC_ATTR_WARN_UNUSED_RESULT
|
||||
{
|
||||
int nr = 0;
|
||||
|
||||
@ -1163,7 +1166,7 @@ static void get_wincmd_addr_type(char_u *arg, exarg_T *eap)
|
||||
case 'd':
|
||||
case Ctrl_D:
|
||||
// window size or any count
|
||||
eap->addr_type = ADDR_LINES; // -V1037
|
||||
eap->addr_type = ADDR_OTHER; // -V1037
|
||||
break;
|
||||
|
||||
case Ctrl_HAT:
|
||||
@ -1199,7 +1202,7 @@ static void get_wincmd_addr_type(char_u *arg, exarg_T *eap)
|
||||
case '=':
|
||||
case CAR:
|
||||
// no count
|
||||
eap->addr_type = 0;
|
||||
eap->addr_type = ADDR_NONE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -1490,9 +1493,7 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
ea.forceit = false;
|
||||
}
|
||||
|
||||
/*
|
||||
* 6. Parse arguments.
|
||||
*/
|
||||
// 6. Parse arguments. Then check for errors.
|
||||
if (!IS_USER_CMDIDX(ea.cmdidx)) {
|
||||
ea.argt = cmdnames[(int)ea.cmdidx].cmd_argt;
|
||||
}
|
||||
@ -1547,12 +1548,10 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
* Don't complain about the range if it is not used
|
||||
* (could happen if line_count is accidentally set to 0).
|
||||
*/
|
||||
if (!ea.skip && !ni) {
|
||||
/*
|
||||
* If the range is backwards, ask for confirmation and, if given, swap
|
||||
* ea.line1 & ea.line2 so it's forwards again.
|
||||
* When global command is busy, don't ask, will fail below.
|
||||
*/
|
||||
if (!ea.skip && !ni && (ea.argt & RANGE)) {
|
||||
// If the range is backwards, ask for confirmation and, if given, swap
|
||||
// ea.line1 & ea.line2 so it's forwards again.
|
||||
// When global command is busy, don't ask, will fail below.
|
||||
if (!global_busy && ea.line1 > ea.line2) {
|
||||
if (msg_silent == 0) {
|
||||
if ((flags & DOCMD_VERBOSE) || exmode_active) {
|
||||
@ -1571,8 +1570,10 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
goto doend;
|
||||
}
|
||||
|
||||
if ((ea.argt & NOTADR) && ea.addr_count == 0) /* default is 1, not cursor */
|
||||
if ((ea.addr_type == ADDR_OTHER) && ea.addr_count == 0) {
|
||||
// default is 1, not cursor
|
||||
ea.line2 = 1;
|
||||
}
|
||||
|
||||
correct_range(&ea);
|
||||
|
||||
@ -1694,6 +1695,7 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
ea.line1 = 1;
|
||||
switch (ea.addr_type) {
|
||||
case ADDR_LINES:
|
||||
case ADDR_OTHER:
|
||||
ea.line2 = curbuf->b_ml.ml_line_count;
|
||||
break;
|
||||
case ADDR_LOADED_BUFFERS:
|
||||
@ -1771,7 +1773,7 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
errormsg = (char_u *)_(e_zerocount);
|
||||
goto doend;
|
||||
}
|
||||
if (ea.argt & NOTADR) { /* e.g. :buffer 2, :sleep 3 */
|
||||
if (ea.addr_type != ADDR_LINES) { // e.g. :buffer 2, :sleep 3
|
||||
ea.line2 = n;
|
||||
if (ea.addr_count == 0)
|
||||
ea.addr_count = 1;
|
||||
@ -1780,8 +1782,7 @@ static char_u * do_one_cmd(char_u **cmdlinep,
|
||||
ea.line2 += n - 1;
|
||||
++ea.addr_count;
|
||||
// Be vi compatible: no error message for out of range.
|
||||
if (ea.addr_type == ADDR_LINES
|
||||
&& ea.line2 > curbuf->b_ml.ml_line_count) {
|
||||
if (ea.line2 > curbuf->b_ml.ml_line_count) {
|
||||
ea.line2 = curbuf->b_ml.ml_line_count;
|
||||
}
|
||||
}
|
||||
@ -2325,6 +2326,7 @@ int parse_cmd_address(exarg_T *eap, char_u **errormsg, bool silent)
|
||||
eap->line1 = eap->line2;
|
||||
switch (eap->addr_type) {
|
||||
case ADDR_LINES:
|
||||
case ADDR_OTHER:
|
||||
// default is current line number
|
||||
eap->line2 = curwin->w_cursor.lnum;
|
||||
break;
|
||||
@ -2365,6 +2367,7 @@ int parse_cmd_address(exarg_T *eap, char_u **errormsg, bool silent)
|
||||
eap->cmd++;
|
||||
switch (eap->addr_type) {
|
||||
case ADDR_LINES:
|
||||
case ADDR_OTHER:
|
||||
eap->line1 = 1;
|
||||
eap->line2 = curbuf->b_ml.ml_line_count;
|
||||
break;
|
||||
@ -2400,7 +2403,6 @@ int parse_cmd_address(exarg_T *eap, char_u **errormsg, bool silent)
|
||||
}
|
||||
break;
|
||||
case ADDR_TABS_RELATIVE:
|
||||
case ADDR_OTHER:
|
||||
*errormsg = (char_u *)_(e_invrange);
|
||||
return FAIL;
|
||||
case ADDR_ARGUMENTS:
|
||||
@ -3723,7 +3725,7 @@ static linenr_T get_address(exarg_T *eap,
|
||||
int address_count) // 1 for first, >1 after comma
|
||||
FUNC_ATTR_NONNULL_ALL
|
||||
{
|
||||
const int addr_type = addr_type_arg;
|
||||
const cmd_addr_T addr_type = addr_type_arg;
|
||||
int c;
|
||||
int i;
|
||||
long n;
|
||||
@ -3741,6 +3743,7 @@ static linenr_T get_address(exarg_T *eap,
|
||||
++cmd;
|
||||
switch (addr_type) {
|
||||
case ADDR_LINES:
|
||||
case ADDR_OTHER:
|
||||
lnum = curwin->w_cursor.lnum;
|
||||
break;
|
||||
case ADDR_WINDOWS:
|
||||
@ -3772,6 +3775,7 @@ static linenr_T get_address(exarg_T *eap,
|
||||
++cmd;
|
||||
switch (addr_type) {
|
||||
case ADDR_LINES:
|
||||
case ADDR_OTHER:
|
||||
lnum = curbuf->b_ml.ml_line_count;
|
||||
break;
|
||||
case ADDR_WINDOWS:
|
||||
@ -3939,7 +3943,9 @@ static linenr_T get_address(exarg_T *eap,
|
||||
if (lnum == MAXLNUM) {
|
||||
switch (addr_type) {
|
||||
case ADDR_LINES:
|
||||
lnum = curwin->w_cursor.lnum; /* "+1" is same as ".+1" */
|
||||
case ADDR_OTHER:
|
||||
// "+1" is same as ".+1"
|
||||
lnum = curwin->w_cursor.lnum;
|
||||
break;
|
||||
case ADDR_WINDOWS:
|
||||
lnum = CURRENT_WIN_NR;
|
||||
@ -4052,11 +4058,10 @@ static char_u *invalid_range(exarg_T *eap)
|
||||
}
|
||||
|
||||
if (eap->argt & RANGE) {
|
||||
switch(eap->addr_type) {
|
||||
switch (eap->addr_type) {
|
||||
case ADDR_LINES:
|
||||
if (!(eap->argt & NOTADR)
|
||||
&& eap->line2 > curbuf->b_ml.ml_line_count
|
||||
+ (eap->cmdidx == CMD_diffget)) {
|
||||
if (eap->line2 > (curbuf->b_ml.ml_line_count
|
||||
+ (eap->cmdidx == CMD_diffget))) {
|
||||
return (char_u *)_(e_invrange);
|
||||
}
|
||||
break;
|
||||
@ -4105,7 +4110,8 @@ static char_u *invalid_range(exarg_T *eap)
|
||||
}
|
||||
break;
|
||||
case ADDR_TABS_RELATIVE:
|
||||
// Do nothing
|
||||
case ADDR_OTHER:
|
||||
// Any range is OK.
|
||||
break;
|
||||
case ADDR_QUICKFIX:
|
||||
assert(eap->line2 >= 0);
|
||||
@ -5376,7 +5382,7 @@ two_count:
|
||||
}
|
||||
|
||||
*def = getdigits_long(&p, true, 0);
|
||||
*argt |= (ZEROR | NOTADR);
|
||||
*argt |= ZEROR;
|
||||
|
||||
if (p != val + vallen || vallen == 0) {
|
||||
invalid_count:
|
||||
@ -5384,8 +5390,16 @@ invalid_count:
|
||||
return FAIL;
|
||||
}
|
||||
}
|
||||
// default for -range is using buffer lines
|
||||
if (*addr_type_arg == ADDR_NONE) {
|
||||
*addr_type_arg = ADDR_LINES;
|
||||
}
|
||||
} else if (STRNICMP(attr, "count", attrlen) == 0) {
|
||||
*argt |= (COUNT | ZEROR | RANGE | NOTADR);
|
||||
*argt |= (COUNT | ZEROR | RANGE);
|
||||
// default for -count is using any number
|
||||
if (*addr_type_arg == ADDR_NONE) {
|
||||
*addr_type_arg = ADDR_OTHER;
|
||||
}
|
||||
|
||||
if (val != NULL) {
|
||||
p = val;
|
||||
@ -5416,11 +5430,11 @@ invalid_count:
|
||||
EMSG(_("E179: argument required for -addr"));
|
||||
return FAIL;
|
||||
}
|
||||
if (parse_addr_type_arg(val, (int)vallen, argt, addr_type_arg) == FAIL) {
|
||||
if (parse_addr_type_arg(val, (int)vallen, addr_type_arg) == FAIL) {
|
||||
return FAIL;
|
||||
}
|
||||
if (*addr_type_arg != ADDR_LINES) {
|
||||
*argt |= (ZEROR | NOTADR);
|
||||
*argt |= ZEROR;
|
||||
}
|
||||
} else {
|
||||
char_u ch = attr[len];
|
||||
@ -5447,7 +5461,7 @@ static void ex_command(exarg_T *eap)
|
||||
int flags = 0;
|
||||
int compl = EXPAND_NOTHING;
|
||||
char_u *compl_arg = NULL;
|
||||
cmd_addr_T addr_type_arg = ADDR_LINES;
|
||||
cmd_addr_T addr_type_arg = ADDR_NONE;
|
||||
int has_attr = (eap->arg[0] == '-');
|
||||
int name_len;
|
||||
|
||||
@ -6105,8 +6119,7 @@ char_u *get_user_cmd_complete(expand_T *xp, int idx)
|
||||
/*
|
||||
* Parse address type argument
|
||||
*/
|
||||
int parse_addr_type_arg(char_u *value, int vallen, uint32_t *argt,
|
||||
cmd_addr_T *addr_type_arg)
|
||||
int parse_addr_type_arg(char_u *value, int vallen, cmd_addr_T *addr_type_arg)
|
||||
FUNC_ATTR_NONNULL_ALL
|
||||
{
|
||||
int i, a, b;
|
||||
@ -6129,9 +6142,6 @@ int parse_addr_type_arg(char_u *value, int vallen, uint32_t *argt,
|
||||
return FAIL;
|
||||
}
|
||||
|
||||
if (*addr_type_arg != ADDR_LINES)
|
||||
*argt |= NOTADR;
|
||||
|
||||
return OK;
|
||||
}
|
||||
|
||||
@ -7423,11 +7433,12 @@ static void ex_read(exarg_T *eap)
|
||||
int empty = (curbuf->b_ml.ml_flags & ML_EMPTY);
|
||||
linenr_T lnum;
|
||||
|
||||
if (eap->usefilter) /* :r!cmd */
|
||||
do_bang(1, eap, FALSE, FALSE, TRUE);
|
||||
else {
|
||||
if (u_save(eap->line2, (linenr_T)(eap->line2 + 1)) == FAIL)
|
||||
if (eap->usefilter) { // :r!cmd
|
||||
do_bang(1, eap, false, false, true);
|
||||
} else {
|
||||
if (u_save(eap->line2, (linenr_T)(eap->line2 + 1)) == FAIL) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (*eap->arg == NUL) {
|
||||
if (check_fname() == FAIL) /* check for no file name */
|
||||
@ -7897,7 +7908,7 @@ static void ex_at(exarg_T *eap)
|
||||
*/
|
||||
static void ex_bang(exarg_T *eap)
|
||||
{
|
||||
do_bang(eap->addr_count, eap, eap->forceit, TRUE, TRUE);
|
||||
do_bang(eap->addr_count, eap, eap->forceit, true, true);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -22,7 +22,10 @@ local defsfname = autodir .. '/ex_cmds_defs.generated.h'
|
||||
local enumfile = io.open(enumfname, 'w')
|
||||
local defsfile = io.open(defsfname, 'w')
|
||||
|
||||
local defs = require('ex_cmds')
|
||||
local bit = require 'bit'
|
||||
local ex_cmds = require('ex_cmds')
|
||||
local defs = ex_cmds.cmds
|
||||
local flags = ex_cmds.flags
|
||||
|
||||
local byte_a = string.byte('a')
|
||||
local byte_z = string.byte('z')
|
||||
@ -51,6 +54,17 @@ static CommandDefinition cmdnames[%u] = {
|
||||
]], #defs, #defs))
|
||||
local cmds, cmdidxs1, cmdidxs2 = {}, {}, {}
|
||||
for _, cmd in ipairs(defs) do
|
||||
if bit.band(cmd.flags, flags.RANGE) == flags.RANGE then
|
||||
assert(cmd.addr_type ~= 'ADDR_NONE',
|
||||
string.format('ex_cmds.lua:%s: Using RANGE with ADDR_NONE\n', cmd.command))
|
||||
else
|
||||
assert(cmd.addr_type == 'ADDR_NONE',
|
||||
string.format('ex_cmds.lua:%s: Missing ADDR_NONE\n', cmd.command))
|
||||
end
|
||||
if bit.band(cmd.flags, flags.DFLALL) == flags.DFLALL then
|
||||
assert(cmd.addr_type ~= 'ADDR_OTHER' and cmd.addr_type ~= 'ADDR_NONE',
|
||||
string.format('ex_cmds.lua:%s: Missing misplaced DFLALL\n', cmd.command))
|
||||
end
|
||||
local enumname = cmd.enum or ('CMD_' .. cmd.command)
|
||||
local byte_cmd = cmd.command:sub(1, 1):byte()
|
||||
if byte_a <= byte_cmd and byte_cmd <= byte_z then
|
||||
|
@ -393,9 +393,13 @@ func Test_addr_all()
|
||||
call assert_equal(len(gettabinfo()), g:a2)
|
||||
bwipe
|
||||
|
||||
command! -addr=other DoSomething echo 'nothing'
|
||||
command! -addr=other DoSomething let g:a1 = <line1> | let g:a2 = <line2>
|
||||
DoSomething
|
||||
call assert_fails('%DoSomething')
|
||||
call assert_equal(line('.'), g:a1)
|
||||
call assert_equal(line('.'), g:a2)
|
||||
%DoSomething
|
||||
call assert_equal(1, g:a1)
|
||||
call assert_equal(line('$'), g:a2)
|
||||
|
||||
delcommand DoSomething
|
||||
endfunc
|
||||
@ -421,7 +425,7 @@ func Test_command_list()
|
||||
\ execute('command DoCmd'))
|
||||
command! -count=2 DoCmd :
|
||||
call assert_equal("\n Name Args Address Complete Definition"
|
||||
\ .. "\n DoCmd 0 2c :",
|
||||
\ .. "\n DoCmd 0 2c ? :",
|
||||
\ execute('command DoCmd'))
|
||||
|
||||
" Test with various -addr= argument values.
|
||||
|
Loading…
Reference in New Issue
Block a user