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.

Raspunde prin e-mail lui