Merge pull request #15972 from seandewar/vim-8.2.3487

vim-patch:8.2.{3416,3448,3470,3478,3480,3486,3487}
This commit is contained in:
Sean Dewar 2022-04-13 20:50:44 +01:00 committed by GitHub
commit a9cd9de01d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 129 additions and 16 deletions

View File

@ -3017,11 +3017,12 @@ void ex_call(exarg_T *eap)
} }
} }
// When inside :try we need to check for following "| catch". // When inside :try we need to check for following "| catch" or "| endtry".
if (!failed || eap->cstack->cs_trylevel > 0) { // Not when there was an error, but do check if an exception was thrown.
if ((!aborting() || current_exception != NULL) && (!failed || eap->cstack->cs_trylevel > 0)) {
// Check for trailing illegal characters and a following command. // Check for trailing illegal characters and a following command.
if (!ends_excmd(*arg)) { if (!ends_excmd(*arg)) {
if (!failed) { if (!failed && !aborting()) {
emsg_severe = true; emsg_severe = true;
emsg(_(e_trailing)); emsg(_(e_trailing));
} }

View File

@ -1083,7 +1083,7 @@ void ex_endwhile(exarg_T *eap)
if (cstack->cs_looplevel <= 0 || cstack->cs_idx < 0) { if (cstack->cs_looplevel <= 0 || cstack->cs_idx < 0) {
eap->errmsg = err; eap->errmsg = err;
} else { } else {
fl = cstack->cs_flags[cstack->cs_idx]; fl = cstack->cs_flags[cstack->cs_idx];
if (!(fl & csf)) { if (!(fl & csf)) {
// If we are in a ":while" or ":for" but used the wrong endloop // If we are in a ":while" or ":for" but used the wrong endloop
// command, do not rewind to the next enclosing ":for"/":while". // command, do not rewind to the next enclosing ":for"/":while".
@ -1575,6 +1575,7 @@ void ex_endtry(exarg_T *eap)
if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) { if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) {
eap->errmsg = get_end_emsg(cstack); eap->errmsg = get_end_emsg(cstack);
// Find the matching ":try" and report what's missing. // Find the matching ":try" and report what's missing.
idx = cstack->cs_idx; idx = cstack->cs_idx;
do { do {
@ -1594,6 +1595,9 @@ void ex_endtry(exarg_T *eap)
if (current_exception) { if (current_exception) {
discard_current_exception(); discard_current_exception();
} }
// report eap->errmsg, also when there already was an error
did_emsg = false;
} else { } else {
idx = cstack->cs_idx; idx = cstack->cs_idx;
@ -1664,8 +1668,10 @@ void ex_endtry(exarg_T *eap)
*/ */
(void)cleanup_conditionals(cstack, CSF_TRY | CSF_SILENT, TRUE); (void)cleanup_conditionals(cstack, CSF_TRY | CSF_SILENT, TRUE);
--cstack->cs_idx; if (cstack->cs_idx >= 0 && (cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) {
--cstack->cs_trylevel; cstack->cs_idx--;
}
cstack->cs_trylevel--;
if (!skip) { if (!skip) {
report_resume_pending(pending, report_resume_pending(pending,
@ -1913,7 +1919,7 @@ int cleanup_conditionals(cstack_T *cstack, int searched_cond, int inclusive)
default: default:
if (cstack->cs_flags[idx] & CSF_FINALLY) { if (cstack->cs_flags[idx] & CSF_FINALLY) {
if (cstack->cs_pending[idx] & CSTP_THROW) { if ((cstack->cs_pending[idx] & CSTP_THROW) && cstack->cs_exception[idx] != NULL) {
// Cancel the pending exception. This is in the // Cancel the pending exception. This is in the
// finally clause, so that the stack of the // finally clause, so that the stack of the
// caught exceptions is not involved. // caught exceptions is not involved.
@ -1934,8 +1940,9 @@ int cleanup_conditionals(cstack_T *cstack, int searched_cond, int inclusive)
*/ */
if (!(cstack->cs_flags[idx] & CSF_FINALLY)) { if (!(cstack->cs_flags[idx] & CSF_FINALLY)) {
if ((cstack->cs_flags[idx] & CSF_ACTIVE) if ((cstack->cs_flags[idx] & CSF_ACTIVE)
&& (cstack->cs_flags[idx] & CSF_CAUGHT)) { && (cstack->cs_flags[idx] & CSF_CAUGHT) && !(cstack->cs_flags[idx] & CSF_FINISHED)) {
finish_exception((except_T *)cstack->cs_exception[idx]); finish_exception((except_T *)cstack->cs_exception[idx]);
cstack->cs_flags[idx] |= CSF_FINISHED;
} }
// Stop at this try conditional - except the try block never // Stop at this try conditional - except the try block never
// got active (because of an inactive surrounding conditional // got active (because of an inactive surrounding conditional

View File

@ -14,9 +14,10 @@
#define CSF_TRY 0x0100 // is a ":try" #define CSF_TRY 0x0100 // is a ":try"
#define CSF_FINALLY 0x0200 // ":finally" has been passed #define CSF_FINALLY 0x0200 // ":finally" has been passed
#define CSF_THROWN 0x0400 // exception thrown to this try conditional #define CSF_THROWN 0x0800 // exception thrown to this try conditional
#define CSF_CAUGHT 0x0800 // exception caught by this try conditional #define CSF_CAUGHT 0x1000 // exception caught by this try conditional
#define CSF_SILENT 0x1000 // "emsg_silent" reset by ":try" #define CSF_FINISHED 0x2000 // CSF_CAUGHT was handled by finish_exception()
#define CSF_SILENT 0x4000 // "emsg_silent" reset by ":try"
// Note that CSF_ELSE is only used when CSF_TRY and CSF_WHILE are unset // Note that CSF_ELSE is only used when CSF_TRY and CSF_WHILE are unset
// (an ":if"), and CSF_SILENT is only used when CSF_TRY is set. // (an ":if"), and CSF_SILENT is only used when CSF_TRY is set.

View File

@ -5173,19 +5173,19 @@ static void win_redr_status(win_T *wp)
*(p + len++) = ' '; *(p + len++) = ' ';
} }
if (bt_help(wp->w_buffer)) { if (bt_help(wp->w_buffer)) {
STRCPY(p + len, _("[Help]")); snprintf((char *)p + len, MAXPATHL - len, "%s", _("[Help]"));
len += (int)STRLEN(p + len); len += (int)STRLEN(p + len);
} }
if (wp->w_p_pvw) { if (wp->w_p_pvw) {
STRCPY(p + len, _("[Preview]")); snprintf((char *)p + len, MAXPATHL - len, "%s", _("[Preview]"));
len += (int)STRLEN(p + len); len += (int)STRLEN(p + len);
} }
if (bufIsChanged(wp->w_buffer)) { if (bufIsChanged(wp->w_buffer)) {
STRCPY(p + len, "[+]"); snprintf((char *)p + len, MAXPATHL - len, "%s", "[+]");
len += 3; len += (int)STRLEN(p + len);
} }
if (wp->w_buffer->b_p_ro) { if (wp->w_buffer->b_p_ro) {
STRCPY(p + len, _("[RO]")); snprintf((char *)p + len, MAXPATHL - len, "%s", _("[RO]"));
// len += (int)STRLEN(p + len); // dead assignment // len += (int)STRLEN(p + len); // dead assignment
} }

View File

@ -523,4 +523,16 @@ func Test_statusline_mbyte_fillchar()
%bw! %bw!
endfunc endfunc
" Used to write beyond allocated memory. This assumes MAXPATHL is 4096 bytes.
func Test_statusline_verylong_filename()
let fname = repeat('x', 4090)
" Nvim's swap file creation fails on Windows (E303) due to fname's length
" exe "new " .. fname
exe "noswapfile new " .. fname
set buftype=help
set previewwindow
redraw
bwipe!
endfunc
" vim: shiftwidth=2 sts=2 expandtab " vim: shiftwidth=2 sts=2 expandtab

View File

@ -1996,5 +1996,97 @@ func Test_reload_in_try_catch()
call delete('Xreload') call delete('Xreload')
endfunc endfunc
" Test for using throw in a called function with following error {{{1
func Test_user_command_throw_in_function_call()
let lines =<< trim END
function s:get_dict() abort
throw 'my_error'
endfunction
try
call s:get_dict().foo()
catch /my_error/
let caught = 'yes'
catch
let caught = v:exception
endtry
call assert_equal('yes', caught)
END
call writefile(lines, 'XtestThrow')
source XtestThrow
call delete('XtestThrow')
unlet g:caught
endfunc
" Test for using throw in a called function with following endtry {{{1
func Test_user_command_function_call_with_endtry()
let lines =<< trim END
funct s:throw(msg) abort
throw a:msg
endfunc
func s:main() abort
try
try
throw 'err1'
catch
call s:throw('err2') | endtry
catch
let s:caught = 'yes'
endtry
endfunc
call s:main()
call assert_equal('yes', s:caught)
END
call writefile(lines, 'XtestThrow')
source XtestThrow
call delete('XtestThrow')
endfunc
func ThisWillFail()
endfunc
" This was crashing prior to the fix in 8.2.3478.
func Test_error_in_catch_and_finally()
let lines =<< trim END
try
echo x
catch
for l in []
finally
END
call writefile(lines, 'XtestCatchAndFinally')
try
source XtestCatchAndFinally
catch /E600:/
endtry
call delete('XtestCatchAndFinally')
endfunc
" This was causing an illegal memory access
func Test_leave_block_in_endtry_not_called()
let lines =<< trim END
" vim9script
" try #
try "
for x in []
if
endwhile
if
endtry
END
call writefile(lines, 'XtestEndtry')
try
source XtestEndtry
catch /E171:/
endtry
call delete('XtestEndtry')
endfunc
" Modeline {{{1 " Modeline {{{1
" vim: ts=8 sw=2 sts=2 expandtab tw=80 fdm=marker " vim: ts=8 sw=2 sts=2 expandtab tw=80 fdm=marker