0
0
mirror of https://github.com/vim/vim.git synced 2025-07-26 11:04:33 -04:00

patch 9.0.0476: varargs does not work for replacement function of substitute()

Problem:    Varargs does not work for replacement function of substitute().
Solution:   Check the varargs flag of the function. (closes #11142)
This commit is contained in:
zeertzjq 2022-09-16 12:10:03 +01:00 committed by Bram Moolenaar
parent dd674774bb
commit 48db5dafec
5 changed files with 20 additions and 14 deletions

View File

@ -1817,14 +1817,14 @@ static regsubmatch_T rsm; // can only be used when can_f_submatch is TRUE
* call_func() by vim_regsub_both(). * call_func() by vim_regsub_both().
*/ */
static int static int
fill_submatch_list(int argc UNUSED, typval_T *argv, int argskip, int argcount) fill_submatch_list(int argc UNUSED, typval_T *argv, int argskip, ufunc_T *fp)
{ {
listitem_T *li; listitem_T *li;
int i; int i;
char_u *s; char_u *s;
typval_T *listarg = argv + argskip; typval_T *listarg = argv + argskip;
if (argcount == argskip) if (!fp->uf_varargs && fp->uf_args.ga_len <= argskip)
// called function doesn't take a submatches argument // called function doesn't take a submatches argument
return argskip; return argskip;

View File

@ -2052,13 +2052,13 @@ typedef struct
// Struct passed between functions dealing with function call execution. // Struct passed between functions dealing with function call execution.
// //
// "argv_func", when not NULL, can be used to fill in arguments only when the // "fe_argv_func", when not NULL, can be used to fill in arguments only when the
// invoked function uses them. It is called like this: // invoked function uses them. It is called like this:
// new_argcount = argv_func(current_argcount, argv, partial_argcount, // new_argcount = fe_argv_func(current_argcount, argv, partial_argcount,
// called_func_argcount) // called_func)
// //
typedef struct { typedef struct {
int (* fe_argv_func)(int, typval_T *, int, int); int (* fe_argv_func)(int, typval_T *, int, ufunc_T *);
linenr_T fe_firstline; // first line of range linenr_T fe_firstline; // first line of range
linenr_T fe_lastline; // last line of range linenr_T fe_lastline; // last line of range
int *fe_doesrange; // if not NULL: return: function handled range int *fe_doesrange; // if not NULL: return: function handled range

View File

@ -439,12 +439,16 @@ endfunc
func SubReplacer(text, submatches) func SubReplacer(text, submatches)
return a:text .. a:submatches[0] .. a:text return a:text .. a:submatches[0] .. a:text
endfunc endfunc
func SubReplacerVar(text, ...)
return a:text .. a:1[0] .. a:text
endfunc
func SubReplacer20(t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15, t16, t17, t18, t19, submatches) func SubReplacer20(t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15, t16, t17, t18, t19, submatches)
return a:t3 .. a:submatches[0] .. a:t11 return a:t3 .. a:submatches[0] .. a:t11
endfunc endfunc
func Test_substitute_partial() func Test_substitute_partial()
call assert_equal('1foo2foo3', substitute('123', '2', function('SubReplacer', ['foo']), 'g')) call assert_equal('1foo2foo3', substitute('123', '2', function('SubReplacer', ['foo']), 'g'))
call assert_equal('1foo2foo3', substitute('123', '2', function('SubReplacerVar', ['foo']), 'g'))
" 19 arguments plus one is just OK " 19 arguments plus one is just OK
let Replacer = function('SubReplacer20', repeat(['foo'], 19)) let Replacer = function('SubReplacer20', repeat(['foo'], 19))

View File

@ -3644,7 +3644,7 @@ call_func(
if (funcexe->fe_argv_func != NULL) if (funcexe->fe_argv_func != NULL)
// postponed filling in the arguments, do it now // postponed filling in the arguments, do it now
argcount = funcexe->fe_argv_func(argcount, argvars, argcount = funcexe->fe_argv_func(argcount, argvars,
argv_clear, fp->uf_args.ga_len); argv_clear, fp);
if (funcexe->fe_basetv != NULL) if (funcexe->fe_basetv != NULL)
{ {

View File

@ -703,6 +703,8 @@ static char *(features[]) =
static int included_patches[] = static int included_patches[] =
{ /* Add new patch number below this line */ { /* Add new patch number below this line */
/**/
476,
/**/ /**/
475, 475,
/**/ /**/