To: vim_dev@googlegroups.com Subject: Patch 8.2.3259 Fcc: outbox From: Bram Moolenaar Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ------------ Patch 8.2.3259 Problem: When 'indentexpr' causes an error the did_throw flag may remain set. Solution: Reset did_throw and show the error. (closes #8677) Files: src/indent.c, src/ex_docmd.c, src/proto/ex_docmd.pro *** ../vim-8.2.3258/src/indent.c 2021-07-27 22:00:39.745712396 +0200 --- src/indent.c 2021-07-31 21:18:02.203913451 +0200 *************** *** 1822,1827 **** --- 1822,1834 ---- check_cursor(); State = save_State; + // Reset did_throw, unless 'debug' has "throw" and inside a try/catch. + if (did_throw && (vim_strchr(p_debug, 't') == NULL || trylevel == 0)) + { + handle_did_throw(); + did_throw = FALSE; + } + // If there is an error, just keep the current indent. if (indent < 0) indent = get_indent(); *** ../vim-8.2.3258/src/ex_docmd.c 2021-07-27 22:00:39.741712405 +0200 --- src/ex_docmd.c 2021-07-31 21:17:05.208066194 +0200 *************** *** 1268,1334 **** * commands are executed. */ if (did_throw) ! { ! char *p = NULL; ! msglist_T *messages = NULL; ! ! /* ! * If the uncaught exception is a user exception, report it as an ! * error. If it is an error exception, display the saved error ! * message now. For an interrupt exception, do nothing; the ! * interrupt message is given elsewhere. ! */ ! switch (current_exception->type) ! { ! case ET_USER: ! vim_snprintf((char *)IObuff, IOSIZE, ! _("E605: Exception not caught: %s"), ! current_exception->value); ! p = (char *)vim_strsave(IObuff); ! break; ! case ET_ERROR: ! messages = current_exception->messages; ! current_exception->messages = NULL; ! break; ! case ET_INTERRUPT: ! break; ! } ! ! estack_push(ETYPE_EXCEPT, current_exception->throw_name, ! current_exception->throw_lnum); ! ESTACK_CHECK_SETUP ! current_exception->throw_name = NULL; ! ! discard_current_exception(); // uses IObuff if 'verbose' ! suppress_errthrow = TRUE; ! force_abort = TRUE; ! ! if (messages != NULL) ! { ! do ! { ! msglist_T *next = messages->next; ! int save_compiling = estack_compiling; ! ! estack_compiling = messages->msg_compiling; ! emsg(messages->msg); ! vim_free(messages->msg); ! vim_free(messages->sfile); ! vim_free(messages); ! messages = next; ! estack_compiling = save_compiling; ! } ! while (messages != NULL); ! } ! else if (p != NULL) ! { ! emsg(p); ! vim_free(p); ! } ! vim_free(SOURCING_NAME); ! ESTACK_CHECK_NOW ! estack_pop(); ! } /* * On an interrupt or an aborting error not converted to an exception, --- 1268,1274 ---- * commands are executed. */ if (did_throw) ! handle_did_throw(); /* * On an interrupt or an aborting error not converted to an exception, *************** *** 1448,1453 **** --- 1388,1460 ---- return retval; } + /* + * Handle when "did_throw" is set after executing commands. + */ + void + handle_did_throw() + { + char *p = NULL; + msglist_T *messages = NULL; + + /* + * If the uncaught exception is a user exception, report it as an + * error. If it is an error exception, display the saved error + * message now. For an interrupt exception, do nothing; the + * interrupt message is given elsewhere. + */ + switch (current_exception->type) + { + case ET_USER: + vim_snprintf((char *)IObuff, IOSIZE, + _("E605: Exception not caught: %s"), + current_exception->value); + p = (char *)vim_strsave(IObuff); + break; + case ET_ERROR: + messages = current_exception->messages; + current_exception->messages = NULL; + break; + case ET_INTERRUPT: + break; + } + + estack_push(ETYPE_EXCEPT, current_exception->throw_name, + current_exception->throw_lnum); + ESTACK_CHECK_SETUP + current_exception->throw_name = NULL; + + discard_current_exception(); // uses IObuff if 'verbose' + suppress_errthrow = TRUE; + force_abort = TRUE; + + if (messages != NULL) + { + do + { + msglist_T *next = messages->next; + int save_compiling = estack_compiling; + + estack_compiling = messages->msg_compiling; + emsg(messages->msg); + vim_free(messages->msg); + vim_free(messages->sfile); + vim_free(messages); + messages = next; + estack_compiling = save_compiling; + } + while (messages != NULL); + } + else if (p != NULL) + { + emsg(p); + vim_free(p); + } + vim_free(SOURCING_NAME); + ESTACK_CHECK_NOW + estack_pop(); + } + #ifdef FEAT_EVAL /* * Obtain a line when inside a ":while" or ":for" loop. *** ../vim-8.2.3258/src/proto/ex_docmd.pro 2021-05-29 12:21:54.948859803 +0200 --- src/proto/ex_docmd.pro 2021-07-31 21:17:40.923970364 +0200 *************** *** 3,8 **** --- 3,9 ---- int do_cmdline_cmd(char_u *cmd); int do_cmd_argument(char_u *cmd); int do_cmdline(char_u *cmdline, char_u *(*fgetline)(int, void *, int, getline_opt_T), void *cookie, int flags); + void handle_did_throw(void); int getline_equal(char_u *(*fgetline)(int, void *, int, getline_opt_T), void *cookie, char_u *(*func)(int, void *, int, getline_opt_T)); void *getline_cookie(char_u *(*fgetline)(int, void *, int, getline_opt_T), void *cookie); char_u *getline_peek(char_u *(*fgetline)(int, void *, int, getline_opt_T), void *cookie); *** ../vim-8.2.3258/src/version.c 2021-07-31 19:12:54.100411000 +0200 --- src/version.c 2021-07-31 21:21:39.699338202 +0200 *************** *** 757,758 **** --- 757,760 ---- { /* Add new patch number below this line */ + /**/ + 3259, /**/ -- DINGO: Wicked wicked Zoot ... she is a bad person and she must pay the penalty. And here in Castle Anthrax, we have but one punishment ... you must tie her down on a bed ... and spank her. Come! GIRLS: A spanking! A spanking! "Monty Python and the Holy Grail" PYTHON (MONTY) PICTURES LTD /// Bram Moolenaar -- Bram@Moolenaar.net -- http://www.Moolenaar.net \\\ /// \\\ \\\ sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ /// \\\ help me help AIDS victims -- http://ICCF-Holland.org ///