From: Todd C. Miller Date: Sat, 13 Aug 2011 18:42:57 +0000 (-0400) Subject: When checking aliases, also check the contents of the alias in case X-Git-Tag: SUDO_1_7_7~15 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=8ae51165b8b97a841880481e6382afa5f666e8d4;p=sudo When checking aliases, also check the contents of the alias in case there are problems with an alias that is referenced inside another. Replace the self reference check with real alias cycle detection. --HG-- branch : 1.7 --- diff --git a/visudo.c b/visudo.c index b6d9d440c..57cec798d 100644 --- a/visudo.c +++ b/visudo.c @@ -107,8 +107,6 @@ static int install_sudoers __P((struct sudoersfile *, int)); static int print_unused __P((void *, void *)); static int reparse_sudoers __P((char *, char *, int, int)); static int run_command __P((char *, char **)); -static void print_selfref __P((char *, int, int, int)); -static void print_undefined __P((char *, int, int, int)); static void setup_signals __P((void)); static void help __P((void)) __attribute__((__noreturn__)); static void usage __P((int)); @@ -967,13 +965,8 @@ alias_remove_recursive(name, type, strict, quiet) if ((a = alias_find(name, type)) != NULL) { tq_foreach_fwd(&a->members, m) { if (m->type == ALIAS) { - if (strcmp(name, m->name) == 0) { - print_selfref(m->name, type, strict, quiet); + if (!alias_remove_recursive(m->name, type, strict, quiet)) error = 1; - } else { - if (!alias_remove_recursive(m->name, type, strict, quiet)) - error = 1; - } } } } @@ -984,6 +977,46 @@ alias_remove_recursive(name, type, strict, quiet) return error; } +static int +check_alias(name, type, strict, quiet) + char *name; + int type; + int strict; + int quiet; +{ + struct member *m; + struct alias *a; + int error = 0; + + if ((a = alias_find(name, type)) != NULL) { + /* check alias contents */ + tq_foreach_fwd(&a->members, m) { + if (m->type == ALIAS) + error += check_alias(m->name, type, strict, quiet); + } + } else { + if (!quiet) { + char *fmt; + if (errno == ELOOP) { + fmt = strict ? + "Error: cycle in %s_Alias `%s'" : + "Warning: cycle in %s_Alias `%s'"; + } else { + fmt = strict ? + "Error: %s_Alias `%s' referenced but not defined" : + "Warning: %s_Alias `%s' referenced but not defined"; + } + warningx(fmt, + type == HOSTALIAS ? "Host" : type == CMNDALIAS ? "Cmnd" : + type == USERALIAS ? "User" : type == RUNASALIAS ? "Runas" : + "Unknown", name); + } + error++; + } + + return error; +} + /* * Iterate through the sudoers datastructures looking for undefined * aliases or unused aliases. @@ -1007,38 +1040,26 @@ check_aliases(strict, quiet) tq_foreach_fwd(&us->users, m) { if (m->type == ALIAS) { alias_seqno++; - if (alias_find(m->name, USERALIAS) == NULL) { - print_undefined(m->name, USERALIAS, strict, quiet); - error++; - } + error += check_alias(m->name, USERALIAS, strict, quiet); } } tq_foreach_fwd(&us->privileges, priv) { tq_foreach_fwd(&priv->hostlist, m) { if (m->type == ALIAS) { alias_seqno++; - if (alias_find(m->name, HOSTALIAS) == NULL) { - print_undefined(m->name, HOSTALIAS, strict, quiet); - error++; - } + error += check_alias(m->name, HOSTALIAS, strict, quiet); } } tq_foreach_fwd(&priv->cmndlist, cs) { tq_foreach_fwd(&cs->runasuserlist, m) { if (m->type == ALIAS) { alias_seqno++; - if (alias_find(m->name, RUNASALIAS) == NULL) { - print_undefined(m->name, RUNASALIAS, strict, quiet); - error++; - } + error += check_alias(m->name, RUNASALIAS, strict, quiet); } } if ((m = cs->cmnd)->type == ALIAS) { alias_seqno++; - if (alias_find(m->name, CMNDALIAS) == NULL) { - print_undefined(m->name, CMNDALIAS, strict, quiet); - error++; - } + error += check_alias(m->name, CMNDALIAS, strict, quiet); } } } @@ -1116,38 +1137,6 @@ check_aliases(strict, quiet) return strict ? error : 0; } -static void -print_undefined(name, type, strict, quiet) - char *name; - int type; - int strict; - int quiet; -{ - if (!quiet) { - warningx("%s: %s_Alias `%s' referenced but not defined", - strict ? "Error" : "Warning", - type == HOSTALIAS ? "Host" : type == CMNDALIAS ? "Cmnd" : - type == USERALIAS ? "User" : type == RUNASALIAS ? "Runas" : - "Unknown", name); - } -} - -static void -print_selfref(name, type, strict, quiet) - char *name; - int type; - int strict; - int quiet; -{ - if (!quiet) { - warningx("%s: %s_Alias `%s' references self", - strict ? "Error" : "Warning", - type == HOSTALIAS ? "Host" : type == CMNDALIAS ? "Cmnd" : - type == USERALIAS ? "User" : type == RUNASALIAS ? "Runas" : - "Unknown", name); - } -} - static int print_unused(v1, v2) void *v1;