changeset 17596:892b4ea3bad6 v8.1.1795

patch 8.1.1795: no syntax HL after splitting windows with :bufdo commit https://github.com/vim/vim/commit/c7f1e4002184903f4e12e429dd5c6ab731932f86 Author: Bram Moolenaar <Bram@vim.org> Date: Sat Aug 3 13:29:46 2019 +0200 patch 8.1.1795: no syntax HL after splitting windows with :bufdo Problem: No syntax HL after splitting windows with :bufdo. (Yasuhiro Matsumoto) Solution: Trigger Syntax autocommands in buffers that are active. (closes #4761)
author Bram Moolenaar <Bram@vim.org>
date Sat, 03 Aug 2019 13:30:07 +0200
parents 50cc81726702
children bdb0cb436806
files src/ex_cmds2.c src/option.c src/testdir/test_syntax.vim src/version.c src/vim.h
diffstat 5 files changed, 89 insertions(+), 15 deletions(-) [+]
line wrap: on
line diff
--- a/src/ex_cmds2.c
+++ b/src/ex_cmds2.c
@@ -1447,9 +1447,15 @@ ex_listdo(exarg_T *eap)
 
 #if defined(FEAT_SYN_HL)
     if (eap->cmdidx != CMD_windo && eap->cmdidx != CMD_tabdo)
+    {
 	/* Don't do syntax HL autocommands.  Skipping the syntax file is a
 	 * great speed improvement. */
 	save_ei = au_event_disable(",Syntax");
+
+	for (buf = firstbuf; buf != NULL; buf = buf->b_next)
+	    buf->b_flags &= ~BF_SYN_SET;
+	buf = curbuf;
+    }
 #endif
 #ifdef FEAT_CLIPBOARD
     start_global_changes();
@@ -1641,9 +1647,35 @@ ex_listdo(exarg_T *eap)
 #if defined(FEAT_SYN_HL)
     if (save_ei != NULL)
     {
+	buf_T		*bnext;
+	aco_save_T	aco;
+
 	au_event_restore(save_ei);
-	apply_autocmds(EVENT_SYNTAX, curbuf->b_p_syn,
+
+	for (buf = firstbuf; buf != NULL; buf = bnext)
+	{
+	    bnext = buf->b_next;
+	    if (buf->b_nwindows > 0 && (buf->b_flags & BF_SYN_SET))
+	    {
+		buf->b_flags &= ~BF_SYN_SET;
+
+		// buffer was opened while Syntax autocommands were disabled,
+		// need to trigger them now.
+		if (buf == curbuf)
+		    apply_autocmds(EVENT_SYNTAX, curbuf->b_p_syn,
 					       curbuf->b_fname, TRUE, curbuf);
+		else
+		{
+		    aucmd_prepbuf(&aco, buf);
+		    apply_autocmds(EVENT_SYNTAX, buf->b_p_syn,
+						      buf->b_fname, TRUE, buf);
+		    aucmd_restbuf(&aco);
+		}
+
+		// start over, in case autocommands messed things up.
+		bnext = firstbuf;
+	    }
+	}
     }
 #endif
 #ifdef FEAT_CLIPBOARD
--- a/src/option.c
+++ b/src/option.c
@@ -7931,6 +7931,7 @@ did_set_string_option(
 	    // recursively, to avoid endless recurrence.
 	    apply_autocmds(EVENT_SYNTAX, curbuf->b_p_syn, curbuf->b_fname,
 		    value_changed || syn_recursive == 1, curbuf);
+	    curbuf->b_flags |= BF_SYN_SET;
 	    --syn_recursive;
 	}
 #endif
--- a/src/testdir/test_syntax.vim
+++ b/src/testdir/test_syntax.vim
@@ -582,3 +582,41 @@ func Test_syn_wrong_z_one()
   call test_override("ALL", 0)
   bwipe!
 endfunc
+
+func Test_syntax_after_bufdo()
+  call writefile(['/* aaa comment */'], 'Xaaa.c')
+  call writefile(['/* bbb comment */'], 'Xbbb.c')
+  call writefile(['/* ccc comment */'], 'Xccc.c')
+  call writefile(['/* ddd comment */'], 'Xddd.c')
+
+  let bnr = bufnr('%')
+  new Xaaa.c
+  badd Xbbb.c
+  badd Xccc.c
+  badd Xddd.c
+  exe "bwipe " . bnr
+  let l = []
+  bufdo call add(l, bufnr('%'))
+  call assert_equal(4, len(l))
+
+  syntax on
+
+  " This used to only enable syntax HL in the last buffer.
+  bufdo tab split
+  tabrewind
+  for tab in range(1, 4)
+    norm fm
+    call assert_equal(['cComment'], map(synstack(line("."), col(".")), 'synIDattr(v:val, "name")'))
+    tabnext
+  endfor
+
+  bwipe! Xaaa.c
+  bwipe! Xbbb.c
+  bwipe! Xccc.c
+  bwipe! Xddd.c
+  syntax off
+  call delete('Xaaa.c')
+  call delete('Xbbb.c')
+  call delete('Xccc.c')
+  call delete('Xddd.c')
+endfunc
--- a/src/version.c
+++ b/src/version.c
@@ -774,6 +774,8 @@ static char *(features[]) =
 static int included_patches[] =
 {   /* Add new patch number below this line */
 /**/
+    1795,
+/**/
     1794,
 /**/
     1793,
--- a/src/vim.h
+++ b/src/vim.h
@@ -698,20 +698,21 @@ extern int (*dyn_libintl_wputenv)(const 
 #define NOTDONE			2   /* not OK or FAIL but skipped */
 
 /* flags for b_flags */
-#define BF_RECOVERED	0x01	/* buffer has been recovered */
-#define BF_CHECK_RO	0x02	/* need to check readonly when loading file
-				   into buffer (set by ":e", may be reset by
-				   ":buf" */
-#define BF_NEVERLOADED	0x04	/* file has never been loaded into buffer,
-				   many variables still need to be set */
-#define BF_NOTEDITED	0x08	/* Set when file name is changed after
-				   starting to edit, reset when file is
-				   written out. */
-#define BF_NEW		0x10	/* file didn't exist when editing started */
-#define BF_NEW_W	0x20	/* Warned for BF_NEW and file created */
-#define BF_READERR	0x40	/* got errors while reading the file */
-#define BF_DUMMY	0x80	/* dummy buffer, only used internally */
-#define BF_PRESERVED	0x100	/* ":preserve" was used */
+#define BF_RECOVERED	0x01	// buffer has been recovered
+#define BF_CHECK_RO	0x02	// need to check readonly when loading file
+				// into buffer (set by ":e", may be reset by
+				// ":buf"
+#define BF_NEVERLOADED	0x04	// file has never been loaded into buffer,
+				// many variables still need to be set
+#define BF_NOTEDITED	0x08	// Set when file name is changed after
+				// starting to edit, reset when file is
+				// written out.
+#define BF_NEW		0x10	// file didn't exist when editing started
+#define BF_NEW_W	0x20	// Warned for BF_NEW and file created
+#define BF_READERR	0x40	// got errors while reading the file
+#define BF_DUMMY	0x80	// dummy buffer, only used internally
+#define BF_PRESERVED	0x100	// ":preserve" was used
+#define BF_SYN_SET	0x200	// 'syntax' option was set
 
 /* Mask to check for flags that prevent normal writing */
 #define BF_WRITE_MASK	(BF_NOTEDITED + BF_NEW + BF_READERR)