vim-patch:7.4.2117

Problem:    Deleting an augroup that still has autocmds does not give a
            warning.  The next defined augroup takes its place.
Solution:   Give a warning and prevent the index being used for another group
            name.

f2c4c39119
This commit is contained in:
lonerover
2017-01-09 08:41:45 +08:00
parent f5d06c52a2
commit 7486e7586d
3 changed files with 76 additions and 18 deletions

View File

@@ -5366,6 +5366,7 @@ static AutoPatCmd *active_apc_list = NULL; /* stack of active autocommands */
*/ */
static garray_T augroups = {0, 0, sizeof(char_u *), 10, NULL}; static garray_T augroups = {0, 0, sizeof(char_u *), 10, NULL};
#define AUGROUP_NAME(i) (((char_u **)augroups.ga_data)[i]) #define AUGROUP_NAME(i) (((char_u **)augroups.ga_data)[i])
static char_u *deleted_augroup = NULL;
/* /*
* The ID of the current group. Group 0 is the default one. * The ID of the current group. Group 0 is the default one.
@@ -5399,10 +5400,11 @@ static void show_autocmd(AutoPat *ap, event_T event)
return; return;
if (event != last_event || ap->group != last_group) { if (event != last_event || ap->group != last_group) {
if (ap->group != AUGROUP_DEFAULT) { if (ap->group != AUGROUP_DEFAULT) {
if (AUGROUP_NAME(ap->group) == NULL) if (AUGROUP_NAME(ap->group) == NULL) {
msg_puts_attr((char_u *)_("--Deleted--"), hl_attr(HLF_E)); msg_puts_attr(deleted_augroup, hl_attr(HLF_E));
else } else {
msg_puts_attr(AUGROUP_NAME(ap->group), hl_attr(HLF_T)); msg_puts_attr(AUGROUP_NAME(ap->group), hl_attr(HLF_T));
}
msg_puts((char_u *)" "); msg_puts((char_u *)" ");
} }
msg_puts_attr(event_nr2name(event), hl_attr(HLF_T)); msg_puts_attr(event_nr2name(event), hl_attr(HLF_T));
@@ -5568,13 +5570,36 @@ static void au_del_group(char_u *name)
int i; int i;
i = au_find_group(name); i = au_find_group(name);
if (i == AUGROUP_ERROR) /* the group doesn't exist */ if (i == AUGROUP_ERROR) { // the group doesn't exist
EMSG2(_("E367: No such group: \"%s\""), name); EMSG2(_("E367: No such group: \"%s\""), name);
else { } else {
event_T event;
AutoPat *ap;
int in_use = false;
for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
event = (event_T)((int)event + 1)) {
for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next) {
if (ap->group == i) {
give_warning((char_u *)
_("W19: Deleting augroup that is still in use"), true);
in_use = true;
event = NUM_EVENTS;
break;
}
}
}
xfree(AUGROUP_NAME(i)); xfree(AUGROUP_NAME(i));
if (in_use) {
if (deleted_augroup == NULL) {
deleted_augroup = (char_u *)_("--Deleted--");
}
AUGROUP_NAME(i) = deleted_augroup;
} else {
AUGROUP_NAME(i) = NULL; AUGROUP_NAME(i) = NULL;
} }
} }
}
/// Find the ID of an autocmd group name. /// Find the ID of an autocmd group name.
/// ///
@@ -5584,8 +5609,9 @@ static void au_del_group(char_u *name)
static int au_find_group(const char_u *name) static int au_find_group(const char_u *name)
FUNC_ATTR_PURE FUNC_ATTR_WARN_UNUSED_RESULT FUNC_ATTR_PURE FUNC_ATTR_WARN_UNUSED_RESULT
{ {
for (int i = 0; i < augroups.ga_len; ++i) { for (int i = 0; i < augroups.ga_len; i++) {
if (AUGROUP_NAME(i) != NULL && STRCMP(AUGROUP_NAME(i), name) == 0) { if (AUGROUP_NAME(i) != NULL && AUGROUP_NAME(i) != deleted_augroup
&& STRCMP(AUGROUP_NAME(i), name) == 0) {
return i; return i;
} }
} }
@@ -5633,10 +5659,21 @@ void do_augroup(char_u *arg, int del_group)
#if defined(EXITFREE) #if defined(EXITFREE)
void free_all_autocmds(void) void free_all_autocmds(void)
{ {
int i;
char_u *s;
for (current_augroup = -1; current_augroup < augroups.ga_len; for (current_augroup = -1; current_augroup < augroups.ga_len;
++current_augroup) current_augroup++) {
do_autocmd((char_u *)"", TRUE); do_autocmd((char_u *)"", true);
ga_clear_strings(&augroups); }
for (i = 0; i < augroups.ga_len; i++) {
s = ((char_u **)(augroups.ga_data))[i];
if (s != deleted_augroup) {
xfree(s);
}
}
ga_clear(&augroups);
} }
#endif #endif
@@ -7098,9 +7135,11 @@ char_u *get_augroup_name(expand_T *xp, int idx)
return (char_u *)"END"; return (char_u *)"END";
if (idx >= augroups.ga_len) /* end of list */ if (idx >= augroups.ga_len) /* end of list */
return NULL; return NULL;
if (AUGROUP_NAME(idx) == NULL) /* skip deleted entries */ if (AUGROUP_NAME(idx) == NULL || AUGROUP_NAME(idx) == deleted_augroup) {
// skip deleted entries
return (char_u *)""; return (char_u *)"";
return AUGROUP_NAME(idx); /* return a name */ }
return AUGROUP_NAME(idx); // return a name
} }
static int include_groups = FALSE; static int include_groups = FALSE;
@@ -7157,10 +7196,12 @@ set_context_in_autocmd (
*/ */
char_u *get_event_name(expand_T *xp, int idx) char_u *get_event_name(expand_T *xp, int idx)
{ {
if (idx < augroups.ga_len) { /* First list group names, if wanted */ if (idx < augroups.ga_len) { // First list group names, if wanted
if (!include_groups || AUGROUP_NAME(idx) == NULL) if (!include_groups || AUGROUP_NAME(idx) == NULL
return (char_u *)""; /* skip deleted entries */ || AUGROUP_NAME(idx) == deleted_augroup) {
return AUGROUP_NAME(idx); /* return a name */ return (char_u *)""; // skip deleted entries
}
return AUGROUP_NAME(idx); // return a name
} }
return (char_u *)event_names[idx - augroups.ga_len].name; return (char_u *)event_names[idx - augroups.ga_len].name;
} }

View File

@@ -151,3 +151,20 @@ func Test_early_bar()
au! vimBarTest|echo 'hello' au! vimBarTest|echo 'hello'
call assert_equal(1, len(split(execute('au vimBarTest'), "\n"))) call assert_equal(1, len(split(execute('au vimBarTest'), "\n")))
endfunc endfunc
func Test_augroup_warning()
augroup TheWarning
au VimEnter * echo 'entering'
augroup END
call assert_true(match(execute('au VimEnter'), "TheWarning.*VimEnter") >= 0)
redir => res
augroup! TheWarning
redir END
call assert_true(match(res, "W19:") >= 0)
call assert_true(match(execute('au VimEnter'), "-Deleted-.*VimEnter") >= 0)
" check "Another" does not take the pace of the deleted entry
augroup Another
augroup END
call assert_true(match(execute('au VimEnter'), "-Deleted-.*VimEnter") >= 0)
endfunc

View File

@@ -323,7 +323,7 @@ static int included_patches[] = {
// 2120, // 2120,
// 2119, // 2119,
// 2118 NA // 2118 NA
// 2117, 2117,
// 2116 NA // 2116 NA
// 2115 NA // 2115 NA
// 2114 NA // 2114 NA