CVE-2022-3591: Use After Free (CWE-416)
value: Use After Free in GitHub repository vim/vim prior to 9.0.0789.
CWE description: The product reuses or references memory after it has been freed. At some point afterward, the memory may be allocated again and saved in another pointer, while the original pointer references a location somewhere within the new allocation. Any operations using the original pointer are no longer valid because the memory "belongs" to the code that operates on the new pointer.
CVSS v3 base score: 7.8
Published: 2022-12-02T17:15Z
Repository: https://github.com/vim/vim
Language: C
Files changed: src/buffer.c, src/testdir/test_autocmd.vim, src/version.c
Commit date: 2022-10-18 17:05:54 +0100
Commit message: patch 9.0.0789: dummy buffer ends up in a window

Problem:    Dummy buffer ends up in a window.
Solution:   Disallow navigating to a dummy buffer.

Diff: diff --git a/src/buffer.c b/src/buffer.c
index 0849b70997a..5a4825feb28 100644
--- a/src/buffer.c
+++ b/src/buffer.c
@@ -1349,10 +1349,17 @@ do_buffer_ext(
     }
 #ifdef FEAT_PROP_POPUP
     if ((flags & DOBUF_NOPOPUP) && bt_popup(buf) && !bt_terminal(buf))
 	return OK;
 #endif
+    if ((action == DOBUF_GOTO || action == DOBUF_SPLIT)
+						  && (buf->b_flags & BF_DUMMY))
+    {
+	// disallow navigating to the dummy buffer
+	semsg(_(e_buffer_nr_does_not_exist), count);
+	return FAIL;
+    }
 
 #ifdef FEAT_GUI
     need_mouse_correct = TRUE;
 #endif
 
diff --git a/src/testdir/test_autocmd.vim b/src/testdir/test_autocmd.vim
index 0706e73070a..6ba1b02dffb 100644
--- a/src/testdir/test_autocmd.vim
+++ b/src/testdir/test_autocmd.vim
@@ -3855,6 +3855,26 @@ func Test_autocmd_delete()
 
   call assert_true(autocmd_delete([[]]))
   call assert_true(autocmd_delete([test_null_dict()]))
 endfunc
 
+func Test_autocmd_split_dummy()
+  " Autocommand trying to split a window containing a dummy buffer.
+  auto BufReadPre * exe "sbuf " .. expand("<abuf>") 
+  " Avoid the "W11" prompt
+  au FileChangedShell * let v:fcs_choice = 'reload'
+  func Xautocmd_changelist()
+    cal writefile(['Xtestfile2:4:4'], 'Xerr')
+    edit Xerr
+    lex 'Xtestfile2:4:4'
+  endfunc
+  call Xautocmd_changelist()
+  call assert_fails('call Xautocmd_changelist()', 'E86:')
+
+  au! BufReadPre
+  au! FileChangedShell
+  delfunc Xautocmd_changelist
+  bwipe! Xerr
+  call delete('Xerr')
+endfunc
+
 " vim: shiftwidth=2 sts=2 expandtab
diff --git a/src/version.c b/src/version.c
index 1c511f94b58..05e619f06ae 100644
--- a/src/version.c
+++ b/src/version.c
@@ -693,10 +693,12 @@ static char *(features[]) =
 	NULL
 };
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    789,
 /**/
     788,
 /**/
     787,
 /**/

Fixed code:     if ((action == DOBUF_GOTO || action == DOBUF_SPLIT)
						  && (buf->b_flags & BF_DUMMY))
    {
	// disallow navigating to the dummy buffer
	semsg(_(e_buffer_nr_does_not_exist), count);
	return FAIL;
    }
func Test_autocmd_split_dummy()
  " Autocommand trying to split a window containing a dummy buffer.
  auto BufReadPre * exe "sbuf " .. expand("<abuf>") 
  " Avoid the "W11" prompt
  au FileChangedShell * let v:fcs_choice = 'reload'
  func Xautocmd_changelist()
    cal writefile(['Xtestfile2:4:4'], 'Xerr')
    edit Xerr
    lex 'Xtestfile2:4:4'
  endfunc
  call Xautocmd_changelist()
  call assert_fails('call Xautocmd_changelist()', 'E86:')

  au! BufReadPre
  au! FileChangedShell
  delfunc Xautocmd_changelist
  bwipe! Xerr
  call delete('Xerr')
endfunc

/**/
    789,