blob: e6cdb361ed037d168ac34e75e12cc400ddb79a7a [file] [log] [blame]
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01001/* vi:set ts=8 sts=4 sw=4 noet:
2 *
3 * VIM - Vi IMproved by Bram Moolenaar
4 *
5 * Do ":help uganda" in Vim to read copying and usage conditions.
6 * Do ":help credits" in Vim to see a list of people who contributed.
7 * See README.txt for an overview of the Vim source code.
8 */
9
10/*
11 * autocmd.c: Autocommand related functions
12 */
13
14#include "vim.h"
15
16/*
17 * The autocommands are stored in a list for each event.
18 * Autocommands for the same pattern, that are consecutive, are joined
19 * together, to avoid having to match the pattern too often.
20 * The result is an array of Autopat lists, which point to AutoCmd lists:
21 *
22 * last_autopat[0] -----------------------------+
23 * V
24 * first_autopat[0] --> Autopat.next --> Autopat.next --> NULL
25 * Autopat.cmds Autopat.cmds
26 * | |
27 * V V
28 * AutoCmd.next AutoCmd.next
29 * | |
30 * V V
31 * AutoCmd.next NULL
32 * |
33 * V
34 * NULL
35 *
36 * last_autopat[1] --------+
37 * V
38 * first_autopat[1] --> Autopat.next --> NULL
39 * Autopat.cmds
40 * |
41 * V
42 * AutoCmd.next
43 * |
44 * V
45 * NULL
46 * etc.
47 *
48 * The order of AutoCmds is important, this is the order in which they were
49 * defined and will have to be executed.
50 */
51typedef struct AutoCmd
52{
53 char_u *cmd; // The command to be executed (NULL
54 // when command has been removed).
Bram Moolenaareb93f3f2019-04-04 15:04:56 +020055 char once; // "One shot": removed after execution
Bram Moolenaar3e460fd2019-01-26 16:21:07 +010056 char nested; // If autocommands nest here.
57 char last; // last command in list
58#ifdef FEAT_EVAL
59 sctx_T script_ctx; // script context where defined
60#endif
61 struct AutoCmd *next; // next AutoCmd in list
62} AutoCmd;
63
64typedef struct AutoPat
65{
66 struct AutoPat *next; // Next AutoPat in AutoPat list; MUST
67 // be the first entry.
68 char_u *pat; // pattern as typed (NULL when pattern
69 // has been removed)
70 regprog_T *reg_prog; // compiled regprog for pattern
71 AutoCmd *cmds; // list of commands to do
72 int group; // group ID
73 int patlen; // strlen() of pat
74 int buflocal_nr; // !=0 for buffer-local AutoPat
75 char allow_dirs; // Pattern may match whole path
76 char last; // last pattern for apply_autocmds()
77} AutoPat;
78
79static struct event_name
80{
81 char *name; // event name
82 event_T event; // event number
83} event_names[] =
84{
85 {"BufAdd", EVENT_BUFADD},
86 {"BufCreate", EVENT_BUFADD},
87 {"BufDelete", EVENT_BUFDELETE},
88 {"BufEnter", EVENT_BUFENTER},
89 {"BufFilePost", EVENT_BUFFILEPOST},
90 {"BufFilePre", EVENT_BUFFILEPRE},
91 {"BufHidden", EVENT_BUFHIDDEN},
92 {"BufLeave", EVENT_BUFLEAVE},
93 {"BufNew", EVENT_BUFNEW},
94 {"BufNewFile", EVENT_BUFNEWFILE},
95 {"BufRead", EVENT_BUFREADPOST},
96 {"BufReadCmd", EVENT_BUFREADCMD},
97 {"BufReadPost", EVENT_BUFREADPOST},
98 {"BufReadPre", EVENT_BUFREADPRE},
99 {"BufUnload", EVENT_BUFUNLOAD},
100 {"BufWinEnter", EVENT_BUFWINENTER},
101 {"BufWinLeave", EVENT_BUFWINLEAVE},
102 {"BufWipeout", EVENT_BUFWIPEOUT},
103 {"BufWrite", EVENT_BUFWRITEPRE},
104 {"BufWritePost", EVENT_BUFWRITEPOST},
105 {"BufWritePre", EVENT_BUFWRITEPRE},
106 {"BufWriteCmd", EVENT_BUFWRITECMD},
107 {"CmdlineChanged", EVENT_CMDLINECHANGED},
108 {"CmdlineEnter", EVENT_CMDLINEENTER},
109 {"CmdlineLeave", EVENT_CMDLINELEAVE},
110 {"CmdwinEnter", EVENT_CMDWINENTER},
111 {"CmdwinLeave", EVENT_CMDWINLEAVE},
112 {"CmdUndefined", EVENT_CMDUNDEFINED},
113 {"ColorScheme", EVENT_COLORSCHEME},
114 {"ColorSchemePre", EVENT_COLORSCHEMEPRE},
Bram Moolenaard7f246c2019-04-08 18:15:41 +0200115 {"CompleteChanged", EVENT_COMPLETECHANGED},
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100116 {"CompleteDone", EVENT_COMPLETEDONE},
117 {"CursorHold", EVENT_CURSORHOLD},
118 {"CursorHoldI", EVENT_CURSORHOLDI},
119 {"CursorMoved", EVENT_CURSORMOVED},
120 {"CursorMovedI", EVENT_CURSORMOVEDI},
121 {"DiffUpdated", EVENT_DIFFUPDATED},
122 {"DirChanged", EVENT_DIRCHANGED},
123 {"EncodingChanged", EVENT_ENCODINGCHANGED},
124 {"ExitPre", EVENT_EXITPRE},
125 {"FileEncoding", EVENT_ENCODINGCHANGED},
126 {"FileAppendPost", EVENT_FILEAPPENDPOST},
127 {"FileAppendPre", EVENT_FILEAPPENDPRE},
128 {"FileAppendCmd", EVENT_FILEAPPENDCMD},
129 {"FileChangedShell",EVENT_FILECHANGEDSHELL},
130 {"FileChangedShellPost",EVENT_FILECHANGEDSHELLPOST},
131 {"FileChangedRO", EVENT_FILECHANGEDRO},
132 {"FileReadPost", EVENT_FILEREADPOST},
133 {"FileReadPre", EVENT_FILEREADPRE},
134 {"FileReadCmd", EVENT_FILEREADCMD},
135 {"FileType", EVENT_FILETYPE},
136 {"FileWritePost", EVENT_FILEWRITEPOST},
137 {"FileWritePre", EVENT_FILEWRITEPRE},
138 {"FileWriteCmd", EVENT_FILEWRITECMD},
139 {"FilterReadPost", EVENT_FILTERREADPOST},
140 {"FilterReadPre", EVENT_FILTERREADPRE},
141 {"FilterWritePost", EVENT_FILTERWRITEPOST},
142 {"FilterWritePre", EVENT_FILTERWRITEPRE},
143 {"FocusGained", EVENT_FOCUSGAINED},
144 {"FocusLost", EVENT_FOCUSLOST},
145 {"FuncUndefined", EVENT_FUNCUNDEFINED},
146 {"GUIEnter", EVENT_GUIENTER},
147 {"GUIFailed", EVENT_GUIFAILED},
148 {"InsertChange", EVENT_INSERTCHANGE},
149 {"InsertEnter", EVENT_INSERTENTER},
150 {"InsertLeave", EVENT_INSERTLEAVE},
151 {"InsertCharPre", EVENT_INSERTCHARPRE},
152 {"MenuPopup", EVENT_MENUPOPUP},
153 {"OptionSet", EVENT_OPTIONSET},
154 {"QuickFixCmdPost", EVENT_QUICKFIXCMDPOST},
155 {"QuickFixCmdPre", EVENT_QUICKFIXCMDPRE},
156 {"QuitPre", EVENT_QUITPRE},
157 {"RemoteReply", EVENT_REMOTEREPLY},
158 {"SessionLoadPost", EVENT_SESSIONLOADPOST},
159 {"ShellCmdPost", EVENT_SHELLCMDPOST},
160 {"ShellFilterPost", EVENT_SHELLFILTERPOST},
161 {"SourceCmd", EVENT_SOURCECMD},
162 {"SourcePre", EVENT_SOURCEPRE},
163 {"SourcePost", EVENT_SOURCEPOST},
164 {"SpellFileMissing",EVENT_SPELLFILEMISSING},
165 {"StdinReadPost", EVENT_STDINREADPOST},
166 {"StdinReadPre", EVENT_STDINREADPRE},
167 {"SwapExists", EVENT_SWAPEXISTS},
168 {"Syntax", EVENT_SYNTAX},
169 {"TabNew", EVENT_TABNEW},
170 {"TabClosed", EVENT_TABCLOSED},
171 {"TabEnter", EVENT_TABENTER},
172 {"TabLeave", EVENT_TABLEAVE},
173 {"TermChanged", EVENT_TERMCHANGED},
174 {"TerminalOpen", EVENT_TERMINALOPEN},
175 {"TermResponse", EVENT_TERMRESPONSE},
176 {"TextChanged", EVENT_TEXTCHANGED},
177 {"TextChangedI", EVENT_TEXTCHANGEDI},
178 {"TextChangedP", EVENT_TEXTCHANGEDP},
179 {"User", EVENT_USER},
180 {"VimEnter", EVENT_VIMENTER},
181 {"VimLeave", EVENT_VIMLEAVE},
182 {"VimLeavePre", EVENT_VIMLEAVEPRE},
183 {"WinNew", EVENT_WINNEW},
184 {"WinEnter", EVENT_WINENTER},
185 {"WinLeave", EVENT_WINLEAVE},
186 {"VimResized", EVENT_VIMRESIZED},
187 {"TextYankPost", EVENT_TEXTYANKPOST},
188 {NULL, (event_T)0}
189};
190
191static AutoPat *first_autopat[NUM_EVENTS] =
192{
193 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
194 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
195 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
196 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
197 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
198 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
199};
200
201static AutoPat *last_autopat[NUM_EVENTS] =
202{
203 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
204 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
205 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
206 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
207 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
208 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
209};
210
211#define AUGROUP_DEFAULT -1 // default autocmd group
212#define AUGROUP_ERROR -2 // erroneous autocmd group
213#define AUGROUP_ALL -3 // all autocmd groups
214
215/*
216 * struct used to keep status while executing autocommands for an event.
217 */
218typedef struct AutoPatCmd
219{
220 AutoPat *curpat; // next AutoPat to examine
221 AutoCmd *nextcmd; // next AutoCmd to execute
222 int group; // group being used
223 char_u *fname; // fname to match with
224 char_u *sfname; // sfname to match with
225 char_u *tail; // tail of fname
226 event_T event; // current event
227 int arg_bufnr; // Initially equal to <abuf>, set to zero when
228 // buf is deleted.
229 struct AutoPatCmd *next; // chain of active apc-s for auto-invalidation
230} AutoPatCmd;
231
232static AutoPatCmd *active_apc_list = NULL; /* stack of active autocommands */
233
234/*
235 * augroups stores a list of autocmd group names.
236 */
237static garray_T augroups = {0, 0, sizeof(char_u *), 10, NULL};
238#define AUGROUP_NAME(i) (((char_u **)augroups.ga_data)[i])
239/* use get_deleted_augroup() to get this */
240static char_u *deleted_augroup = NULL;
241
242/*
243 * Set by the apply_autocmds_group function if the given event is equal to
244 * EVENT_FILETYPE. Used by the readfile function in order to determine if
245 * EVENT_BUFREADPOST triggered the EVENT_FILETYPE.
246 *
247 * Relying on this value requires one to reset it prior calling
248 * apply_autocmds_group.
249 */
250int au_did_filetype INIT(= FALSE);
251
252/*
253 * The ID of the current group. Group 0 is the default one.
254 */
255static int current_augroup = AUGROUP_DEFAULT;
256
257static int au_need_clean = FALSE; /* need to delete marked patterns */
258
259static char_u *event_nr2name(event_T event);
260static int au_get_grouparg(char_u **argp);
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200261static int do_autocmd_event(event_T event, char_u *pat, int once, int nested, char_u *cmd, int forceit, int group);
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100262static int apply_autocmds_group(event_T event, char_u *fname, char_u *fname_io, int force, int group, buf_T *buf, exarg_T *eap);
263static void auto_next_pat(AutoPatCmd *apc, int stop_at_last);
264static int au_find_group(char_u *name);
265
266static event_T last_event;
267static int last_group;
268static int autocmd_blocked = 0; /* block all autocmds */
269
270 static char_u *
271get_deleted_augroup(void)
272{
273 if (deleted_augroup == NULL)
274 deleted_augroup = (char_u *)_("--Deleted--");
275 return deleted_augroup;
276}
277
278/*
279 * Show the autocommands for one AutoPat.
280 */
281 static void
282show_autocmd(AutoPat *ap, event_T event)
283{
284 AutoCmd *ac;
285
286 // Check for "got_int" (here and at various places below), which is set
287 // when "q" has been hit for the "--more--" prompt
288 if (got_int)
289 return;
290 if (ap->pat == NULL) // pattern has been removed
291 return;
292
293 msg_putchar('\n');
294 if (got_int)
295 return;
296 if (event != last_event || ap->group != last_group)
297 {
298 if (ap->group != AUGROUP_DEFAULT)
299 {
300 if (AUGROUP_NAME(ap->group) == NULL)
301 msg_puts_attr((char *)get_deleted_augroup(), HL_ATTR(HLF_E));
302 else
303 msg_puts_attr((char *)AUGROUP_NAME(ap->group), HL_ATTR(HLF_T));
304 msg_puts(" ");
305 }
306 msg_puts_attr((char *)event_nr2name(event), HL_ATTR(HLF_T));
307 last_event = event;
308 last_group = ap->group;
309 msg_putchar('\n');
310 if (got_int)
311 return;
312 }
313 msg_col = 4;
314 msg_outtrans(ap->pat);
315
316 for (ac = ap->cmds; ac != NULL; ac = ac->next)
317 {
318 if (ac->cmd != NULL) // skip removed commands
319 {
320 if (msg_col >= 14)
321 msg_putchar('\n');
322 msg_col = 14;
323 if (got_int)
324 return;
325 msg_outtrans(ac->cmd);
326#ifdef FEAT_EVAL
327 if (p_verbose > 0)
328 last_set_msg(ac->script_ctx);
329#endif
330 if (got_int)
331 return;
332 if (ac->next != NULL)
333 {
334 msg_putchar('\n');
335 if (got_int)
336 return;
337 }
338 }
339 }
340}
341
342/*
343 * Mark an autocommand pattern for deletion.
344 */
345 static void
346au_remove_pat(AutoPat *ap)
347{
348 VIM_CLEAR(ap->pat);
349 ap->buflocal_nr = -1;
350 au_need_clean = TRUE;
351}
352
353/*
354 * Mark all commands for a pattern for deletion.
355 */
356 static void
357au_remove_cmds(AutoPat *ap)
358{
359 AutoCmd *ac;
360
361 for (ac = ap->cmds; ac != NULL; ac = ac->next)
362 VIM_CLEAR(ac->cmd);
363 au_need_clean = TRUE;
364}
365
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200366// Delete one command from an autocmd pattern.
367static void au_del_cmd(AutoCmd *ac)
368{
369 VIM_CLEAR(ac->cmd);
370 au_need_clean = TRUE;
371}
372
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100373/*
374 * Cleanup autocommands and patterns that have been deleted.
375 * This is only done when not executing autocommands.
376 */
377 static void
378au_cleanup(void)
379{
380 AutoPat *ap, **prev_ap;
381 AutoCmd *ac, **prev_ac;
382 event_T event;
383
384 if (autocmd_busy || !au_need_clean)
385 return;
386
387 // loop over all events
388 for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
389 event = (event_T)((int)event + 1))
390 {
391 // loop over all autocommand patterns
392 prev_ap = &(first_autopat[(int)event]);
393 for (ap = *prev_ap; ap != NULL; ap = *prev_ap)
394 {
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200395 int has_cmd = FALSE;
396
Bram Moolenaar8f4aeb52019-04-04 15:40:56 +0200397 // loop over all commands for this pattern
398 prev_ac = &(ap->cmds);
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100399 for (ac = *prev_ac; ac != NULL; ac = *prev_ac)
400 {
401 // remove the command if the pattern is to be deleted or when
402 // the command has been marked for deletion
403 if (ap->pat == NULL || ac->cmd == NULL)
404 {
405 *prev_ac = ac->next;
406 vim_free(ac->cmd);
407 vim_free(ac);
408 }
Bram Moolenaar8f4aeb52019-04-04 15:40:56 +0200409 else
410 {
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200411 has_cmd = TRUE;
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100412 prev_ac = &(ac->next);
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200413 }
414 }
415
Bram Moolenaar8f4aeb52019-04-04 15:40:56 +0200416 if (ap->pat != NULL && !has_cmd)
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200417 // Pattern was not marked for deletion, but all of its
418 // commands were. So mark the pattern for deletion.
419 au_remove_pat(ap);
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100420
421 // remove the pattern if it has been marked for deletion
422 if (ap->pat == NULL)
423 {
424 if (ap->next == NULL)
425 {
426 if (prev_ap == &(first_autopat[(int)event]))
427 last_autopat[(int)event] = NULL;
428 else
429 // this depends on the "next" field being the first in
430 // the struct
431 last_autopat[(int)event] = (AutoPat *)prev_ap;
432 }
433 *prev_ap = ap->next;
434 vim_regfree(ap->reg_prog);
435 vim_free(ap);
436 }
437 else
438 prev_ap = &(ap->next);
439 }
440 }
441
442 au_need_clean = FALSE;
443}
444
445/*
446 * Called when buffer is freed, to remove/invalidate related buffer-local
447 * autocmds.
448 */
449 void
450aubuflocal_remove(buf_T *buf)
451{
452 AutoPat *ap;
453 event_T event;
454 AutoPatCmd *apc;
455
456 // invalidate currently executing autocommands
457 for (apc = active_apc_list; apc; apc = apc->next)
458 if (buf->b_fnum == apc->arg_bufnr)
459 apc->arg_bufnr = 0;
460
461 // invalidate buflocals looping through events
462 for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
463 event = (event_T)((int)event + 1))
464 // loop over all autocommand patterns
465 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next)
466 if (ap->buflocal_nr == buf->b_fnum)
467 {
468 au_remove_pat(ap);
469 if (p_verbose >= 6)
470 {
471 verbose_enter();
472 smsg(_("auto-removing autocommand: %s <buffer=%d>"),
473 event_nr2name(event), buf->b_fnum);
474 verbose_leave();
475 }
476 }
477 au_cleanup();
478}
479
480/*
481 * Add an autocmd group name.
482 * Return its ID. Returns AUGROUP_ERROR (< 0) for error.
483 */
484 static int
485au_new_group(char_u *name)
486{
487 int i;
488
489 i = au_find_group(name);
490 if (i == AUGROUP_ERROR) // the group doesn't exist yet, add it
491 {
492 // First try using a free entry.
493 for (i = 0; i < augroups.ga_len; ++i)
494 if (AUGROUP_NAME(i) == NULL)
495 break;
496 if (i == augroups.ga_len && ga_grow(&augroups, 1) == FAIL)
497 return AUGROUP_ERROR;
498
499 AUGROUP_NAME(i) = vim_strsave(name);
500 if (AUGROUP_NAME(i) == NULL)
501 return AUGROUP_ERROR;
502 if (i == augroups.ga_len)
503 ++augroups.ga_len;
504 }
505
506 return i;
507}
508
509 static void
510au_del_group(char_u *name)
511{
512 int i;
513
514 i = au_find_group(name);
515 if (i == AUGROUP_ERROR) // the group doesn't exist
516 semsg(_("E367: No such group: \"%s\""), name);
517 else if (i == current_augroup)
518 emsg(_("E936: Cannot delete the current group"));
519 else
520 {
521 event_T event;
522 AutoPat *ap;
523 int in_use = FALSE;
524
525 for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
526 event = (event_T)((int)event + 1))
527 {
528 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next)
529 if (ap->group == i && ap->pat != NULL)
530 {
531 give_warning((char_u *)_("W19: Deleting augroup that is still in use"), TRUE);
532 in_use = TRUE;
533 event = NUM_EVENTS;
534 break;
535 }
536 }
537 vim_free(AUGROUP_NAME(i));
538 if (in_use)
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100539 AUGROUP_NAME(i) = get_deleted_augroup();
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100540 else
541 AUGROUP_NAME(i) = NULL;
542 }
543}
544
545/*
546 * Find the ID of an autocmd group name.
547 * Return its ID. Returns AUGROUP_ERROR (< 0) for error.
548 */
549 static int
550au_find_group(char_u *name)
551{
552 int i;
553
554 for (i = 0; i < augroups.ga_len; ++i)
555 if (AUGROUP_NAME(i) != NULL && AUGROUP_NAME(i) != get_deleted_augroup()
556 && STRCMP(AUGROUP_NAME(i), name) == 0)
557 return i;
558 return AUGROUP_ERROR;
559}
560
561/*
562 * Return TRUE if augroup "name" exists.
563 */
564 int
565au_has_group(char_u *name)
566{
567 return au_find_group(name) != AUGROUP_ERROR;
568}
569
570/*
571 * ":augroup {name}".
572 */
573 void
574do_augroup(char_u *arg, int del_group)
575{
576 int i;
577
578 if (del_group)
579 {
580 if (*arg == NUL)
581 emsg(_(e_argreq));
582 else
583 au_del_group(arg);
584 }
585 else if (STRICMP(arg, "end") == 0) // ":aug end": back to group 0
586 current_augroup = AUGROUP_DEFAULT;
587 else if (*arg) // ":aug xxx": switch to group xxx
588 {
589 i = au_new_group(arg);
590 if (i != AUGROUP_ERROR)
591 current_augroup = i;
592 }
593 else // ":aug": list the group names
594 {
595 msg_start();
596 for (i = 0; i < augroups.ga_len; ++i)
597 {
598 if (AUGROUP_NAME(i) != NULL)
599 {
600 msg_puts((char *)AUGROUP_NAME(i));
601 msg_puts(" ");
602 }
603 }
604 msg_clr_eos();
605 msg_end();
606 }
607}
608
609#if defined(EXITFREE) || defined(PROTO)
610 void
611free_all_autocmds(void)
612{
613 int i;
614 char_u *s;
615
616 for (current_augroup = -1; current_augroup < augroups.ga_len;
617 ++current_augroup)
618 do_autocmd((char_u *)"", TRUE);
619
620 for (i = 0; i < augroups.ga_len; ++i)
621 {
622 s = ((char_u **)(augroups.ga_data))[i];
623 if (s != get_deleted_augroup())
624 vim_free(s);
625 }
626 ga_clear(&augroups);
627}
628#endif
629
630/*
631 * Return the event number for event name "start".
632 * Return NUM_EVENTS if the event name was not found.
633 * Return a pointer to the next event name in "end".
634 */
635 static event_T
636event_name2nr(char_u *start, char_u **end)
637{
638 char_u *p;
639 int i;
640 int len;
641
642 // the event name ends with end of line, '|', a blank or a comma
643 for (p = start; *p && !VIM_ISWHITE(*p) && *p != ',' && *p != '|'; ++p)
644 ;
645 for (i = 0; event_names[i].name != NULL; ++i)
646 {
647 len = (int)STRLEN(event_names[i].name);
648 if (len == p - start && STRNICMP(event_names[i].name, start, len) == 0)
649 break;
650 }
651 if (*p == ',')
652 ++p;
653 *end = p;
654 if (event_names[i].name == NULL)
655 return NUM_EVENTS;
656 return event_names[i].event;
657}
658
659/*
660 * Return the name for event "event".
661 */
662 static char_u *
663event_nr2name(event_T event)
664{
665 int i;
666
667 for (i = 0; event_names[i].name != NULL; ++i)
668 if (event_names[i].event == event)
669 return (char_u *)event_names[i].name;
670 return (char_u *)"Unknown";
671}
672
673/*
674 * Scan over the events. "*" stands for all events.
675 */
676 static char_u *
677find_end_event(
678 char_u *arg,
679 int have_group) // TRUE when group name was found
680{
681 char_u *pat;
682 char_u *p;
683
684 if (*arg == '*')
685 {
686 if (arg[1] && !VIM_ISWHITE(arg[1]))
687 {
688 semsg(_("E215: Illegal character after *: %s"), arg);
689 return NULL;
690 }
691 pat = arg + 1;
692 }
693 else
694 {
695 for (pat = arg; *pat && *pat != '|' && !VIM_ISWHITE(*pat); pat = p)
696 {
697 if ((int)event_name2nr(pat, &p) >= (int)NUM_EVENTS)
698 {
699 if (have_group)
700 semsg(_("E216: No such event: %s"), pat);
701 else
702 semsg(_("E216: No such group or event: %s"), pat);
703 return NULL;
704 }
705 }
706 }
707 return pat;
708}
709
710/*
711 * Return TRUE if "event" is included in 'eventignore'.
712 */
713 static int
714event_ignored(event_T event)
715{
716 char_u *p = p_ei;
717
718 while (*p != NUL)
719 {
720 if (STRNICMP(p, "all", 3) == 0 && (p[3] == NUL || p[3] == ','))
721 return TRUE;
722 if (event_name2nr(p, &p) == event)
723 return TRUE;
724 }
725
726 return FALSE;
727}
728
729/*
730 * Return OK when the contents of p_ei is valid, FAIL otherwise.
731 */
732 int
733check_ei(void)
734{
735 char_u *p = p_ei;
736
737 while (*p)
738 {
739 if (STRNICMP(p, "all", 3) == 0 && (p[3] == NUL || p[3] == ','))
740 {
741 p += 3;
742 if (*p == ',')
743 ++p;
744 }
745 else if (event_name2nr(p, &p) == NUM_EVENTS)
746 return FAIL;
747 }
748
749 return OK;
750}
751
752# if defined(FEAT_SYN_HL) || defined(PROTO)
753
754/*
755 * Add "what" to 'eventignore' to skip loading syntax highlighting for every
756 * buffer loaded into the window. "what" must start with a comma.
757 * Returns the old value of 'eventignore' in allocated memory.
758 */
759 char_u *
760au_event_disable(char *what)
761{
762 char_u *new_ei;
763 char_u *save_ei;
764
765 save_ei = vim_strsave(p_ei);
766 if (save_ei != NULL)
767 {
768 new_ei = vim_strnsave(p_ei, (int)(STRLEN(p_ei) + STRLEN(what)));
769 if (new_ei != NULL)
770 {
771 if (*what == ',' && *p_ei == NUL)
772 STRCPY(new_ei, what + 1);
773 else
774 STRCAT(new_ei, what);
775 set_string_option_direct((char_u *)"ei", -1, new_ei,
776 OPT_FREE, SID_NONE);
777 vim_free(new_ei);
778 }
779 }
780 return save_ei;
781}
782
783 void
784au_event_restore(char_u *old_ei)
785{
786 if (old_ei != NULL)
787 {
788 set_string_option_direct((char_u *)"ei", -1, old_ei,
789 OPT_FREE, SID_NONE);
790 vim_free(old_ei);
791 }
792}
793# endif /* FEAT_SYN_HL */
794
795/*
796 * do_autocmd() -- implements the :autocmd command. Can be used in the
797 * following ways:
798 *
799 * :autocmd <event> <pat> <cmd> Add <cmd> to the list of commands that
800 * will be automatically executed for <event>
801 * when editing a file matching <pat>, in
802 * the current group.
803 * :autocmd <event> <pat> Show the autocommands associated with
804 * <event> and <pat>.
805 * :autocmd <event> Show the autocommands associated with
806 * <event>.
807 * :autocmd Show all autocommands.
808 * :autocmd! <event> <pat> <cmd> Remove all autocommands associated with
809 * <event> and <pat>, and add the command
810 * <cmd>, for the current group.
811 * :autocmd! <event> <pat> Remove all autocommands associated with
812 * <event> and <pat> for the current group.
813 * :autocmd! <event> Remove all autocommands associated with
814 * <event> for the current group.
815 * :autocmd! Remove ALL autocommands for the current
816 * group.
817 *
818 * Multiple events and patterns may be given separated by commas. Here are
819 * some examples:
820 * :autocmd bufread,bufenter *.c,*.h set tw=0 smartindent noic
821 * :autocmd bufleave * set tw=79 nosmartindent ic infercase
822 *
823 * :autocmd * *.c show all autocommands for *.c files.
824 *
825 * Mostly a {group} argument can optionally appear before <event>.
826 */
827 void
828do_autocmd(char_u *arg_in, int forceit)
829{
830 char_u *arg = arg_in;
831 char_u *pat;
832 char_u *envpat = NULL;
833 char_u *cmd;
834 event_T event;
835 int need_free = FALSE;
836 int nested = FALSE;
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200837 int once = FALSE;
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100838 int group;
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200839 int i;
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100840
841 if (*arg == '|')
842 {
843 arg = (char_u *)"";
844 group = AUGROUP_ALL; // no argument, use all groups
845 }
846 else
847 {
848 /*
849 * Check for a legal group name. If not, use AUGROUP_ALL.
850 */
851 group = au_get_grouparg(&arg);
852 if (arg == NULL) // out of memory
853 return;
854 }
855
856 /*
857 * Scan over the events.
858 * If we find an illegal name, return here, don't do anything.
859 */
860 pat = find_end_event(arg, group != AUGROUP_ALL);
861 if (pat == NULL)
862 return;
863
864 pat = skipwhite(pat);
865 if (*pat == '|')
866 {
867 pat = (char_u *)"";
868 cmd = (char_u *)"";
869 }
870 else
871 {
872 /*
873 * Scan over the pattern. Put a NUL at the end.
874 */
875 cmd = pat;
876 while (*cmd && (!VIM_ISWHITE(*cmd) || cmd[-1] == '\\'))
877 cmd++;
878 if (*cmd)
879 *cmd++ = NUL;
880
881 // Expand environment variables in the pattern. Set 'shellslash', we
882 // want forward slashes here.
883 if (vim_strchr(pat, '$') != NULL || vim_strchr(pat, '~') != NULL)
884 {
885#ifdef BACKSLASH_IN_FILENAME
886 int p_ssl_save = p_ssl;
887
888 p_ssl = TRUE;
889#endif
890 envpat = expand_env_save(pat);
891#ifdef BACKSLASH_IN_FILENAME
892 p_ssl = p_ssl_save;
893#endif
894 if (envpat != NULL)
895 pat = envpat;
896 }
897
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100898 cmd = skipwhite(cmd);
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200899 for (i = 0; i < 2; i++)
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100900 {
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200901 if (*cmd != NUL)
902 {
903 // Check for "++once" flag.
904 if (STRNCMP(cmd, "++once", 6) == 0 && VIM_ISWHITE(cmd[6]))
905 {
906 if (once)
907 semsg(_(e_duparg2), "++once");
908 once = TRUE;
909 cmd = skipwhite(cmd + 6);
910 }
911
912 // Check for "++nested" flag.
913 if ((STRNCMP(cmd, "++nested", 8) == 0 && VIM_ISWHITE(cmd[8])))
914 {
915 if (nested)
916 semsg(_(e_duparg2), "++nested");
917 nested = TRUE;
918 cmd = skipwhite(cmd + 8);
919 }
920
921 // Check for the old "nested" flag.
922 if (STRNCMP(cmd, "nested", 6) == 0 && VIM_ISWHITE(cmd[6]))
923 {
924 if (nested)
925 semsg(_(e_duparg2), "nested");
926 nested = TRUE;
927 cmd = skipwhite(cmd + 6);
928 }
929 }
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100930 }
931
932 /*
933 * Find the start of the commands.
934 * Expand <sfile> in it.
935 */
936 if (*cmd != NUL)
937 {
938 cmd = expand_sfile(cmd);
939 if (cmd == NULL) // some error
940 return;
941 need_free = TRUE;
942 }
943 }
944
945 /*
946 * Print header when showing autocommands.
947 */
948 if (!forceit && *cmd == NUL)
949 // Highlight title
950 msg_puts_title(_("\n--- Autocommands ---"));
951
952 /*
953 * Loop over the events.
954 */
955 last_event = (event_T)-1; // for listing the event name
956 last_group = AUGROUP_ERROR; // for listing the group name
957 if (*arg == '*' || *arg == NUL || *arg == '|')
958 {
959 for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
960 event = (event_T)((int)event + 1))
961 if (do_autocmd_event(event, pat,
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200962 once, nested, cmd, forceit, group) == FAIL)
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100963 break;
964 }
965 else
966 {
967 while (*arg && *arg != '|' && !VIM_ISWHITE(*arg))
968 if (do_autocmd_event(event_name2nr(arg, &arg), pat,
Bram Moolenaareb93f3f2019-04-04 15:04:56 +0200969 once, nested, cmd, forceit, group) == FAIL)
Bram Moolenaar3e460fd2019-01-26 16:21:07 +0100970 break;
971 }
972
973 if (need_free)
974 vim_free(cmd);
975 vim_free(envpat);
976}
977
978/*
979 * Find the group ID in a ":autocmd" or ":doautocmd" argument.
980 * The "argp" argument is advanced to the following argument.
981 *
982 * Returns the group ID, AUGROUP_ERROR for error (out of memory).
983 */
984 static int
985au_get_grouparg(char_u **argp)
986{
987 char_u *group_name;
988 char_u *p;
989 char_u *arg = *argp;
990 int group = AUGROUP_ALL;
991
992 for (p = arg; *p && !VIM_ISWHITE(*p) && *p != '|'; ++p)
993 ;
994 if (p > arg)
995 {
996 group_name = vim_strnsave(arg, (int)(p - arg));
997 if (group_name == NULL) // out of memory
998 return AUGROUP_ERROR;
999 group = au_find_group(group_name);
1000 if (group == AUGROUP_ERROR)
1001 group = AUGROUP_ALL; // no match, use all groups
1002 else
1003 *argp = skipwhite(p); // match, skip over group name
1004 vim_free(group_name);
1005 }
1006 return group;
1007}
1008
1009/*
1010 * do_autocmd() for one event.
1011 * If *pat == NUL do for all patterns.
1012 * If *cmd == NUL show entries.
1013 * If forceit == TRUE delete entries.
1014 * If group is not AUGROUP_ALL, only use this group.
1015 */
1016 static int
1017do_autocmd_event(
1018 event_T event,
1019 char_u *pat,
Bram Moolenaareb93f3f2019-04-04 15:04:56 +02001020 int once,
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01001021 int nested,
1022 char_u *cmd,
1023 int forceit,
1024 int group)
1025{
1026 AutoPat *ap;
1027 AutoPat **prev_ap;
1028 AutoCmd *ac;
1029 AutoCmd **prev_ac;
1030 int brace_level;
1031 char_u *endpat;
1032 int findgroup;
1033 int allgroups;
1034 int patlen;
1035 int is_buflocal;
1036 int buflocal_nr;
1037 char_u buflocal_pat[25]; /* for "<buffer=X>" */
1038
1039 if (group == AUGROUP_ALL)
1040 findgroup = current_augroup;
1041 else
1042 findgroup = group;
1043 allgroups = (group == AUGROUP_ALL && !forceit && *cmd == NUL);
1044
1045 /*
1046 * Show or delete all patterns for an event.
1047 */
1048 if (*pat == NUL)
1049 {
1050 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next)
1051 {
1052 if (forceit) // delete the AutoPat, if it's in the current group
1053 {
1054 if (ap->group == findgroup)
1055 au_remove_pat(ap);
1056 }
1057 else if (group == AUGROUP_ALL || ap->group == group)
1058 show_autocmd(ap, event);
1059 }
1060 }
1061
1062 /*
1063 * Loop through all the specified patterns.
1064 */
1065 for ( ; *pat; pat = (*endpat == ',' ? endpat + 1 : endpat))
1066 {
1067 /*
1068 * Find end of the pattern.
1069 * Watch out for a comma in braces, like "*.\{obj,o\}".
1070 */
1071 brace_level = 0;
1072 for (endpat = pat; *endpat && (*endpat != ',' || brace_level
1073 || (endpat > pat && endpat[-1] == '\\')); ++endpat)
1074 {
1075 if (*endpat == '{')
1076 brace_level++;
1077 else if (*endpat == '}')
1078 brace_level--;
1079 }
1080 if (pat == endpat) // ignore single comma
1081 continue;
1082 patlen = (int)(endpat - pat);
1083
1084 /*
1085 * detect special <buflocal[=X]> buffer-local patterns
1086 */
1087 is_buflocal = FALSE;
1088 buflocal_nr = 0;
1089
1090 if (patlen >= 8 && STRNCMP(pat, "<buffer", 7) == 0
1091 && pat[patlen - 1] == '>')
1092 {
1093 // "<buffer...>": Error will be printed only for addition.
1094 // printing and removing will proceed silently.
1095 is_buflocal = TRUE;
1096 if (patlen == 8)
1097 // "<buffer>"
1098 buflocal_nr = curbuf->b_fnum;
1099 else if (patlen > 9 && pat[7] == '=')
1100 {
1101 if (patlen == 13 && STRNICMP(pat, "<buffer=abuf>", 13) == 0)
1102 // "<buffer=abuf>"
1103 buflocal_nr = autocmd_bufnr;
1104 else if (skipdigits(pat + 8) == pat + patlen - 1)
1105 // "<buffer=123>"
1106 buflocal_nr = atoi((char *)pat + 8);
1107 }
1108 }
1109
1110 if (is_buflocal)
1111 {
1112 // normalize pat into standard "<buffer>#N" form
1113 sprintf((char *)buflocal_pat, "<buffer=%d>", buflocal_nr);
1114 pat = buflocal_pat; // can modify pat and patlen
1115 patlen = (int)STRLEN(buflocal_pat); // but not endpat
1116 }
1117
1118 /*
1119 * Find AutoPat entries with this pattern. When adding a command it
1120 * always goes at or after the last one, so start at the end.
1121 */
1122 if (!forceit && *cmd != NUL && last_autopat[(int)event] != NULL)
1123 prev_ap = &last_autopat[(int)event];
1124 else
1125 prev_ap = &first_autopat[(int)event];
1126 while ((ap = *prev_ap) != NULL)
1127 {
1128 if (ap->pat != NULL)
1129 {
1130 /* Accept a pattern when:
1131 * - a group was specified and it's that group, or a group was
1132 * not specified and it's the current group, or a group was
1133 * not specified and we are listing
1134 * - the length of the pattern matches
1135 * - the pattern matches.
1136 * For <buffer[=X]>, this condition works because we normalize
1137 * all buffer-local patterns.
1138 */
1139 if ((allgroups || ap->group == findgroup)
1140 && ap->patlen == patlen
1141 && STRNCMP(pat, ap->pat, patlen) == 0)
1142 {
1143 /*
1144 * Remove existing autocommands.
1145 * If adding any new autocmd's for this AutoPat, don't
1146 * delete the pattern from the autopat list, append to
1147 * this list.
1148 */
1149 if (forceit)
1150 {
1151 if (*cmd != NUL && ap->next == NULL)
1152 {
1153 au_remove_cmds(ap);
1154 break;
1155 }
1156 au_remove_pat(ap);
1157 }
1158
1159 /*
1160 * Show autocmd's for this autopat, or buflocals <buffer=X>
1161 */
1162 else if (*cmd == NUL)
1163 show_autocmd(ap, event);
1164
1165 /*
1166 * Add autocmd to this autopat, if it's the last one.
1167 */
1168 else if (ap->next == NULL)
1169 break;
1170 }
1171 }
1172 prev_ap = &ap->next;
1173 }
1174
1175 /*
1176 * Add a new command.
1177 */
1178 if (*cmd != NUL)
1179 {
1180 /*
1181 * If the pattern we want to add a command to does appear at the
1182 * end of the list (or not is not in the list at all), add the
1183 * pattern at the end of the list.
1184 */
1185 if (ap == NULL)
1186 {
1187 /* refuse to add buffer-local ap if buffer number is invalid */
1188 if (is_buflocal && (buflocal_nr == 0
1189 || buflist_findnr(buflocal_nr) == NULL))
1190 {
1191 semsg(_("E680: <buffer=%d>: invalid buffer number "),
1192 buflocal_nr);
1193 return FAIL;
1194 }
1195
1196 ap = (AutoPat *)alloc((unsigned)sizeof(AutoPat));
1197 if (ap == NULL)
1198 return FAIL;
1199 ap->pat = vim_strnsave(pat, patlen);
1200 ap->patlen = patlen;
1201 if (ap->pat == NULL)
1202 {
1203 vim_free(ap);
1204 return FAIL;
1205 }
1206
1207 if (is_buflocal)
1208 {
1209 ap->buflocal_nr = buflocal_nr;
1210 ap->reg_prog = NULL;
1211 }
1212 else
1213 {
1214 char_u *reg_pat;
1215
1216 ap->buflocal_nr = 0;
1217 reg_pat = file_pat_to_reg_pat(pat, endpat,
1218 &ap->allow_dirs, TRUE);
1219 if (reg_pat != NULL)
1220 ap->reg_prog = vim_regcomp(reg_pat, RE_MAGIC);
1221 vim_free(reg_pat);
1222 if (reg_pat == NULL || ap->reg_prog == NULL)
1223 {
1224 vim_free(ap->pat);
1225 vim_free(ap);
1226 return FAIL;
1227 }
1228 }
1229 ap->cmds = NULL;
1230 *prev_ap = ap;
1231 last_autopat[(int)event] = ap;
1232 ap->next = NULL;
1233 if (group == AUGROUP_ALL)
1234 ap->group = current_augroup;
1235 else
1236 ap->group = group;
1237 }
1238
1239 /*
1240 * Add the autocmd at the end of the AutoCmd list.
1241 */
1242 prev_ac = &(ap->cmds);
1243 while ((ac = *prev_ac) != NULL)
1244 prev_ac = &ac->next;
1245 ac = (AutoCmd *)alloc((unsigned)sizeof(AutoCmd));
1246 if (ac == NULL)
1247 return FAIL;
1248 ac->cmd = vim_strsave(cmd);
1249#ifdef FEAT_EVAL
1250 ac->script_ctx = current_sctx;
1251 ac->script_ctx.sc_lnum += sourcing_lnum;
1252#endif
1253 if (ac->cmd == NULL)
1254 {
1255 vim_free(ac);
1256 return FAIL;
1257 }
1258 ac->next = NULL;
1259 *prev_ac = ac;
Bram Moolenaareb93f3f2019-04-04 15:04:56 +02001260 ac->once = once;
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01001261 ac->nested = nested;
1262 }
1263 }
1264
1265 au_cleanup(); // may really delete removed patterns/commands now
1266 return OK;
1267}
1268
1269/*
1270 * Implementation of ":doautocmd [group] event [fname]".
1271 * Return OK for success, FAIL for failure;
1272 */
1273 int
1274do_doautocmd(
1275 char_u *arg,
1276 int do_msg, // give message for no matching autocmds?
1277 int *did_something)
1278{
1279 char_u *fname;
1280 int nothing_done = TRUE;
1281 int group;
1282
1283 if (did_something != NULL)
1284 *did_something = FALSE;
1285
1286 /*
1287 * Check for a legal group name. If not, use AUGROUP_ALL.
1288 */
1289 group = au_get_grouparg(&arg);
1290 if (arg == NULL) // out of memory
1291 return FAIL;
1292
1293 if (*arg == '*')
1294 {
1295 emsg(_("E217: Can't execute autocommands for ALL events"));
1296 return FAIL;
1297 }
1298
1299 /*
1300 * Scan over the events.
1301 * If we find an illegal name, return here, don't do anything.
1302 */
1303 fname = find_end_event(arg, group != AUGROUP_ALL);
1304 if (fname == NULL)
1305 return FAIL;
1306
1307 fname = skipwhite(fname);
1308
1309 /*
1310 * Loop over the events.
1311 */
1312 while (*arg && !ends_excmd(*arg) && !VIM_ISWHITE(*arg))
1313 if (apply_autocmds_group(event_name2nr(arg, &arg),
1314 fname, NULL, TRUE, group, curbuf, NULL))
1315 nothing_done = FALSE;
1316
1317 if (nothing_done && do_msg)
1318 msg(_("No matching autocommands"));
1319 if (did_something != NULL)
1320 *did_something = !nothing_done;
1321
1322#ifdef FEAT_EVAL
1323 return aborting() ? FAIL : OK;
1324#else
1325 return OK;
1326#endif
1327}
1328
1329/*
1330 * ":doautoall": execute autocommands for each loaded buffer.
1331 */
1332 void
1333ex_doautoall(exarg_T *eap)
1334{
1335 int retval;
1336 aco_save_T aco;
1337 buf_T *buf;
1338 bufref_T bufref;
1339 char_u *arg = eap->arg;
1340 int call_do_modelines = check_nomodeline(&arg);
1341 int did_aucmd;
1342
1343 /*
1344 * This is a bit tricky: For some commands curwin->w_buffer needs to be
1345 * equal to curbuf, but for some buffers there may not be a window.
1346 * So we change the buffer for the current window for a moment. This
1347 * gives problems when the autocommands make changes to the list of
1348 * buffers or windows...
1349 */
1350 FOR_ALL_BUFFERS(buf)
1351 {
1352 if (buf->b_ml.ml_mfp != NULL)
1353 {
1354 // find a window for this buffer and save some values
1355 aucmd_prepbuf(&aco, buf);
1356 set_bufref(&bufref, buf);
1357
1358 // execute the autocommands for this buffer
1359 retval = do_doautocmd(arg, FALSE, &did_aucmd);
1360
1361 if (call_do_modelines && did_aucmd)
1362 {
1363 // Execute the modeline settings, but don't set window-local
1364 // options if we are using the current window for another
1365 // buffer.
1366 do_modelines(curwin == aucmd_win ? OPT_NOWIN : 0);
1367 }
1368
1369 // restore the current window
1370 aucmd_restbuf(&aco);
1371
1372 // stop if there is some error or buffer was deleted
1373 if (retval == FAIL || !bufref_valid(&bufref))
1374 break;
1375 }
1376 }
1377
1378 check_cursor(); // just in case lines got deleted
1379}
1380
1381/*
1382 * Check *argp for <nomodeline>. When it is present return FALSE, otherwise
1383 * return TRUE and advance *argp to after it.
1384 * Thus return TRUE when do_modelines() should be called.
1385 */
1386 int
1387check_nomodeline(char_u **argp)
1388{
1389 if (STRNCMP(*argp, "<nomodeline>", 12) == 0)
1390 {
1391 *argp = skipwhite(*argp + 12);
1392 return FALSE;
1393 }
1394 return TRUE;
1395}
1396
1397/*
1398 * Prepare for executing autocommands for (hidden) buffer "buf".
1399 * Search for a visible window containing the current buffer. If there isn't
1400 * one then use "aucmd_win".
1401 * Set "curbuf" and "curwin" to match "buf".
1402 */
1403 void
1404aucmd_prepbuf(
1405 aco_save_T *aco, // structure to save values in
1406 buf_T *buf) // new curbuf
1407{
1408 win_T *win;
1409 int save_ea;
1410#ifdef FEAT_AUTOCHDIR
1411 int save_acd;
1412#endif
1413
1414 // Find a window that is for the new buffer
1415 if (buf == curbuf) // be quick when buf is curbuf
1416 win = curwin;
1417 else
1418 FOR_ALL_WINDOWS(win)
1419 if (win->w_buffer == buf)
1420 break;
1421
1422 // Allocate "aucmd_win" when needed. If this fails (out of memory) fall
1423 // back to using the current window.
1424 if (win == NULL && aucmd_win == NULL)
1425 {
1426 win_alloc_aucmd_win();
1427 if (aucmd_win == NULL)
1428 win = curwin;
1429 }
1430 if (win == NULL && aucmd_win_used)
1431 // Strange recursive autocommand, fall back to using the current
1432 // window. Expect a few side effects...
1433 win = curwin;
1434
1435 aco->save_curwin = curwin;
1436 aco->save_curbuf = curbuf;
1437 aco->save_prevwin = prevwin;
1438 if (win != NULL)
1439 {
1440 // There is a window for "buf" in the current tab page, make it the
1441 // curwin. This is preferred, it has the least side effects (esp. if
1442 // "buf" is curbuf).
1443 aco->use_aucmd_win = FALSE;
1444 curwin = win;
1445 }
1446 else
1447 {
1448 // There is no window for "buf", use "aucmd_win". To minimize the side
1449 // effects, insert it in the current tab page.
1450 // Anything related to a window (e.g., setting folds) may have
1451 // unexpected results.
1452 aco->use_aucmd_win = TRUE;
1453 aucmd_win_used = TRUE;
1454 aucmd_win->w_buffer = buf;
1455#if defined(FEAT_SYN_HL) || defined(FEAT_SPELL)
1456 aucmd_win->w_s = &buf->b_s;
1457#endif
1458 ++buf->b_nwindows;
1459 win_init_empty(aucmd_win); // set cursor and topline to safe values
1460
1461 // Make sure w_localdir and globaldir are NULL to avoid a chdir() in
1462 // win_enter_ext().
1463 VIM_CLEAR(aucmd_win->w_localdir);
1464 aco->globaldir = globaldir;
1465 globaldir = NULL;
1466
1467
1468 // Split the current window, put the aucmd_win in the upper half.
1469 // We don't want the BufEnter or WinEnter autocommands.
1470 block_autocmds();
1471 make_snapshot(SNAP_AUCMD_IDX);
1472 save_ea = p_ea;
1473 p_ea = FALSE;
1474
1475#ifdef FEAT_AUTOCHDIR
1476 // Prevent chdir() call in win_enter_ext(), through do_autochdir().
1477 save_acd = p_acd;
1478 p_acd = FALSE;
1479#endif
1480
1481 (void)win_split_ins(0, WSP_TOP, aucmd_win, 0);
1482 (void)win_comp_pos(); // recompute window positions
1483 p_ea = save_ea;
1484#ifdef FEAT_AUTOCHDIR
1485 p_acd = save_acd;
1486#endif
1487 unblock_autocmds();
1488 curwin = aucmd_win;
1489 }
1490 curbuf = buf;
1491 aco->new_curwin = curwin;
1492 set_bufref(&aco->new_curbuf, curbuf);
1493}
1494
1495/*
1496 * Cleanup after executing autocommands for a (hidden) buffer.
1497 * Restore the window as it was (if possible).
1498 */
1499 void
1500aucmd_restbuf(
1501 aco_save_T *aco) // structure holding saved values
1502{
1503 int dummy;
1504
1505 if (aco->use_aucmd_win)
1506 {
1507 --curbuf->b_nwindows;
1508 // Find "aucmd_win", it can't be closed, but it may be in another tab
1509 // page. Do not trigger autocommands here.
1510 block_autocmds();
1511 if (curwin != aucmd_win)
1512 {
1513 tabpage_T *tp;
1514 win_T *wp;
1515
1516 FOR_ALL_TAB_WINDOWS(tp, wp)
1517 {
1518 if (wp == aucmd_win)
1519 {
1520 if (tp != curtab)
1521 goto_tabpage_tp(tp, TRUE, TRUE);
1522 win_goto(aucmd_win);
1523 goto win_found;
1524 }
1525 }
1526 }
1527win_found:
1528
1529 // Remove the window and frame from the tree of frames.
1530 (void)winframe_remove(curwin, &dummy, NULL);
1531 win_remove(curwin, NULL);
1532 aucmd_win_used = FALSE;
1533 last_status(FALSE); // may need to remove last status line
1534
1535 if (!valid_tabpage_win(curtab))
1536 // no valid window in current tabpage
1537 close_tabpage(curtab);
1538
1539 restore_snapshot(SNAP_AUCMD_IDX, FALSE);
1540 (void)win_comp_pos(); // recompute window positions
1541 unblock_autocmds();
1542
1543 if (win_valid(aco->save_curwin))
1544 curwin = aco->save_curwin;
1545 else
1546 // Hmm, original window disappeared. Just use the first one.
1547 curwin = firstwin;
1548 if (win_valid(aco->save_prevwin))
1549 prevwin = aco->save_prevwin;
1550#ifdef FEAT_EVAL
1551 vars_clear(&aucmd_win->w_vars->dv_hashtab); // free all w: variables
1552 hash_init(&aucmd_win->w_vars->dv_hashtab); // re-use the hashtab
1553#endif
1554 curbuf = curwin->w_buffer;
1555
1556 vim_free(globaldir);
1557 globaldir = aco->globaldir;
1558
1559 // the buffer contents may have changed
1560 check_cursor();
1561 if (curwin->w_topline > curbuf->b_ml.ml_line_count)
1562 {
1563 curwin->w_topline = curbuf->b_ml.ml_line_count;
1564#ifdef FEAT_DIFF
1565 curwin->w_topfill = 0;
1566#endif
1567 }
1568#if defined(FEAT_GUI)
1569 // Hide the scrollbars from the aucmd_win and update.
1570 gui_mch_enable_scrollbar(&aucmd_win->w_scrollbars[SBAR_LEFT], FALSE);
1571 gui_mch_enable_scrollbar(&aucmd_win->w_scrollbars[SBAR_RIGHT], FALSE);
1572 gui_may_update_scrollbars();
1573#endif
1574 }
1575 else
1576 {
1577 // restore curwin
1578 if (win_valid(aco->save_curwin))
1579 {
1580 // Restore the buffer which was previously edited by curwin, if
1581 // it was changed, we are still the same window and the buffer is
1582 // valid.
1583 if (curwin == aco->new_curwin
1584 && curbuf != aco->new_curbuf.br_buf
1585 && bufref_valid(&aco->new_curbuf)
1586 && aco->new_curbuf.br_buf->b_ml.ml_mfp != NULL)
1587 {
1588# if defined(FEAT_SYN_HL) || defined(FEAT_SPELL)
1589 if (curwin->w_s == &curbuf->b_s)
1590 curwin->w_s = &aco->new_curbuf.br_buf->b_s;
1591# endif
1592 --curbuf->b_nwindows;
1593 curbuf = aco->new_curbuf.br_buf;
1594 curwin->w_buffer = curbuf;
1595 ++curbuf->b_nwindows;
1596 }
1597
1598 curwin = aco->save_curwin;
1599 curbuf = curwin->w_buffer;
1600 if (win_valid(aco->save_prevwin))
1601 prevwin = aco->save_prevwin;
1602 // In case the autocommand move the cursor to a position that that
1603 // not exist in curbuf.
1604 check_cursor();
1605 }
1606 }
1607}
1608
1609static int autocmd_nested = FALSE;
1610
1611/*
1612 * Execute autocommands for "event" and file name "fname".
1613 * Return TRUE if some commands were executed.
1614 */
1615 int
1616apply_autocmds(
1617 event_T event,
1618 char_u *fname, // NULL or empty means use actual file name
1619 char_u *fname_io, // fname to use for <afile> on cmdline
1620 int force, // when TRUE, ignore autocmd_busy
1621 buf_T *buf) // buffer for <abuf>
1622{
1623 return apply_autocmds_group(event, fname, fname_io, force,
1624 AUGROUP_ALL, buf, NULL);
1625}
1626
1627/*
1628 * Like apply_autocmds(), but with extra "eap" argument. This takes care of
1629 * setting v:filearg.
1630 */
1631 int
1632apply_autocmds_exarg(
1633 event_T event,
1634 char_u *fname,
1635 char_u *fname_io,
1636 int force,
1637 buf_T *buf,
1638 exarg_T *eap)
1639{
1640 return apply_autocmds_group(event, fname, fname_io, force,
1641 AUGROUP_ALL, buf, eap);
1642}
1643
1644/*
1645 * Like apply_autocmds(), but handles the caller's retval. If the script
1646 * processing is being aborted or if retval is FAIL when inside a try
1647 * conditional, no autocommands are executed. If otherwise the autocommands
1648 * cause the script to be aborted, retval is set to FAIL.
1649 */
1650 int
1651apply_autocmds_retval(
1652 event_T event,
1653 char_u *fname, // NULL or empty means use actual file name
1654 char_u *fname_io, // fname to use for <afile> on cmdline
1655 int force, // when TRUE, ignore autocmd_busy
1656 buf_T *buf, // buffer for <abuf>
1657 int *retval) // pointer to caller's retval
1658{
1659 int did_cmd;
1660
1661#ifdef FEAT_EVAL
1662 if (should_abort(*retval))
1663 return FALSE;
1664#endif
1665
1666 did_cmd = apply_autocmds_group(event, fname, fname_io, force,
1667 AUGROUP_ALL, buf, NULL);
1668 if (did_cmd
1669#ifdef FEAT_EVAL
1670 && aborting()
1671#endif
1672 )
1673 *retval = FAIL;
1674 return did_cmd;
1675}
1676
1677/*
1678 * Return TRUE when there is a CursorHold autocommand defined.
1679 */
1680 int
1681has_cursorhold(void)
1682{
1683 return (first_autopat[(int)(get_real_state() == NORMAL_BUSY
1684 ? EVENT_CURSORHOLD : EVENT_CURSORHOLDI)] != NULL);
1685}
1686
1687/*
1688 * Return TRUE if the CursorHold event can be triggered.
1689 */
1690 int
1691trigger_cursorhold(void)
1692{
1693 int state;
1694
1695 if (!did_cursorhold
1696 && has_cursorhold()
1697 && reg_recording == 0
1698 && typebuf.tb_len == 0
1699#ifdef FEAT_INS_EXPAND
1700 && !ins_compl_active()
1701#endif
1702 )
1703 {
1704 state = get_real_state();
1705 if (state == NORMAL_BUSY || (state & INSERT) != 0)
1706 return TRUE;
1707 }
1708 return FALSE;
1709}
1710
1711/*
1712 * Return TRUE when there is a CursorMoved autocommand defined.
1713 */
1714 int
1715has_cursormoved(void)
1716{
1717 return (first_autopat[(int)EVENT_CURSORMOVED] != NULL);
1718}
1719
1720#if defined(FEAT_CONCEAL) || defined(PROTO)
1721/*
1722 * Return TRUE when there is a CursorMovedI autocommand defined.
1723 */
1724 int
1725has_cursormovedI(void)
1726{
1727 return (first_autopat[(int)EVENT_CURSORMOVEDI] != NULL);
1728}
1729#endif
1730
1731/*
1732 * Return TRUE when there is a TextChanged autocommand defined.
1733 */
1734 int
1735has_textchanged(void)
1736{
1737 return (first_autopat[(int)EVENT_TEXTCHANGED] != NULL);
1738}
1739
1740/*
1741 * Return TRUE when there is a TextChangedI autocommand defined.
1742 */
1743 int
1744has_textchangedI(void)
1745{
1746 return (first_autopat[(int)EVENT_TEXTCHANGEDI] != NULL);
1747}
1748
1749#if defined(FEAT_INS_EXPAND) || defined(PROTO)
1750/*
1751 * Return TRUE when there is a TextChangedP autocommand defined.
1752 */
1753 int
1754has_textchangedP(void)
1755{
1756 return (first_autopat[(int)EVENT_TEXTCHANGEDP] != NULL);
1757}
1758#endif
1759
1760/*
1761 * Return TRUE when there is an InsertCharPre autocommand defined.
1762 */
1763 int
1764has_insertcharpre(void)
1765{
1766 return (first_autopat[(int)EVENT_INSERTCHARPRE] != NULL);
1767}
1768
1769/*
1770 * Return TRUE when there is an CmdUndefined autocommand defined.
1771 */
1772 int
1773has_cmdundefined(void)
1774{
1775 return (first_autopat[(int)EVENT_CMDUNDEFINED] != NULL);
1776}
1777
1778/*
1779 * Return TRUE when there is an FuncUndefined autocommand defined.
1780 */
1781 int
1782has_funcundefined(void)
1783{
1784 return (first_autopat[(int)EVENT_FUNCUNDEFINED] != NULL);
1785}
1786
1787#if defined(FEAT_EVAL) || defined(PROTO)
1788/*
1789 * Return TRUE when there is a TextYankPost autocommand defined.
1790 */
1791 int
1792has_textyankpost(void)
1793{
1794 return (first_autopat[(int)EVENT_TEXTYANKPOST] != NULL);
1795}
1796#endif
1797
Bram Moolenaard7f246c2019-04-08 18:15:41 +02001798#if defined(FEAT_EVAL) || defined(PROTO)
1799/*
1800 * Return TRUE when there is a CompleteChanged autocommand defined.
1801 */
1802 int
1803has_completechanged(void)
1804{
1805 return (first_autopat[(int)EVENT_COMPLETECHANGED] != NULL);
1806}
1807#endif
1808
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01001809/*
1810 * Execute autocommands for "event" and file name "fname".
1811 * Return TRUE if some commands were executed.
1812 */
1813 static int
1814apply_autocmds_group(
1815 event_T event,
1816 char_u *fname, // NULL or empty means use actual file name
1817 char_u *fname_io, // fname to use for <afile> on cmdline, NULL means
1818 // use fname
1819 int force, // when TRUE, ignore autocmd_busy
1820 int group, // group ID, or AUGROUP_ALL
1821 buf_T *buf, // buffer for <abuf>
1822 exarg_T *eap UNUSED) // command arguments
1823{
1824 char_u *sfname = NULL; // short file name
1825 char_u *tail;
1826 int save_changed;
1827 buf_T *old_curbuf;
1828 int retval = FALSE;
1829 char_u *save_sourcing_name;
1830 linenr_T save_sourcing_lnum;
1831 char_u *save_autocmd_fname;
1832 int save_autocmd_fname_full;
1833 int save_autocmd_bufnr;
1834 char_u *save_autocmd_match;
1835 int save_autocmd_busy;
1836 int save_autocmd_nested;
1837 static int nesting = 0;
1838 AutoPatCmd patcmd;
1839 AutoPat *ap;
1840#ifdef FEAT_EVAL
1841 sctx_T save_current_sctx;
1842 funccal_entry_T funccal_entry;
1843 char_u *save_cmdarg;
1844 long save_cmdbang;
1845#endif
1846 static int filechangeshell_busy = FALSE;
1847#ifdef FEAT_PROFILE
1848 proftime_T wait_time;
1849#endif
1850 int did_save_redobuff = FALSE;
1851 save_redo_T save_redo;
1852 int save_KeyTyped = KeyTyped;
1853
1854 /*
1855 * Quickly return if there are no autocommands for this event or
1856 * autocommands are blocked.
1857 */
1858 if (event == NUM_EVENTS || first_autopat[(int)event] == NULL
1859 || autocmd_blocked > 0)
1860 goto BYPASS_AU;
1861
1862 /*
1863 * When autocommands are busy, new autocommands are only executed when
1864 * explicitly enabled with the "nested" flag.
1865 */
1866 if (autocmd_busy && !(force || autocmd_nested))
1867 goto BYPASS_AU;
1868
1869#ifdef FEAT_EVAL
1870 /*
1871 * Quickly return when immediately aborting on error, or when an interrupt
1872 * occurred or an exception was thrown but not caught.
1873 */
1874 if (aborting())
1875 goto BYPASS_AU;
1876#endif
1877
1878 /*
1879 * FileChangedShell never nests, because it can create an endless loop.
1880 */
1881 if (filechangeshell_busy && (event == EVENT_FILECHANGEDSHELL
1882 || event == EVENT_FILECHANGEDSHELLPOST))
1883 goto BYPASS_AU;
1884
1885 /*
1886 * Ignore events in 'eventignore'.
1887 */
1888 if (event_ignored(event))
1889 goto BYPASS_AU;
1890
1891 /*
1892 * Allow nesting of autocommands, but restrict the depth, because it's
1893 * possible to create an endless loop.
1894 */
1895 if (nesting == 10)
1896 {
1897 emsg(_("E218: autocommand nesting too deep"));
1898 goto BYPASS_AU;
1899 }
1900
1901 /*
1902 * Check if these autocommands are disabled. Used when doing ":all" or
1903 * ":ball".
1904 */
1905 if ( (autocmd_no_enter
1906 && (event == EVENT_WINENTER || event == EVENT_BUFENTER))
1907 || (autocmd_no_leave
1908 && (event == EVENT_WINLEAVE || event == EVENT_BUFLEAVE)))
1909 goto BYPASS_AU;
1910
1911 /*
1912 * Save the autocmd_* variables and info about the current buffer.
1913 */
1914 save_autocmd_fname = autocmd_fname;
1915 save_autocmd_fname_full = autocmd_fname_full;
1916 save_autocmd_bufnr = autocmd_bufnr;
1917 save_autocmd_match = autocmd_match;
1918 save_autocmd_busy = autocmd_busy;
1919 save_autocmd_nested = autocmd_nested;
1920 save_changed = curbuf->b_changed;
1921 old_curbuf = curbuf;
1922
1923 /*
1924 * Set the file name to be used for <afile>.
1925 * Make a copy to avoid that changing a buffer name or directory makes it
1926 * invalid.
1927 */
1928 if (fname_io == NULL)
1929 {
1930 if (event == EVENT_COLORSCHEME || event == EVENT_COLORSCHEMEPRE
1931 || event == EVENT_OPTIONSET)
1932 autocmd_fname = NULL;
1933 else if (fname != NULL && !ends_excmd(*fname))
1934 autocmd_fname = fname;
1935 else if (buf != NULL)
1936 autocmd_fname = buf->b_ffname;
1937 else
1938 autocmd_fname = NULL;
1939 }
1940 else
1941 autocmd_fname = fname_io;
1942 if (autocmd_fname != NULL)
1943 autocmd_fname = vim_strsave(autocmd_fname);
1944 autocmd_fname_full = FALSE; // call FullName_save() later
1945
1946 /*
1947 * Set the buffer number to be used for <abuf>.
1948 */
1949 if (buf == NULL)
1950 autocmd_bufnr = 0;
1951 else
1952 autocmd_bufnr = buf->b_fnum;
1953
1954 /*
1955 * When the file name is NULL or empty, use the file name of buffer "buf".
1956 * Always use the full path of the file name to match with, in case
1957 * "allow_dirs" is set.
1958 */
1959 if (fname == NULL || *fname == NUL)
1960 {
1961 if (buf == NULL)
1962 fname = NULL;
1963 else
1964 {
1965#ifdef FEAT_SYN_HL
1966 if (event == EVENT_SYNTAX)
1967 fname = buf->b_p_syn;
1968 else
1969#endif
1970 if (event == EVENT_FILETYPE)
1971 fname = buf->b_p_ft;
1972 else
1973 {
1974 if (buf->b_sfname != NULL)
1975 sfname = vim_strsave(buf->b_sfname);
1976 fname = buf->b_ffname;
1977 }
1978 }
1979 if (fname == NULL)
1980 fname = (char_u *)"";
1981 fname = vim_strsave(fname); // make a copy, so we can change it
1982 }
1983 else
1984 {
1985 sfname = vim_strsave(fname);
1986 // Don't try expanding FileType, Syntax, FuncUndefined, WindowID,
1987 // ColorScheme, QuickFixCmd* or DirChanged
1988 if (event == EVENT_FILETYPE
1989 || event == EVENT_SYNTAX
1990 || event == EVENT_CMDLINECHANGED
1991 || event == EVENT_CMDLINEENTER
1992 || event == EVENT_CMDLINELEAVE
1993 || event == EVENT_CMDWINENTER
1994 || event == EVENT_CMDWINLEAVE
1995 || event == EVENT_CMDUNDEFINED
1996 || event == EVENT_FUNCUNDEFINED
1997 || event == EVENT_REMOTEREPLY
1998 || event == EVENT_SPELLFILEMISSING
1999 || event == EVENT_QUICKFIXCMDPRE
2000 || event == EVENT_COLORSCHEME
2001 || event == EVENT_COLORSCHEMEPRE
2002 || event == EVENT_OPTIONSET
2003 || event == EVENT_QUICKFIXCMDPOST
2004 || event == EVENT_DIRCHANGED)
2005 {
2006 fname = vim_strsave(fname);
2007 autocmd_fname_full = TRUE; // don't expand it later
2008 }
2009 else
2010 fname = FullName_save(fname, FALSE);
2011 }
2012 if (fname == NULL) // out of memory
2013 {
2014 vim_free(sfname);
2015 retval = FALSE;
2016 goto BYPASS_AU;
2017 }
2018
2019#ifdef BACKSLASH_IN_FILENAME
2020 /*
2021 * Replace all backslashes with forward slashes. This makes the
2022 * autocommand patterns portable between Unix and MS-DOS.
2023 */
2024 if (sfname != NULL)
2025 forward_slash(sfname);
2026 forward_slash(fname);
2027#endif
2028
2029#ifdef VMS
2030 // remove version for correct match
2031 if (sfname != NULL)
2032 vms_remove_version(sfname);
2033 vms_remove_version(fname);
2034#endif
2035
2036 /*
2037 * Set the name to be used for <amatch>.
2038 */
2039 autocmd_match = fname;
2040
2041
2042 // Don't redraw while doing autocommands.
2043 ++RedrawingDisabled;
2044 save_sourcing_name = sourcing_name;
2045 sourcing_name = NULL; // don't free this one
2046 save_sourcing_lnum = sourcing_lnum;
2047 sourcing_lnum = 0; // no line number here
2048
2049#ifdef FEAT_EVAL
2050 save_current_sctx = current_sctx;
2051
2052# ifdef FEAT_PROFILE
2053 if (do_profiling == PROF_YES)
2054 prof_child_enter(&wait_time); // doesn't count for the caller itself
2055# endif
2056
2057 // Don't use local function variables, if called from a function.
2058 save_funccal(&funccal_entry);
2059#endif
2060
2061 /*
2062 * When starting to execute autocommands, save the search patterns.
2063 */
2064 if (!autocmd_busy)
2065 {
2066 save_search_patterns();
2067#ifdef FEAT_INS_EXPAND
2068 if (!ins_compl_active())
2069#endif
2070 {
2071 saveRedobuff(&save_redo);
2072 did_save_redobuff = TRUE;
2073 }
2074 did_filetype = keep_filetype;
2075 }
2076
2077 /*
2078 * Note that we are applying autocmds. Some commands need to know.
2079 */
2080 autocmd_busy = TRUE;
2081 filechangeshell_busy = (event == EVENT_FILECHANGEDSHELL);
2082 ++nesting; // see matching decrement below
2083
2084 // Remember that FileType was triggered. Used for did_filetype().
2085 if (event == EVENT_FILETYPE)
2086 did_filetype = TRUE;
2087
2088 tail = gettail(fname);
2089
2090 // Find first autocommand that matches
2091 patcmd.curpat = first_autopat[(int)event];
2092 patcmd.nextcmd = NULL;
2093 patcmd.group = group;
2094 patcmd.fname = fname;
2095 patcmd.sfname = sfname;
2096 patcmd.tail = tail;
2097 patcmd.event = event;
2098 patcmd.arg_bufnr = autocmd_bufnr;
2099 patcmd.next = NULL;
2100 auto_next_pat(&patcmd, FALSE);
2101
2102 // found one, start executing the autocommands
2103 if (patcmd.curpat != NULL)
2104 {
2105 // add to active_apc_list
2106 patcmd.next = active_apc_list;
2107 active_apc_list = &patcmd;
2108
2109#ifdef FEAT_EVAL
2110 // set v:cmdarg (only when there is a matching pattern)
2111 save_cmdbang = (long)get_vim_var_nr(VV_CMDBANG);
2112 if (eap != NULL)
2113 {
2114 save_cmdarg = set_cmdarg(eap, NULL);
2115 set_vim_var_nr(VV_CMDBANG, (long)eap->forceit);
2116 }
2117 else
2118 save_cmdarg = NULL; // avoid gcc warning
2119#endif
2120 retval = TRUE;
2121 // mark the last pattern, to avoid an endless loop when more patterns
2122 // are added when executing autocommands
2123 for (ap = patcmd.curpat; ap->next != NULL; ap = ap->next)
2124 ap->last = FALSE;
2125 ap->last = TRUE;
Bram Moolenaara68e5952019-04-25 22:22:01 +02002126
2127 // make sure cursor and topline are valid
2128 check_lnums(TRUE);
2129
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01002130 do_cmdline(NULL, getnextac, (void *)&patcmd,
2131 DOCMD_NOWAIT|DOCMD_VERBOSE|DOCMD_REPEAT);
Bram Moolenaara68e5952019-04-25 22:22:01 +02002132
2133 // restore cursor and topline, unless they were changed
2134 reset_lnums();
2135
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01002136#ifdef FEAT_EVAL
2137 if (eap != NULL)
2138 {
2139 (void)set_cmdarg(NULL, save_cmdarg);
2140 set_vim_var_nr(VV_CMDBANG, save_cmdbang);
2141 }
2142#endif
2143 // delete from active_apc_list
2144 if (active_apc_list == &patcmd) // just in case
2145 active_apc_list = patcmd.next;
2146 }
2147
2148 --RedrawingDisabled;
2149 autocmd_busy = save_autocmd_busy;
2150 filechangeshell_busy = FALSE;
2151 autocmd_nested = save_autocmd_nested;
2152 vim_free(sourcing_name);
2153 sourcing_name = save_sourcing_name;
2154 sourcing_lnum = save_sourcing_lnum;
2155 vim_free(autocmd_fname);
2156 autocmd_fname = save_autocmd_fname;
2157 autocmd_fname_full = save_autocmd_fname_full;
2158 autocmd_bufnr = save_autocmd_bufnr;
2159 autocmd_match = save_autocmd_match;
2160#ifdef FEAT_EVAL
2161 current_sctx = save_current_sctx;
2162 restore_funccal();
2163# ifdef FEAT_PROFILE
2164 if (do_profiling == PROF_YES)
2165 prof_child_exit(&wait_time);
2166# endif
2167#endif
2168 KeyTyped = save_KeyTyped;
2169 vim_free(fname);
2170 vim_free(sfname);
2171 --nesting; // see matching increment above
2172
2173 /*
2174 * When stopping to execute autocommands, restore the search patterns and
2175 * the redo buffer. Free any buffers in the au_pending_free_buf list and
2176 * free any windows in the au_pending_free_win list.
2177 */
2178 if (!autocmd_busy)
2179 {
2180 restore_search_patterns();
2181 if (did_save_redobuff)
2182 restoreRedobuff(&save_redo);
2183 did_filetype = FALSE;
2184 while (au_pending_free_buf != NULL)
2185 {
2186 buf_T *b = au_pending_free_buf->b_next;
2187 vim_free(au_pending_free_buf);
2188 au_pending_free_buf = b;
2189 }
2190 while (au_pending_free_win != NULL)
2191 {
2192 win_T *w = au_pending_free_win->w_next;
2193 vim_free(au_pending_free_win);
2194 au_pending_free_win = w;
2195 }
2196 }
2197
2198 /*
2199 * Some events don't set or reset the Changed flag.
2200 * Check if still in the same buffer!
2201 */
2202 if (curbuf == old_curbuf
2203 && (event == EVENT_BUFREADPOST
2204 || event == EVENT_BUFWRITEPOST
2205 || event == EVENT_FILEAPPENDPOST
2206 || event == EVENT_VIMLEAVE
2207 || event == EVENT_VIMLEAVEPRE))
2208 {
2209#ifdef FEAT_TITLE
2210 if (curbuf->b_changed != save_changed)
2211 need_maketitle = TRUE;
2212#endif
2213 curbuf->b_changed = save_changed;
2214 }
2215
2216 au_cleanup(); // may really delete removed patterns/commands now
2217
2218BYPASS_AU:
2219 // When wiping out a buffer make sure all its buffer-local autocommands
2220 // are deleted.
2221 if (event == EVENT_BUFWIPEOUT && buf != NULL)
2222 aubuflocal_remove(buf);
2223
2224 if (retval == OK && event == EVENT_FILETYPE)
2225 au_did_filetype = TRUE;
2226
2227 return retval;
2228}
2229
2230# ifdef FEAT_EVAL
2231static char_u *old_termresponse = NULL;
2232# endif
2233
2234/*
2235 * Block triggering autocommands until unblock_autocmd() is called.
2236 * Can be used recursively, so long as it's symmetric.
2237 */
2238 void
2239block_autocmds(void)
2240{
2241# ifdef FEAT_EVAL
2242 // Remember the value of v:termresponse.
2243 if (autocmd_blocked == 0)
2244 old_termresponse = get_vim_var_str(VV_TERMRESPONSE);
2245# endif
2246 ++autocmd_blocked;
2247}
2248
2249 void
2250unblock_autocmds(void)
2251{
2252 --autocmd_blocked;
2253
2254# ifdef FEAT_EVAL
2255 // When v:termresponse was set while autocommands were blocked, trigger
2256 // the autocommands now. Esp. useful when executing a shell command
2257 // during startup (vimdiff).
2258 if (autocmd_blocked == 0
2259 && get_vim_var_str(VV_TERMRESPONSE) != old_termresponse)
2260 apply_autocmds(EVENT_TERMRESPONSE, NULL, NULL, FALSE, curbuf);
2261# endif
2262}
2263
2264#if defined(FEAT_EVAL) && (defined(FEAT_XIM) || defined(IME_WITHOUT_XIM)) \
2265 || defined(PROTO)
2266 int
2267is_autocmd_blocked(void)
2268{
2269 return autocmd_blocked != 0;
2270}
2271#endif
2272
2273/*
2274 * Find next autocommand pattern that matches.
2275 */
2276 static void
2277auto_next_pat(
2278 AutoPatCmd *apc,
2279 int stop_at_last) // stop when 'last' flag is set
2280{
2281 AutoPat *ap;
2282 AutoCmd *cp;
2283 char_u *name;
2284 char *s;
2285
2286 VIM_CLEAR(sourcing_name);
2287
2288 for (ap = apc->curpat; ap != NULL && !got_int; ap = ap->next)
2289 {
2290 apc->curpat = NULL;
2291
2292 // Only use a pattern when it has not been removed, has commands and
2293 // the group matches. For buffer-local autocommands only check the
2294 // buffer number.
2295 if (ap->pat != NULL && ap->cmds != NULL
2296 && (apc->group == AUGROUP_ALL || apc->group == ap->group))
2297 {
2298 // execution-condition
2299 if (ap->buflocal_nr == 0
2300 ? (match_file_pat(NULL, &ap->reg_prog, apc->fname,
2301 apc->sfname, apc->tail, ap->allow_dirs))
2302 : ap->buflocal_nr == apc->arg_bufnr)
2303 {
2304 name = event_nr2name(apc->event);
2305 s = _("%s Autocommands for \"%s\"");
2306 sourcing_name = alloc((unsigned)(STRLEN(s)
2307 + STRLEN(name) + ap->patlen + 1));
2308 if (sourcing_name != NULL)
2309 {
2310 sprintf((char *)sourcing_name, s,
2311 (char *)name, (char *)ap->pat);
2312 if (p_verbose >= 8)
2313 {
2314 verbose_enter();
2315 smsg(_("Executing %s"), sourcing_name);
2316 verbose_leave();
2317 }
2318 }
2319
2320 apc->curpat = ap;
2321 apc->nextcmd = ap->cmds;
2322 // mark last command
2323 for (cp = ap->cmds; cp->next != NULL; cp = cp->next)
2324 cp->last = FALSE;
2325 cp->last = TRUE;
2326 }
2327 line_breakcheck();
2328 if (apc->curpat != NULL) // found a match
2329 break;
2330 }
2331 if (stop_at_last && ap->last)
2332 break;
2333 }
2334}
2335
2336/*
2337 * Get next autocommand command.
2338 * Called by do_cmdline() to get the next line for ":if".
2339 * Returns allocated string, or NULL for end of autocommands.
2340 */
2341 char_u *
2342getnextac(int c UNUSED, void *cookie, int indent UNUSED)
2343{
2344 AutoPatCmd *acp = (AutoPatCmd *)cookie;
2345 char_u *retval;
2346 AutoCmd *ac;
2347
2348 // Can be called again after returning the last line.
2349 if (acp->curpat == NULL)
2350 return NULL;
2351
2352 // repeat until we find an autocommand to execute
2353 for (;;)
2354 {
2355 // skip removed commands
2356 while (acp->nextcmd != NULL && acp->nextcmd->cmd == NULL)
2357 if (acp->nextcmd->last)
2358 acp->nextcmd = NULL;
2359 else
2360 acp->nextcmd = acp->nextcmd->next;
2361
2362 if (acp->nextcmd != NULL)
2363 break;
2364
2365 // at end of commands, find next pattern that matches
2366 if (acp->curpat->last)
2367 acp->curpat = NULL;
2368 else
2369 acp->curpat = acp->curpat->next;
2370 if (acp->curpat != NULL)
2371 auto_next_pat(acp, TRUE);
2372 if (acp->curpat == NULL)
2373 return NULL;
2374 }
2375
2376 ac = acp->nextcmd;
2377
2378 if (p_verbose >= 9)
2379 {
2380 verbose_enter_scroll();
2381 smsg(_("autocommand %s"), ac->cmd);
2382 msg_puts("\n"); // don't overwrite this either
2383 verbose_leave_scroll();
2384 }
2385 retval = vim_strsave(ac->cmd);
Bram Moolenaareb93f3f2019-04-04 15:04:56 +02002386 // Remove one-shot ("once") autocmd in anticipation of its execution.
2387 if (ac->once)
2388 au_del_cmd(ac);
Bram Moolenaar3e460fd2019-01-26 16:21:07 +01002389 autocmd_nested = ac->nested;
2390#ifdef FEAT_EVAL
2391 current_sctx = ac->script_ctx;
2392#endif
2393 if (ac->last)
2394 acp->nextcmd = NULL;
2395 else
2396 acp->nextcmd = ac->next;
2397 return retval;
2398}
2399
2400/*
2401 * Return TRUE if there is a matching autocommand for "fname".
2402 * To account for buffer-local autocommands, function needs to know
2403 * in which buffer the file will be opened.
2404 */
2405 int
2406has_autocmd(event_T event, char_u *sfname, buf_T *buf)
2407{
2408 AutoPat *ap;
2409 char_u *fname;
2410 char_u *tail = gettail(sfname);
2411 int retval = FALSE;
2412
2413 fname = FullName_save(sfname, FALSE);
2414 if (fname == NULL)
2415 return FALSE;
2416
2417#ifdef BACKSLASH_IN_FILENAME
2418 /*
2419 * Replace all backslashes with forward slashes. This makes the
2420 * autocommand patterns portable between Unix and MS-DOS.
2421 */
2422 sfname = vim_strsave(sfname);
2423 if (sfname != NULL)
2424 forward_slash(sfname);
2425 forward_slash(fname);
2426#endif
2427
2428 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next)
2429 if (ap->pat != NULL && ap->cmds != NULL
2430 && (ap->buflocal_nr == 0
2431 ? match_file_pat(NULL, &ap->reg_prog,
2432 fname, sfname, tail, ap->allow_dirs)
2433 : buf != NULL && ap->buflocal_nr == buf->b_fnum
2434 ))
2435 {
2436 retval = TRUE;
2437 break;
2438 }
2439
2440 vim_free(fname);
2441#ifdef BACKSLASH_IN_FILENAME
2442 vim_free(sfname);
2443#endif
2444
2445 return retval;
2446}
2447
2448#if defined(FEAT_CMDL_COMPL) || defined(PROTO)
2449/*
2450 * Function given to ExpandGeneric() to obtain the list of autocommand group
2451 * names.
2452 */
2453 char_u *
2454get_augroup_name(expand_T *xp UNUSED, int idx)
2455{
2456 if (idx == augroups.ga_len) // add "END" add the end
2457 return (char_u *)"END";
2458 if (idx >= augroups.ga_len) // end of list
2459 return NULL;
2460 if (AUGROUP_NAME(idx) == NULL || AUGROUP_NAME(idx) == get_deleted_augroup())
2461 // skip deleted entries
2462 return (char_u *)"";
2463 return AUGROUP_NAME(idx); // return a name
2464}
2465
2466static int include_groups = FALSE;
2467
2468 char_u *
2469set_context_in_autocmd(
2470 expand_T *xp,
2471 char_u *arg,
2472 int doautocmd) // TRUE for :doauto*, FALSE for :autocmd
2473{
2474 char_u *p;
2475 int group;
2476
2477 // check for a group name, skip it if present
2478 include_groups = FALSE;
2479 p = arg;
2480 group = au_get_grouparg(&arg);
2481 if (group == AUGROUP_ERROR)
2482 return NULL;
2483 // If there only is a group name that's what we expand.
2484 if (*arg == NUL && group != AUGROUP_ALL && !VIM_ISWHITE(arg[-1]))
2485 {
2486 arg = p;
2487 group = AUGROUP_ALL;
2488 }
2489
2490 // skip over event name
2491 for (p = arg; *p != NUL && !VIM_ISWHITE(*p); ++p)
2492 if (*p == ',')
2493 arg = p + 1;
2494 if (*p == NUL)
2495 {
2496 if (group == AUGROUP_ALL)
2497 include_groups = TRUE;
2498 xp->xp_context = EXPAND_EVENTS; // expand event name
2499 xp->xp_pattern = arg;
2500 return NULL;
2501 }
2502
2503 // skip over pattern
2504 arg = skipwhite(p);
2505 while (*arg && (!VIM_ISWHITE(*arg) || arg[-1] == '\\'))
2506 arg++;
2507 if (*arg)
2508 return arg; // expand (next) command
2509
2510 if (doautocmd)
2511 xp->xp_context = EXPAND_FILES; // expand file names
2512 else
2513 xp->xp_context = EXPAND_NOTHING; // pattern is not expanded
2514 return NULL;
2515}
2516
2517/*
2518 * Function given to ExpandGeneric() to obtain the list of event names.
2519 */
2520 char_u *
2521get_event_name(expand_T *xp UNUSED, int idx)
2522{
2523 if (idx < augroups.ga_len) // First list group names, if wanted
2524 {
2525 if (!include_groups || AUGROUP_NAME(idx) == NULL
2526 || AUGROUP_NAME(idx) == get_deleted_augroup())
2527 return (char_u *)""; // skip deleted entries
2528 return AUGROUP_NAME(idx); // return a name
2529 }
2530 return (char_u *)event_names[idx - augroups.ga_len].name;
2531}
2532
2533#endif // FEAT_CMDL_COMPL
2534
2535#if defined(FEAT_EVAL) || defined(PROTO)
2536/*
2537 * Return TRUE if autocmd is supported.
2538 */
2539 int
2540autocmd_supported(char_u *name)
2541{
2542 char_u *p;
2543
2544 return (event_name2nr(name, &p) != NUM_EVENTS);
2545}
2546
2547/*
2548 * Return TRUE if an autocommand is defined for a group, event and
2549 * pattern: The group can be omitted to accept any group. "event" and "pattern"
2550 * can be NULL to accept any event and pattern. "pattern" can be NULL to accept
2551 * any pattern. Buffer-local patterns <buffer> or <buffer=N> are accepted.
2552 * Used for:
2553 * exists("#Group") or
2554 * exists("#Group#Event") or
2555 * exists("#Group#Event#pat") or
2556 * exists("#Event") or
2557 * exists("#Event#pat")
2558 */
2559 int
2560au_exists(char_u *arg)
2561{
2562 char_u *arg_save;
2563 char_u *pattern = NULL;
2564 char_u *event_name;
2565 char_u *p;
2566 event_T event;
2567 AutoPat *ap;
2568 buf_T *buflocal_buf = NULL;
2569 int group;
2570 int retval = FALSE;
2571
2572 // Make a copy so that we can change the '#' chars to a NUL.
2573 arg_save = vim_strsave(arg);
2574 if (arg_save == NULL)
2575 return FALSE;
2576 p = vim_strchr(arg_save, '#');
2577 if (p != NULL)
2578 *p++ = NUL;
2579
2580 // First, look for an autocmd group name
2581 group = au_find_group(arg_save);
2582 if (group == AUGROUP_ERROR)
2583 {
2584 // Didn't match a group name, assume the first argument is an event.
2585 group = AUGROUP_ALL;
2586 event_name = arg_save;
2587 }
2588 else
2589 {
2590 if (p == NULL)
2591 {
2592 // "Group": group name is present and it's recognized
2593 retval = TRUE;
2594 goto theend;
2595 }
2596
2597 // Must be "Group#Event" or "Group#Event#pat".
2598 event_name = p;
2599 p = vim_strchr(event_name, '#');
2600 if (p != NULL)
2601 *p++ = NUL; // "Group#Event#pat"
2602 }
2603
2604 pattern = p; // "pattern" is NULL when there is no pattern
2605
2606 // find the index (enum) for the event name
2607 event = event_name2nr(event_name, &p);
2608
2609 // return FALSE if the event name is not recognized
2610 if (event == NUM_EVENTS)
2611 goto theend;
2612
2613 // Find the first autocommand for this event.
2614 // If there isn't any, return FALSE;
2615 // If there is one and no pattern given, return TRUE;
2616 ap = first_autopat[(int)event];
2617 if (ap == NULL)
2618 goto theend;
2619
2620 // if pattern is "<buffer>", special handling is needed which uses curbuf
2621 // for pattern "<buffer=N>, fnamecmp() will work fine
2622 if (pattern != NULL && STRICMP(pattern, "<buffer>") == 0)
2623 buflocal_buf = curbuf;
2624
2625 // Check if there is an autocommand with the given pattern.
2626 for ( ; ap != NULL; ap = ap->next)
2627 // only use a pattern when it has not been removed and has commands.
2628 // For buffer-local autocommands, fnamecmp() works fine.
2629 if (ap->pat != NULL && ap->cmds != NULL
2630 && (group == AUGROUP_ALL || ap->group == group)
2631 && (pattern == NULL
2632 || (buflocal_buf == NULL
2633 ? fnamecmp(ap->pat, pattern) == 0
2634 : ap->buflocal_nr == buflocal_buf->b_fnum)))
2635 {
2636 retval = TRUE;
2637 break;
2638 }
2639
2640theend:
2641 vim_free(arg_save);
2642 return retval;
2643}
2644#endif