0
0
mirror of https://github.com/vim/vim.git synced 2025-09-23 03:43:49 -04:00

patch 8.2.3410: crash with linebreak, listchars and large tabstop

Problem:    Crash with linebreak, listchars and large tabstop.
Solution:   Account for different size listchars for a tab. (closes #8841)
This commit is contained in:
Bram Moolenaar
2021-09-07 20:45:31 +02:00
parent 65b6056659
commit 89a54b413a
3 changed files with 47 additions and 30 deletions

View File

@@ -2109,25 +2109,31 @@ win_line(
int i; int i;
int saved_nextra = n_extra; int saved_nextra = n_extra;
#ifdef FEAT_CONCEAL # ifdef FEAT_CONCEAL
if (vcol_off > 0) if (vcol_off > 0)
// there are characters to conceal // there are characters to conceal
tab_len += vcol_off; tab_len += vcol_off;
// boguscols before FIX_FOR_BOGUSCOLS macro from above // boguscols before FIX_FOR_BOGUSCOLS macro from above
if (wp->w_p_list && wp->w_lcs_chars.tab1 if (wp->w_p_list && wp->w_lcs_chars.tab1
&& old_boguscols > 0 && old_boguscols > 0
&& n_extra > tab_len) && n_extra > tab_len)
tab_len += n_extra - tab_len; tab_len += n_extra - tab_len;
#endif # endif
// If n_extra > 0, it gives the number of chars, to
// if n_extra > 0, it gives the number of chars, to
// use for a tab, else we need to calculate the width // use for a tab, else we need to calculate the width
// for a tab // for a tab.
len = (tab_len * mb_char2len(wp->w_lcs_chars.tab2)); len = (tab_len * mb_char2len(wp->w_lcs_chars.tab2));
if (wp->w_lcs_chars.tab3)
len += mb_char2len(wp->w_lcs_chars.tab3);
if (n_extra > 0) if (n_extra > 0)
len += n_extra - tab_len; len += n_extra - tab_len;
c = wp->w_lcs_chars.tab1; c = wp->w_lcs_chars.tab1;
p = alloc(len + 1); p = alloc(len + 1);
if (p == NULL)
n_extra = 0;
else
{
vim_memset(p, ' ', len); vim_memset(p, ' ', len);
p[len] = NUL; p[len] = NUL;
vim_free(p_extra_free); vim_free(p_extra_free);
@@ -2142,22 +2148,21 @@ win_line(
break; break;
} }
// if tab3 is given, need to change the char // if tab3 is given, use it for the last char
// for tab
if (wp->w_lcs_chars.tab3 && i == tab_len - 1) if (wp->w_lcs_chars.tab3 && i == tab_len - 1)
lcs = wp->w_lcs_chars.tab3; lcs = wp->w_lcs_chars.tab3;
mb_char2bytes(lcs, p); p += mb_char2bytes(lcs, p);
p += mb_char2len(lcs);
n_extra += mb_char2len(lcs) n_extra += mb_char2len(lcs)
- (saved_nextra > 0 ? 1 : 0); - (saved_nextra > 0 ? 1 : 0);
} }
p_extra = p_extra_free; p_extra = p_extra_free;
#ifdef FEAT_CONCEAL # ifdef FEAT_CONCEAL
// n_extra will be increased by FIX_FOX_BOGUSCOLS // n_extra will be increased by FIX_FOX_BOGUSCOLS
// macro below, so need to adjust for that here // macro below, so need to adjust for that here
if (vcol_off > 0) if (vcol_off > 0)
n_extra -= vcol_off; n_extra -= vcol_off;
#endif # endif
}
} }
#endif #endif
#ifdef FEAT_CONCEAL #ifdef FEAT_CONCEAL

View File

@@ -70,6 +70,16 @@ func Test_nolinebreak_with_list()
call s:close_windows() call s:close_windows()
endfunc endfunc
" this was causing a crash
func Test_linebreak_with_list_and_tabs()
set linebreak list listchars=tab:⇤\ ⇥ tabstop=100
new
call setline(1, "\t\t\ttext")
redraw
bwipe!
set nolinebreak nolist listchars&vim tabstop=8
endfunc
func Test_linebreak_with_nolist() func Test_linebreak_with_nolist()
call s:test_windows('setl nolist') call s:test_windows('setl nolist')
call setline(1, "\t*mask = nil;") call setline(1, "\t*mask = nil;")

View File

@@ -755,6 +755,8 @@ static char *(features[]) =
static int included_patches[] = static int included_patches[] =
{ /* Add new patch number below this line */ { /* Add new patch number below this line */
/**/
3410,
/**/ /**/
3409, 3409,
/**/ /**/