Patch 8.2.3640
Problem: Freeze when calling term_wait() in a close callback.
Solution: Set a "closing" flag to tell term_wait() to return. (closes #9152)
Files: src/channel.c, src/terminal.c, src/proto/terminal.pro,
src/testdir/test_terminal.vim
*** ../vim-8.2.3639/src/channel.c 2021-09-08 13:57:38.233188064 +0100
--- src/channel.c 2021-11-21 14:33:20.956234348 +0000
***************
*** 3156,3161 ****
--- 3156,3165 ----
{
ch_part_T part;
+ #ifdef FEAT_TERMINAL
+ // let the terminal know it is closing to avoid getting stuck
+ term_channel_closing(channel);
+ #endif
// Invoke callbacks and flush buffers before the close callback.
if (channel->ch_close_cb.cb_name != NULL)
ch_log(channel,
*** ../vim-8.2.3639/src/terminal.c 2021-11-20 13:45:37.810729599 +0000
--- src/terminal.c 2021-11-21 14:48:21.217602864 +0000
***************
*** 99,104 ****
--- 99,105 ----
int tl_vterm_size_changed;
int tl_normal_mode; // TRUE: Terminal-Normal mode
+ int tl_channel_closing;
int tl_channel_closed;
int tl_channel_recently_closed; // still need to handle
tl_finish
***************
*** 3459,3464 ****
--- 3460,3479 ----
#endif
/*
+ * Called when a channel is going to be closed, before invoking the close
+ * callback.
+ */
+ void
+ term_channel_closing(channel_T *ch)
+ {
+ term_T *term;
+
+ for (term = first_term; term != NULL; term = term->tl_next)
+ if (term->tl_job == ch->ch_job && !term->tl_channel_closed)
+ term->tl_channel_closing = TRUE;
+ }
+
+ /*
* Called when a channel has been closed.
* If this was a channel for a terminal window then finish it up.
*/
***************
*** 6438,6443 ****
--- 6453,6461 ----
// If the terminal is closed when the channel is closed the
// buffer disappears.
break;
+ if (buf->b_term == NULL || buf->b_term->tl_channel_closing)
+ // came here from a close callback, only wait one time
+ break;
}
term_flush_messages();
*** ../vim-8.2.3639/src/proto/terminal.pro 2021-11-20 13:45:37.806729612
+0000
--- src/proto/terminal.pro 2021-11-21 14:38:42.599163461 +0000
***************
*** 20,25 ****
--- 20,26 ----
void term_win_entered(void);
int terminal_loop(int blocking);
int may_close_term_popup(void);
+ void term_channel_closing(channel_T *ch);
void term_channel_closed(channel_T *ch);
void term_check_channel_closed_recently(void);
int term_do_update_window(win_T *wp);
*** ../vim-8.2.3639/src/testdir/test_terminal.vim 2021-11-19
17:01:05.559037762 +0000
--- src/testdir/test_terminal.vim 2021-11-21 14:47:06.217790097 +0000
***************
*** 2058,2062 ****
--- 2058,2079 ----
bwipe!
endfunc
+ func Close_cb(ch, ctx)
+ call term_wait(a:ctx.bufnr)
+ let g:close_done = 'done'
+ endfunc
+
+ func Test_term_wait_in_close_cb()
+ let g:close_done = ''
+ let ctx = {}
+ let ctx.bufnr = term_start('echo "HELLO WORLD"',
+ \ {'close_cb': {ch -> Close_cb(ch, ctx)}})
+
+ call WaitForAssert({-> assert_equal("done", g:close_done)})
+
+ unlet g:close_done
+ bwipe!
+ endfunc
+
" vim: shiftwidth=2 sts=2 expandtab
*** ../vim-8.2.3639/src/version.c 2021-11-21 12:27:09.954898888 +0000
--- src/version.c 2021-11-21 14:34:29.819985168 +0000
***************
*** 759,760 ****
--- 759,762 ----
{ /* Add new patch number below this line */
+ /**/
+ 3640,
/**/
--
I wonder, do vegetarians eat fruit bats?
/// Bram Moolenaar -- [email protected] -- http://www.Moolenaar.net \\\
/// \\\
\\\ sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ ///
\\\ help me help AIDS victims -- http://ICCF-Holland.org ///
--
--
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
---
You received this message because you are subscribed to the Google Groups
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/vim_dev/20211121145153.293971C3DC0%40moolenaar.net.