I am using @lifepillar's stylepicker plugin which creates a popup in the buffer. This one is difficult to reproduce; I've managed to do it 3 times today, but the precise steps are difficult to identify. The trigger, however, is pressing 'X' to close the stylepicker popup.
I'm reporting this because I managed to get a core dump with debug symbols. I will continue to try and identify a reproducible list of steps.
Pressing 'X' to close the popup should not cause a segfault.
9.1.1465
NixOS
foot
tmux-256color
[New LWP 89963] [New LWP 89975] [Thread debugging using libthread_db enabled] Using host libthread_db library "/nix/store/cg9s562sa33k78m63njfn1rw47dp9z0i-glibc-2.40-66/lib/libthread_db.so.1". Core was generated by `/nix/store/87ik2hf22cwn2bcjgcfhi7a9284rgf30-vim-acd04b2/bin/vim -N -u /nix/store/4wfrnpf50sg8zhfx4wg7j4vshaw0qysc-vimrc templates/forlorne.colortemplate'. Program terminated with signal SIGSEGV, Segmentation fault. #0 0x00007f48cca586bb in kill () from /nix/store/cg9s562sa33k78m63njfn1rw47dp9z0i-glibc-2.40-66/lib/libc.so.6 [Current thread is 1 (Thread 0x7f48cca16080 (LWP 89963))] #0 0x00007f48cca586bb in kill () from /nix/store/cg9s562sa33k78m63njfn1rw47dp9z0i-glibc-2.40-66/lib/libc.so.6 No symbol table info available. #1 0x000000000040a176 in may_core_dump () at os_unix.c:3718 No locals. #2 0x000000000040a12e in mch_exit (r=1) at os_unix.c:3684 No locals. #3 0x00000000005d8cea in getout (exitval=1) at main.c:1829 No locals. #4 0x00000000003bfc7a in preserve_exit () at misc1.c:2303 buf = 0x1ca56a50 #5 0x00000000004083e6 in deathtrap (sigarg=11) at os_unix.c:1238 entered = 1 i = 7 #6 <signal handler called> No symbol table info available. #7 0x00000000005313f0 in call_callback (callback=0x1e214918, len=-1, rettv=0x7ffd2fc77be0, argcount=2, argvars=0x7ffd2fc77bf0) at userfunc.c:3768 funcexe = {fe_argv_func = 0x7ffd2fc77c00, fe_firstline = 5174227, fe_lastline = 140725405056160, fe_doesrange = 0x0, fe_evaluate = 0, fe_ufunc = 0x100000000, fe_partial = 0x0, fe_selfdict = 0x1, fe_object = 0x1000000001, fe_basetv = 0x10, fe_check_type = 0x9, fe_found_var = 801602512} ret = 0 #8 0x0000000000419da7 in invoke_popup_callback (wp=0x1e214680, result=0x7ffd2fc77c80) at popupwin.c:2403 rettv = {v_type = VAR_UNKNOWN, v_lock = -3 '\375', vval = {v_number = 5196446864987749120, v_float = 2.5085495631117798e+39, v_string = 0x481d7ce449c97b00 <error: Cannot access memory at address 0x481d7ce449c97b00>, v_list = 0x481d7ce449c97b00, v_dict = 0x481d7ce449c97b00, v_partial = 0x481d7ce449c97b00, v_job = 0x481d7ce449c97b00, v_channel = 0x481d7ce449c97b00, v_blob = 0x481d7ce449c97b00, v_instr = 0x481d7ce449c97b00, v_class = 0x481d7ce449c97b00, v_object = 0x481d7ce449c97b00, v_typealias = 0x481d7ce449c97b00, v_tuple = 0x481d7ce449c97b00}} argv = {{v_type = VAR_NUMBER, v_lock = -3 '\375', vval = {v_number = 506239456, v_float = 2.5011552377896131e-315, v_string = 0x1e2c99e0 "\001", v_list = 0x1e2c99e0, v_dict = 0x1e2c99e0, v_partial = 0x1e2c99e0, v_job = 0x1e2c99e0, v_channel = 0x1e2c99e0, v_blob = 0x1e2c99e0, v_instr = 0x1e2c99e0, v_class = 0x1e2c99e0, v_object = 0x1e2c99e0, v_typealias = 0x1e2c99e0, v_tuple = 0x1e2c99e0}}, {v_type = VAR_NUMBER, v_lock = 0 '\000', vval = {v_number = -1, v_float = -nan(0xfffffffffffff), v_string = 0xffffffffffffffff "", v_list = 0xffffffffffffffff, v_dict = 0xffffffffffffffff, v_partial = 0xffffffffffffffff, v_job = 0xffffffffffffffff, v_channel = 0xffffffffffffffff, v_blob = 0xffffffffffffffff, v_instr = 0xffffffffffffffff, v_class = 0xffffffffffffffff, v_object = 0xffffffffffffffff, v_typealias = 0xffffffffffffffff, v_tuple = 0xffffffffffffffff}}, {v_type = VAR_UNKNOWN, v_lock = -1 '\377', vval = {v_number = 505497904, v_float = 2.4974914841115644e-315, v_string = 0x1e214930 "ck/vim/start/vimplugin-vim-prettier,/nix/store/jn6jrxhjhhpb1jnx0k022iqdrp06pp6q-vim-pack-dir/pack/vim/start/vimplugin-vim-haskell-indent,/nix/store/jn6jrxhjhhpb1jnx0k022iqdrp06pp6q-vim-pack-dir/pack/v"..., v_list = 0x1e214930, v_dict = 0x1e214930, v_partial = 0x1e214930, v_job = 0x1e214930, v_channel = 0x1e214930, v_blob = 0x1e214930, v_instr = 0x1e214930, v_class = 0x1e214930, v_object = 0x1e214930, v_typealias = 0x1e214930, v_tuple = 0x1e214930}}} #9 0x0000000000419fce in popup_close_and_callback (wp=0x1e214680, arg=0x7ffd2fc77c80) at popupwin.c:2471 id = 506239456 #10 0x000000000041a028 in popup_close_with_retval (wp=0x1e214680, retval=-1) at popupwin.c:2484 res = {v_type = VAR_NUMBER, v_lock = 0 '\000', vval = {v_number = -1, v_float = -nan(0xfffffffffffff), v_string = 0xffffffffffffffff "", v_list = 0xffffffffffffffff, v_dict = 0xffffffffffffffff, v_partial = 0xffffffffffffffff, v_job = 0xffffffffffffffff, v_channel = 0xffffffffffffffff, v_blob = 0xffffffffffffffff, v_instr = 0xffffffffffffffff, v_class = 0xffffffffffffffff, v_object = 0xffffffffffffffff, v_typealias = 0xffffffffffffffff, v_tuple = 0xffffffffffffffff}} #11 0x000000000041c621 in invoke_popup_filter (wp=0x1e214680, c=88) at popupwin.c:3521 res = 3526158 rettv = {v_type = VAR_NUMBER, v_lock = 0 '\000', vval = {v_number = 0, v_float = 0, v_string = 0x0, v_list = 0x0, v_dict = 0x0, v_partial = 0x0, v_job = 0x0, v_channel = 0x0, v_blob = 0x0, v_instr = 0x0, v_class = 0x0, v_object = 0x0, v_typealias = 0x0, v_tuple = 0x0}} argv = {{v_type = VAR_NUMBER, v_lock = 0 '\000', vval = {v_number = 1024, v_float = 5.0592322134143646e-321, v_string = 0x400 <error: Cannot access memory at address 0x400>, v_list = 0x400, v_dict = 0x400, v_partial = 0x400, v_job = 0x400, v_channel = 0x400, v_blob = 0x400, v_instr = 0x400, v_class = 0x400, v_object = 0x400, v_typealias = 0x400, v_tuple = 0x400}}, {v_type = VAR_STRING, v_lock = -3 '\375', vval = {v_number = 506270784, v_float = 2.5013100186751423e-315, v_string = 0x1e2d1440 "X", v_list = 0x1e2d1440, v_dict = 0x1e2d1440, v_partial = 0x1e2d1440, v_job = 0x1e2d1440, v_channel = 0x1e2d1440, v_blob = 0x1e2d1440, v_instr = 0x1e2d1440, v_class = 0x1e2d1440, v_object = 0x1e2d1440, v_typealias = 0x1e2d1440, v_tuple = 0x1e2d1440}}, {v_type = VAR_UNKNOWN, v_lock = 0 '\000', vval = {v_number = 4301508704, v_float = 2.1252276759335034e-314, v_string = 0x10063d060 <error: Cannot access memory at address 0x10063d060>, v_list = 0x10063d060, v_dict = 0x10063d060, v_partial = 0x10063d060, v_job = 0x10063d060, v_channel = 0x10063d060, v_blob = 0x10063d060, v_instr = 0x10063d060, v_class = 0x10063d060, v_object = 0x10063d060, v_typealias = 0x10063d060, v_tuple = 0x10063d060}}} buf = "X", '\000' <repeats 15 times>, "X\000\000\000\000\000\000\000\032\000\000\000\033\000\000\000\001\000\000\000\000\000\000\000\002\000\000\000\000\000\000\000\001\000\000\000\375\177\000\000t\262,\0002\000\000\000" old_lnum = 1 prev_did_emsg = 0 #12 0x000000000041c8a7 in popup_do_filter (c=88) at popupwin.c:3594 recursive = 1 res = 0 wp = 0x1e214680 save_KeyTyped = 1 state = 4097 was_must_redraw = 0 #13 0x000000000035e418 in vgetc () at getchar.c:2171 c = 88 c2 = 0 n = 1 buf = "\001\000\000\000\000\000\000\000K\234\374\034\001\000\000\000\001\000\000\000\000" i = 0 #14 0x000000000035e767 in safe_vgetc () at getchar.c:2277 c = 0 #15 0x00000000003d430a in normal_cmd (oap=0x7ffd2fc77f30, toplevel=1) at normal.c:764 ca = {oap = 0x7ffd2fc77f30, prechar = 0, cmdchar = 0, nchar = 0, ncharC1 = 0, ncharC2 = 0, extra_char = 0, opcount = 0, count0 = 0, count1 = 0, arg = 0, retval = 0, searchbuf = 0x0} c = 0 ctrl_w = 0 old_col = 52 need_flushbuf = 0 old_pos = {lnum = 140725405056672, col = 480602704, coladd = 0} mapped_len = 0 old_mapped_len = 0 idx = 3980045 set_prevcount = 0 save_did_cursorhold = 0 prev_finish_op = 0 #16 0x00000000005d88e1 in main_loop (cmdwin=0, noexmode=0) at main.c:1610 oa = {op_type = 0, regname = 0, motion_type = 0, motion_force = 0, use_reg_one = 0, inclusive = 1, end_adjusted = 0, start = {lnum = 34, col = 32, coladd = 0}, end = {lnum = 34, col = 33, coladd = 0}, cursor_start = {lnum = 0, col = 0, coladd = 0}, line_count = 1, empty = 0, is_VIsual = 0, block_mode = 0, start_vcol = 0, end_vcol = 0, prev_opcount = 0, prev_count0 = 0, excl_tr_ws = 0} prev_oap = 0x0 previous_got_int = 0 conceal_old_cursor_line = 30 conceal_new_cursor_line = 210 conceal_update_lines = 0 #17 0x00000000005d7b51 in vim_main2 () at main.c:948 No locals. #18 0x00000000005d7244 in main (argc=5, argv=0x7ffd2fc78158) at main.c:446 i = 5
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
I figured it out: it's very specific and relates to @lifepillar's plugins for building colorschemes.
You'll see:
Error detected while processing function <SNR>38_UI.HandleEvent[17]..<SNR>38_Cancel:
line 4:
E185: Cannot find color scheme 'my-colorscheme'
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
cannot seem to reproduce
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
I can reproduce it. It crashes inside invoke_popup_callback(). It seems a bug involving :colorscheme and popups and, perhaps, autocommands.I will try to reduce it to a minimal example that does not depend on any plugin.
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
I can reproduce it using this bug-colorscheme.vim script:
vim9script def Filter(winid: number, keyCode: string): bool popup_close(winid) colorscheme idontexist return true enddef def Popup(): number return popup_create('', { border: [2, 2, 2, 2], close: 'button', filter: Filter, }) enddef nnoremap <buffer> gs <scriptcmd>Popup()<cr>
Steps to reproduce:
vim --clean bug-colorscheme.vim.gs, then another key to close the popup. Every time the popup is closed, E185 is raised: dismiss the error message by pressing Enter. You should get a segfault after a few tries. This looks like memory corruption, so it may take crash at once or take a while before crashing.It seems that the issue is triggered by :colorscheme used with a non-existing color scheme (which is a regression in my plugin, but that's irrelevant here).
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
Hm, ASAN reports this as a use after free:
=================================================================
==51240==ERROR: AddressSanitizer: heap-use-after-free on address 0x52500115f900 at pc 0x55b31a5b0b3d bp 0x7ffcae9d93e0 sp 0x7ffcae9d93d8
READ of size 4 at 0x52500115f900 thread T0
#0 0x55b31a5b0b3c in popup_close_and_callback /home/chrisbra/code/vim-upstream/src/popupwin.c:2428
#1 0x55b31a5b1301 in popup_close_with_retval /home/chrisbra/code/vim-upstream/src/popupwin.c:2484
#2 0x55b31a5bbb87 in invoke_popup_filter /home/chrisbra/code/vim-upstream/src/popupwin.c:3521
#3 0x55b31a5bc681 in popup_do_filter /home/chrisbra/code/vim-upstream/src/popupwin.c:3594
#4 0x55b31a23e80c in vgetc /home/chrisbra/code/vim-upstream/src/getchar.c:2171
#5 0x55b31a23f44a in safe_vgetc /home/chrisbra/code/vim-upstream/src/getchar.c:2277
#6 0x55b31a4592a0 in normal_cmd /home/chrisbra/code/vim-upstream/src/normal.c:764
#7 0x55b31ad48538 in main_loop /home/chrisbra/code/vim-upstream/src/main.c:1610
#8 0x55b31ad467f3 in vim_main2 /home/chrisbra/code/vim-upstream/src/main.c:948
#9 0x55b31ad456bf in main /home/chrisbra/code/vim-upstream/src/main.c:446
#10 0x7fdacf833ca7 in __libc_start_call_main ../sysdeps/nptl/libc_start_call_main.h:58
#11 0x7fdacf833d64 in __libc_start_main_impl ../csu/libc-start.c:360
#12 0x55b319e021b0 in _start (/home/chrisbra/code/vim-upstream/src/vim+0x144d1b0) (BuildId: 51950f44d200ef2f8f3397e0943e57f1e2b4eb1b)
0x52500115f900 is located 0 bytes inside of 9560-byte region [0x52500115f900,0x525001161e58)
freed by thread T0 here:
#0 0x7fdad12f38f8 in free ../../../../src/libsanitizer/asan/asan_malloc_linux.cpp:52
#1 0x55b319e02981 in vim_free /home/chrisbra/code/vim-upstream/src/alloc.c:616
#2 0x55b31ac05d9d in win_free /home/chrisbra/code/vim-upstream/src/window.c:6005
#3 0x55b31ac061c4 in win_free_popup /home/chrisbra/code/vim-upstream/src/window.c:6041
#4 0x55b31a5b4a2d in popup_free /home/chrisbra/code/vim-upstream/src/popupwin.c:2909
#5 0x55b31a5b53cc in popup_close_tabpage /home/chrisbra/code/vim-upstream/src/popupwin.c:3010
#6 0x55b31a5b4fff in popup_close /home/chrisbra/code/vim-upstream/src/popupwin.c:2979
#7 0x55b31a5b1202 in popup_close_and_callback /home/chrisbra/code/vim-upstream/src/popupwin.c:2473
#8 0x55b31a5b3773 in f_popup_close /home/chrisbra/code/vim-upstream/src/popupwin.c:2749
#9 0x55b31a05c8cf in call_internal_func_by_idx /home/chrisbra/code/vim-upstream/src/evalfunc.c:3470
#10 0x55b31aae030a in call_bfunc /home/chrisbra/code/vim-upstream/src/vim9execute.c:1380
#11 0x55b31ab10bdd in exec_instructions /home/chrisbra/code/vim-upstream/src/vim9execute.c:4834
#12 0x55b31ab32c65 in call_def_function /home/chrisbra/code/vim-upstream/src/vim9execute.c:6836
#13 0x55b31aa2643c in call_user_func /home/chrisbra/code/vim-upstream/src/userfunc.c:3033
#14 0x55b31aa2c55f in call_user_func_check /home/chrisbra/code/vim-upstream/src/userfunc.c:3468
#15 0x55b31aa31292 in call_func /home/chrisbra/code/vim-upstream/src/userfunc.c:4091
#16 0x55b31aa2e794 in call_callback /home/chrisbra/code/vim-upstream/src/userfunc.c:3787
#17 0x55b31a5bbb6f in invoke_popup_filter /home/chrisbra/code/vim-upstream/src/popupwin.c:3517
#18 0x55b31a5bc681 in popup_do_filter /home/chrisbra/code/vim-upstream/src/popupwin.c:3594
#19 0x55b31a23e80c in vgetc /home/chrisbra/code/vim-upstream/src/getchar.c:2171
#20 0x55b31a23f44a in safe_vgetc /home/chrisbra/code/vim-upstream/src/getchar.c:2277
#21 0x55b31a4592a0 in normal_cmd /home/chrisbra/code/vim-upstream/src/normal.c:764
#22 0x55b31ad48538 in main_loop /home/chrisbra/code/vim-upstream/src/main.c:1610
#23 0x55b31ad467f3 in vim_main2 /home/chrisbra/code/vim-upstream/src/main.c:948
#24 0x55b31ad456bf in main /home/chrisbra/code/vim-upstream/src/main.c:446
previously allocated by thread T0 here:
#0 0x7fdad12f4c57 in malloc ../../../../src/libsanitizer/asan/asan_malloc_linux.cpp:69
#1 0x55b319e02650 in lalloc /home/chrisbra/code/vim-upstream/src/alloc.c:246
#2 0x55b319e024c3 in alloc_clear /home/chrisbra/code/vim-upstream/src/alloc.c:177
#3 0x55b31ac036ed in win_alloc /home/chrisbra/code/vim-upstream/src/window.c:5781
#4 0x55b31abfa26a in win_alloc_popup_win /home/chrisbra/code/vim-upstream/src/window.c:4500
#5 0x55b31a5ac9bf in popup_create /home/chrisbra/code/vim-upstream/src/popupwin.c:2096
#6 0x55b31a5b05bc in f_popup_create /home/chrisbra/code/vim-upstream/src/popupwin.c:2357
#7 0x55b31a05c8cf in call_internal_func_by_idx /home/chrisbra/code/vim-upstream/src/evalfunc.c:3470
#8 0x55b31aae030a in call_bfunc /home/chrisbra/code/vim-upstream/src/vim9execute.c:1380
#9 0x55b31ab10bdd in exec_instructions /home/chrisbra/code/vim-upstream/src/vim9execute.c:4834
#10 0x55b31ab32c65 in call_def_function /home/chrisbra/code/vim-upstream/src/vim9execute.c:6836
#11 0x55b31aa2643c in call_user_func /home/chrisbra/code/vim-upstream/src/userfunc.c:3033
#12 0x55b31aa2c55f in call_user_func_check /home/chrisbra/code/vim-upstream/src/userfunc.c:3468
#13 0x55b31aa31292 in call_func /home/chrisbra/code/vim-upstream/src/userfunc.c:4091
#14 0x55b31aa1e312 in get_func_tv /home/chrisbra/code/vim-upstream/src/userfunc.c:2177
#15 0x55b31a01ec56 in eval_func /home/chrisbra/code/vim-upstream/src/eval.c:3182
#16 0x55b31a02ea81 in eval9_var_func_name /home/chrisbra/code/vim-upstream/src/eval.c:5069
#17 0x55b31a02f93a in eval9 /home/chrisbra/code/vim-upstream/src/eval.c:5278 #18 0x55b31a02bd17 in eval8 /home/chrisbra/code/vim-upstream/src/eval.c:4748
#19 0x55b31a02a9f2 in eval7 /home/chrisbra/code/vim-upstream/src/eval.c:4646
#20 0x55b31a028a46 in eval6 /home/chrisbra/code/vim-upstream/src/eval.c:4396
#21 0x55b31a02705f in eval5 /home/chrisbra/code/vim-upstream/src/eval.c:4190
#22 0x55b31a024d2c in eval4 /home/chrisbra/code/vim-upstream/src/eval.c:3977
#23 0x55b31a023bb9 in eval3 /home/chrisbra/code/vim-upstream/src/eval.c:3838
#24 0x55b31a022ab0 in eval2 /home/chrisbra/code/vim-upstream/src/eval.c:3712
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
ah, I see what is happening:
We are calling invoke_popup_filter(), which calls call_callback(), which then eventually already closes the popup window and frees the window pointer.
However after call_callback() returns FAIL, wp is now essentially pointing to freed memory and the popup_close_with_retval() accesses this window pointer causing a use-after-free.
I think the following patch fixes it:
diff --git a/src/popupwin.c b/src/popupwin.c index 199ffaf8d..6f82dae5a 100644 --- a/src/popupwin.c +++ b/src/popupwin.c @@ -2421,11 +2421,17 @@ back_to_prevwin(win_T *wp) /* * Close popup "wp" and invoke any close callback for it. + * Careful: callback function might have freed the popup window already */ static void popup_close_and_callback(win_T *wp, typval_T *arg) { - int id = wp->w_id; + int id; + + if (!win_valid(wp)) + return; + + id = wp->w_id; #ifdef FEAT_TERMINAL if (wp == curwin && curbuf->b_term != NULL)
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()
With that patch, I am not able to crash Vim any longer.
—
Reply to this email directly, view it on GitHub.
You are receiving this because you are subscribed to this thread.![]()