mirror of
https://github.com/neovim/neovim.git
synced 2026-08-27 17:41:48 +00:00
vim-patch:8.2.2198: ml_get error when resizing window and using text property
Problem: ml_get error when resizing window and using text property.
Solution: Validate botline of the right window. (closes vim/vim#7528)
23999d799c
Migrate to Vim's (in)validate_botline_win() API.
Nvim wants to pass "curwin" instead of hiding them
behind alias/macro/inline-function.
https://github.com/neovim/neovim/pull/37164#discussion_r2655006908
Co-authored-by: Bram Moolenaar <Bram@vim.org>
This commit is contained in:
committed by
Jan Edmund Lazo
parent
0f9aae20ec
commit
ff8edbaa6c
@@ -1269,7 +1269,7 @@ static void fix_cursor(win_T *win, linenr_T lo, linenr_T hi, linenr_T extra)
|
|||||||
win->w_valid &= ~(VALID_BOTLINE_AP);
|
win->w_valid &= ~(VALID_BOTLINE_AP);
|
||||||
update_topline(win);
|
update_topline(win);
|
||||||
} else {
|
} else {
|
||||||
invalidate_botline(win);
|
invalidate_botline_win(win);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1343,7 +1343,7 @@ static void fix_cursor_cols(win_T *win, linenr_T start_row, colnr_T start_col, l
|
|||||||
|
|
||||||
check_cursor_col(win);
|
check_cursor_col(win);
|
||||||
changed_cline_bef_curs(win);
|
changed_cline_bef_curs(win);
|
||||||
invalidate_botline(win);
|
invalidate_botline_win(win);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Initialise a string array either:
|
/// Initialise a string array either:
|
||||||
|
|||||||
@@ -139,7 +139,7 @@ void decor_providers_invoke_win(win_T *wp)
|
|||||||
&& decor_state.future_begin == (int)kv_size(decor_state.ranges_i));
|
&& decor_state.future_begin == (int)kv_size(decor_state.ranges_i));
|
||||||
|
|
||||||
if (kv_size(decor_providers) > 0) {
|
if (kv_size(decor_providers) > 0) {
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
}
|
}
|
||||||
linenr_T botline = MIN(wp->w_botline, wp->w_buffer->b_ml.ml_line_count);
|
linenr_T botline = MIN(wp->w_botline, wp->w_buffer->b_ml.ml_line_count);
|
||||||
|
|
||||||
|
|||||||
@@ -2535,7 +2535,7 @@ void diff_set_topline(win_T *fromwin, win_T *towin)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// When w_topline changes need to recompute w_botline and cursor position
|
// When w_topline changes need to recompute w_botline and cursor position
|
||||||
invalidate_botline(towin);
|
invalidate_botline_win(towin);
|
||||||
changed_line_abv_curs_win(towin);
|
changed_line_abv_curs_win(towin);
|
||||||
|
|
||||||
check_topfill(towin, false);
|
check_topfill(towin, false);
|
||||||
|
|||||||
@@ -363,7 +363,7 @@ void screen_resize(int width, int height)
|
|||||||
maketitle();
|
maketitle();
|
||||||
|
|
||||||
changed_line_abv_curs();
|
changed_line_abv_curs();
|
||||||
invalidate_botline(curwin);
|
invalidate_botline_win(curwin);
|
||||||
|
|
||||||
// We only redraw when it's needed:
|
// We only redraw when it's needed:
|
||||||
// - While at the more prompt or executing an external command, don't
|
// - While at the more prompt or executing an external command, don't
|
||||||
|
|||||||
@@ -5361,7 +5361,7 @@ pos_T *var2fpos(const typval_T *const tv, const bool dollar_lnum, int *const ret
|
|||||||
|
|
||||||
if (name[0] == 'w' && dollar_lnum) {
|
if (name[0] == 'w' && dollar_lnum) {
|
||||||
// the "w_valid" flags are not reset when moving the cursor, but they
|
// the "w_valid" flags are not reset when moving the cursor, but they
|
||||||
// do matter for update_topline() and validate_botline().
|
// do matter for update_topline() and validate_botline_win().
|
||||||
check_cursor_moved(wp);
|
check_cursor_moved(wp);
|
||||||
|
|
||||||
pos.col = 0;
|
pos.col = 0;
|
||||||
@@ -5372,7 +5372,7 @@ pos_T *var2fpos(const typval_T *const tv, const bool dollar_lnum, int *const ret
|
|||||||
pos.lnum = wp->w_topline > 0 ? wp->w_topline : 1;
|
pos.lnum = wp->w_topline > 0 ? wp->w_topline : 1;
|
||||||
return &pos;
|
return &pos;
|
||||||
} else if (name[1] == '$') { // "w$": last visible line
|
} else if (name[1] == '$') { // "w$": last visible line
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
// In silent Ex mode botline is zero, return zero then.
|
// In silent Ex mode botline is zero, return zero then.
|
||||||
pos.lnum = wp->w_botline > 0 ? wp->w_botline - 1 : 0;
|
pos.lnum = wp->w_botline > 0 ? wp->w_botline - 1 : 0;
|
||||||
return &pos;
|
return &pos;
|
||||||
|
|||||||
@@ -328,7 +328,7 @@ static dict_T *get_win_info(win_T *wp, int16_t tpnr, int16_t winnr)
|
|||||||
dict_T *const dict = tv_dict_alloc();
|
dict_T *const dict = tv_dict_alloc();
|
||||||
|
|
||||||
// make sure w_botline is valid
|
// make sure w_botline is valid
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
|
|
||||||
tv_dict_add_nr(dict, S_LEN("tabnr"), tpnr);
|
tv_dict_add_nr(dict, S_LEN("tabnr"), tpnr);
|
||||||
tv_dict_add_nr(dict, S_LEN("winnr"), winnr);
|
tv_dict_add_nr(dict, S_LEN("winnr"), winnr);
|
||||||
|
|||||||
@@ -1279,7 +1279,7 @@ static void do_filter(linenr_T line1, linenr_T line2, exarg_T *eap, char *cmd, b
|
|||||||
curwin->w_cursor.lnum = line1;
|
curwin->w_cursor.lnum = line1;
|
||||||
curwin->w_cursor.col = 0;
|
curwin->w_cursor.col = 0;
|
||||||
changed_line_abv_curs();
|
changed_line_abv_curs();
|
||||||
invalidate_botline(curwin);
|
invalidate_botline_win(curwin);
|
||||||
|
|
||||||
// When using temp files:
|
// When using temp files:
|
||||||
// 1. * Form temp file names
|
// 1. * Form temp file names
|
||||||
|
|||||||
@@ -4652,7 +4652,7 @@ static int open_cmdwin(void)
|
|||||||
curwin->w_cursor.lnum = curbuf->b_ml.ml_line_count;
|
curwin->w_cursor.lnum = curbuf->b_ml.ml_line_count;
|
||||||
curwin->w_cursor.col = ccline.cmdpos;
|
curwin->w_cursor.col = ccline.cmdpos;
|
||||||
changed_line_abv_curs();
|
changed_line_abv_curs();
|
||||||
invalidate_botline(curwin);
|
invalidate_botline_win(curwin);
|
||||||
ui_ext_cmdline_hide(false);
|
ui_ext_cmdline_hide(false);
|
||||||
redraw_later(curwin, UPD_SOME_VALID);
|
redraw_later(curwin, UPD_SOME_VALID);
|
||||||
|
|
||||||
|
|||||||
@@ -368,7 +368,7 @@ void update_topline(win_T *wp)
|
|||||||
// for every small change.
|
// for every small change.
|
||||||
if (check_botline) {
|
if (check_botline) {
|
||||||
if (!(wp->w_valid & VALID_BOTLINE_AP)) {
|
if (!(wp->w_valid & VALID_BOTLINE_AP)) {
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(wp->w_buffer != 0);
|
assert(wp->w_buffer != 0);
|
||||||
@@ -571,6 +571,9 @@ void set_topline(win_T *wp, linenr_T lnum)
|
|||||||
hasFolding(wp, lnum, &lnum, NULL);
|
hasFolding(wp, lnum, &lnum, NULL);
|
||||||
// Approximate the value of w_botline
|
// Approximate the value of w_botline
|
||||||
wp->w_botline += lnum - wp->w_topline;
|
wp->w_botline += lnum - wp->w_topline;
|
||||||
|
if (wp->w_botline > wp->w_buffer->b_ml.ml_line_count + 1) {
|
||||||
|
wp->w_botline = wp->w_buffer->b_ml.ml_line_count + 1;
|
||||||
|
}
|
||||||
wp->w_topline = lnum;
|
wp->w_topline = lnum;
|
||||||
wp->w_topline_was_set = true;
|
wp->w_topline_was_set = true;
|
||||||
if (lnum != prev_topline) {
|
if (lnum != prev_topline) {
|
||||||
@@ -608,16 +611,18 @@ void changed_line_abv_curs_win(win_T *wp)
|
|||||||
|VALID_CHEIGHT|VALID_TOPLINE);
|
|VALID_CHEIGHT|VALID_TOPLINE);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Make sure the value of wp->w_botline is valid.
|
/// Make sure the value of wp->w_botline is valid.
|
||||||
void validate_botline(win_T *wp)
|
void validate_botline_win(win_T *wp)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
{
|
{
|
||||||
if (!(wp->w_valid & VALID_BOTLINE)) {
|
if (!(wp->w_valid & VALID_BOTLINE)) {
|
||||||
comp_botline(wp);
|
comp_botline(wp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Mark wp->w_botline as invalid (because of some change in the buffer).
|
/// Mark wp->w_botline as invalid (because of some change in the buffer).
|
||||||
void invalidate_botline(win_T *wp)
|
void invalidate_botline_win(win_T *wp)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
{
|
{
|
||||||
wp->w_valid &= ~(VALID_BOTLINE|VALID_BOTLINE_AP);
|
wp->w_valid &= ~(VALID_BOTLINE|VALID_BOTLINE_AP);
|
||||||
}
|
}
|
||||||
@@ -1397,7 +1402,7 @@ bool scrolldown(win_T *wp, linenr_T line_count, int byfold)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
wp->w_botline--; // approximate w_botline
|
wp->w_botline--; // approximate w_botline
|
||||||
invalidate_botline(wp);
|
invalidate_botline_win(wp);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Adjust for concealed lines above w_topline
|
// Adjust for concealed lines above w_topline
|
||||||
@@ -1960,7 +1965,7 @@ void scroll_cursor_bot(win_T *wp, int min_scroll, bool set_topbot)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
}
|
}
|
||||||
|
|
||||||
// The lines of the cursor line itself are always used.
|
// The lines of the cursor line itself are always used.
|
||||||
@@ -2276,7 +2281,7 @@ void cursor_correct(win_T *wp)
|
|||||||
int max_off = wp->w_view_height / 2;
|
int max_off = wp->w_view_height / 2;
|
||||||
below_wanted = MIN(below_wanted, max_off);
|
below_wanted = MIN(below_wanted, max_off);
|
||||||
}
|
}
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
if (wp->w_botline == wp->w_buffer->b_ml.ml_line_count + 1
|
if (wp->w_botline == wp->w_buffer->b_ml.ml_line_count + 1
|
||||||
&& mouse_dragging == 0) {
|
&& mouse_dragging == 0) {
|
||||||
below_wanted = 0;
|
below_wanted = 0;
|
||||||
@@ -2365,7 +2370,7 @@ static int get_scroll_overlap(Direction dir)
|
|||||||
lineoff_T loff;
|
lineoff_T loff;
|
||||||
int min_height = curwin->w_view_height - 2;
|
int min_height = curwin->w_view_height - 2;
|
||||||
|
|
||||||
validate_botline(curwin);
|
validate_botline_win(curwin);
|
||||||
if ((dir == BACKWARD && curwin->w_topline == 1)
|
if ((dir == BACKWARD && curwin->w_topline == 1)
|
||||||
|| (dir == FORWARD && curwin->w_botline > curbuf->b_ml.ml_line_count)) {
|
|| (dir == FORWARD && curwin->w_botline > curbuf->b_ml.ml_line_count)) {
|
||||||
return min_height + 2; // no overlap, still handle 'smoothscroll'
|
return min_height + 2; // no overlap, still handle 'smoothscroll'
|
||||||
@@ -2516,7 +2521,7 @@ int pagescroll(Direction dir, int count, bool half)
|
|||||||
|
|
||||||
if (!nochange) {
|
if (!nochange) {
|
||||||
// Place cursor at top or bottom of window.
|
// Place cursor at top or bottom of window.
|
||||||
validate_botline(curwin);
|
validate_botline_win(curwin);
|
||||||
linenr_T lnum = (dir == FORWARD ? curwin->w_topline : curwin->w_botline - 1);
|
linenr_T lnum = (dir == FORWARD ? curwin->w_topline : curwin->w_botline - 1);
|
||||||
// In silent Ex mode the value of w_botline - 1 may be 0,
|
// In silent Ex mode the value of w_botline - 1 may be 0,
|
||||||
// but cursor lnum needs to be at least 1.
|
// but cursor lnum needs to be at least 1.
|
||||||
|
|||||||
@@ -2800,7 +2800,7 @@ static void nv_zet(cmdarg_T *cap)
|
|||||||
case '+':
|
case '+':
|
||||||
if (cap->count0 == 0) {
|
if (cap->count0 == 0) {
|
||||||
// No count given: put cursor at the line below screen
|
// No count given: put cursor at the line below screen
|
||||||
validate_botline(curwin); // make sure w_botline is valid
|
validate_botline_win(curwin); // make sure w_botline is valid
|
||||||
curwin->w_cursor.lnum = MIN(curwin->w_botline, curbuf->b_ml.ml_line_count);
|
curwin->w_cursor.lnum = MIN(curwin->w_botline, curbuf->b_ml.ml_line_count);
|
||||||
}
|
}
|
||||||
FALLTHROUGH;
|
FALLTHROUGH;
|
||||||
@@ -3622,7 +3622,7 @@ static void nv_scroll(cmdarg_T *cap)
|
|||||||
setpcmark();
|
setpcmark();
|
||||||
|
|
||||||
if (cap->cmdchar == 'L') {
|
if (cap->cmdchar == 'L') {
|
||||||
validate_botline(curwin); // make sure curwin->w_botline is valid
|
validate_botline_win(curwin); // make sure curwin->w_botline is valid
|
||||||
curwin->w_cursor.lnum = curwin->w_botline - 1;
|
curwin->w_cursor.lnum = curwin->w_botline - 1;
|
||||||
if (cap->count1 - 1 >= curwin->w_cursor.lnum) {
|
if (cap->count1 - 1 >= curwin->w_cursor.lnum) {
|
||||||
curwin->w_cursor.lnum = 1;
|
curwin->w_cursor.lnum = 1;
|
||||||
@@ -3645,7 +3645,7 @@ static void nv_scroll(cmdarg_T *cap)
|
|||||||
int used = 0;
|
int used = 0;
|
||||||
// Don't count filler lines above the window.
|
// Don't count filler lines above the window.
|
||||||
used -= win_get_fill(curwin, curwin->w_topline) - curwin->w_topfill;
|
used -= win_get_fill(curwin, curwin->w_topline) - curwin->w_topfill;
|
||||||
validate_botline(curwin); // make sure w_empty_rows is valid
|
validate_botline_win(curwin); // make sure w_empty_rows is valid
|
||||||
int half = (curwin->w_view_height - curwin->w_empty_rows + 1) / 2;
|
int half = (curwin->w_view_height - curwin->w_empty_rows + 1) / 2;
|
||||||
for (n = 0; curwin->w_topline + n < curbuf->b_ml.ml_line_count; n++) {
|
for (n = 0; curwin->w_topline + n < curbuf->b_ml.ml_line_count; n++) {
|
||||||
// Count half the number of filler lines to be "below this
|
// Count half the number of filler lines to be "below this
|
||||||
|
|||||||
@@ -1841,7 +1841,7 @@ void do_put(int regname, yankreg_T *reg, int dir, int count, int flags)
|
|||||||
if (lnum == curwin->w_cursor.lnum) {
|
if (lnum == curwin->w_cursor.lnum) {
|
||||||
// make sure curwin->w_virtcol is updated
|
// make sure curwin->w_virtcol is updated
|
||||||
changed_cline_bef_curs(curwin);
|
changed_cline_bef_curs(curwin);
|
||||||
invalidate_botline(curwin);
|
invalidate_botline_win(curwin);
|
||||||
curwin->w_cursor.col += (colnr_T)(totlen - 1);
|
curwin->w_cursor.col += (colnr_T)(totlen - 1);
|
||||||
}
|
}
|
||||||
changed_bytes(lnum, col);
|
changed_bytes(lnum, col);
|
||||||
|
|||||||
@@ -6576,8 +6576,8 @@ void win_fix_scroll(bool resize)
|
|||||||
wp->w_valid &= ~VALID_CROW;
|
wp->w_valid &= ~VALID_CROW;
|
||||||
}
|
}
|
||||||
|
|
||||||
invalidate_botline(wp);
|
invalidate_botline_win(wp);
|
||||||
validate_botline(wp);
|
validate_botline_win(wp);
|
||||||
}
|
}
|
||||||
wp->w_prev_height = wp->w_height;
|
wp->w_prev_height = wp->w_height;
|
||||||
wp->w_prev_winrow = wp->w_winrow;
|
wp->w_prev_winrow = wp->w_winrow;
|
||||||
@@ -6634,7 +6634,7 @@ static void win_fix_cursor(bool normal)
|
|||||||
} else { // Scroll instead when not in normal mode.
|
} else { // Scroll instead when not in normal mode.
|
||||||
wp->w_fraction = (nlnum == bot) ? FRACTION_MULT : 0;
|
wp->w_fraction = (nlnum == bot) ? FRACTION_MULT : 0;
|
||||||
scroll_to_fraction(wp, wp->w_prev_height);
|
scroll_to_fraction(wp, wp->w_prev_height);
|
||||||
validate_botline(curwin);
|
validate_botline_win(curwin);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -6746,7 +6746,7 @@ void scroll_to_fraction(win_T *wp, int prev_height)
|
|||||||
}
|
}
|
||||||
|
|
||||||
redraw_later(wp, UPD_SOME_VALID);
|
redraw_later(wp, UPD_SOME_VALID);
|
||||||
invalidate_botline(wp);
|
invalidate_botline_win(wp);
|
||||||
}
|
}
|
||||||
|
|
||||||
void win_set_inner_size(win_T *wp, bool valid_cursor)
|
void win_set_inner_size(win_T *wp, bool valid_cursor)
|
||||||
@@ -6793,7 +6793,7 @@ void win_set_inner_size(win_T *wp, bool valid_cursor)
|
|||||||
wp->w_lines_valid = 0;
|
wp->w_lines_valid = 0;
|
||||||
if (valid_cursor) {
|
if (valid_cursor) {
|
||||||
changed_line_abv_curs_win(wp);
|
changed_line_abv_curs_win(wp);
|
||||||
invalidate_botline(wp);
|
invalidate_botline_win(wp);
|
||||||
if (wp == curwin && (*p_spk == 'c' || wp->w_floating)) {
|
if (wp == curwin && (*p_spk == 'c' || wp->w_floating)) {
|
||||||
curs_columns(wp, true); // validate w_wrow
|
curs_columns(wp, true); // validate w_wrow
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user