Hi, Valgrind memory checker finds the following bug in
Vim-7.2.b.4 BETA. It's not a new issue, since it
also happens at least in Vim-7.1.214 for example:
==17908== Conditional jump or move depends on uninitialised value(s)
==17908== at 0x578E51: get_tags (tag.c:3823)
==17908== by 0x4467DB: f_taglist (eval.c:16953)
==17908== by 0x43A0C7: call_func (eval.c:8023)
==17908== by 0x439BE8: get_func_tv (eval.c:7841)
==17908== by 0x435C81: eval7 (eval.c:4979)
==17908== by 0x43555D: eval6 (eval.c:4646)
==17908== by 0x435153: eval5 (eval.c:4462)
==17908== by 0x4346D7: eval4 (eval.c:4157)
==17908== by 0x43453C: eval3 (eval.c:4069)
==17908== by 0x4343C4: eval2 (eval.c:3998)
==17908== by 0x434205: eval1 (eval.c:3923)
==17908== by 0x434172: eval0 (eval.c:3880)
==17908== by 0x43049E: ex_let (eval.c:1794)
==17908== by 0x46525D: do_one_cmd (ex_docmd.c:2621)
==17908== by 0x462A3D: do_cmdline (ex_docmd.c:1095)
I observe the bug when typing 'this->' with C++ code
with the "omnicppcomplete.txt" plugin (which triggers
tag search and displays the pum). I does not happen
with all C++ source codes, and I don't know what
triggers it yet, but I have a 100% reproducible case.
Looking at the code, the bug is quite clear:
tag.c:
3822 for (p = tp.command_end + 3;
! 3823 *p != NUL && *p != '\n' && *p != '\r'; ++p)
3824 {
3825 if (...)
....
.... snip
....
3832 else if (!vim_iswhite(*p))
3833 {
3834 char_u *s, *n;
3835 int len;
3836
3837 /* Add extra field as a dict entry. Fields are
3838 * separated by Tabs. */
3839 n = p;
! 3840 while (*p != NUL && *p >= ' ' && *p < 127 && *p != ':')
3841 ++p;
3842 len = (int)(p - n);
3843 if (*p == ':' && len > 0)
3844 {
3845 s = ++p;
! 3846 while (*p != NUL && *p >= ' ')
3847 ++p;
3848 n[len] = NUL;
3849 if (add_tag_field(dict, (char *)n, s, p) == FAIL)
3850 ret = FAIL;
3851 n[len] = ':';
3852 }
3853 else
3854 /* Skip field without colon. */
! 3855 while (*p != NUL && *p >= ' ')
3856 ++p;
3857 }
3858 }
The bug happens if 'while' loop at lines 3840 (or at line 3846 or
line 3855) ends when reaching end of string (*p == NUL). In that case,
'for' loop at line 3823 will:
- first do '++p' which will go one character beyond end of string, since
p was already at end of string)
- and then it will check condition '*p != NUL', hence accessing beyond
end of string, where memory not initialized.
After that, loop may continue to access several other characters
beyond end of string (depending on bytes values beyond EOS).
The attach patch fixes it.
-- Dominique
--~--~---------~--~----~------------~-------~--~----~
You received this message from the "vim_dev" maillist.
For more information, visit http://www.vim.org/maillist.php
-~----------~----~----~----~------~----~------~--~---
Index: tag.c
===================================================================
RCS file: /cvsroot/vim/vim7/src/tag.c,v
retrieving revision 1.43
diff -c -r1.43 tag.c
*** tag.c 13 Jul 2008 17:25:59 -0000 1.43
--- tag.c 15 Jul 2008 19:01:06 -0000
***************
*** 3854,3859 ****
--- 3854,3861 ----
/* Skip field without colon. */
while (*p != NUL && *p >= ' ')
++p;
+ if (*p == NUL)
+ break;
}
}
}