diff options
author | Bram Moolenaar <Bram@vim.org> | 2021-01-01 18:43:51 +0100 |
---|---|---|
committer | Bram Moolenaar <Bram@vim.org> | 2021-01-01 18:43:51 +0100 |
commit | 5178b1b02fc96f42d62199a4be9184c2aea8a49a (patch) | |
tree | 19f56b937a4af6ca509310d6b03a49aa830dd48c | |
parent | 69f7050cebb0f069d6e39571961b9bbe8531c69a (diff) | |
download | vim-git-5178b1b02fc96f42d62199a4be9184c2aea8a49a.tar.gz |
patch 8.2.2264: Vim9: no error for mismatched :endfunc or :enddefv8.2.2264
Problem: Vim9: no error for mismatched :endfunc or :enddef.
Solution: Check for the mismatch. (issue #7582)
-rw-r--r-- | src/errors.h | 4 | ||||
-rw-r--r-- | src/testdir/test_vim9_func.vim | 19 | ||||
-rw-r--r-- | src/userfunc.c | 60 | ||||
-rw-r--r-- | src/version.c | 2 |
4 files changed, 63 insertions, 22 deletions
diff --git a/src/errors.h b/src/errors.h index 4b4245a1b..6f4ac0e1a 100644 --- a/src/errors.h +++ b/src/errors.h @@ -335,3 +335,7 @@ EXTERN char e_script_variable_invalid_after_reload_in_function_str[] INIT(= N_("E1149: Script variable is invalid after reload in function %s")); EXTERN char e_script_variable_type_changed[] INIT(= N_("E1150: Script variable type changed")); +EXTERN char e_mismatched_endfunction[] + INIT(= N_("E1151: Mismatched endfunction")); +EXTERN char e_mismatched_enddef[] + INIT(= N_("E1152: Mismatched enddef")); diff --git a/src/testdir/test_vim9_func.vim b/src/testdir/test_vim9_func.vim index a2d1ed3e2..223b2fbda 100644 --- a/src/testdir/test_vim9_func.vim +++ b/src/testdir/test_vim9_func.vim @@ -79,6 +79,25 @@ def Test_funcdepth_error() set maxfuncdepth& enddef +def Test_endfunc_enddef() + var lines =<< trim END + def Test() + echo 'test' + endfunc + enddef + END + CheckScriptFailure(lines, 'E1151:', 3) + + lines =<< trim END + def Test() + func Nested() + echo 'test' + enddef + enddef + END + CheckScriptFailure(lines, 'E1152:', 4) +enddef + def ReturnString(): string return 'string' enddef diff --git a/src/userfunc.c b/src/userfunc.c index bc3dd0e9a..f0877e1c3 100644 --- a/src/userfunc.c +++ b/src/userfunc.c @@ -3404,35 +3404,51 @@ define_function(exarg_T *eap, char_u *name_arg) // Check for "endfunction" or "enddef". if (checkforcmd(&p, nesting_def[nesting] - ? "enddef" : "endfunction", 4) && nesting-- == 0) + ? "enddef" : "endfunction", 4)) { - char_u *nextcmd = NULL; - - if (*p == '|') - nextcmd = p + 1; - else if (line_arg != NULL && *skipwhite(line_arg) != NUL) - nextcmd = line_arg; - else if (*p != NUL && *p != '"' && p_verbose > 0) - give_warning2(eap->cmdidx == CMD_def - ? (char_u *)_("W1001: Text found after :enddef: %s") - : (char_u *)_("W22: Text found after :endfunction: %s"), - p, TRUE); - if (nextcmd != NULL) + if (nesting-- == 0) { - // Another command follows. If the line came from "eap" we - // can simply point into it, otherwise we need to change - // "eap->cmdlinep". - eap->nextcmd = nextcmd; - if (line_to_free != NULL) + char_u *nextcmd = NULL; + + if (*p == '|') + nextcmd = p + 1; + else if (line_arg != NULL && *skipwhite(line_arg) != NUL) + nextcmd = line_arg; + else if (*p != NUL && *p != '"' && p_verbose > 0) + give_warning2(eap->cmdidx == CMD_def + ? (char_u *)_("W1001: Text found after :enddef: %s") + : (char_u *)_("W22: Text found after :endfunction: %s"), + p, TRUE); + if (nextcmd != NULL) { - vim_free(*eap->cmdlinep); - *eap->cmdlinep = line_to_free; - line_to_free = NULL; + // Another command follows. If the line came from "eap" + // we can simply point into it, otherwise we need to + // change "eap->cmdlinep". + eap->nextcmd = nextcmd; + if (line_to_free != NULL) + { + vim_free(*eap->cmdlinep); + *eap->cmdlinep = line_to_free; + line_to_free = NULL; + } } + break; } - break; } + // Check for mismatched "endfunc" or "enddef". + // We don't check for "def" inside "func" thus we also can't check + // for "enddef". + // We continue to find the end of the function, although we might + // not find it. + else if (nesting_def[nesting]) + { + if (checkforcmd(&p, "endfunction", 4)) + emsg(_(e_mismatched_endfunction)); + } + else if (eap->cmdidx == CMD_def && checkforcmd(&p, "enddef", 4)) + emsg(_(e_mismatched_enddef)); + // Increase indent inside "if", "while", "for" and "try", decrease // at "end". if (indent > 2 && (*p == '}' || STRNCMP(p, "end", 3) == 0)) diff --git a/src/version.c b/src/version.c index 26c9d8bf8..3fc3c01e1 100644 --- a/src/version.c +++ b/src/version.c @@ -751,6 +751,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 2264, +/**/ 2263, /**/ 2262, |