summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBram Moolenaar <Bram@vim.org>2017-03-31 22:27:12 +0200
committerBram Moolenaar <Bram@vim.org>2017-03-31 22:27:12 +0200
commit658a3a2caf5852d071b6b1be92d9d6614a6208dc (patch)
treec78aa94abed7966b0b6c69fe2b56d720e6d91666
parent13489b9c41922b9ecb16fa47564ec76641515c08 (diff)
downloadvim-658a3a2caf5852d071b6b1be92d9d6614a6208dc.zip
patch 8.0.0530: buffer overflow when 'columns' is very big
Problem: Buffer overflow when 'columns' is very big. (Nikolai Pavlov) Solution: Correctly compute where to truncate. Fix translation. (closes #1600)
-rw-r--r--src/edit.c34
-rw-r--r--src/testdir/test_edit.vim21
-rw-r--r--src/version.c2
3 files changed, 47 insertions, 10 deletions
diff --git a/src/edit.c b/src/edit.c
index cdde11e40..8aa15af83 100644
--- a/src/edit.c
+++ b/src/edit.c
@@ -4756,7 +4756,6 @@ ins_compl_next(
int in_compl_func) /* called from complete_check() */
{
int num_matches = -1;
- int i;
int todo = count;
compl_T *found_compl = NULL;
int found_end = FALSE;
@@ -4948,15 +4947,30 @@ ins_compl_next(
*/
if (compl_shown_match->cp_fname != NULL)
{
- STRCPY(IObuff, "match in file ");
- i = (vim_strsize(compl_shown_match->cp_fname) + 16) - sc_col;
- if (i <= 0)
- i = 0;
- else
- STRCAT(IObuff, "<");
- STRCAT(IObuff, compl_shown_match->cp_fname + i);
- msg(IObuff);
- redraw_cmdline = FALSE; /* don't overwrite! */
+ char *lead = _("match in file");
+ int space = sc_col - vim_strsize((char_u *)lead) - 2;
+ char_u *s;
+ char_u *e;
+
+ if (space > 0)
+ {
+ /* We need the tail that fits. With double-byte encoding going
+ * back from the end is very slow, thus go from the start and keep
+ * the text that fits in "space" between "s" and "e". */
+ for (s = e = compl_shown_match->cp_fname; *e != NUL; MB_PTR_ADV(e))
+ {
+ space -= ptr2cells(e);
+ while (space < 0)
+ {
+ space += ptr2cells(s);
+ MB_PTR_ADV(s);
+ }
+ }
+ vim_snprintf((char *)IObuff, IOSIZE, "%s %s%s", lead,
+ s > compl_shown_match->cp_fname ? "<" : "", s);
+ msg(IObuff);
+ redraw_cmdline = FALSE; /* don't overwrite! */
+ }
}
return num_matches;
diff --git a/src/testdir/test_edit.vim b/src/testdir/test_edit.vim
index 344c12664..b43f84ba2 100644
--- a/src/testdir/test_edit.vim
+++ b/src/testdir/test_edit.vim
@@ -1322,3 +1322,24 @@ func! Test_edit_rightleft()
set norightleft
bw!
endfunc
+
+func Test_edit_complete_very_long_name()
+ let save_columns = &columns
+ set columns=5000
+ call assert_equal(5000, &columns)
+ set noswapfile
+ let dirname = getcwd() . "/Xdir"
+ let longdirname = dirname . repeat('/' . repeat('d', 255), 4)
+ let longfilename = longdirname . '/' . repeat('a', 255)
+ call mkdir(longdirname, 'p')
+ call writefile(['Totum', 'Table'], longfilename)
+ new
+ exe "next Xfile " . longfilename
+ exe "normal iT\<C-N>"
+
+ bwipe!
+ exe 'bwipe! ' . longfilename
+ call delete(dirname, 'rf')
+ let &columns = save_columns
+ set swapfile&
+endfunc
diff --git a/src/version.c b/src/version.c
index 82510cdfe..16ebc8784 100644
--- a/src/version.c
+++ b/src/version.c
@@ -765,6 +765,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 530,
+/**/
529,
/**/
528,