#ifndef lint
static char yyrcsid[]
#if __GNUC__ == 2
__attribute__ ((unused))
#endif
= "$OpenBSD: skeleton.c,v 1.18 2001/11/19 19:02:18 mpech Exp $";
#endif
#include <stdlib.h>
#define YYBYACC 1
#define YYMAJOR 1
#define YYMINOR 9
#define YYLEX yylex()
#define YYEMPTY -1
#define yyclearin (yychar=(YYEMPTY))
#define yyerrok (yyerrflag=0)
#define YYRECOVERING() (yyerrflag!=0)
#define YYPREFIX "yy"
#line 2 "parse.yacc"
#include "config.h"
#include <sys/types.h>
#include <sys/param.h>
#include <stdio.h>
#ifdef STDC_HEADERS
# include <stdlib.h>
# include <stddef.h>
#else
# ifdef HAVE_STDLIB_H
# include <stdlib.h>
# endif
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#else
# ifdef HAVE_STRINGS_H
# include <strings.h>
# endif
#endif
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#include <pwd.h>
#if defined(HAVE_MALLOC_H) && !defined(STDC_HEADERS)
# include <malloc.h>
#endif
#if defined(YYBISON) && defined(HAVE_ALLOCA_H) && !defined(__GNUC__)
# include <alloca.h>
#endif
#ifdef HAVE_LSEARCH
# include <search.h>
#endif
#include "sudo.h"
#include "parse.h"
#ifndef HAVE_LSEARCH
#include "emul/search.h"
#endif
#ifndef lint
static const char rcsid[] = "$Sudo: sudo.tab.c,v 1.57 2001/12/30 18:45:41 millert Exp $";
#endif
extern int sudolineno, parse_error;
int errorlineno = -1;
int clearaliases = TRUE;
int printmatches = FALSE;
int pedantic = FALSE;
int keepall = FALSE;
int quiet = FALSE;
#define HOST_ALIAS 1
#define CMND_ALIAS 2
#define USER_ALIAS 3
#define RUNAS_ALIAS 4
struct matchstack *match;
int top = 0, stacksize = 0;
#define push \
do { \
if (top >= stacksize) { \
while ((stacksize += STACKINCREMENT) < top); \
match = (struct matchstack *) erealloc(match, sizeof(struct matchstack) * stacksize); \
} \
match[top].user = -1; \
match[top].cmnd = -1; \
match[top].host = -1; \
match[top].runas = -1; \
match[top].nopass = def_flag(I_AUTHENTICATE) ? -1 : TRUE; \
top++; \
} while (0)
#define pushcp \
do { \
if (top >= stacksize) { \
while ((stacksize += STACKINCREMENT) < top); \
match = (struct matchstack *) erealloc(match, sizeof(struct matchstack) * stacksize); \
} \
match[top].user = match[top-1].user; \
match[top].cmnd = match[top-1].cmnd; \
match[top].host = match[top-1].host; \
match[top].runas = match[top-1].runas; \
match[top].nopass = match[top-1].nopass; \
top++; \
} while (0)
#define pop \
{ \
if (top == 0) \
yyerror("matching stack underflow"); \
else \
top--; \
}
#define append_cmnd(s, p) append(s, &cm_list[cm_list_len].cmnd, \
&cm_list[cm_list_len].cmnd_len, &cm_list[cm_list_len].cmnd_size, p)
#define append_runas(s, p) append(s, &cm_list[cm_list_len].runas, \
&cm_list[cm_list_len].runas_len, &cm_list[cm_list_len].runas_size, p)
#define append_entries(s, p) append(s, &ga_list[ga_list_len-1].entries, \
&ga_list[ga_list_len-1].entries_len, \
&ga_list[ga_list_len-1].entries_size, p)
static struct command_match *cm_list = NULL;
static size_t cm_list_len = 0, cm_list_size = 0;
static int in_alias = FALSE;
static size_t ga_list_len = 0, ga_list_size = 0;
static struct generic_alias *ga_list = NULL;
static int defaults_matches = 0;
static int add_alias __P((char *, int, int));
static void append __P((char *, char **, size_t *, size_t *, char *));
static void expand_ga_list __P((void));
static void expand_match_list __P((void));
static aliasinfo *find_alias __P((char *, int));
static int more_aliases __P((void));
void init_parser __P((void));
void yyerror __P((char *));
void
yyerror(s)
char *s;
{
if (errorlineno == -1)
errorlineno = sudolineno ? sudolineno - 1 : 0;
if (s && !quiet) {
#ifndef TRACELEXER
(void) fprintf(stderr, ">>> sudoers file: %s, line %d <<<\n", s,
sudolineno ? sudolineno - 1 : 0);
#else
(void) fprintf(stderr, "<*> ");
#endif
}
parse_error = TRUE;
}
#line 215 "parse.yacc"
typedef union {
char *string;
int BOOLEAN;
struct sudo_command command;
int tok;
} YYSTYPE;
#line 239 "sudo.tab.c"
#define COMMAND 257
#define ALIAS 258
#define DEFVAR 259
#define NTWKADDR 260
#define NETGROUP 261
#define USERGROUP 262
#define WORD 263
#define DEFAULTS 264
#define DEFAULTS_HOST 265
#define DEFAULTS_USER 266
#define RUNAS 267
#define NOPASSWD 268
#define PASSWD 269
#define ALL 270
#define COMMENT 271
#define HOSTALIAS 272
#define CMNDALIAS 273
#define USERALIAS 274
#define RUNASALIAS 275
#define ERROR 276
#define YYERRCODE 256
short yylhs[] = { -1,
0, 0, 7, 7, 9, 7, 7, 7, 7, 7,
7, 15, 16, 18, 16, 20, 16, 17, 17, 21,
21, 21, 21, 21, 10, 10, 22, 24, 24, 2,
2, 2, 2, 2, 23, 23, 25, 28, 29, 28,
26, 26, 5, 5, 4, 30, 4, 3, 3, 3,
3, 3, 27, 27, 27, 1, 1, 1, 12, 12,
32, 31, 19, 19, 13, 13, 34, 33, 35, 35,
14, 14, 37, 36, 11, 11, 39, 38, 8, 8,
40, 40, 6, 6, 6, 6, 6,
};
short yylen[] = { 2,
1, 2, 1, 2, 0, 3, 2, 2, 2, 2,
1, 2, 1, 0, 3, 0, 3, 1, 3, 1,
2, 3, 3, 3, 1, 3, 3, 1, 2, 1,
1, 1, 1, 1, 1, 3, 3, 1, 0, 3,
0, 2, 1, 3, 1, 0, 3, 1, 1, 1,
1, 1, 0, 1, 1, 1, 1, 1, 1, 3,
0, 4, 1, 3, 1, 3, 0, 4, 1, 3,
1, 3, 0, 4, 1, 3, 0, 4, 1, 3,
1, 2, 1, 1, 1, 1, 1,
};
short yydefred[] = { 0,
0, 13, 16, 14, 3, 0, 0, 0, 0, 0,
1, 0, 11, 0, 4, 0, 0, 61, 0, 59,
67, 0, 65, 77, 0, 75, 73, 0, 71, 2,
86, 85, 84, 83, 87, 0, 81, 0, 79, 0,
0, 12, 0, 34, 31, 32, 33, 30, 0, 28,
0, 63, 0, 0, 0, 0, 0, 0, 0, 0,
0, 82, 0, 0, 0, 25, 0, 0, 0, 21,
0, 29, 0, 0, 60, 0, 66, 0, 76, 0,
72, 80, 0, 0, 22, 23, 24, 19, 64, 0,
58, 57, 56, 39, 38, 69, 0, 0, 51, 50,
49, 48, 52, 46, 45, 43, 0, 26, 0, 0,
35, 0, 0, 0, 0, 0, 0, 0, 54, 55,
0, 40, 70, 47, 44, 36, 37,
};
short yydgoto[] = { 10,
95, 50, 105, 106, 107, 37, 11, 38, 12, 64,
25, 19, 22, 28, 13, 14, 42, 17, 65, 16,
43, 66, 110, 52, 111, 112, 121, 96, 113, 115,
20, 54, 23, 56, 97, 29, 60, 26, 58, 39,
};
short yysindex[] = { -236,
-264, 0, 0, 0, 0, -249, -243, -231, -227, -236,
0, -23, 0, -30, 0, -17, -23, 0, -36, 0,
0, -26, 0, 0, -14, 0, 0, -7, 0, 0,
0, 0, 0, 0, 0, -215, 0, -33, 0, -3,
-226, 0, 5, 0, 0, 0, 0, 0, -194, 0,
6, 0, 8, -5, -249, -4, -243, -2, -231, -1,
-227, 0, -23, 7, -38, 0, -210, -193, -188, 0,
-30, 0, -17, -17, 0, -25, 0, -23, 0, 245,
0, 0, -17, -189, 0, 0, 0, 0, 0, 6,
0, 0, 0, 0, 0, 0, 33, 8, 0, 0,
0, 0, 0, 0, 0, 0, 38, 0, 245, 39,
0, -251, -244, -25, -190, 245, 38, -189, 0, 0,
-25, 0, 0, 0, 0, 0, 0,
};
short yyrindex[] = { 255,
0, 0, 0, 0, 0, 0, 0, 0, 0, 255,
0, 0, 0, 0, 0, 0, 0, 0, 121, 0,
0, 141, 0, 0, 161, 0, 0, 181, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 1,
0, 0, 201, 0, 0, 0, 0, 0, 0, 0,
-28, 0, -8, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 221, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 265, 0, 0, 0, 0, 0, 21,
0, 0, 0, 0, 0, 0, 41, 61, 0, 0,
0, 0, 0, 0, 0, 0, 81, 0, 0, 101,
0, -9, 0, 0, 0, 0, 285, 265, 0, 0,
0, 0, 0, 0, 0, 0, 0,
};
short yygindex[] = { 0,
-29, 36, -27, -24, -22, 50, 79, -15, 0, 0,
0, 0, 0, 0, 0, 0, 19, 0, -12, 0,
0, 10, 0, 18, -21, 0, 0, -102, 0, 0,
40, 0, 43, 0, 0, 35, 0, 44, 0, 42,
};
#define YYTABLESIZE 555
short yytable[] = { 49,
20, 53, 41, 51, 17, 73, 15, 94, 18, 36,
63, 123, 91, 92, 21, 49, 119, 120, 127, 1,
62, 55, 84, 53, 15, 93, 24, 2, 3, 4,
27, 57, 70, 20, 5, 6, 7, 8, 9, 68,
68, 69, 31, 59, 20, 32, 33, 34, 71, 73,
61, 63, 85, 62, 35, 74, 76, 67, 78, 80,
78, 90, 98, 44, 83, 45, 46, 99, 47, 86,
100, 101, 102, 68, 87, 48, 114, 109, 62, 103,
74, 116, 118, 122, 72, 62, 117, 124, 30, 88,
89, 125, 108, 78, 75, 81, 126, 0, 68, 77,
27, 0, 79, 0, 82, 0, 0, 0, 0, 0,
0, 0, 0, 74, 0, 0, 0, 0, 78, 0,
8, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 27, 0, 0, 0, 0, 74, 0,
9, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 8, 0, 0, 0, 0, 27, 0,
7, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 9, 0, 0, 0, 0, 0, 0,
10, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 7, 0, 0, 0, 0, 0, 0,
18, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 10, 0, 0, 0, 0, 0, 0,
6, 0, 0, 0, 44, 0, 45, 46, 40, 47,
17, 91, 92, 18, 31, 0, 48, 32, 33, 34,
44, 0, 45, 46, 93, 47, 35, 53, 53, 0,
15, 0, 48, 6, 0, 0, 20, 0, 20, 0,
53, 20, 20, 20, 20, 20, 20, 0, 0, 0,
20, 20, 20, 20, 20, 20, 62, 104, 62, 0,
0, 62, 62, 62, 62, 62, 62, 5, 0, 0,
62, 62, 62, 62, 62, 62, 68, 41, 68, 0,
0, 68, 68, 68, 68, 68, 68, 0, 0, 0,
68, 68, 68, 68, 68, 68, 78, 42, 78, 0,
0, 78, 78, 78, 78, 78, 78, 0, 0, 0,
78, 78, 78, 78, 78, 78, 74, 0, 74, 0,
0, 74, 74, 74, 74, 74, 74, 0, 0, 0,
74, 74, 74, 74, 74, 74, 27, 0, 27, 0,
0, 27, 27, 27, 27, 27, 27, 0, 0, 0,
27, 27, 27, 27, 27, 27, 8, 0, 8, 0,
0, 8, 8, 8, 8, 8, 8, 0, 0, 0,
8, 8, 8, 8, 8, 8, 9, 0, 9, 0,
0, 9, 9, 9, 9, 9, 9, 0, 0, 0,
9, 9, 9, 9, 9, 9, 7, 0, 7, 0,
0, 7, 7, 7, 7, 7, 7, 0, 0, 0,
7, 7, 7, 7, 7, 7, 10, 0, 10, 0,
0, 10, 10, 10, 10, 10, 10, 0, 0, 0,
10, 10, 10, 10, 10, 10, 18, 0, 18, 0,
0, 18, 18, 18, 18, 18, 18, 0, 0, 0,
18, 18, 18, 18, 18, 18, 6, 0, 6, 0,
0, 6, 6, 6, 6, 6, 6, 0, 0, 0,
6, 6, 6, 6, 6, 6, 0, 0, 0, 0,
0, 0, 99, 0, 0, 100, 101, 102, 0, 0,
0, 0, 5, 0, 103, 5, 5, 5, 0, 0,
0, 41, 41, 0, 5, 0, 0, 0, 0, 0,
0, 0, 41, 41, 41, 0, 0, 0, 0, 0,
0, 42, 42, 0, 0, 0, 0, 0, 0, 0,
0, 0, 42, 42, 42,
};
short yycheck[] = { 33,
0, 17, 33, 16, 33, 44, 271, 33, 258, 33,
44, 114, 257, 258, 258, 33, 268, 269, 121, 256,
0, 58, 61, 33, 33, 270, 258, 264, 265, 266,
258, 58, 259, 33, 271, 272, 273, 274, 275, 43,
0, 45, 258, 58, 44, 261, 262, 263, 44, 44,
58, 44, 263, 33, 270, 61, 61, 61, 61, 61,
0, 74, 78, 258, 58, 260, 261, 258, 263, 263,
261, 262, 263, 33, 263, 270, 44, 267, 58, 270,
0, 44, 44, 113, 49, 36, 109, 115, 10, 71,
73, 116, 83, 33, 55, 61, 118, -1, 58, 57,
0, -1, 59, -1, 63, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, 58, -1,
0, -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, 58, -1,
0, -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, 58, -1,
0, -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, -1, -1,
0, -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, -1, -1,
0, -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, 33, -1, -1, -1, -1, -1, -1,
0, -1, -1, -1, 258, -1, 260, 261, 259, 263,
259, 257, 258, 33, 258, -1, 270, 261, 262, 263,
258, -1, 260, 261, 270, 263, 270, 257, 258, -1,
259, -1, 270, 33, -1, -1, 256, -1, 258, -1,
270, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, 33, 258, -1,
-1, 261, 262, 263, 264, 265, 266, 33, -1, -1,
270, 271, 272, 273, 274, 275, 256, 33, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, 33, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, 256, -1, 258, -1,
-1, 261, 262, 263, 264, 265, 266, -1, -1, -1,
270, 271, 272, 273, 274, 275, -1, -1, -1, -1,
-1, -1, 258, -1, -1, 261, 262, 263, -1, -1,
-1, -1, 258, -1, 270, 261, 262, 263, -1, -1,
-1, 257, 258, -1, 270, -1, -1, -1, -1, -1,
-1, -1, 268, 269, 270, -1, -1, -1, -1, -1,
-1, 257, 258, -1, -1, -1, -1, -1, -1, -1,
-1, -1, 268, 269, 270,
};
#define YYFINAL 10
#ifndef YYDEBUG
#define YYDEBUG 0
#endif
#define YYMAXTOKEN 276
#if YYDEBUG
#if defined(__cplusplus) || __STDC__
const char * const yyname[] =
#else
char *yyname[] =
#endif
{
"end-of-file",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
"'!'",0,0,0,0,0,0,0,0,0,"'+'","','","'-'",0,0,0,0,0,0,0,0,0,0,0,0,"':'",0,0,
"'='",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
"COMMAND","ALIAS","DEFVAR","NTWKADDR","NETGROUP","USERGROUP","WORD","DEFAULTS",
"DEFAULTS_HOST","DEFAULTS_USER","RUNAS","NOPASSWD","PASSWD","ALL","COMMENT",
"HOSTALIAS","CMNDALIAS","USERALIAS","RUNASALIAS","ERROR",
};
#if defined(__cplusplus) || __STDC__
const char * const yyrule[] =
#else
char *yyrule[] =
#endif
{"$accept : file",
"file : entry",
"file : file entry",
"entry : COMMENT",
"entry : error COMMENT",
"$$1 :",
"entry : $$1 userlist privileges",
"entry : USERALIAS useraliases",
"entry : HOSTALIAS hostaliases",
"entry : CMNDALIAS cmndaliases",
"entry : RUNASALIAS runasaliases",
"entry : defaults_line",
"defaults_line : defaults_type defaults_list",
"defaults_type : DEFAULTS",
"$$2 :",
"defaults_type : DEFAULTS_USER $$2 userlist",
"$$3 :",
"defaults_type : DEFAULTS_HOST $$3 hostlist",
"defaults_list : defaults_entry",
"defaults_list : defaults_entry ',' defaults_list",
"defaults_entry : DEFVAR",
"defaults_entry : '!' DEFVAR",
"defaults_entry : DEFVAR '=' WORD",
"defaults_entry : DEFVAR '+' WORD",
"defaults_entry : DEFVAR '-' WORD",
"privileges : privilege",
"privileges : privileges ':' privilege",
"privilege : hostlist '=' cmndspeclist",
"ophost : host",
"ophost : '!' host",
"host : ALL",
"host : NTWKADDR",
"host : NETGROUP",
"host : WORD",
"host : ALIAS",
"cmndspeclist : cmndspec",
"cmndspeclist : cmndspeclist ',' cmndspec",
"cmndspec : runasspec nopasswd opcmnd",
"opcmnd : cmnd",
"$$4 :",
"opcmnd : '!' $$4 cmnd",
"runasspec :",
"runasspec : RUNAS runaslist",
"runaslist : oprunasuser",
"runaslist : runaslist ',' oprunasuser",
"oprunasuser : runasuser",
"$$5 :",
"oprunasuser : '!' $$5 runasuser",
"runasuser : WORD",
"runasuser : USERGROUP",
"runasuser : NETGROUP",
"runasuser : ALIAS",
"runasuser : ALL",
"nopasswd :",
"nopasswd : NOPASSWD",
"nopasswd : PASSWD",
"cmnd : ALL",
"cmnd : ALIAS",
"cmnd : COMMAND",
"hostaliases : hostalias",
"hostaliases : hostaliases ':' hostalias",
"$$6 :",
"hostalias : ALIAS $$6 '=' hostlist",
"hostlist : ophost",
"hostlist : hostlist ',' ophost",
"cmndaliases : cmndalias",
"cmndaliases : cmndaliases ':' cmndalias",
"$$7 :",
"cmndalias : ALIAS $$7 '=' cmndlist",
"cmndlist : opcmnd",
"cmndlist : cmndlist ',' opcmnd",
"runasaliases : runasalias",
"runasaliases : runasaliases ':' runasalias",
"$$8 :",
"runasalias : ALIAS $$8 '=' runaslist",
"useraliases : useralias",
"useraliases : useraliases ':' useralias",
"$$9 :",
"useralias : ALIAS $$9 '=' userlist",
"userlist : opuser",
"userlist : userlist ',' opuser",
"opuser : user",
"opuser : '!' user",
"user : WORD",
"user : USERGROUP",
"user : NETGROUP",
"user : ALIAS",
"user : ALL",
};
#endif
#ifdef YYSTACKSIZE
#undef YYMAXDEPTH
#define YYMAXDEPTH YYSTACKSIZE
#else
#ifdef YYMAXDEPTH
#define YYSTACKSIZE YYMAXDEPTH
#else
#define YYSTACKSIZE 10000
#define YYMAXDEPTH 10000
#endif
#endif
#define YYINITSTACKSIZE 200
int yydebug;
int yynerrs;
int yyerrflag;
int yychar;
short *yyssp;
YYSTYPE *yyvsp;
YYSTYPE yyval;
YYSTYPE yylval;
short *yyss;
short *yysslim;
YYSTYPE *yyvs;
int yystacksize;
#line 845 "parse.yacc"
#define MOREALIASES (32)
aliasinfo *aliases = NULL;
size_t naliases = 0;
size_t nslots = 0;
static int
aliascmp(a1, a2)
const VOID *a1, *a2;
{
int r;
aliasinfo *ai1, *ai2;
ai1 = (aliasinfo *) a1;
ai2 = (aliasinfo *) a2;
if ((r = strcmp(ai1->name, ai2->name)) == 0)
r = ai1->type - ai2->type;
return(r);
}
static int
genaliascmp(entry, key)
const VOID *entry, *key;
{
int r;
struct generic_alias *ga1, *ga2;
ga1 = (struct generic_alias *) key;
ga2 = (struct generic_alias *) entry;
if ((r = strcmp(ga1->alias, ga2->alias)) == 0)
r = ga1->type - ga2->type;
return(r);
}
static int
add_alias(alias, type, val)
char *alias;
int type;
int val;
{
aliasinfo ai, *aip;
size_t onaliases;
char s[512];
if (naliases >= nslots && !more_aliases()) {
(void) snprintf(s, sizeof(s), "Out of memory defining alias `%s'",
alias);
yyerror(s);
return(FALSE);
}
ai.type = type;
ai.val = val;
ai.name = estrdup(alias);
onaliases = naliases;
aip = (aliasinfo *) lsearch((VOID *)&ai, (VOID *)aliases, &naliases,
sizeof(ai), aliascmp);
if (aip == NULL) {
(void) snprintf(s, sizeof(s), "Aliases corrupted defining alias `%s'",
alias);
yyerror(s);
return(FALSE);
}
if (onaliases == naliases) {
(void) snprintf(s, sizeof(s), "Alias `%s' already defined", alias);
yyerror(s);
return(FALSE);
}
return(TRUE);
}
static aliasinfo *
find_alias(alias, type)
char *alias;
int type;
{
aliasinfo ai;
ai.name = alias;
ai.type = type;
return((aliasinfo *) lfind((VOID *)&ai, (VOID *)aliases, &naliases,
sizeof(ai), aliascmp));
}
static int
more_aliases()
{
nslots += MOREALIASES;
if (nslots == MOREALIASES)
aliases = (aliasinfo *) malloc(nslots * sizeof(aliasinfo));
else
aliases = (aliasinfo *) realloc(aliases, nslots * sizeof(aliasinfo));
return(aliases != NULL);
}
void
dumpaliases()
{
size_t n;
for (n = 0; n < naliases; n++) {
if (aliases[n].val == -1)
continue;
switch (aliases[n].type) {
case HOST_ALIAS:
(void) puts("HOST_ALIAS");
break;
case CMND_ALIAS:
(void) puts("CMND_ALIAS");
break;
case USER_ALIAS:
(void) puts("USER_ALIAS");
break;
case RUNAS_ALIAS:
(void) puts("RUNAS_ALIAS");
break;
}
(void) printf("\t%s: %d\n", aliases[n].name, aliases[n].val);
}
}
void
list_matches()
{
int i;
char *p;
struct generic_alias *ga, key;
(void) printf("User %s may run the following commands on this host:\n",
user_name);
for (i = 0; i < cm_list_len; i++) {
(void) fputs(" ", stdout);
if (cm_list[i].runas) {
(void) putchar('(');
p = strtok(cm_list[i].runas, ", ");
do {
if (p != cm_list[i].runas)
(void) fputs(", ", stdout);
key.alias = p;
key.type = RUNAS_ALIAS;
if ((ga = (struct generic_alias *) lfind((VOID *) &key,
(VOID *) &ga_list[0], &ga_list_len, sizeof(key), genaliascmp)))
(void) fputs(ga->entries, stdout);
else
(void) fputs(p, stdout);
} while ((p = strtok(NULL, ", ")));
(void) fputs(") ", stdout);
} else {
(void) printf("(%s) ", def_str(I_RUNAS_DEFAULT));
}
if (cm_list[i].nopasswd == TRUE && def_flag(I_AUTHENTICATE))
(void) fputs("NOPASSWD: ", stdout);
else if (cm_list[i].nopasswd == FALSE && !def_flag(I_AUTHENTICATE))
(void) fputs("PASSWD: ", stdout);
key.alias = cm_list[i].cmnd;
key.type = CMND_ALIAS;
if ((ga = (struct generic_alias *) lfind((VOID *) &key,
(VOID *) &ga_list[0], &ga_list_len, sizeof(key), genaliascmp)))
(void) puts(ga->entries);
else
(void) puts(cm_list[i].cmnd);
}
for (i = 0; i < ga_list_len; i++) {
free(ga_list[i].alias);
free(ga_list[i].entries);
}
free(ga_list);
ga_list = NULL;
for (i = 0; i < cm_list_len; i++) {
free(cm_list[i].runas);
free(cm_list[i].cmnd);
}
free(cm_list);
cm_list = NULL;
cm_list_len = 0;
cm_list_size = 0;
}
static void
append(src, dstp, dst_len, dst_size, separator)
char *src, **dstp;
size_t *dst_len, *dst_size;
char *separator;
{
size_t src_len = strlen(src);
char *dst = *dstp;
if (separator && dst && dst[*dst_len - 1] != '!')
src_len += strlen(separator);
else
separator = NULL;
if (dst == NULL) {
dst = (char *) emalloc(BUFSIZ);
*dst_size = BUFSIZ;
*dst_len = 0;
*dstp = dst;
}
if (*dst_size <= *dst_len + src_len) {
while (*dst_size <= *dst_len + src_len)
*dst_size += BUFSIZ;
dst = (char *) erealloc(dst, *dst_size);
*dstp = dst;
}
dst += *dst_len;
*dst_len += src_len;
*dst = '\0';
if (separator)
(void) strcat(dst, separator);
(void) strcat(dst, src);
}
void
reset_aliases()
{
size_t n;
if (aliases) {
for (n = 0; n < naliases; n++)
free(aliases[n].name);
free(aliases);
aliases = NULL;
}
naliases = nslots = 0;
}
static void
expand_ga_list()
{
if (++ga_list_len >= ga_list_size) {
while ((ga_list_size += STACKINCREMENT) < ga_list_len)
;
ga_list = (struct generic_alias *)
erealloc(ga_list, sizeof(struct generic_alias) * ga_list_size);
}
ga_list[ga_list_len - 1].entries = NULL;
}
static void
expand_match_list()
{
if (++cm_list_len >= cm_list_size) {
while ((cm_list_size += STACKINCREMENT) < cm_list_len)
;
if (cm_list == NULL)
cm_list_len = 0;
cm_list = (struct command_match *)
erealloc(cm_list, sizeof(struct command_match) * cm_list_size);
}
cm_list[cm_list_len].runas = cm_list[cm_list_len].cmnd = NULL;
cm_list[cm_list_len].nopasswd = FALSE;
}
void
init_parser()
{
if (match) {
free(match);
match = NULL;
top = 0;
parse_error = FALSE;
errorlineno = -1;
sudolineno = 1;
}
stacksize = STACKINCREMENT;
match = (struct matchstack *) emalloc(sizeof(struct matchstack) * stacksize);
if (printmatches == TRUE)
expand_match_list();
}
#line 941 "sudo.tab.c"
#if defined(__cplusplus) || __STDC__
static int yygrowstack(void)
#else
static int yygrowstack()
#endif
{
int newsize, i;
short *newss;
YYSTYPE *newvs;
if ((newsize = yystacksize) == 0)
newsize = YYINITSTACKSIZE;
else if (newsize >= YYMAXDEPTH)
return -1;
else if ((newsize *= 2) > YYMAXDEPTH)
newsize = YYMAXDEPTH;
i = yyssp - yyss;
newss = yyss ? (short *)realloc(yyss, newsize * sizeof *newss) :
(short *)malloc(newsize * sizeof *newss);
if (newss == NULL)
goto bail;
yyss = newss;
yyssp = newss + i;
newvs = yyvs ? (YYSTYPE *)realloc(yyvs, newsize * sizeof *newvs) :
(YYSTYPE *)malloc(newsize * sizeof *newvs);
if (newvs == NULL)
goto bail;
yyvs = newvs;
yyvsp = newvs + i;
yystacksize = newsize;
yysslim = yyss + newsize - 1;
return 0;
bail:
if (yyss)
free(yyss);
if (yyvs)
free(yyvs);
yyss = yyssp = NULL;
yyvs = yyvsp = NULL;
yystacksize = 0;
return -1;
}
#define YYABORT goto yyabort
#define YYREJECT goto yyabort
#define YYACCEPT goto yyaccept
#define YYERROR goto yyerrlab
int
#if defined(__cplusplus) || __STDC__
yyparse(void)
#else
yyparse()
#endif
{
int yym, yyn, yystate;
#if YYDEBUG
#if defined(__cplusplus) || __STDC__
const char *yys;
#else
char *yys;
#endif
if ((yys = getenv("YYDEBUG")))
{
yyn = *yys;
if (yyn >= '0' && yyn <= '9')
yydebug = yyn - '0';
}
#endif
yynerrs = 0;
yyerrflag = 0;
yychar = (-1);
if (yyss == NULL && yygrowstack()) goto yyoverflow;
yyssp = yyss;
yyvsp = yyvs;
*yyssp = yystate = 0;
yyloop:
if ((yyn = yydefred[yystate]) != 0) goto yyreduce;
if (yychar < 0)
{
if ((yychar = yylex()) < 0) yychar = 0;
#if YYDEBUG
if (yydebug)
{
yys = 0;
if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
if (!yys) yys = "illegal-symbol";
printf("%sdebug: state %d, reading %d (%s)\n",
YYPREFIX, yystate, yychar, yys);
}
#endif
}
if ((yyn = yysindex[yystate]) && (yyn += yychar) >= 0 &&
yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
{
#if YYDEBUG
if (yydebug)
printf("%sdebug: state %d, shifting to state %d\n",
YYPREFIX, yystate, yytable[yyn]);
#endif
if (yyssp >= yysslim && yygrowstack())
{
goto yyoverflow;
}
*++yyssp = yystate = yytable[yyn];
*++yyvsp = yylval;
yychar = (-1);
if (yyerrflag > 0) --yyerrflag;
goto yyloop;
}
if ((yyn = yyrindex[yystate]) && (yyn += yychar) >= 0 &&
yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
{
yyn = yytable[yyn];
goto yyreduce;
}
if (yyerrflag) goto yyinrecovery;
#if defined(lint) || defined(__GNUC__)
goto yynewerror;
#endif
yynewerror:
yyerror("syntax error");
#if defined(lint) || defined(__GNUC__)
goto yyerrlab;
#endif
yyerrlab:
++yynerrs;
yyinrecovery:
if (yyerrflag < 3)
{
yyerrflag = 3;
for (;;)
{
if ((yyn = yysindex[*yyssp]) && (yyn += YYERRCODE) >= 0 &&
yyn <= YYTABLESIZE && yycheck[yyn] == YYERRCODE)
{
#if YYDEBUG
if (yydebug)
printf("%sdebug: state %d, error recovery shifting\
to state %d\n", YYPREFIX, *yyssp, yytable[yyn]);
#endif
if (yyssp >= yysslim && yygrowstack())
{
goto yyoverflow;
}
*++yyssp = yystate = yytable[yyn];
*++yyvsp = yylval;
goto yyloop;
}
else
{
#if YYDEBUG
if (yydebug)
printf("%sdebug: error recovery discarding state %d\n",
YYPREFIX, *yyssp);
#endif
if (yyssp <= yyss) goto yyabort;
--yyssp;
--yyvsp;
}
}
}
else
{
if (yychar == 0) goto yyabort;
#if YYDEBUG
if (yydebug)
{
yys = 0;
if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
if (!yys) yys = "illegal-symbol";
printf("%sdebug: state %d, error recovery discards token %d (%s)\n",
YYPREFIX, yystate, yychar, yys);
}
#endif
yychar = (-1);
goto yyloop;
}
yyreduce:
#if YYDEBUG
if (yydebug)
printf("%sdebug: state %d, reducing by rule %d (%s)\n",
YYPREFIX, yystate, yyn, yyrule[yyn]);
#endif
yym = yylen[yyn];
yyval = yyvsp[1-yym];
switch (yyn)
{
case 3:
#line 265 "parse.yacc"
{ ; }
break;
case 4:
#line 267 "parse.yacc"
{ yyerrok; }
break;
case 5:
#line 268 "parse.yacc"
{ push; }
break;
case 6:
#line 268 "parse.yacc"
{
while (top && user_matches != TRUE)
pop;
}
break;
case 7:
#line 273 "parse.yacc"
{ ; }
break;
case 8:
#line 275 "parse.yacc"
{ ; }
break;
case 9:
#line 277 "parse.yacc"
{ ; }
break;
case 10:
#line 279 "parse.yacc"
{ ; }
break;
case 11:
#line 281 "parse.yacc"
{ ; }
break;
case 13:
#line 286 "parse.yacc"
{
defaults_matches = TRUE;
}
break;
case 14:
#line 289 "parse.yacc"
{ push; }
break;
case 15:
#line 289 "parse.yacc"
{
defaults_matches = user_matches;
pop;
}
break;
case 16:
#line 293 "parse.yacc"
{ push; }
break;
case 17:
#line 293 "parse.yacc"
{
defaults_matches = host_matches;
pop;
}
break;
case 20:
#line 302 "parse.yacc"
{
if (defaults_matches == TRUE &&
!set_default(yyvsp[0].string, NULL, TRUE)) {
yyerror(NULL);
YYERROR;
}
free(yyvsp[0].string);
}
break;
case 21:
#line 310 "parse.yacc"
{
if (defaults_matches == TRUE &&
!set_default(yyvsp[0].string, NULL, FALSE)) {
yyerror(NULL);
YYERROR;
}
free(yyvsp[0].string);
}
break;
case 22:
#line 318 "parse.yacc"
{
if (defaults_matches == TRUE &&
!set_default(yyvsp[-2].string, yyvsp[0].string, TRUE)) {
yyerror(NULL);
YYERROR;
}
free(yyvsp[-2].string);
free(yyvsp[0].string);
}
break;
case 23:
#line 327 "parse.yacc"
{
if (defaults_matches == TRUE &&
!set_default(yyvsp[-2].string, yyvsp[0].string, '+')) {
yyerror(NULL);
YYERROR;
}
free(yyvsp[-2].string);
free(yyvsp[0].string);
}
break;
case 24:
#line 336 "parse.yacc"
{
if (defaults_matches == TRUE &&
!set_default(yyvsp[-2].string, yyvsp[0].string, '-')) {
yyerror(NULL);
YYERROR;
}
free(yyvsp[-2].string);
free(yyvsp[0].string);
}
break;
case 27:
#line 350 "parse.yacc"
{
host_matches = -1;
runas_matches = -1;
if (def_flag(I_AUTHENTICATE))
no_passwd = -1;
else
no_passwd = TRUE;
}
break;
case 28:
#line 365 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
host_matches = yyvsp[0].BOOLEAN;
}
break;
case 29:
#line 369 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
host_matches = ! yyvsp[0].BOOLEAN;
}
break;
case 30:
#line 374 "parse.yacc"
{
yyval.BOOLEAN = TRUE;
}
break;
case 31:
#line 377 "parse.yacc"
{
if (addr_matches(yyvsp[0].string))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 32:
#line 384 "parse.yacc"
{
if (netgr_matches(yyvsp[0].string, user_host, user_shost, NULL))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 33:
#line 391 "parse.yacc"
{
if (hostname_matches(user_shost, user_host, yyvsp[0].string) == 0)
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 34:
#line 398 "parse.yacc"
{
aliasinfo *aip = find_alias(yyvsp[0].string, HOST_ALIAS);
if (aip)
yyval.BOOLEAN = aip->val;
else if (strcasecmp(user_shost, yyvsp[0].string) == 0)
yyval.BOOLEAN = TRUE;
else {
if (pedantic) {
(void) fprintf(stderr,
"%s: undeclared Host_Alias `%s' referenced near line %d\n",
(pedantic == 1) ? "Warning" : "Error", yyvsp[0].string, sudolineno);
if (pedantic > 1) {
yyerror(NULL);
YYERROR;
}
}
yyval.BOOLEAN = -1;
}
free(yyvsp[0].string);
}
break;
case 37:
#line 426 "parse.yacc"
{
if (user_matches != -1 && host_matches != -1 &&
cmnd_matches != -1 && runas_matches != -1)
pushcp;
else if (user_matches != -1 && (top == 1 ||
(top == 2 && host_matches != -1 &&
match[0].host == -1)))
pushcp;
else if (user_matches == TRUE && keepall)
pushcp;
cmnd_matches = -1;
}
break;
case 38:
#line 453 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
cmnd_matches = yyvsp[0].BOOLEAN;
}
break;
case 39:
#line 457 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries("!", ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_cmnd("!", NULL);
}
}
break;
case 40:
#line 465 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
cmnd_matches = ! yyvsp[0].BOOLEAN;
}
break;
case 41:
#line 471 "parse.yacc"
{
if (printmatches == TRUE && host_matches == TRUE &&
user_matches == TRUE) {
if (runas_matches == -1) {
cm_list[cm_list_len].runas_len = 0;
} else {
cm_list[cm_list_len].runas =
estrdup(cm_list[cm_list_len-1].runas);
cm_list[cm_list_len].runas_len =
cm_list[cm_list_len-1].runas_len;
cm_list[cm_list_len].runas_size =
cm_list[cm_list_len-1].runas_size;
}
}
if (runas_matches == -1)
runas_matches = (strcmp(*user_runas,
def_str(I_RUNAS_DEFAULT)) == 0);
}
break;
case 42:
#line 494 "parse.yacc"
{
runas_matches = (yyvsp[0].BOOLEAN == TRUE ? TRUE : FALSE);
}
break;
case 43:
#line 499 "parse.yacc"
{ ; }
break;
case 44:
#line 500 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
yyval.BOOLEAN = yyvsp[0].BOOLEAN;
else
yyval.BOOLEAN = yyvsp[-2].BOOLEAN;
}
break;
case 45:
#line 509 "parse.yacc"
{ ; }
break;
case 46:
#line 510 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries("!", ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas("!", ", ");
}
}
break;
case 47:
#line 518 "parse.yacc"
{
yyval.BOOLEAN = (yyvsp[0].BOOLEAN == -1 ? -1 : ! yyvsp[0].BOOLEAN);
}
break;
case 48:
#line 523 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries(yyvsp[0].string, ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas(yyvsp[0].string, ", ");
}
if (strcmp(yyvsp[0].string, *user_runas) == 0)
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 49:
#line 537 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries(yyvsp[0].string, ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas(yyvsp[0].string, ", ");
}
if (usergr_matches(yyvsp[0].string, *user_runas))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 50:
#line 551 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries(yyvsp[0].string, ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas(yyvsp[0].string, ", ");
}
if (netgr_matches(yyvsp[0].string, NULL, NULL, *user_runas))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 51:
#line 565 "parse.yacc"
{
aliasinfo *aip = find_alias(yyvsp[0].string, RUNAS_ALIAS);
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries(yyvsp[0].string, ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas(yyvsp[0].string, ", ");
}
if (aip)
yyval.BOOLEAN = aip->val;
else if (strcmp(yyvsp[0].string, *user_runas) == 0)
yyval.BOOLEAN = TRUE;
else {
if (pedantic) {
(void) fprintf(stderr,
"%s: undeclared Runas_Alias `%s' referenced near line %d\n",
(pedantic == 1) ? "Warning" : "Error", yyvsp[0].string, sudolineno);
if (pedantic > 1) {
yyerror(NULL);
YYERROR;
}
}
yyval.BOOLEAN = -1;
}
free(yyvsp[0].string);
}
break;
case 52:
#line 594 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries("ALL", ", ");
else if (host_matches == TRUE &&
user_matches == TRUE)
append_runas("ALL", ", ");
}
yyval.BOOLEAN = TRUE;
}
break;
case 53:
#line 606 "parse.yacc"
{
if (printmatches == TRUE && host_matches == TRUE &&
user_matches == TRUE) {
if (no_passwd == TRUE)
cm_list[cm_list_len].nopasswd = TRUE;
else
cm_list[cm_list_len].nopasswd = FALSE;
}
}
break;
case 54:
#line 616 "parse.yacc"
{
no_passwd = TRUE;
if (printmatches == TRUE && host_matches == TRUE &&
user_matches == TRUE)
cm_list[cm_list_len].nopasswd = TRUE;
}
break;
case 55:
#line 622 "parse.yacc"
{
no_passwd = FALSE;
if (printmatches == TRUE && host_matches == TRUE &&
user_matches == TRUE)
cm_list[cm_list_len].nopasswd = FALSE;
}
break;
case 56:
#line 630 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries("ALL", ", ");
else if (host_matches == TRUE &&
user_matches == TRUE) {
append_cmnd("ALL", NULL);
expand_match_list();
}
}
yyval.BOOLEAN = TRUE;
if (safe_cmnd)
free(safe_cmnd);
safe_cmnd = estrdup(user_cmnd);
}
break;
case 57:
#line 647 "parse.yacc"
{
aliasinfo *aip;
if (printmatches == TRUE) {
if (in_alias == TRUE)
append_entries(yyvsp[0].string, ", ");
else if (host_matches == TRUE &&
user_matches == TRUE) {
append_cmnd(yyvsp[0].string, NULL);
expand_match_list();
}
}
if ((aip = find_alias(yyvsp[0].string, CMND_ALIAS)))
yyval.BOOLEAN = aip->val;
else {
if (pedantic) {
(void) fprintf(stderr,
"%s: undeclared Cmnd_Alias `%s' referenced near line %d\n",
(pedantic == 1) ? "Warning" : "Error", yyvsp[0].string, sudolineno);
if (pedantic > 1) {
yyerror(NULL);
YYERROR;
}
}
yyval.BOOLEAN = -1;
}
free(yyvsp[0].string);
}
break;
case 58:
#line 676 "parse.yacc"
{
if (printmatches == TRUE) {
if (in_alias == TRUE) {
append_entries(yyvsp[0].command.cmnd, ", ");
if (yyvsp[0].command.args)
append_entries(yyvsp[0].command.args, " ");
}
if (host_matches == TRUE &&
user_matches == TRUE) {
append_cmnd(yyvsp[0].command.cmnd, NULL);
if (yyvsp[0].command.args)
append_cmnd(yyvsp[0].command.args, " ");
expand_match_list();
}
}
if (command_matches(user_cmnd, user_args,
yyvsp[0].command.cmnd, yyvsp[0].command.args))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].command.cmnd);
if (yyvsp[0].command.args)
free(yyvsp[0].command.args);
}
break;
case 61:
#line 708 "parse.yacc"
{ push; }
break;
case 62:
#line 708 "parse.yacc"
{
if ((host_matches != -1 || pedantic) &&
!add_alias(yyvsp[-3].string, HOST_ALIAS, host_matches))
YYERROR;
pop;
}
break;
case 67:
#line 724 "parse.yacc"
{
push;
if (printmatches == TRUE) {
in_alias = TRUE;
expand_ga_list();
ga_list[ga_list_len-1].type = CMND_ALIAS;
ga_list[ga_list_len-1].alias = estrdup(yyvsp[0].string);
}
}
break;
case 68:
#line 733 "parse.yacc"
{
if ((cmnd_matches != -1 || pedantic) &&
!add_alias(yyvsp[-3].string, CMND_ALIAS, cmnd_matches))
YYERROR;
pop;
free(yyvsp[-3].string);
if (printmatches == TRUE)
in_alias = FALSE;
}
break;
case 69:
#line 745 "parse.yacc"
{ ; }
break;
case 73:
#line 753 "parse.yacc"
{
if (printmatches == TRUE) {
in_alias = TRUE;
expand_ga_list();
ga_list[ga_list_len-1].type = RUNAS_ALIAS;
ga_list[ga_list_len-1].alias = estrdup(yyvsp[0].string);
}
}
break;
case 74:
#line 761 "parse.yacc"
{
if ((yyvsp[0].BOOLEAN != -1 || pedantic) &&
!add_alias(yyvsp[-3].string, RUNAS_ALIAS, yyvsp[0].BOOLEAN))
YYERROR;
free(yyvsp[-3].string);
if (printmatches == TRUE)
in_alias = FALSE;
}
break;
case 77:
#line 776 "parse.yacc"
{ push; }
break;
case 78:
#line 776 "parse.yacc"
{
if ((user_matches != -1 || pedantic) &&
!add_alias(yyvsp[-3].string, USER_ALIAS, user_matches))
YYERROR;
pop;
free(yyvsp[-3].string);
}
break;
case 81:
#line 789 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
user_matches = yyvsp[0].BOOLEAN;
}
break;
case 82:
#line 793 "parse.yacc"
{
if (yyvsp[0].BOOLEAN != -1)
user_matches = ! yyvsp[0].BOOLEAN;
}
break;
case 83:
#line 798 "parse.yacc"
{
if (strcmp(yyvsp[0].string, user_name) == 0)
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 84:
#line 805 "parse.yacc"
{
if (usergr_matches(yyvsp[0].string, user_name))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 85:
#line 812 "parse.yacc"
{
if (netgr_matches(yyvsp[0].string, NULL, NULL, user_name))
yyval.BOOLEAN = TRUE;
else
yyval.BOOLEAN = -1;
free(yyvsp[0].string);
}
break;
case 86:
#line 819 "parse.yacc"
{
aliasinfo *aip = find_alias(yyvsp[0].string, USER_ALIAS);
if (aip)
yyval.BOOLEAN = aip->val;
else if (strcmp(yyvsp[0].string, user_name) == 0)
yyval.BOOLEAN = TRUE;
else {
if (pedantic) {
(void) fprintf(stderr,
"%s: undeclared User_Alias `%s' referenced near line %d\n",
(pedantic == 1) ? "Warning" : "Error", yyvsp[0].string, sudolineno);
if (pedantic > 1)
YYERROR;
}
yyval.BOOLEAN = -1;
}
free(yyvsp[0].string);
}
break;
case 87:
#line 839 "parse.yacc"
{
yyval.BOOLEAN = TRUE;
}
break;
#line 1835 "sudo.tab.c"
}
yyssp -= yym;
yystate = *yyssp;
yyvsp -= yym;
yym = yylhs[yyn];
if (yystate == 0 && yym == 0)
{
#if YYDEBUG
if (yydebug)
printf("%sdebug: after reduction, shifting from state 0 to\
state %d\n", YYPREFIX, YYFINAL);
#endif
yystate = YYFINAL;
*++yyssp = YYFINAL;
*++yyvsp = yyval;
if (yychar < 0)
{
if ((yychar = yylex()) < 0) yychar = 0;
#if YYDEBUG
if (yydebug)
{
yys = 0;
if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
if (!yys) yys = "illegal-symbol";
printf("%sdebug: state %d, reading %d (%s)\n",
YYPREFIX, YYFINAL, yychar, yys);
}
#endif
}
if (yychar == 0) goto yyaccept;
goto yyloop;
}
if ((yyn = yygindex[yym]) && (yyn += yystate) >= 0 &&
yyn <= YYTABLESIZE && yycheck[yyn] == yystate)
yystate = yytable[yyn];
else
yystate = yydgoto[yym];
#if YYDEBUG
if (yydebug)
printf("%sdebug: after reduction, shifting from state %d \
to state %d\n", YYPREFIX, *yyssp, yystate);
#endif
if (yyssp >= yysslim && yygrowstack())
{
goto yyoverflow;
}
*++yyssp = yystate;
*++yyvsp = yyval;
goto yyloop;
yyoverflow:
yyerror("yacc stack overflow");
yyabort:
return (1);
yyaccept:
return (0);
}