diff options
Diffstat (limited to 'src/nvim/ex_eval.c')
-rw-r--r-- | src/nvim/ex_eval.c | 341 |
1 files changed, 171 insertions, 170 deletions
diff --git a/src/nvim/ex_eval.c b/src/nvim/ex_eval.c index f67c8a6720..6dddafcfcb 100644 --- a/src/nvim/ex_eval.c +++ b/src/nvim/ex_eval.c @@ -16,12 +16,12 @@ #include "nvim/debugger.h" #include "nvim/eval.h" #include "nvim/eval/userfunc.h" -#include "nvim/ex_cmds2.h" #include "nvim/ex_docmd.h" #include "nvim/ex_eval.h" #include "nvim/memory.h" #include "nvim/message.h" #include "nvim/regexp.h" +#include "nvim/runtime.h" #include "nvim/strings.h" #include "nvim/vim.h" @@ -45,20 +45,19 @@ // there or even outside the try conditional. Try conditionals may be nested. // Configuration whether an exception is thrown on error or interrupt. When -// the preprocessor macros below evaluate to FALSE, an error (did_emsg) or +// the preprocessor macros below evaluate to false, an error (did_emsg) or // interrupt (got_int) under an active try conditional terminates the script // after the non-active finally clauses of all active try conditionals have been // executed. Otherwise, errors and/or interrupts are converted into catchable -// exceptions, which terminate the script only if not caught. For user -// exceptions, only current_exception is set. (Note: got_int can be set -// asynchronously afterwards by a SIGINT, so current_exception && got_int is not +// exceptions (did_throw additionally set), which terminate the script only if +// not caught. For user exceptions, only did_throw is set. (Note: got_int can +// be set asynchronously afterwards by a SIGINT, so did_throw && got_int is not // a reliant test that the exception currently being thrown is an interrupt // exception. Similarly, did_emsg can be set afterwards on an error in an -// (unskipped) conditional command inside an inactive conditional, so -// current_exception && did_emsg is not a reliant test that the exception -// currently being thrown is an error exception.) - The macros can be defined -// as expressions checking for a variable that is allowed to be changed during -// execution of a script. +// (unskipped) conditional command inside an inactive conditional, so did_throw +// && did_emsg is not a reliant test that the exception currently being thrown +// is an error exception.) - The macros can be defined as expressions checking +// for a variable that is allowed to be changed during execution of a script. // Values used for the Vim release. #define THROW_ON_ERROR true @@ -71,7 +70,7 @@ #define CHECK_SKIP \ (did_emsg \ || got_int \ - || current_exception \ + || did_throw \ || (cstack->cs_idx > 0 \ && !(cstack->cs_flags[cstack->cs_idx - 1] & CSF_ACTIVE))) @@ -82,14 +81,14 @@ static void discard_pending_return(typval_T *p) /* * When several errors appear in a row, setting "force_abort" is delayed until - * the failing command returned. "cause_abort" is set to TRUE meanwhile, in + * the failing command returned. "cause_abort" is set to true meanwhile, in * order to indicate that situation. This is useful when "force_abort" was set * during execution of a function call from an expression: the aborting of the * expression evaluation is done without producing any error messages, but all * error messages on parsing errors during the expression evaluation are given * (even if a try conditional is active). */ -static int cause_abort = FALSE; +static int cause_abort = false; /// @return true when immediately aborting on error, or when an interrupt /// occurred or an exception was thrown but not caught. @@ -104,7 +103,7 @@ static int cause_abort = FALSE; /// value. "got_int" is also set by calling interrupt(). int aborting(void) { - return (did_emsg && force_abort) || got_int || current_exception; + return (did_emsg && force_abort) || got_int || did_throw; } /// The value of "force_abort" is temporarily reset by the first emsg() call @@ -114,11 +113,11 @@ int aborting(void) void update_force_abort(void) { if (cause_abort) { - force_abort = TRUE; + force_abort = true; } } -/// @return TRUE if a command with a subcommand resulting in "retcode" should +/// @return true if a command with a subcommand resulting in "retcode" should /// abort the script processing. Can be used to suppress an autocommand after /// execution of a failing subcommand as long as the error message has not been /// displayed and actually caused the abortion. @@ -127,7 +126,7 @@ int should_abort(int retcode) return (retcode == FAIL && trylevel != 0 && !emsg_silent) || aborting(); } -/// @return TRUE if a function with the "abort" flag should not be considered +/// @return true if a function with the "abort" flag should not be considered /// ended on an error. This means that parsing commands is continued in order /// to find finally clauses to be executed, and that some errors in skipped /// commands are still reported. @@ -151,8 +150,8 @@ int aborted_in_try(void) bool cause_errthrow(const char *mesg, bool severe, bool *ignore) FUNC_ATTR_NONNULL_ALL { - struct msglist *elem; - struct msglist **plist; + msglist_T *elem; + msglist_T **plist; /* * Do nothing when displaying the interrupt message or reporting an @@ -175,7 +174,7 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) */ if (!did_emsg) { cause_abort = force_abort; - force_abort = FALSE; + force_abort = false; } /* @@ -186,7 +185,7 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) * currently throwing an exception, do nothing. The message text will * then be stored to v:errmsg by emsg() without displaying it. */ - if (((trylevel == 0 && !cause_abort) || emsg_silent) && !current_exception) { + if (((trylevel == 0 && !cause_abort) || emsg_silent) && !did_throw) { return false; } @@ -206,7 +205,7 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) * Ensure that all commands in nested function calls and sourced files * are aborted immediately. */ - cause_abort = TRUE; + cause_abort = true; /* * When an exception is being thrown, some commands (like conditionals) are @@ -217,7 +216,7 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) * exception currently being thrown to prevent it from being caught. Just * execute finally clauses and terminate. */ - if (current_exception) { + if (did_throw) { // When discarding an interrupt exception, reset got_int to prevent the // same interrupt being converted to an exception again and discarding // the error exception we are about to throw here. @@ -254,7 +253,7 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) plist = &(*plist)->next; } - elem = xmalloc(sizeof(struct msglist)); + elem = xmalloc(sizeof(msglist_T)); elem->msg = xstrdup(mesg); elem->next = NULL; elem->throw_msg = NULL; @@ -275,20 +274,26 @@ bool cause_errthrow(const char *mesg, bool severe, bool *ignore) (*msg_list)->throw_msg = tmsg; } } + + // Get the source name and lnum now, it may change before + // reaching do_errthrow(). + elem->sfile = estack_sfile(ESTACK_NONE); + elem->slnum = SOURCING_LNUM; } return true; } } /// Free a "msg_list" and the messages it contains. -static void free_msglist(struct msglist *l) +static void free_msglist(msglist_T *l) { - struct msglist *messages, *next; + msglist_T *messages, *next; messages = l; while (messages != NULL) { next = messages->next; xfree(messages->msg); + xfree(messages->sfile); xfree(messages); messages = next; } @@ -312,8 +317,8 @@ void do_errthrow(cstack_T *cstack, char *cmdname) * are aborted immediately. */ if (cause_abort) { - cause_abort = FALSE; - force_abort = TRUE; + cause_abort = false; + force_abort = true; } // If no exception is to be thrown or the conversion should be done after @@ -328,7 +333,7 @@ void do_errthrow(cstack_T *cstack, char *cmdname) if (cstack != NULL) { do_throw(cstack); } else { - need_rethrow = TRUE; + need_rethrow = true; } } *msg_list = NULL; @@ -337,13 +342,13 @@ void do_errthrow(cstack_T *cstack, char *cmdname) /// do_intthrow(): Replace the current exception by an interrupt or interrupt /// exception if appropriate. /// -/// @return TRUE if the current exception is discarded or, -/// FALSE otherwise. +/// @return true if the current exception is discarded or, +/// false otherwise. int do_intthrow(cstack_T *cstack) { // If no interrupt occurred or no try conditional is active and no exception // is being thrown, do nothing (for compatibility of non-EH scripts). - if (!got_int || (trylevel == 0 && !current_exception)) { + if (!got_int || (trylevel == 0 && !did_throw)) { return false; } @@ -352,7 +357,7 @@ int do_intthrow(cstack_T *cstack) // The interrupt aborts everything except for executing finally clauses. // Discard any user or error or interrupt exception currently being // thrown. - if (current_exception) { + if (did_throw) { discard_current_exception(); } } else { @@ -363,7 +368,7 @@ int do_intthrow(cstack_T *cstack) // will be terminated then. - If an interrupt exception is already // being thrown, do nothing. - if (current_exception) { + if (did_throw) { if (current_exception->type == ET_INTERRUPT) { return false; } @@ -389,7 +394,7 @@ char *get_exception_string(void *value, except_type_T type, char *cmdname, int * if (type == ET_ERROR) { *should_free = true; - mesg = ((struct msglist *)value)->throw_msg; + mesg = ((msglist_T *)value)->throw_msg; if (cmdname != NULL && *cmdname != NUL) { size_t cmdlen = STRLEN(cmdname); ret = xstrnsave("Vim(", 4 + cmdlen + 2 + STRLEN(mesg)); @@ -469,7 +474,7 @@ static int throw_exception(void *value, except_type_T type, char *cmdname) if (type == ET_ERROR) { // Store the original message and prefix the exception value with // "Vim:" or, if a command name is given, "Vim(cmdname):". - excp->messages = (struct msglist *)value; + excp->messages = (msglist_T *)value; } excp->value = get_exception_string(value, type, cmdname, &should_free); @@ -478,20 +483,30 @@ static int throw_exception(void *value, except_type_T type, char *cmdname) } excp->type = type; - excp->throw_name = xstrdup(sourcing_name == NULL ? "" : sourcing_name); - excp->throw_lnum = sourcing_lnum; + if (type == ET_ERROR && ((msglist_T *)value)->sfile != NULL) { + msglist_T *entry = (msglist_T *)value; + excp->throw_name = entry->sfile; + entry->sfile = NULL; + excp->throw_lnum = entry->slnum; + } else { + excp->throw_name = estack_sfile(ESTACK_NONE); + if (excp->throw_name == NULL) { + excp->throw_name = xstrdup(""); + } + excp->throw_lnum = SOURCING_LNUM; + } if (p_verbose >= 13 || debug_break_level > 0) { int save_msg_silent = msg_silent; if (debug_break_level > 0) { - msg_silent = FALSE; // display messages + msg_silent = false; // display messages } else { verbose_enter(); } - ++no_wait_return; + no_wait_return++; if (debug_break_level > 0 || *p_vfile == NUL) { - msg_scroll = TRUE; // always scroll up, don't overwrite + msg_scroll = true; // always scroll up, don't overwrite } smsg(_("Exception thrown: %s"), excp->value); msg_puts("\n"); // don't overwrite this either @@ -499,7 +514,7 @@ static int throw_exception(void *value, except_type_T type, char *cmdname) if (debug_break_level > 0 || *p_vfile == NUL) { cmdline_row = msg_row; } - --no_wait_return; + no_wait_return--; if (debug_break_level > 0) { msg_silent = save_msg_silent; } else { @@ -538,13 +553,13 @@ static void discard_exception(except_T *excp, bool was_finished) saved_IObuff = (char *)vim_strsave(IObuff); if (debug_break_level > 0) { - msg_silent = FALSE; // display messages + msg_silent = false; // display messages } else { verbose_enter(); } - ++no_wait_return; + no_wait_return++; if (debug_break_level > 0 || *p_vfile == NUL) { - msg_scroll = TRUE; // always scroll up, don't overwrite + msg_scroll = true; // always scroll up, don't overwrite } smsg(was_finished ? _("Exception finished: %s") : _("Exception discarded: %s"), @@ -580,6 +595,7 @@ void discard_current_exception(void) } // Note: all globals manipulated here should be saved/restored in // try_enter/try_leave. + did_throw = false; need_rethrow = false; } @@ -606,13 +622,13 @@ static void catch_exception(except_T *excp) int save_msg_silent = msg_silent; if (debug_break_level > 0) { - msg_silent = FALSE; // display messages + msg_silent = false; // display messages } else { verbose_enter(); } - ++no_wait_return; + no_wait_return++; if (debug_break_level > 0 || *p_vfile == NUL) { - msg_scroll = TRUE; // always scroll up, don't overwrite + msg_scroll = true; // always scroll up, don't overwrite } smsg(_("Exception caught: %s"), excp->value); msg_puts("\n"); // don't overwrite this either @@ -620,7 +636,7 @@ static void catch_exception(except_T *excp) if (debug_break_level > 0 || *p_vfile == NUL) { cmdline_row = msg_row; } - --no_wait_return; + no_wait_return--; if (debug_break_level > 0) { msg_silent = save_msg_silent; } else { @@ -710,14 +726,14 @@ static void report_pending(int action, int pending, void *value) break; case CSTP_RETURN: // ":return" command producing value, allocated - s = (char *)get_return_cmd(value); + s = get_return_cmd(value); break; default: if (pending & CSTP_THROW) { vim_snprintf((char *)IObuff, IOSIZE, mesg, _("Exception")); - mesg = (char *)concat_str(IObuff, (char_u *)": %s"); + mesg = concat_str((char *)IObuff, ": %s"); s = ((except_T *)value)->value; } else if ((pending & CSTP_ERROR) && (pending & CSTP_INTERRUPT)) { s = _("Error and interrupt"); @@ -730,14 +746,14 @@ static void report_pending(int action, int pending, void *value) save_msg_silent = msg_silent; if (debug_break_level > 0) { - msg_silent = FALSE; // display messages + msg_silent = false; // display messages } - ++no_wait_return; - msg_scroll = TRUE; // always scroll up, don't overwrite + no_wait_return++; + msg_scroll = true; // always scroll up, don't overwrite smsg(mesg, s); msg_puts("\n"); // don't overwrite this either cmdline_row = msg_row; - --no_wait_return; + no_wait_return--; if (debug_break_level > 0) { msg_silent = save_msg_silent; } @@ -814,7 +830,7 @@ void ex_if(exarg_T *eap) if (cstack->cs_idx == CSTACK_LEN - 1) { eap->errmsg = _("E579: :if nesting too deep"); } else { - ++cstack->cs_idx; + cstack->cs_idx++; cstack->cs_flags[cstack->cs_idx] = 0; skip = CHECK_SKIP; @@ -854,7 +870,7 @@ void ex_endif(exarg_T *eap) (void)do_intthrow(eap->cstack); } - --eap->cstack->cs_idx; + eap->cstack->cs_idx--; } } @@ -948,8 +964,8 @@ void ex_while(exarg_T *eap) * cstack entry. */ if ((cstack->cs_lflags & CSL_HAD_LOOP) == 0) { - ++cstack->cs_idx; - ++cstack->cs_looplevel; + cstack->cs_idx++; + cstack->cs_looplevel++; cstack->cs_line[cstack->cs_idx] = -1; } cstack->cs_flags[cstack->cs_idx] = @@ -971,7 +987,7 @@ void ex_while(exarg_T *eap) // Jumping here from a ":continue" or ":endfor": use the // previously evaluated list. fi = cstack->cs_forinfo[cstack->cs_idx]; - error = FALSE; + error = false; } else { // Evaluate the argument and get the info in a structure. fi = eval_for_line(eap->arg, &error, &eap->nextcmd, skip); @@ -982,7 +998,7 @@ void ex_while(exarg_T *eap) if (!error && fi != NULL && !skip) { result = next_for_item(fi, eap->arg); } else { - result = FALSE; + result = false; } if (!result) { @@ -1102,7 +1118,7 @@ void ex_endwhile(exarg_T *eap) eap->errmsg = _(e_endtry); } // Try to find the matching ":while" and report what's missing. - for (idx = cstack->cs_idx; idx > 0; --idx) { + for (idx = cstack->cs_idx; idx > 0; idx--) { fl = cstack->cs_flags[idx]; if ((fl & CSF_TRY) && !(fl & CSF_FINALLY)) { // Give up at a try conditional not in its finally clause. @@ -1115,7 +1131,7 @@ void ex_endwhile(exarg_T *eap) } } // Cleanup and rewind all contained (and unclosed) conditionals. - (void)cleanup_conditionals(cstack, CSF_WHILE | CSF_FOR, FALSE); + (void)cleanup_conditionals(cstack, CSF_WHILE | CSF_FOR, false); rewind_conditionals(cstack, idx, CSF_TRY, &cstack->cs_trylevel); } else if (cstack->cs_flags[cstack->cs_idx] & CSF_TRUE && !(cstack->cs_flags[cstack->cs_idx] & CSF_ACTIVE) @@ -1170,7 +1186,7 @@ void ex_throw(exarg_T *eap) void do_throw(cstack_T *cstack) { int idx; - int inactivate_try = FALSE; + int inactivate_try = false; // // Cleanup and deactivate up to the next surrounding try conditional that @@ -1183,14 +1199,14 @@ void do_throw(cstack_T *cstack) // #ifndef THROW_ON_ERROR_TRUE if (did_emsg && !THROW_ON_ERROR) { - inactivate_try = TRUE; - did_emsg = FALSE; + inactivate_try = true; + did_emsg = false; } #endif #ifndef THROW_ON_INTERRUPT_TRUE if (got_int && !THROW_ON_INTERRUPT) { - inactivate_try = TRUE; - got_int = FALSE; + inactivate_try = true; + got_int = false; } #endif idx = cleanup_conditionals(cstack, 0, inactivate_try); @@ -1221,6 +1237,8 @@ void do_throw(cstack_T *cstack) cstack->cs_flags[idx] &= ~CSF_ACTIVE; cstack->cs_exception[idx] = current_exception; } + + did_throw = true; } /// Handle ":try" @@ -1232,8 +1250,8 @@ void ex_try(exarg_T *eap) if (cstack->cs_idx == CSTACK_LEN - 1) { eap->errmsg = _("E601: :try nesting too deep"); } else { - ++cstack->cs_idx; - ++cstack->cs_trylevel; + cstack->cs_idx++; + cstack->cs_trylevel++; cstack->cs_flags[cstack->cs_idx] = CSF_TRY; cstack->cs_pending[cstack->cs_idx] = CSTP_NONE; @@ -1298,7 +1316,7 @@ void ex_catch(exarg_T *eap) eap->errmsg = get_end_emsg(cstack); skip = true; } - for (idx = cstack->cs_idx; idx > 0; --idx) { + for (idx = cstack->cs_idx; idx > 0; idx--) { if (cstack->cs_flags[idx] & CSF_TRY) { break; } @@ -1317,10 +1335,10 @@ void ex_catch(exarg_T *eap) if (ends_excmd(*eap->arg)) { // no argument, catch all errors pat = ".*"; end = NULL; - eap->nextcmd = (char *)find_nextcmd((char_u *)eap->arg); + eap->nextcmd = find_nextcmd(eap->arg); } else { pat = eap->arg + 1; - end = (char *)skip_regexp((char_u *)pat, *eap->arg, true, NULL); + end = skip_regexp(pat, *eap->arg, true, NULL); } if (!give_up) { @@ -1329,7 +1347,7 @@ void ex_catch(exarg_T *eap) * corresponding try block never got active (because of an inactive * surrounding conditional or after an error or interrupt or throw). */ - if (!current_exception || !(cstack->cs_flags[idx] & CSF_TRUE)) { + if (!did_throw || !(cstack->cs_flags[idx] & CSF_TRUE)) { skip = true; } @@ -1360,7 +1378,7 @@ void ex_catch(exarg_T *eap) *end = NUL; } save_cpo = p_cpo; - p_cpo = ""; + p_cpo = empty_option; // Disable error messages, it will make current exception // invalid emsg_off++; @@ -1390,10 +1408,10 @@ void ex_catch(exarg_T *eap) } if (caught) { - // Make this ":catch" clause active and reset did_emsg and got_int. - // Put the exception on the caught stack. + // Make this ":catch" clause active and reset did_emsg, got_int, + // and did_throw. Put the exception on the caught stack. cstack->cs_flags[idx] |= CSF_ACTIVE | CSF_CAUGHT; - did_emsg = got_int = false; + did_emsg = got_int = did_throw = false; catch_exception((except_T *)cstack->cs_exception[idx]); // It's mandatory that the current exception is stored in the cstack // so that it can be discarded at the next ":catch", ":finally", or @@ -1403,10 +1421,6 @@ void ex_catch(exarg_T *eap) if (cstack->cs_exception[cstack->cs_idx] != current_exception) { internal_error("ex_catch()"); } - // Discarding current_exceptions happens based on what is stored in - // cstack->cs_exception, *all* calls to discard_current_exception() are - // (and must be) guarded by current_exception check. - current_exception = NULL; } else { /* * If there is a preceding catch clause and it caught the exception, @@ -1418,12 +1432,12 @@ void ex_catch(exarg_T *eap) * a ":continue", ":break", ":return", or ":finish", discard the * pending action. */ - cleanup_conditionals(cstack, CSF_TRY, TRUE); + cleanup_conditionals(cstack, CSF_TRY, true); } } if (end != NULL) { - eap->nextcmd = (char *)find_nextcmd((char_u *)end); + eap->nextcmd = find_nextcmd(end); } } @@ -1431,7 +1445,7 @@ void ex_catch(exarg_T *eap) void ex_finally(exarg_T *eap) { int idx; - int skip = FALSE; + int skip = false; int pending = CSTP_NONE; cstack_T *const cstack = eap->cstack; @@ -1440,7 +1454,7 @@ void ex_finally(exarg_T *eap) } else { if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) { eap->errmsg = get_end_emsg(cstack); - for (idx = cstack->cs_idx - 1; idx > 0; --idx) { + for (idx = cstack->cs_idx - 1; idx > 0; idx--) { if (cstack->cs_flags[idx] & CSF_TRY) { break; } @@ -1461,14 +1475,12 @@ void ex_finally(exarg_T *eap) rewind_conditionals(cstack, idx, CSF_WHILE | CSF_FOR, &cstack->cs_looplevel); - /* - * Don't do something when the corresponding try block never got active - * (because of an inactive surrounding conditional or after an error or - * interrupt or throw) or for a ":finally" without ":try" or a multiple - * ":finally". After every other error (did_emsg or the conditional - * errors detected above) or after an interrupt (got_int) or an - * exception (current_exception), the finally clause must be executed. - */ + // Don't do something when the corresponding try block never got active + // (because of an inactive surrounding conditional or after an error or + // interrupt or throw) or for a ":finally" without ":try" or a multiple + // ":finally". After every other error (did_emsg or the conditional + // errors detected above) or after an interrupt (got_int) or an + // exception (did_throw), the finally clause must be executed. skip = !(cstack->cs_flags[cstack->cs_idx] & CSF_TRUE); if (!skip) { @@ -1491,24 +1503,22 @@ void ex_finally(exarg_T *eap) * ":continue", ":break", ":finish", or ":return" from the preceding * try block or catch clause. */ - cleanup_conditionals(cstack, CSF_TRY, FALSE); - - /* - * Make did_emsg, got_int, current_exception pending. If set, they - * overrule a pending ":continue", ":break", ":return", or ":finish". - * Then we have particularly to discard a pending return value (as done - * by the call to cleanup_conditionals() above when did_emsg or - * got_int is set). The pending values are restored by the - * ":endtry", except if there is a new error, interrupt, exception, - * ":continue", ":break", ":return", or ":finish" in the following - * finally clause. A missing ":endwhile", ":endfor" or ":endif" - * detected here is treated as if did_emsg and current_exception had - * already been set, respectively in case that the error is not - * converted to an exception, current_exception had already been unset. - * We must not set did_emsg here since that would suppress the - * error message. - */ - if (pending == CSTP_ERROR || did_emsg || got_int || current_exception) { + cleanup_conditionals(cstack, CSF_TRY, false); + + // Make did_emsg, got_int, did_throw pending. If set, they overrule + // a pending ":continue", ":break", ":return", or ":finish". Then + // we have particularly to discard a pending return value (as done + // by the call to cleanup_conditionals() above when did_emsg or + // got_int is set). The pending values are restored by the + // ":endtry", except if there is a new error, interrupt, exception, + // ":continue", ":break", ":return", or ":finish" in the following + // finally clause. A missing ":endwhile", ":endfor" or ":endif" + // detected here is treated as if did_emsg and did_throw had + // already been set, respectively in case that the error is not + // converted to an exception, did_throw had already been unset. + // We must not set did_emsg here since that would suppress the + // error message. + if (pending == CSTP_ERROR || did_emsg || got_int || did_throw) { if (cstack->cs_pending[cstack->cs_idx] == CSTP_RETURN) { report_discard_pending(CSTP_RETURN, cstack->cs_rettv[cstack->cs_idx]); @@ -1517,7 +1527,7 @@ void ex_finally(exarg_T *eap) if (pending == CSTP_ERROR && !did_emsg) { pending |= (THROW_ON_ERROR ? CSTP_THROW : 0); } else { - pending |= (current_exception ? CSTP_THROW : 0); + pending |= (did_throw ? CSTP_THROW : 0); } pending |= did_emsg ? CSTP_ERROR : 0; pending |= got_int ? CSTP_INTERRUPT : 0; @@ -1531,19 +1541,16 @@ void ex_finally(exarg_T *eap) // exception. When emsg() is called for a missing ":endif" or // a missing ":endwhile"/":endfor" detected here, the // exception will be discarded. - if (current_exception - && cstack->cs_exception[cstack->cs_idx] != current_exception) { + if (did_throw && cstack->cs_exception[cstack->cs_idx] != current_exception) { internal_error("ex_finally()"); } } - /* - * Set CSL_HAD_FINA, so do_cmdline() will reset did_emsg, - * got_int, and current_exception and make the finally clause active. - * This will happen after emsg() has been called for a missing - * ":endif" or a missing ":endwhile"/":endfor" detected here, so - * that the following finally clause will be executed even then. - */ + // Set CSL_HAD_FINA, so do_cmdline() will reset did_emsg, + // got_int, and did_throw and make the finally clause active. + // This will happen after emsg() has been called for a missing + // ":endif" or a missing ":endwhile"/":endfor" detected here, so + // that the following finally clause will be executed even then. cstack->cs_lflags |= CSL_HAD_FINA; } } @@ -1571,8 +1578,7 @@ void ex_endtry(exarg_T *eap) // made inactive by a ":continue", ":break", ":return", or ":finish" in // the finally clause. The latter case need not be tested since then // anything pending has already been discarded. - bool skip = did_emsg || got_int || current_exception - || !(cstack->cs_flags[cstack->cs_idx] & CSF_TRUE); + bool skip = did_emsg || got_int || did_throw || !(cstack->cs_flags[cstack->cs_idx] & CSF_TRUE); if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) { eap->errmsg = get_end_emsg(cstack); @@ -1586,14 +1592,12 @@ void ex_endtry(exarg_T *eap) &cstack->cs_looplevel); skip = true; - /* - * If an exception is being thrown, discard it to prevent it from - * being rethrown at the end of this function. It would be - * discarded by the error message, anyway. Resets current_exception. - * This does not affect the script termination due to the error - * since "trylevel" is decremented after emsg() has been called. - */ - if (current_exception) { + // If an exception is being thrown, discard it to prevent it from + // being rethrown at the end of this function. It would be + // discarded by the error message, anyway. Resets did_throw. + // This does not affect the script termination due to the error + // since "trylevel" is decremented after emsg() has been called. + if (did_throw) { discard_current_exception(); } @@ -1608,7 +1612,7 @@ void ex_endtry(exarg_T *eap) * a finally clause, we need to rethrow it after closing the try * conditional. */ - if (current_exception + if (did_throw && (cstack->cs_flags[idx] & CSF_TRUE) && !(cstack->cs_flags[idx] & CSF_FINALLY)) { rethrow = true; @@ -1632,10 +1636,10 @@ void ex_endtry(exarg_T *eap) if (got_int) { skip = true; (void)do_intthrow(cstack); - // The do_intthrow() call may have reset current_exception or + // The do_intthrow() call may have reset did_throw or // cstack->cs_pending[idx]. rethrow = false; - if (current_exception && !(cstack->cs_flags[idx] & CSF_FINALLY)) { + if (did_throw && !(cstack->cs_flags[idx] & CSF_FINALLY)) { rethrow = true; } } @@ -1667,7 +1671,7 @@ void ex_endtry(exarg_T *eap) * after errors except when this ":endtry" is not within a ":try". * Restore "emsg_silent" if it has been reset by this try conditional. */ - (void)cleanup_conditionals(cstack, CSF_TRY | CSF_SILENT, TRUE); + (void)cleanup_conditionals(cstack, CSF_TRY | CSF_SILENT, true); if (cstack->cs_idx >= 0 && (cstack->cs_flags[cstack->cs_idx] & CSF_TRY)) { cstack->cs_idx--; @@ -1696,16 +1700,16 @@ void ex_endtry(exarg_T *eap) ex_break(eap); break; case CSTP_RETURN: - do_return(eap, FALSE, FALSE, rettv); + do_return(eap, false, false, rettv); break; case CSTP_FINISH: - do_finish(eap, FALSE); + do_finish(eap, false); break; // When the finally clause was entered due to an error, // interrupt or throw (as opposed to a ":continue", ":break", // ":return", or ":finish"), restore the pending values of - // did_emsg, got_int, and current_exception. This is skipped, if there + // did_emsg, got_int, and did_throw. This is skipped, if there // was a new error, interrupt, throw, ":continue", ":break", // ":return", or ":finish". in the finally clause. default: @@ -1752,35 +1756,32 @@ void enter_cleanup(cleanup_T *csp) { int pending = CSTP_NONE; - /* - * Postpone did_emsg, got_int, current_exception. The pending values will be - * restored by leave_cleanup() except if there was an aborting error, - * interrupt, or uncaught exception after this function ends. - */ - if (did_emsg || got_int || current_exception || need_rethrow) { + // Postpone did_emsg, got_int, did_throw. The pending values will be + // restored by leave_cleanup() except if there was an aborting error, + // interrupt, or uncaught exception after this function ends. + if (did_emsg || got_int || did_throw || need_rethrow) { csp->pending = (did_emsg ? CSTP_ERROR : 0) | (got_int ? CSTP_INTERRUPT : 0) - | (current_exception ? CSTP_THROW : 0) + | (did_throw ? CSTP_THROW : 0) | (need_rethrow ? CSTP_THROW : 0); - // If we are currently throwing an exception, save it as well. On an error - // not yet converted to an exception, update "force_abort" and reset - // "cause_abort" (as do_errthrow() would do). This is needed for the - // do_cmdline() call that is going to be made for autocommand execution. We - // need not save *msg_list because there is an extra instance for every call - // of do_cmdline(), anyway. - if (current_exception || need_rethrow) { + // If we are currently throwing an exception (did_throw), save it as + // well. On an error not yet converted to an exception, update + // "force_abort" and reset "cause_abort" (as do_errthrow() would do). + // This is needed for the do_cmdline() call that is going to be made + // for autocommand execution. We need not save *msg_list because + // there is an extra instance for every call of do_cmdline(), anyway. + if (did_throw || need_rethrow) { csp->exception = current_exception; current_exception = NULL; } else { csp->exception = NULL; if (did_emsg) { force_abort |= cause_abort; - cause_abort = FALSE; + cause_abort = false; } } - did_emsg = got_int = need_rethrow = false; - current_exception = NULL; + did_emsg = got_int = did_throw = need_rethrow = false; // Report if required by the 'verbose' option or when debugging. report_make_pending(pending, csp->exception); @@ -1847,10 +1848,10 @@ void leave_cleanup(cleanup_T *csp) // enter_cleanup() was called, let "cause_abort" take the part of // "force_abort" (as done by cause_errthrow()). cause_abort = force_abort; - force_abort = FALSE; + force_abort = false; } - // Restore the pending values of did_emsg, got_int, and current_exception. + // Restore the pending values of did_emsg, got_int, and did_throw. if (pending & CSTP_ERROR) { did_emsg = true; } @@ -1858,7 +1859,7 @@ void leave_cleanup(cleanup_T *csp) got_int = true; } if (pending & CSTP_THROW) { - need_rethrow = true; // current_exception will be set by do_one_cmd() + need_rethrow = true; // did_throw will be set by do_one_cmd() } // Report if required by the 'verbose' option or when debugging. @@ -1879,7 +1880,7 @@ void leave_cleanup(cleanup_T *csp) /// inactive itself (a try conditional not in its finally /// clause possibly find before is always made inactive). /// -/// If "inclusive" is TRUE and "searched_cond" is CSF_TRY|CSF_SILENT, the saved +/// If "inclusive" is true and "searched_cond" is CSF_TRY|CSF_SILENT, the saved /// former value of "emsg_silent", if reset when the try conditional finally /// reached was entered, is restored (used by ex_endtry()). This is normally /// done only when such a try conditional is left. @@ -1888,9 +1889,9 @@ void leave_cleanup(cleanup_T *csp) int cleanup_conditionals(cstack_T *cstack, int searched_cond, int inclusive) { int idx; - int stop = FALSE; + int stop = false; - for (idx = cstack->cs_idx; idx >= 0; --idx) { + for (idx = cstack->cs_idx; idx >= 0; idx--) { if (cstack->cs_flags[idx] & CSF_TRY) { /* * Discard anything pending in a finally clause and continue the @@ -1952,20 +1953,20 @@ int cleanup_conditionals(cstack_T *cstack, int searched_cond, int inclusive) if (searched_cond == 0 && !inclusive) { break; } - stop = TRUE; + stop = true; } } } // Stop on the searched conditional type (even when the surrounding // conditional is not active or something has been made pending). - // If "inclusive" is TRUE and "searched_cond" is CSF_TRY|CSF_SILENT, + // If "inclusive" is true and "searched_cond" is CSF_TRY|CSF_SILENT, // check first whether "emsg_silent" needs to be restored. if (cstack->cs_flags[idx] & searched_cond) { if (!inclusive) { break; } - stop = TRUE; + stop = true; } cstack->cs_flags[idx] &= ~CSF_ACTIVE; if (stop && searched_cond != (CSF_TRY | CSF_SILENT)) { @@ -2020,7 +2021,7 @@ void rewind_conditionals(cstack_T *cstack, int idx, int cond_type, int *cond_lev if (cstack->cs_flags[cstack->cs_idx] & CSF_FOR) { free_for_info(cstack->cs_forinfo[cstack->cs_idx]); } - --cstack->cs_idx; + cstack->cs_idx--; } } @@ -2030,7 +2031,7 @@ void ex_endfunction(exarg_T *eap) emsg(_("E193: :endfunction not inside a function")); } -/// @return TRUE if the string "p" looks like a ":while" or ":for" command. +/// @return true if the string "p" looks like a ":while" or ":for" command. int has_loop_cmd(char *p) { int len; @@ -2038,7 +2039,7 @@ int has_loop_cmd(char *p) // skip modifiers, white space and ':' for (;;) { while (*p == ' ' || *p == '\t' || *p == ':') { - ++p; + p++; } len = modifier_len(p); if (len == 0) { @@ -2048,7 +2049,7 @@ int has_loop_cmd(char *p) } if ((p[0] == 'w' && p[1] == 'h') || (p[0] == 'f' && p[1] == 'o' && p[2] == 'r')) { - return TRUE; + return true; } - return FALSE; + return false; } |