]> granicus.if.org Git - vim/commitdiff
patch 8.0.1402: crash with nasty autocommand v8.0.1402
authorBram Moolenaar <Bram@vim.org>
Mon, 18 Dec 2017 11:37:55 +0000 (12:37 +0100)
committerBram Moolenaar <Bram@vim.org>
Mon, 18 Dec 2017 11:37:55 +0000 (12:37 +0100)
Problem:    Crash with nasty autocommand. (gy741, Dominique Pelle)
Solution:   Check that the new current buffer isn't wiped out. (closes #2447)

src/buffer.c
src/testdir/test_autocmd.vim
src/version.c

index ed5773e882d3e28d93fc26b4b0a1aab3874c1ae6..eeba5301255c449dfb1b69279895382f973ae0b9 100644 (file)
@@ -1665,7 +1665,8 @@ set_curbuf(buf_T *buf, int action)
 #ifdef FEAT_SYN_HL
     long       old_tw = curbuf->b_p_tw;
 #endif
-    bufref_T   bufref;
+    bufref_T   newbufref;
+    bufref_T   prevbufref;
 
     setpcmark();
     if (!cmdmod.keepalt)
@@ -1675,18 +1676,22 @@ set_curbuf(buf_T *buf, int action)
     /* Don't restart Select mode after switching to another buffer. */
     VIsual_reselect = FALSE;
 
-    /* close_windows() or apply_autocmds() may change curbuf */
+    /* close_windows() or apply_autocmds() may change curbuf and wipe out "buf"
+     */
     prevbuf = curbuf;
-    set_bufref(&bufref, prevbuf);
+    set_bufref(&prevbufref, prevbuf);
+    set_bufref(&newbufref, buf);
 
 #ifdef FEAT_AUTOCMD
+    /* Autocommands may delete the curren buffer and/or the buffer we wan to go
+     * to.  In those cases don't close the buffer. */
     if (!apply_autocmds(EVENT_BUFLEAVE, NULL, NULL, FALSE, curbuf)
+           || (bufref_valid(&prevbufref)
+               && bufref_valid(&newbufref)
 # ifdef FEAT_EVAL
-           || (bufref_valid(&bufref) && !aborting())
-# else
-           || bufref_valid(&bufref)
+               && !aborting()
 # endif
-       )
+              ))
 #endif
     {
 #ifdef FEAT_SYN_HL
@@ -1696,9 +1701,9 @@ set_curbuf(buf_T *buf, int action)
        if (unload)
            close_windows(prevbuf, FALSE);
 #if defined(FEAT_AUTOCMD) && defined(FEAT_EVAL)
-       if (bufref_valid(&bufref) && !aborting())
+       if (bufref_valid(&prevbufref) && !aborting())
 #else
-       if (bufref_valid(&bufref))
+       if (bufref_valid(&prevbufref))
 #endif
        {
            win_T  *previouswin = curwin;
index bf106f33c7b65303ccb57c88cca388ed3cc785a6..8ac8811075aa3c4f5d9fecc747a14807b2eb8f3e 100644 (file)
@@ -1163,3 +1163,11 @@ func Test_TextYankPost()
   unlet g:event
   bwipe!
 endfunc
+
+func Test_nocatch_wipe_all_buffers()
+  " Real nasty autocommand: wipe all buffers on any event.
+  au * * bwipe *
+  call assert_fails('next x', 'E93')
+  bwipe
+  au!
+endfunc
index ba65a54fac116a514ea75bfc9bd93cc115bdecb1..fc2eda65e471762d1773d8f34b2c6567604ba778 100644 (file)
@@ -771,6 +771,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1402,
 /**/
     1401,
 /**/