summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBram Moolenaar <Bram@vim.org>2020-10-25 17:55:09 +0100
committerBram Moolenaar <Bram@vim.org>2020-10-25 17:55:09 +0100
commit4882d983397057ea91c584c5a54aaccf15016d18 (patch)
treeb793825c5fdfb96bb9ad2a1bae573026e0998e26
parent89b693e5627715cde080c3580c7b641c9bf0c06a (diff)
downloadvim-git-4882d983397057ea91c584c5a54aaccf15016d18.tar.gz
patch 8.2.1905: the wininfo list may contain stale entriesv8.2.1905
Problem: The wininfo list may contain stale entries. Solution: When closing a window remove any other entry where the window pointer is NULL.
-rw-r--r--src/buffer.c25
-rw-r--r--src/proto/buffer.pro1
-rw-r--r--src/version.c2
-rw-r--r--src/window.c19
4 files changed, 39 insertions, 8 deletions
diff --git a/src/buffer.c b/src/buffer.c
index 318ce7f98..5a5eb9f41 100644
--- a/src/buffer.c
+++ b/src/buffer.c
@@ -1006,6 +1006,22 @@ free_buffer_stuff(
}
/*
+ * Free one wininfo_T.
+ */
+ void
+free_wininfo(wininfo_T *wip)
+{
+ if (wip->wi_optset)
+ {
+ clear_winopt(&wip->wi_opt);
+#ifdef FEAT_FOLDING
+ deleteFoldRecurse(&wip->wi_folds);
+#endif
+ }
+ vim_free(wip);
+}
+
+/*
* Free the b_wininfo list for buffer "buf".
*/
static void
@@ -1017,14 +1033,7 @@ clear_wininfo(buf_T *buf)
{
wip = buf->b_wininfo;
buf->b_wininfo = wip->wi_next;
- if (wip->wi_optset)
- {
- clear_winopt(&wip->wi_opt);
-#ifdef FEAT_FOLDING
- deleteFoldRecurse(&wip->wi_folds);
-#endif
- }
- vim_free(wip);
+ free_wininfo(wip);
}
}
diff --git a/src/proto/buffer.pro b/src/proto/buffer.pro
index 3a6329936..4d890ce45 100644
--- a/src/proto/buffer.pro
+++ b/src/proto/buffer.pro
@@ -8,6 +8,7 @@ int buf_valid(buf_T *buf);
void close_buffer(win_T *win, buf_T *buf, int action, int abort_if_last, int ignore_abort);
void buf_clear_file(buf_T *buf);
void buf_freeall(buf_T *buf, int flags);
+void free_wininfo(wininfo_T *wip);
void goto_buffer(exarg_T *eap, int start, int dir, int count);
void handle_swap_exists(bufref_T *old_curbuf);
char *do_bufdel(int command, char_u *arg, int addr_count, int start_bnr, int end_bnr, int forceit);
diff --git a/src/version.c b/src/version.c
index 2d3606023..1cde8c724 100644
--- a/src/version.c
+++ b/src/version.c
@@ -751,6 +751,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 1905,
+/**/
1904,
/**/
1903,
diff --git a/src/window.c b/src/window.c
index 243bd3299..9dbfae210 100644
--- a/src/window.c
+++ b/src/window.c
@@ -5015,7 +5015,26 @@ win_free(
FOR_ALL_BUFFERS(buf)
FOR_ALL_BUF_WININFO(buf, wip)
if (wip->wi_win == wp)
+ {
+ wininfo_T *wip2;
+
+ // If there already is an entry with "wi_win" set to NULL it
+ // must be removed, it would never be used.
+ for (wip2 = buf->b_wininfo; wip2 != NULL; wip2 = wip2->wi_next)
+ if (wip2->wi_win == NULL)
+ {
+ if (wip2->wi_next != NULL)
+ wip2->wi_next->wi_prev = wip2->wi_prev;
+ if (wip2->wi_prev == NULL)
+ buf->b_wininfo = wip2->wi_next;
+ else
+ wip2->wi_prev->wi_next = wip2->wi_next;
+ free_wininfo(wip2);
+ break;
+ }
+
wip->wi_win = NULL;
+ }
#ifdef FEAT_SEARCH_EXTRA
clear_matches(wp);