Bram Moolenaar wrote: > Dominique Pelle wrote: > >> 3 remarks about vim/src/undo.c (at changeset: 271a5907f944): >> >> (1) Using persistent-undo, I notice once in a while the following memory >> leak, but I have not found the way to reproduce it all the time: >> >> ==3371== 10 bytes in 2 blocks are definitely lost in loss record 23 of 116 >> ==3371== at 0x4024F70: malloc (vg_replace_malloc.c:236) >> ==3371== by 0x8114F98: lalloc (misc2.c:919) >> ==3371== by 0x81BCC06: u_read_undo (undo.c:983) >> ==3371== by 0x80C5359: readfile (fileio.c:2591) >> ==3371== by 0x8053976: open_buffer (buffer.c:132) >> ==3371== by 0x8098ABE: do_ecmd (ex_cmds.c:3658) >> ==3371== by 0x80AEF7B: do_exedit (ex_docmd.c:7620) >> ==3371== by 0x80AEC38: ex_edit (ex_docmd.c:7516) >> ==3371== by 0x80A782C: do_one_cmd (ex_docmd.c:2639) >> ==3371== by 0x80A5105: do_cmdline (ex_docmd.c:1108) >> ==3371== by 0x812AD39: nv_colon (normal.c:5226) >> ==3371== by 0x81245C3: normal_cmd (normal.c:1188) >> ==3371== by 0x80E7938: main_loop (main.c:1216) >> ==3371== by 0x80E742F: main (main.c:960) >> >> It's this alloc in undo.c: >> >> 983 array = (char_u **)U_ALLOC_LINE( >> 984 (unsigned)(sizeof(char_u *) * >> uep->ue_size)); >> >> Looking at the undo.c code, memory seems to be properly freed >> but I might be missing something since Valgrind does not generally >> give spurious leak messages. > > The logic is not easy to follow. Also, there are hardly any checks for > the undo file to contain invalid information. I think it's good to > assume that every value read from the file might be wrong. > > I think we need to add more checks that what is read back from the undo > file is correct. E.g., when "num_head" is too small the code would > gladly store pointers beyond the end of uhp_table[].
Regarding the leak in undo.c, I found a way to reproduce
it all the times with Vim-7.3a (2216:dd5c1983e355).
It also give an error E438 (which is an internal error):
Using attached file leak.vim, run:
$ rm -f foo* ; valgrind --leak-check=yes 2> vg.log \
vim -u NONE --noplugin -c 'set undofile' \
-c 'so! leak.vim' \
-c 'so! leak.vim' foo
Then quit with :q!
Log file vg.log shows 2 leaks both in u_read_undo():
==2962== 2 bytes in 2 blocks are definitely lost in loss record 2 of 106
==2962== at 0x4024F70: malloc (vg_replace_malloc.c:236)
==2962== by 0x81144F6: lalloc (misc2.c:919)
==2962== by 0x81BC14C: u_read_undo (undo.c:1001)
==2962== by 0x80C4C09: readfile (fileio.c:2591)
==2962== by 0x8053226: open_buffer (buffer.c:132)
==2962== by 0x809836E: do_ecmd (ex_cmds.c:3658)
==2962== by 0x80AE82B: do_exedit (ex_docmd.c:7620)
==2962== by 0x80AE4E8: ex_edit (ex_docmd.c:7516)
==2962== by 0x80A70DC: do_one_cmd (ex_docmd.c:2639)
==2962== by 0x80A49B5: do_cmdline (ex_docmd.c:1108)
==2962== by 0x812A22D: nv_colon (normal.c:5226)
==2962== by 0x8123AB7: normal_cmd (normal.c:1188)
==2962== 1,705 (802 direct, 903 indirect) bytes in 2 blocks are
definitely lost in loss record 101 of 106
==2962== at 0x4024F70: malloc (vg_replace_malloc.c:236)
==2962== by 0x81144F6: lalloc (misc2.c:919)
==2962== by 0x81BBE9E: u_read_undo (undo.c:938)
==2962== by 0x80C4C09: readfile (fileio.c:2591)
==2962== by 0x8053226: open_buffer (buffer.c:132)
==2962== by 0x809836E: do_ecmd (ex_cmds.c:3658)
==2962== by 0x80AE82B: do_exedit (ex_docmd.c:7620)
==2962== by 0x80AE4E8: ex_edit (ex_docmd.c:7516)
==2962== by 0x80A70DC: do_one_cmd (ex_docmd.c:2639)
==2962== by 0x80A49B5: do_cmdline (ex_docmd.c:1108)
==2962== by 0x812A22D: nv_colon (normal.c:5226)
==2962== by 0x8123AB7: normal_cmd (normal.c:1188)
undo.c:
938 uhp = (u_header_T *)U_ALLOC_LINE((unsigned)sizeof(u_header_T));
...
1001 array = (char_u **)U_ALLOC_LINE(
1002 (unsigned)(sizeof(char_u *) *
uep->ue_size));
If you source 'so! leak.vim' n times (n == 2 in my example)
then 2*n blocks blocks are leaked.
Now if you add -N as follows, you also get error
"E438: u_undo: line numbers wrong" (which is an
internal error:
$ rm -f foo* ; valgrind --leak-check=yes 2> vg.log \
vim -N -u NONE --noplugin -c 'set undofile' \
-c 'so! leak.vim' \
-c 'so! leak.vim' foo
The patch I sent earlier (which avoids wasting 1 byte
in some alloc) actually fixes one of the leaks but not both.
E438 happens with or without patch.
I have not found how to fix this yet. Any idea?
-- Dominique
--
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php
leak.vim
Description: Binary data
