struct group *pr_auth_getgrent(pool *p) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct group *res = NULL; cmd = make_cmd(p, 0); mr = dispatch_auth(cmd, "getgrent", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) res = mr->data; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) return NULL; /* Make sure the GID is not -1 */ if (res->gr_gid == (gid_t) -1) { pr_log_pri(PR_LOG_ERR, "error: GID of -1 not allowed"); return NULL; } return res; }
struct group *pr_auth_getgrgid(pool *p, gid_t gid) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct group *res = NULL; cmd = make_cmd(p, 1, (void *) &gid); mr = dispatch_auth(cmd, "getgrgid", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) res = mr->data; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) { errno = ENOENT; return NULL; } /* Make sure the GID is not -1 */ if (res->gr_gid == (gid_t) -1) { pr_log_pri(PR_LOG_ERR, "error: GID of -1 not allowed"); return NULL; } pr_log_debug(DEBUG10, "retrieved group '%s' for GID %lu", res->gr_name, (unsigned long) gid); return res; }
static int process_command(int argc, char **argv) { static struct option long_options[] = { { "dump", no_argument, 0, 'd' }, { "codegen", no_argument, 0, 'c' }, { "make", no_argument, 0, 'm' }, { 0, 0, 0, 0 } }; opterr = 0; optind = 1; int index = 0; const char *spec = "aer"; switch (getopt_long(MIN(argc, 2), argv, spec, long_options, &index)) { case 'a': return analyse(argc, argv); case 'e': return elaborate(argc, argv); case 'r': return run(argc, argv); case 'd': return dump_cmd(argc, argv); case 'c': return codegen(argc, argv); case 'm': return make_cmd(argc, argv); default: fatal("missing command, try %s --help for usage", PACKAGE); return EXIT_FAILURE; } }
CMD* make_cmd(token_list** list_ref) { token_list* list = *list_ref; if (!list) return make_error_cmd("could not form command (no tokens)"); CMD* cmd_tree = make_andor(&list); if (cmd_tree->type == ERROR) return cmd_tree; int next_type = type(list); if (next_type == SEP_END || next_type == SEP_BG) { advance(&list); CMD* parent = mallocCMD(); parent->type = next_type; parent->left = cmd_tree; cmd_tree = parent; // See if it is possible to make a subcommand; if not, return to initial // state (because subcommand is optional following ; or & token_list* old_head = list; // Hold onto a copy in case sub command // returns an error CMD* sub_cmd = make_cmd(&list); if (sub_cmd->type == ERROR) { freeCMD(sub_cmd); sub_cmd = NULL; list = old_head; } cmd_tree->right = sub_cmd; } *list_ref = list; return cmd_tree; }
struct passwd *pr_auth_getpwent(pool *p) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct passwd *res = NULL; cmd = make_cmd(p, 0); mr = dispatch_auth(cmd, "getpwent", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) { res = mr->data; } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) return NULL; /* Make sure the UID and GID are not -1 */ if (res->pw_uid == (uid_t) -1) { pr_log_pri(PR_LOG_WARNING, "error: UID of -1 not allowed"); return NULL; } if (res->pw_gid == (gid_t) -1) { pr_log_pri(PR_LOG_WARNING, "error: GID of -1 not allowed"); return NULL; } return res; }
const char *pr_auth_gid2name(pool *p, gid_t gid) { cmd_rec *cmd = NULL; modret_t *mr = NULL; static char namebuf[64]; char *res = NULL; int have_name = FALSE; memset(namebuf, '\0', sizeof(namebuf)); gidcache_create(); if ((auth_caching & PR_AUTH_CACHE_FL_GID2NAME) && gid_tab) { void *v = NULL; v = pr_table_kget(gid_tab, (const void *) &gid, sizeof(gid_t), NULL); if (v) { sstrncpy(namebuf, v, sizeof(namebuf)); pr_trace_msg(trace_channel, 8, "using name '%s' from gidcache for GID %lu", namebuf, (unsigned long) gid); res = namebuf; return res; } else { pr_trace_msg(trace_channel, 9, "no value found in gidcache for GID %lu: %s", (unsigned long) gid, strerror(errno)); } } cmd = make_cmd(p, 1, (void *) &gid); mr = dispatch_auth(cmd, "gid2name", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) { res = mr->data; sstrncpy(namebuf, res, sizeof(namebuf)); res = namebuf; gidcache_add(gid, res); have_name = TRUE; } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } if (!have_name) { snprintf(namebuf, sizeof(namebuf)-1, "%lu", (unsigned long) gid); } res = namebuf; return res; }
static void run_shell(void) { int done = 0; static const char *help_argv[] = { HELP_COMMAND, NULL }; /* Print help if enabled */ run_command_v_opt(help_argv, RUN_SILENT_EXEC_FAILURE); do { struct strbuf line = STRBUF_INIT; const char *prog; char *full_cmd; char *rawargs; char *split_args; const char **argv; int code; int count; fprintf(stderr, "git> "); if (strbuf_getline(&line, stdin, '\n') == EOF) { fprintf(stderr, "\n"); strbuf_release(&line); break; } strbuf_trim(&line); rawargs = strbuf_detach(&line, NULL); split_args = xstrdup(rawargs); count = split_cmdline(split_args, &argv); if (count < 0) { fprintf(stderr, "invalid command format '%s': %s\n", rawargs, split_cmdline_strerror(count)); free(split_args); free(rawargs); continue; } prog = argv[0]; if (!strcmp(prog, "")) { } else if (!strcmp(prog, "quit") || !strcmp(prog, "logout") || !strcmp(prog, "exit") || !strcmp(prog, "bye")) { done = 1; } else if (is_valid_cmd_name(prog)) { full_cmd = make_cmd(prog); argv[0] = full_cmd; code = run_command_v_opt(argv, RUN_SILENT_EXEC_FAILURE); if (code == -1 && errno == ENOENT) { fprintf(stderr, "unrecognized command '%s'\n", prog); } free(full_cmd); } else { fprintf(stderr, "invalid command format '%s'\n", prog); } free(argv); free(rawargs); } while (!done); }
cmd *parseCmd(char *s) /*to break up string by '>' and then pass that off to parseRedToken*/ { char *saveptr=s; char *token; token = strtok_r(saveptr, ">", &saveptr); cmd *cm = make_cmd(parseRedToken(token)); cmd *f = cm; while(token != NULL){ token = strtok_r(NULL, ">", &saveptr); if(token == NULL) { return f; } cm->next = make_cmd(parseRedToken(token)); cm = cm->next; } return f; }
void pr_auth_endgrent(pool *p) { cmd_rec *cmd = NULL; cmd = make_cmd(p, 0); (void) dispatch_auth(cmd, "endgrent", NULL); if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return; }
char *status_equal_zero(char *tmp, char *str, int i, int status) { (void)status; if (i == 0 && tmp[0] != '.' && tmp[0] != '/') tmp = show_tab(tmp); else if (tmp[0] == '-') { if (!tmp[1]) show_diff_option(make_cmd(str)); } else tmp = argument_completion(tmp, str); return (tmp); }
int main (int argc, char *argv[]) { int i, c, fd, len; unsigned char rsp[3], cmd[7] = {0x08,0x22,0,0,0,0,0}; if (-1 == system("stty -F /dev/ttyAMA0 -ixon -ixoff -crtscts speed 9600")) { perror("stty"); return EIO; } fd = open("/dev/ttyAMA0", O_RDWR); if (fd == -1) { perror("/dev/ttyAMA0"); return EIO; } for (i = 1; i < argc ; ++i) { char *arg = argv[i]; unsigned char *codes = NULL; if (0 == strcmp("raw", arg)) { codes = get_raw_hex(++i, argv); i += 4; } else { for (c = 0; commands[c].name; ++c) { if (0 == strcmp(commands[c].name, arg)) { codes = commands[c].codes; break; } } } if (!codes) { fprintf(stderr, "unknown command: %s\n", arg); return EINVAL; } make_cmd(cmd, codes); if (7 != write(fd, cmd, 7)) { perror("write()"); return EIO; } memset(rsp, 0, 3); len = read(fd, rsp, 3); printf("response: (%d) 0x%02x 0x%02x 0x%02x\n", len, rsp[0], rsp[1], rsp[2]); if ((i + 1) < argc) sleep(1); } return 0; }
void on_setup(Executor& exec) { if (exe.empty()) //cmd style { exec.exe = args.front().c_str(); exec.cmd_style = true; } else exec.exe = &exe.front(); if (!args.empty()) { cmd_impl = make_cmd(); exec.cmd_line = cmd_impl.data(); } }
static void get_request_str(char *uid, char *cmd) { int len = strlen(uid); char *msg = uid; char index[2] = {0}; memcpy(index, msg+len-2, 1); char key[18] = {0}; snprintf(key, 18, "contact_upload_%s", index); char *field = uid; if (make_cmd(cmd, REDIS_CMD_LEN, 3, "hget", key, field) < 0) { print_log(LOG_TYPE_ERROR, "hget %s %s error, file = %s, line = %d", key, field, __FILE__, __LINE__); return; } }
/* The top level function of a recursive descent parser for the grammar defined * in parse.h. Parses a token list into a command structure. * * @list = list of tokens to parse * * Returns: a pointer to the resulting command structure; NULL if errors found */ CMD* parse(token_list* list) { CMD* parse_tree = make_cmd(&list); if (parse_tree->type == ERROR) { assert(parse_tree); ERROR(parse_tree->argv[0]); freeCMD(parse_tree); return NULL; } if (list) { ERROR("could not parse remaining tokens"); freeCMD(parse_tree); return NULL; } return parse_tree; }
uid_t pr_auth_name2uid(pool *p, const char *name) { cmd_rec *cmd = NULL; modret_t *mr = NULL; uid_t res = (uid_t) -1; cmd = make_cmd(p, 1, name); mr = dispatch_auth(cmd, "name2uid", NULL); if (MODRET_ISHANDLED(mr)) res = *((uid_t *) mr->data); else errno = EINVAL; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; }
void pr_auth_endpwent(pool *p) { cmd_rec *cmd = NULL; cmd = make_cmd(p, 0); (void) dispatch_auth(cmd, "endpwent", NULL); if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } if (auth_tab) { pr_trace_msg(trace_channel, 5, "emptying authcache"); (void) pr_table_empty(auth_tab); (void) pr_table_free(auth_tab); auth_tab = NULL; } return; }
int pr_auth_authorize(pool *p, const char *name) { cmd_rec *cmd = NULL; modret_t *mr = NULL; module *m = NULL; int res = PR_AUTH_OK; cmd = make_cmd(p, 1, name); if (auth_tab) { /* Fetch the specific module to be used for authenticating this user. */ void *v = pr_table_get(auth_tab, name, NULL); if (v) { m = *((module **) v); pr_trace_msg(trace_channel, 4, "using module 'mod_%s.c' from authcache to authorize user '%s'", m->name, name); } } mr = dispatch_auth(cmd, "authorize", m ? &m : NULL); /* Unlike the other auth calls, we assume here that unless the handlers * explicitly return ERROR, the user is authorized. Thus HANDLED and * DECLINED are both treated as "yes, this user is authorized". This * handles the case where the authenticating module (e.g. mod_sql) * does NOT provide an 'authorize' handler. */ if (MODRET_ISERROR(mr)) { res = MODRET_ERROR(mr); } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; }
int pr_auth_requires_pass(pool *p, const char *name) { cmd_rec *cmd; modret_t *mr; int res = TRUE; cmd = make_cmd(p, 1, name); mr = dispatch_auth(cmd, "requires_pass", NULL); if (MODRET_ISHANDLED(mr)) res = FALSE; else if (MODRET_ISERROR(mr)) res = MODRET_ERROR(mr); if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; }
struct passwd *pr_auth_getpwuid(pool *p, uid_t uid) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct passwd *res = NULL; cmd = make_cmd(p, 1, (void *) &uid); mr = dispatch_auth(cmd, "getpwuid", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) { res = mr->data; } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) { errno = ENOENT; return NULL; } /* Make sure the UID and GID are not -1 */ if (res->pw_uid == (uid_t) -1) { pr_log_pri(PR_LOG_WARNING, "error: UID of -1 not allowed"); return NULL; } if (res->pw_gid == (gid_t) -1) { pr_log_pri(PR_LOG_WARNING, "error: GID of -1 not allowed"); return NULL; } pr_log_debug(DEBUG10, "retrieved user '%s' for UID %lu", res->pw_name, (unsigned long) uid); return res; }
static void reids_heartbeat(connector_t pconredis) { struct timeval tm_now; gettimeofday(&tm_now, NULL); if ((tm_now.tv_sec - pconredis->pworker->ticktime) < REDIS_IDLETIME) return; pconredis->pworker->ticktime = tm_now.tv_sec; char *key = REDIS_HBKEY; char cmd[REDIS_CMD_LEN] = {0}; if (make_cmd(cmd, REDIS_CMD_LEN, 2, "get", key) < 0) { print_log(LOG_TYPE_ERROR, "get %s error, file = %s, line = %d", key, __FILE__, __LINE__); return; } int len = strlen(cmd); buffer_write(pconredis->pwritebuf, cmd, len); connector_write(pconredis); }
struct group *pr_auth_getgrnam(pool *p, const char *name) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct group *res = NULL; cmd = make_cmd(p, 1, name); mr = dispatch_auth(cmd, "getgrnam", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) { res = mr->data; } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) { errno = ENOENT; return NULL; } /* Make sure the GID is not -1 */ if (res->gr_gid == (gid_t) -1) { pr_log_pri(PR_LOG_WARNING, "error: GID of -1 not allowed"); return NULL; } gidcache_add(res->gr_gid, name); pr_log_debug(DEBUG10, "retrieved GID %lu for group '%s'", (unsigned long) res->gr_gid, name); return res; }
int main(int argc, char **argv) { char *prog; const char **user_argv; struct commands *cmd; int devnull_fd; int count; git_setup_gettext(); git_extract_argv0_path(argv[0]); /* * Always open file descriptors 0/1/2 to avoid clobbering files * in die(). It also avoids not messing up when the pipes are * dup'ed onto stdin/stdout/stderr in the child processes we spawn. */ devnull_fd = open("/dev/null", O_RDWR); while (devnull_fd >= 0 && devnull_fd <= 2) devnull_fd = dup(devnull_fd); if (devnull_fd == -1) die_errno("opening /dev/null failed"); close (devnull_fd); /* * Special hack to pretend to be a CVS server */ if (argc == 2 && !strcmp(argv[1], "cvs server")) { argv--; } else if (argc == 1) { /* Allow the user to run an interactive shell */ cd_to_homedir(); if (access(COMMAND_DIR, R_OK | X_OK) == -1) { die("Interactive git shell is not enabled.\n" "hint: ~/" COMMAND_DIR " should exist " "and have read and execute access."); } run_shell(); exit(0); } else if (argc != 3 || strcmp(argv[1], "-c")) { /* * We do not accept any other modes except "-c" followed by * "cmd arg", where "cmd" is a very limited subset of git * commands or a command in the COMMAND_DIR */ die("Run with no arguments or with -c cmd"); } prog = xstrdup(argv[2]); if (!strncmp(prog, "git", 3) && isspace(prog[3])) /* Accept "git foo" as if the caller said "git-foo". */ prog[3] = '-'; for (cmd = cmd_list ; cmd->name ; cmd++) { int len = strlen(cmd->name); char *arg; if (strncmp(cmd->name, prog, len)) continue; arg = NULL; switch (prog[len]) { case '\0': arg = NULL; break; case ' ': arg = prog + len + 1; break; default: continue; } exit(cmd->exec(cmd->name, arg)); } cd_to_homedir(); count = split_cmdline(prog, &user_argv); if (count >= 0) { if (is_valid_cmd_name(user_argv[0])) { prog = make_cmd(user_argv[0]); user_argv[0] = prog; execv(user_argv[0], (char *const *) user_argv); } free(prog); free(user_argv); die("unrecognized command '%s'", argv[2]); } else { free(prog); die("invalid command format '%s': %s", argv[2], split_cmdline_strerror(count)); } }
int pr_auth_check(pool *p, const char *cpw, const char *name, const char *pw) { cmd_rec *cmd = NULL; modret_t *mr = NULL; module *m = NULL; int res = PR_AUTH_BADPWD; cmd = make_cmd(p, 3, cpw, name, pw); /* First, check for any of the modules in the "authenticating only" list * of modules. This is usually only mod_auth_pam, but other modules * might also add themselves (e.g. mod_radius under certain conditions). */ if (auth_module_list) { struct auth_module_elt *elt; for (elt = (struct auth_module_elt *) auth_module_list->xas_list; elt; elt = elt->next) { m = pr_module_get(elt->name); if (m) { mr = dispatch_auth(cmd, "check", &m); if (MODRET_ISHANDLED(mr)) { pr_trace_msg(trace_channel, 4, "module '%s' used for authenticating user '%s'", elt->name, name); res = MODRET_HASDATA(mr) ? PR_AUTH_RFC2228_OK : PR_AUTH_OK; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; } if (MODRET_ISERROR(mr)) { res = MODRET_ERROR(mr); if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; } m = NULL; } } } if (auth_tab) { /* Fetch the specific module to be used for authenticating this user. */ void *v = pr_table_get(auth_tab, name, NULL); if (v) { m = *((module **) v); pr_trace_msg(trace_channel, 4, "using module 'mod_%s.c' from authcache to authenticate user '%s'", m->name, name); } } mr = dispatch_auth(cmd, "check", m ? &m : NULL); if (MODRET_ISHANDLED(mr)) res = MODRET_HASDATA(mr) ? PR_AUTH_RFC2228_OK : PR_AUTH_OK; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; }
int cmd_main(int argc, const char **argv) { char *prog; const char **user_argv; struct commands *cmd; int count; /* * Special hack to pretend to be a CVS server */ if (argc == 2 && !strcmp(argv[1], "cvs server")) { argv--; } else if (argc == 1) { /* Allow the user to run an interactive shell */ cd_to_homedir(); if (access(COMMAND_DIR, R_OK | X_OK) == -1) { die("Interactive git shell is not enabled.\n" "hint: ~/" COMMAND_DIR " should exist " "and have read and execute access."); } run_shell(); exit(0); } else if (argc != 3 || strcmp(argv[1], "-c")) { /* * We do not accept any other modes except "-c" followed by * "cmd arg", where "cmd" is a very limited subset of git * commands or a command in the COMMAND_DIR */ die("Run with no arguments or with -c cmd"); } prog = xstrdup(argv[2]); if (!strncmp(prog, "git", 3) && isspace(prog[3])) /* Accept "git foo" as if the caller said "git-foo". */ prog[3] = '-'; for (cmd = cmd_list ; cmd->name ; cmd++) { int len = strlen(cmd->name); char *arg; if (strncmp(cmd->name, prog, len)) continue; arg = NULL; switch (prog[len]) { case '\0': arg = NULL; break; case ' ': arg = prog + len + 1; break; default: continue; } exit(cmd->exec(cmd->name, arg)); } cd_to_homedir(); count = split_cmdline(prog, &user_argv); if (count >= 0) { if (is_valid_cmd_name(user_argv[0])) { prog = make_cmd(user_argv[0]); user_argv[0] = prog; execv(user_argv[0], (char *const *) user_argv); } free(prog); free(user_argv); die("unrecognized command '%s'", argv[2]); } else { free(prog); die("invalid command format '%s': %s", argv[2], split_cmdline_strerror(count)); } }
struct passwd *pr_auth_getpwnam(pool *p, const char *name) { cmd_rec *cmd = NULL; modret_t *mr = NULL; struct passwd *res = NULL; module *m = NULL; cmd = make_cmd(p, 1, name); mr = dispatch_auth(cmd, "getpwnam", &m); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) res = mr->data; if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } /* Sanity check */ if (res == NULL) { errno = ENOENT; return NULL; } /* Make sure the UID and GID are not -1 */ if (res->pw_uid == (uid_t) -1) { pr_log_pri(PR_LOG_ERR, "error: UID of -1 not allowed"); return NULL; } if (res->pw_gid == (gid_t) -1) { pr_log_pri(PR_LOG_ERR, "error: GID of -1 not allowed"); return NULL; } if ((auth_caching & PR_AUTH_CACHE_FL_AUTH_MODULE) && !auth_tab && auth_pool) { auth_tab = pr_table_alloc(auth_pool, 0); } if (m && auth_tab) { int count = 0; void *value = NULL; value = palloc(auth_pool, sizeof(module *)); *((module **) value) = m; count = pr_table_exists(auth_tab, name); if (count <= 0) { if (pr_table_add(auth_tab, pstrdup(auth_pool, name), value, sizeof(module *)) < 0) { pr_trace_msg(trace_channel, 3, "error adding module 'mod_%s.c' for user '%s' to the authcache: %s", m->name, name, strerror(errno)); } else { pr_trace_msg(trace_channel, 5, "stashed module 'mod_%s.c' for user '%s' in the authcache", m->name, name); } } else { if (pr_table_set(auth_tab, pstrdup(auth_pool, name), value, sizeof(module *)) < 0) { pr_trace_msg(trace_channel, 3, "error setting module 'mod_%s.c' for user '%s' in the authcache: %s", m->name, name, strerror(errno)); } else { pr_trace_msg(trace_channel, 5, "stashed module 'mod_%s.c' for user '%s' in the authcache", m->name, name); } } } uidcache_add(res->pw_uid, name); /* Get the (possibly rewritten) home directory. */ res->pw_dir = pr_auth_get_home(p, res->pw_dir); pr_log_debug(DEBUG10, "retrieved UID %lu for user '%s'", (unsigned long) res->pw_uid, name); return res; }
CMD* make_stage(token_list** list_ref) { token_list* list = *list_ref; if (!list) return make_error_cmd("could not form stage (no tokens)"); CMD* stage_tree = mallocCMD(); // Current type is NONE int next_type = NONE; // Hold the type of the head token of list bool redir_in = false; // Has there been a previous input redirection? bool redir_out = false; // Loop until hit a pipe or a separator; raise an error if multiple redirect // or both a command and subcommand while ((next_type = type(list)) != -1 && !ISSEP(next_type) && !ISPIPE(next_type) && next_type != PAR_RIGHT) { bool error = false; // Signals whether the current action results in an // error if (next_type == SIMPLE && stage_tree->type != SUBCMD) { int argc = stage_tree->argc + 1; char** argv = stage_tree->argv; argv = realloc(argv, (argc + 1) * sizeof(char*)); // +1 for trailing // NULL required // by freeCMD argv[argc - 1] = strdup(text(list)); argv[argc] = NULL; stage_tree->argc = argc; stage_tree->argv = argv; stage_tree->type = SIMPLE; } else if ((next_type == RED_IN || next_type == RED_HERE) && !redir_in) { error = make_redirect(stage_tree, &redir_in, next_type, &list); } else if (ISREDOUT(next_type) && !redir_out) { error = make_redirect(stage_tree, &redir_out, next_type, &list); } else if (next_type == PAR_LEFT && stage_tree->type == NONE) { // Can't have two subcommands in a stage advance(&list); // Advance past left parentheses CMD* subcmd_tree = make_cmd(&list); error = subcmd_tree->type == ERROR || type(list) != PAR_RIGHT; stage_tree->type = SUBCMD; stage_tree->left = subcmd_tree; } else { error = true; } if (error) { freeCMD(stage_tree); return make_error_cmd("Invalid stage"); } advance(&list); } // Make sure we didn't double-redirect if (ISPIPE(next_type) && redir_out) { freeCMD(stage_tree); return make_error_cmd("Double redirect - pipe and >"); } // Make sure there was actually an argument if (stage_tree->type == NONE) { freeCMD(stage_tree); return make_error_cmd("No arguments for simple command"); } assert(stage_tree->type != NONE); *list_ref = list; return stage_tree; }
int pr_auth_getgroups(pool *p, const char *name, array_header **group_ids, array_header **group_names) { cmd_rec *cmd = NULL; modret_t *mr = NULL; int res = -1; /* Allocate memory for the array_headers of GIDs and group names. */ if (group_ids) *group_ids = make_array(permanent_pool, 2, sizeof(gid_t)); if (group_names) *group_names = make_array(permanent_pool, 2, sizeof(char *)); cmd = make_cmd(p, 3, name, group_ids ? *group_ids : NULL, group_names ? *group_names : NULL); mr = dispatch_auth(cmd, "getgroups", NULL); if (MODRET_ISHANDLED(mr) && MODRET_HASDATA(mr)) { res = *((int *) mr->data); /* Note: the number of groups returned should, barring error, * always be at least 1, as per getgroups(2) behavior. This one * ID is present because it is the primary group membership set in * struct passwd, from /etc/passwd. This will need to be documented * for the benefit of auth_getgroup() implementors. */ if (group_ids) { register unsigned int i; char *strgids = ""; gid_t *gids = (*group_ids)->elts; for (i = 0; i < (*group_ids)->nelts; i++) { char buf[64]; snprintf(buf, sizeof(buf)-1, "%lu", (unsigned long) gids[i]); buf[sizeof(buf)-1] = '\0'; strgids = pstrcat(p, strgids, i != 0 ? ", " : "", buf, NULL); } pr_log_debug(DEBUG10, "retrieved group %s: %s", (*group_ids)->nelts == 1 ? "ID" : "IDs", strgids); } if (group_names) { register unsigned int i; char *strgroups = ""; char **groups = (*group_names)->elts; for (i = 0; i < (*group_names)->nelts; i++) strgroups = pstrcat(p, strgroups, i != 0 ? ", " : "", groups[i], NULL); pr_log_debug(DEBUG10, "retrieved group %s: %s", (*group_names)->nelts == 1 ? "name" : "names", strgroups); } } if (cmd->tmp_pool) { destroy_pool(cmd->tmp_pool); cmd->tmp_pool = NULL; } return res; }
int main(int argc, char **argv) { term_init(); set_default_opts(); if (getenv("NVC_GDB") != NULL) register_gdb_signal_handlers(); else register_trace_signal_handlers(); atexit(fbuf_cleanup); static struct option long_options[] = { { "help", no_argument, 0, 'h' }, { "version", no_argument, 0, 'v' }, { "work", required_argument, 0, 'w' }, { "dump", no_argument, 0, 'd' }, { "codegen", no_argument, 0, 'c' }, { "make", no_argument, 0, 'm' }, { "std", required_argument, 0, 's' }, { 0, 0, 0, 0 } }; int c, index = 0; const char *spec = "aehrvL:"; while ((c = getopt_long(argc, argv, spec, long_options, &index)) != -1) { switch (c) { case 0: // Set a flag break; case 'h': usage(); exit(EXIT_SUCCESS); case 'v': printf("%s\n%s\n", version_string, copy_string); exit(EXIT_SUCCESS); case 'w': opt_set_str("work-name", optarg); break; case 'L': lib_add_search_path(optarg); break; case 's': set_standard(parse_standard(optarg)); break; case 'a': case 'e': case 'd': case 'r': case 'c': case 'm': // Subcommand options are parsed later argc -= (optind - 1); argv += (optind - 1); goto getopt_out; case '?': // getopt_long already printed an error message exit(EXIT_FAILURE); default: abort(); } } getopt_out: switch (c) { case 'a': return analyse(argc, argv); case 'e': return elaborate(argc, argv); case 'r': return run(argc, argv); case 'd': return dump_cmd(argc, argv); case 'c': return codegen(argc, argv); case 'm': return make_cmd(argc, argv); default: fprintf(stderr, "%s: missing command\n", PACKAGE); return EXIT_FAILURE; } }