diff src/terminal.c @ 22226:4ed106deb772 v8.2.1662

patch 8.2.1662: :mksession does not restore shared terminal buffer properly Commit: https://github.com/vim/vim/commit/0e655111e9dbdbdf69fee1b199f2b9c355bf4a10 Author: Bram Moolenaar <Bram@vim.org> Date: Fri Sep 11 20:36:36 2020 +0200 patch 8.2.1662: :mksession does not restore shared terminal buffer properly Problem: :mksession does not restore shared terminal buffer properly. Solution: Keep a hashtab with terminal buffers. (Rob Pilling, closes https://github.com/vim/vim/issues/6930)
author Bram Moolenaar <Bram@vim.org>
date Fri, 11 Sep 2020 20:45:04 +0200
parents de47cb7b41e6
children 0bbc8be90207
line wrap: on
line diff
--- a/src/terminal.c
+++ b/src/terminal.c
@@ -935,9 +935,30 @@ theend:
  * Return FAIL if writing fails.
  */
     int
-term_write_session(FILE *fd, win_T *wp)
-{
-    term_T *term = wp->w_buffer->b_term;
+term_write_session(FILE *fd, win_T *wp, hashtab_T *terminal_bufs)
+{
+    const int	bufnr = wp->w_buffer->b_fnum;
+    term_T	*term = wp->w_buffer->b_term;
+
+    if (wp->w_buffer->b_nwindows > 1)
+    {
+	// There are multiple views into this terminal buffer. We don't want to
+	// create the terminal multiple times. If it's the first time, create,
+	// otherwise link to the first buffer.
+	char	    id_as_str[NUMBUFLEN];
+	hashitem_T  *entry;
+
+	vim_snprintf(id_as_str, sizeof(id_as_str), "%d", bufnr);
+
+	entry = hash_find(terminal_bufs, (char_u *)id_as_str);
+	if (!HASHITEM_EMPTY(entry))
+	{
+	    // we've already opened this terminal buffer
+	    if (fprintf(fd, "execute 'buffer ' . s:term_buf_%d", bufnr) < 0)
+		return FAIL;
+	    return put_eol(fd);
+	}
+    }
 
     // Create the terminal and run the command.  This is not without
     // risk, but let's assume the user only creates a session when this
@@ -951,6 +972,19 @@ term_write_session(FILE *fd, win_T *wp)
 #endif
     if (term->tl_command != NULL && fputs((char *)term->tl_command, fd) < 0)
 	return FAIL;
+    if (put_eol(fd) != OK)
+	return FAIL;
+
+    if (fprintf(fd, "let s:term_buf_%d = bufnr()", bufnr) < 0)
+	return FAIL;
+
+    if (wp->w_buffer->b_nwindows > 1)
+    {
+	char *hash_key = alloc(NUMBUFLEN);
+
+	vim_snprintf(hash_key, NUMBUFLEN, "%d", bufnr);
+	hash_add(terminal_bufs, (char_u *)hash_key);
+    }
 
     return put_eol(fd);
 }