aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorzeertzjq <zeertzjq@outlook.com>2023-04-17 09:07:30 +0800
committerGitHub <noreply@github.com>2023-04-17 09:07:30 +0800
commit78535664bd29e6f2bd4b64c20cb29ef40f9bccd4 (patch)
treee17c639826f36fdac4805ed9f7f35f4c60c746ca
parent55d346fc2683a18256320eaae75eb4f3137dcced (diff)
downloadrneovim-78535664bd29e6f2bd4b64c20cb29ef40f9bccd4.tar.gz
rneovim-78535664bd29e6f2bd4b64c20cb29ef40f9bccd4.tar.bz2
rneovim-78535664bd29e6f2bd4b64c20cb29ef40f9bccd4.zip
vim-patch:8.2.2172: Vim9: number of arguments is not always checked (#23142)
Problem: Vim9: number of arguments is not always checked. (Yegappan Lakshmanan) Solution: Check number of arguments when calling function by name. https://github.com/vim/vim/commit/5082471f91dd42ed8c35e0f649d0a6572e6fe3fc Co-authored-by: Bram Moolenaar <Bram@vim.org>
-rw-r--r--src/nvim/eval/userfunc.c26
1 files changed, 20 insertions, 6 deletions
diff --git a/src/nvim/eval/userfunc.c b/src/nvim/eval/userfunc.c
index 734a6655bb..6016ad0646 100644
--- a/src/nvim/eval/userfunc.c
+++ b/src/nvim/eval/userfunc.c
@@ -1290,6 +1290,21 @@ static bool func_name_refcount(const char *name)
return isdigit((uint8_t)(*name)) || *name == '<';
}
+/// Check the argument count for user function "fp".
+/// @return FCERR_UNKNOWN if OK, FCERR_TOOFEW or FCERR_TOOMANY otherwise.
+static int check_user_func_argcount(ufunc_T *fp, int argcount)
+ FUNC_ATTR_NONNULL_ALL
+{
+ const int regular_args = fp->uf_args.ga_len;
+
+ if (argcount < regular_args - fp->uf_def_args.ga_len) {
+ return FCERR_TOOFEW;
+ } else if (!fp->uf_varargs && argcount > regular_args) {
+ return FCERR_TOOMANY;
+ }
+ return FCERR_UNKNOWN;
+}
+
/// Call a user function after checking the arguments.
static int call_user_func_check(ufunc_T *fp, int argcount, typval_T *argvars, typval_T *rettv,
funcexe_T *funcexe, dict_T *selfdict)
@@ -1302,12 +1317,11 @@ static int call_user_func_check(ufunc_T *fp, int argcount, typval_T *argvars, ty
if ((fp->uf_flags & FC_RANGE) && funcexe->fe_doesrange != NULL) {
*funcexe->fe_doesrange = true;
}
- int error;
- if (argcount < fp->uf_args.ga_len - fp->uf_def_args.ga_len) {
- error = FCERR_TOOFEW;
- } else if (!fp->uf_varargs && argcount > fp->uf_args.ga_len) {
- error = FCERR_TOOMANY;
- } else if ((fp->uf_flags & FC_DICT) && selfdict == NULL) {
+ int error = check_user_func_argcount(fp, argcount);
+ if (error != FCERR_UNKNOWN) {
+ return error;
+ }
+ if ((fp->uf_flags & FC_DICT) && selfdict == NULL) {
error = FCERR_DICT;
} else {
// Call the user function.