diff options
author | Josh Rahm <rahm@google.com> | 2022-08-19 12:26:08 -0600 |
---|---|---|
committer | Josh Rahm <rahm@google.com> | 2022-08-19 13:06:41 -0600 |
commit | a7237662f96933efe29eed8212464571e3778cd0 (patch) | |
tree | 27930202726b4251437c8cfa53069f65b4db90dc /src/nvim/message.c | |
parent | 02292344929069ea63c0bb872cc22d552d86b67f (diff) | |
parent | b2f979b30beac67906b2dd717fcb6a34f46f5e54 (diff) | |
download | rneovim-tmp.tar.gz rneovim-tmp.tar.bz2 rneovim-tmp.zip |
Merge branch 'master' of https://github.com/neovim/neovim into rahmtmp
Diffstat (limited to 'src/nvim/message.c')
-rw-r--r-- | src/nvim/message.c | 143 |
1 files changed, 87 insertions, 56 deletions
diff --git a/src/nvim/message.c b/src/nvim/message.c index 7cccd046c9..684cf7207c 100644 --- a/src/nvim/message.c +++ b/src/nvim/message.c @@ -15,6 +15,7 @@ #include "nvim/ascii.h" #include "nvim/assert.h" #include "nvim/charset.h" +#include "nvim/drawscreen.h" #include "nvim/eval.h" #include "nvim/ex_docmd.h" #include "nvim/ex_eval.h" @@ -23,7 +24,9 @@ #include "nvim/func_attr.h" #include "nvim/garray.h" #include "nvim/getchar.h" +#include "nvim/grid.h" #include "nvim/highlight.h" +#include "nvim/indent.h" #include "nvim/input.h" #include "nvim/keycodes.h" #include "nvim/main.h" @@ -38,7 +41,7 @@ #include "nvim/os/os.h" #include "nvim/os/time.h" #include "nvim/regexp.h" -#include "nvim/screen.h" +#include "nvim/runtime.h" #include "nvim/strings.h" #include "nvim/syntax.h" #include "nvim/ui.h" @@ -318,7 +321,7 @@ bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline) if (entered >= 3) { return TRUE; } - ++entered; + entered++; // Add message to history (unless it's a repeated kept message or a // truncated message) @@ -355,7 +358,7 @@ bool msg_attr_keep(const char *s, int attr, bool keep, bool multiline) need_fileinfo = false; xfree(buf); - --entered; + entered--; return retval; } @@ -524,7 +527,7 @@ int smsg_attr_keep(int attr, const char *s, ...) * isn't printed each time when it didn't change. */ static int last_sourcing_lnum = 0; -static char_u *last_sourcing_name = NULL; +static char *last_sourcing_name = NULL; /// Reset the last used sourcing name/lnum. Makes sure it is displayed again /// for the next error message; @@ -534,16 +537,16 @@ void reset_last_sourcing(void) last_sourcing_lnum = 0; } -/// @return TRUE if "sourcing_name" differs from "last_sourcing_name". -static int other_sourcing_name(void) +/// @return true if "SOURCING_NAME" differs from "last_sourcing_name". +static bool other_sourcing_name(void) { - if (sourcing_name != NULL) { + if (SOURCING_NAME != NULL) { if (last_sourcing_name != NULL) { - return STRCMP(sourcing_name, last_sourcing_name) != 0; + return strcmp(SOURCING_NAME, last_sourcing_name) != 0; } - return TRUE; + return true; } - return FALSE; + return false; } /// Get the message about the source, as used for an error message @@ -553,11 +556,19 @@ static int other_sourcing_name(void) static char *get_emsg_source(void) FUNC_ATTR_MALLOC FUNC_ATTR_WARN_UNUSED_RESULT { - if (sourcing_name != NULL && other_sourcing_name()) { + if (SOURCING_NAME != NULL && other_sourcing_name()) { + char *sname = estack_sfile(ESTACK_NONE); + char *tofree = sname; + + if (sname == NULL) { + sname = SOURCING_NAME; + } + const char *const p = _("Error detected while processing %s:"); - const size_t buf_len = STRLEN(sourcing_name) + strlen(p) + 1; + const size_t buf_len = STRLEN(sname) + strlen(p) + 1; char *const buf = xmalloc(buf_len); - snprintf(buf, buf_len, p, sourcing_name); + snprintf(buf, buf_len, p, sname); + xfree(tofree); return buf; } return NULL; @@ -572,13 +583,13 @@ static char *get_emsg_lnum(void) { // lnum is 0 when executing a command from the command line // argument, we don't want a line number then - if (sourcing_name != NULL - && (other_sourcing_name() || sourcing_lnum != last_sourcing_lnum) - && sourcing_lnum != 0) { + if (SOURCING_NAME != NULL + && (other_sourcing_name() || SOURCING_LNUM != last_sourcing_lnum) + && SOURCING_LNUM != 0) { const char *const p = _("line %4ld:"); const size_t buf_len = 20 + strlen(p); char *const buf = xmalloc(buf_len); - snprintf(buf, buf_len, p, (long)sourcing_lnum); + snprintf(buf, buf_len, p, (long)SOURCING_LNUM); return buf; } return NULL; @@ -589,6 +600,15 @@ static char *get_emsg_lnum(void) /// is only displayed if it changed. void msg_source(int attr) { + static bool recursive = false; + + // Bail out if something called here causes an error. + if (recursive) { + return; + } + recursive = true; + + msg_scroll = true; // this will take more than one line no_wait_return++; char *p = get_emsg_source(); if (p != NULL) { @@ -599,19 +619,19 @@ void msg_source(int attr) if (p != NULL) { msg_attr(p, HL_ATTR(HLF_N)); xfree(p); - last_sourcing_lnum = sourcing_lnum; // only once for each line + last_sourcing_lnum = SOURCING_LNUM; // only once for each line } // remember the last sourcing name printed, also when it's empty - if (sourcing_name == NULL || other_sourcing_name()) { - xfree(last_sourcing_name); - if (sourcing_name == NULL) { - last_sourcing_name = NULL; - } else { - last_sourcing_name = vim_strsave((char_u *)sourcing_name); + if (SOURCING_NAME == NULL || other_sourcing_name()) { + XFREE_CLEAR(last_sourcing_name); + if (SOURCING_NAME != NULL) { + last_sourcing_name = xstrdup(SOURCING_NAME); } } - --no_wait_return; + no_wait_return--; + + recursive = false; } /// @return TRUE if not giving error messages right now: @@ -686,9 +706,9 @@ static bool emsg_multiline(const char *s, bool multiline) } // Log (silent) errors as debug messages. - if (sourcing_name != NULL && sourcing_lnum != 0) { + if (SOURCING_NAME != NULL && SOURCING_LNUM != 0) { DLOG("(:silent) %s (%s (line %ld))", - s, sourcing_name, (long)sourcing_lnum); + s, SOURCING_NAME, (long)SOURCING_LNUM); } else { DLOG("(:silent) %s", s); } @@ -697,8 +717,8 @@ static bool emsg_multiline(const char *s, bool multiline) } // Log editor errors as INFO. - if (sourcing_name != NULL && sourcing_lnum != 0) { - ILOG("%s (%s (line %ld))", s, sourcing_name, (long)sourcing_lnum); + if (SOURCING_NAME != NULL && SOURCING_LNUM != 0) { + ILOG("%s (%s (line %ld))", s, SOURCING_NAME, (long)SOURCING_LNUM); } else { ILOG("%s", s); } @@ -722,7 +742,6 @@ static bool emsg_multiline(const char *s, bool multiline) } emsg_on_display = true; // remember there is an error message - msg_scroll++; // don't overwrite a previous message attr = HL_ATTR(HLF_E); // set highlight mode for error messages if (msg_scrolled != 0) { need_wait_return = true; // needed in case emsg() is called after @@ -733,9 +752,8 @@ static bool emsg_multiline(const char *s, bool multiline) msg_ext_set_kind("emsg"); } - /* - * Display name and line number for the source of the error. - */ + // Display name and line number for the source of the error. + // Sets "msg_scroll". msg_source(attr); // Display the error message itself. @@ -812,8 +830,15 @@ static bool semsgv(const char *fmt, va_list ap) /// detected when fuzzing vim. void iemsg(const char *s) { + if (emsg_not_now()) { + return; + } + emsg(s); #ifdef ABORT_ON_INTERNAL_ERROR + set_vim_var_string(VV_ERRMSG, s, -1); + msg_putchar('\n'); // avoid overwriting the error message + ui_flush(); abort(); #endif } @@ -823,11 +848,17 @@ void iemsg(const char *s) /// detected when fuzzing vim. void siemsg(const char *s, ...) { + if (emsg_not_now()) { + return; + } + va_list ap; va_start(ap, s); (void)semsgv(s, ap); va_end(ap); #ifdef ABORT_ON_INTERNAL_ERROR + msg_putchar('\n'); // avoid overwriting the error message + ui_flush(); abort(); #endif } @@ -999,7 +1030,7 @@ int delete_first_msg(void) xfree(p->msg); hl_msg_free(p->multiattr); xfree(p); - --msg_hist_len; + msg_hist_len--; return OK; } @@ -1964,13 +1995,13 @@ static char_u *screen_puts_mbyte(char_u *s, int l, int attr) msg_col -= cw; if (msg_col == 0) { msg_col = Columns; - ++msg_row; + msg_row++; } } else { msg_col += cw; if (msg_col >= Columns) { msg_col = 0; - ++msg_row; + msg_row++; } } return s + l; @@ -2123,7 +2154,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs int t_col = 0; // Screen cells todo, 0 when "t_s" not used. int l; int cw; - const char_u *sb_str = str; + const char *sb_str = (char *)str; int sb_col = msg_col; int wrap; int did_last_char; @@ -2208,7 +2239,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs if (p_more) { // Store text for scrolling back. - store_sb_text((char_u **)&sb_str, (char_u *)s, attr, &sb_col, true); + store_sb_text((char **)&sb_str, (char *)s, attr, &sb_col, true); } inc_msg_scrolled(); @@ -2223,7 +2254,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs * for a character. */ if (lines_left > 0) { - --lines_left; + lines_left--; } if (p_more && lines_left == 0 && State != MODE_HITRETURN && !msg_no_more && !exmode_active) { @@ -2255,7 +2286,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs if (wrap && p_more && !recurse) { // Store text for scrolling back. - store_sb_text((char_u **)&sb_str, (char_u *)s, attr, &sb_col, true); + store_sb_text((char **)&sb_str, (char *)s, attr, &sb_col, true); } if (*s == '\n') { // go to next line @@ -2272,7 +2303,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs msg_col = 0; } else if (*s == '\b') { // go to previous char if (msg_col) { - --msg_col; + msg_col--; } } else if (*s == TAB) { // translate Tab into spaces do { @@ -2306,7 +2337,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs s += l - 1; } } - ++s; + s++; } // Output any postponed text. @@ -2314,7 +2345,7 @@ static void msg_puts_display(const char_u *str, int maxlen, int attr, int recurs t_puts(&t_col, t_s, s, attr); } if (p_more && !recurse) { - store_sb_text((char_u **)&sb_str, (char_u *)s, attr, &sb_col, false); + store_sb_text((char **)&sb_str, (char *)s, attr, &sb_col, false); } msg_check(); @@ -2457,7 +2488,7 @@ void msg_reset_scroll(void) static void inc_msg_scrolled(void) { if (*get_vim_var_str(VV_SCROLLSTART) == NUL) { - char *p = sourcing_name; + char *p = SOURCING_NAME; char *tofree = NULL; // v:scrollstart is empty, set it to the script/function name and line @@ -2468,7 +2499,7 @@ static void inc_msg_scrolled(void) size_t len = strlen(p) + 40; tofree = xmalloc(len); vim_snprintf(tofree, len, _("%s line %" PRId64), - p, (int64_t)sourcing_lnum); + p, (int64_t)SOURCING_LNUM); p = tofree; } set_vim_var_string(VV_SCROLLSTART, p, -1); @@ -2497,7 +2528,7 @@ static sb_clear_T do_clear_sb_text = SB_CLEAR_NONE; /// @param sb_str start of string /// @param s just after string /// @param finish line ends -static void store_sb_text(char_u **sb_str, char_u *s, int attr, int *sb_col, int finish) +static void store_sb_text(char **sb_str, char *s, int attr, int *sb_col, int finish) { msgchunk_T *mp; @@ -2654,7 +2685,7 @@ static msgchunk_T *disp_sb_line(int row, msgchunk_T *smp) msg_col = mp->sb_msg_col; p = mp->sb_text; if (*p == '\n') { // don't display the line break - ++p; + p++; } msg_puts_display(p, -1, mp->sb_attr, TRUE); if (mp->sb_eol || mp->sb_next == NULL) { @@ -2683,7 +2714,7 @@ static void t_puts(int *t_col, const char_u *t_s, const char_u *s, int attr) } if (msg_col >= Columns) { msg_col = 0; - ++msg_row; + msg_row++; } } @@ -2938,7 +2969,7 @@ static int do_more_prompt(int typed_char) HL_ATTR(HLF_MSG)); for (i = 0; mp != NULL && i < Rows - 1; i++) { mp = disp_sb_line(i, mp); - ++msg_scrolled; + msg_scrolled++; } to_redraw = false; } @@ -3037,12 +3068,12 @@ static void msg_screen_putchar(int c, int attr) if (cmdmsg_rl) { if (--msg_col == 0) { msg_col = Columns; - ++msg_row; + msg_row++; } } else { if (++msg_col >= Columns) { msg_col = 0; - ++msg_row; + msg_row++; } } } @@ -3339,7 +3370,7 @@ int redirecting(void) void verbose_enter(void) { if (*p_vfile != NUL) { - ++msg_silent; + msg_silent++; } } @@ -3358,7 +3389,7 @@ void verbose_leave(void) void verbose_enter_scroll(void) { if (*p_vfile != NUL) { - ++msg_silent; + msg_silent++; } else { // always scroll up, don't overwrite msg_scroll = TRUE; @@ -3520,7 +3551,7 @@ int do_dialog(int type, char_u *title, char_u *message, char_u *buttons, int dfl * Since we wait for a keypress, don't make the * user press RETURN as well afterwards. */ - ++no_wait_return; + no_wait_return++; hotkeys = msg_show_console_dialog(message, buttons, dfltbutton); for (;;) { @@ -3569,7 +3600,7 @@ int do_dialog(int type, char_u *title, char_u *message, char_u *buttons, int dfl msg_silent = save_msg_silent; State = oldState; setmouse(); - --no_wait_return; + no_wait_return--; msg_end_prompt(); return retval; @@ -3723,7 +3754,7 @@ static void copy_hotkeys_and_msg(const char_u *message, char_u *buttons, int def } } else if (*r == DLG_HOTKEY_CHAR || first_hotkey) { if (*r == DLG_HOTKEY_CHAR) { - ++r; + r++; } first_hotkey = false; |