bool isNumber(string s) { int i, ri, begin; bool result; // process leading empty space for (i = 0; i != s.length(); i++) { if (s[i] != ' ') { break; } } // process trailing empty space for (ri = s.length() - 1; ri >= i; ri--) { if (s[ri] != ' ') { break; } } begin = i; result = parsenum(s, &i, ri, true); if (i > ri) { return result; } if ((s[i] == 'e') && result) { i++; result = parsenum(s, &i, ri, false); if (i > ri) { return result; } } return false; }
/* ensure value is exactly one number */ static int dlist_tonum64(struct dlist *dl, bit64 *valp) { const char *end; bit64 newval; if (!dl) return 0; switch (dl->type) { case DL_ATOM: case DL_BUF: if (parsenum(dl->sval, &end, dl->nval, &newval)) return 0; if (end - dl->sval != (int)dl->nval) return 0; /* successfully parsed - switch to a numeric value */ dlist_makenum64(dl, newval); break; case DL_NUM: case DL_HEX: case DL_DATE: break; default: return 0; } if (valp) *valp = dl->nval; return 1; }
static int group(int argc, char *argv[]) { struct group *gr; unsigned long id; int i, rv; assert(argc > 1); assert(argv != NULL); #define GROUPPRINT printfmtstrings(gr->gr_mem, ":", ",", "%s:%s:%u", \ gr->gr_name, gr->gr_passwd, gr->gr_gid) setgroupent(1); rv = RV_OK; if (argc == 2) { while ((gr = getgrent()) != NULL) GROUPPRINT; } else { for (i = 2; i < argc; i++) { if (parsenum(argv[i], &id)) gr = getgrgid((gid_t)id); else gr = getgrnam(argv[i]); if (gr != NULL) GROUPPRINT; else { rv = RV_NOTFOUND; break; } } } endgrent(); return rv; }
void l_charity(void) { long donation; print2("'Greetings, friend. Do you wish to make a donation?' [yn] "); if (ynq2()!='y') print3("'Pinchpurse!'"); else { clearmsg(); // print1("How much can you give? "); donation = parsenum("How much can you give?"); if (donation < 1) print2("'Go stick your head in a pig.'"); else if (donation > Player.cash) print2("'I'm afraid you're charity is bigger than your purse!'"); else if (donation < max(100,Player.level*Player.level*100)) { print2("'Oh, can't you do better than that?'"); print3("'Well, I guess we'll take it....'"); if (Player.alignment < 10) Player.alignment++; Player.cash -= donation; } else { print2("'Oh thank you kindly, friend, and bless you!'"); Player.cash -= donation; Player.alignment += 5; } } dataprint(); }
/* * protocols */ static int protocols(int argc, char *argv[]) { struct protoent *pe; unsigned long id; int i, rv; assert(argc > 1); assert(argv != NULL); #define PROTOCOLSPRINT printfmtstrings(pe->p_aliases, " ", " ", \ "%-16s %5d", pe->p_name, pe->p_proto) setprotoent(1); rv = RV_OK; if (argc == 2) { while ((pe = getprotoent()) != NULL) PROTOCOLSPRINT; } else { for (i = 2; i < argc; i++) { if (parsenum(argv[i], &id)) pe = getprotobynumber((int)id); else pe = getprotobyname(argv[i]); if (pe != NULL) PROTOCOLSPRINT; else { rv = RV_NOTFOUND; break; } } } endprotoent(); return rv; }
static tlHandle parse(tlBuffer* buf) { char c; do { c = tlBufferPeekByte(buf, 0); } while (c && c <= 32); trace("probing: %c", c); switch (c) { case '{': { tlBufferSkipByte(buf); trace("{"); tlHashMap* map = tlHashMapNew(); while (true) { tlHandle k = parsekey(buf); if (!k) break; do { c = tlBufferReadByte(buf); } while (c && c <= 32); if (c != '=') { warning("no '=' %c", c); return null; } tlHandle v = parse(buf); if (!v) { warning("no value"); return null; } tlHashMapSet(map, k, v); do { c = tlBufferReadByte(buf); } while (c && c <= 32); if (c != ',') { tlBufferRewind(buf, 1); break; } } c = tlBufferReadByte(buf); if (c != '}') { warning("no '}' %c", c); return null; } trace("}"); tlObject* res = tlHashMapToObject(map); trace("map: %d", tlObjectSize(res)); return res; } case '[': { tlBufferSkipByte(buf); trace("["); tlArray* ls = tlArrayNew(); while (true) { tlHandle h = parse(buf); if (!h) break; tlArrayAdd(ls, h); do { c = tlBufferReadByte(buf); } while (c && c <= 32); if (c != ',') { tlBufferRewind(buf, 1); break; } } c = tlBufferReadByte(buf); if (c != ']') { warning("no ']' %c", c); return null; } trace("]"); return tlArrayToList(ls); } case '"': case '\'': return parsestring(buf, c); case 'n': { tlBufferReadSkip(buf, 4); return tlNull; } case 'f': { tlBufferReadSkip(buf, 5); return tlFalse; } case 't': { tlBufferReadSkip(buf, 4); return tlTrue; } case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': case '-': case '+': case '.': return parsenum(buf); } warning("unparsable: %c", c); return null; }
static void test_parsenum(void) { const char NUM[] = "18338747846901181684 some other stuff"; uint64_t val = CANARY64; int r; r = parsenum(NUM, NULL, strlen(NUM), &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(val, 18338747846901181684LLU); }
static int parse_next_delta_command(struct diffcmd *dc) { int cmd; long line1, nlines; cmd = in_buffer_getc(); if (cmd==EOF) return -1; line1 = parsenum(); while (in_buffer_getc() == ' ') ; in_buffer_ungetc(); nlines = parsenum(); while (in_buffer_getc() != '\n') ; if (!nlines || (cmd != 'a' && cmd != 'd') || line1+nlines < line1) fatal_error("Corrupt delta"); if (cmd == 'a') { if (line1 < dc->adprev) fatal_error("backward insertion in delta"); dc->adprev = line1 + 1; } else if (cmd == 'd') { if (line1 < dc->adprev || line1 < dc->dafter) fatal_error("backward deletion in delta"); dc->adprev = line1; dc->dafter = line1 + nlines; } dc->line1 = line1; dc->nlines = nlines; return cmd == 'a'; }
int parsedate(char *s) { struct dosdate_t d; unsigned char leap; int nums[3], items; assert(s); /* Parse at maximum three numbers */ s = parsenum(s, 3, &items, nums); if (!s || *s) /* general error or too many characters */ return 0; _dos_getdate(&d); /* fetch current info */ switch (items) { case 0: /* empty line --> always OK */ return 1; case 1: /* single number --> day only */ d.day = nums[0]; break; case 3: /* three numbers --> year, month & day */ d.year = nums[2]; /* fall through */ case 2: /* two numbers --> month & day */ d.day = nums[1], d.month = nums[0]; break; } /* if only entered two digits for year, assume 1900's */ if (d.year <= 99) d.year += 1900; leap = (!(d.year % 4) && (d.year % 100)) || !(d.year % 400); if ((d.month >= 1 && d.month <= 12) && (d.day >= 1 && d.day <= months[leap][d.month]) && (d.year >= 1980 && d.year <= 2099)) { _dos_setdate(&d); return 1; } return 0; }
void debugmon(void) { dprintf("Entering crappy crash monitor.\n ? for help.\n"); while (1) { char cmd[128]; char *p = cmd+1; int len; dprintf("#> "); len = dreadline(cmd, 128); switch (cmd[0]) { case '?': dprintf("?\t\thelp\n" "m addr len\tShow memory as words from addr for len words\n" ); break; case 'm': { unsigned int *addr; int mlen; int i; addr = (unsigned int *)parsenum(&p); mlen = parsenum(&p); for (i=0;i<mlen;i++) { if ((i & 7) == 0) dprintf("\n0x%08x:", addr); dprintf(" 0x%08x", *addr); addr++; } dprintf("\n"); break; } default: dprintf("%s: Unknown command or arguments\n", cmd); break; } } }
void warp(int blessing) { int newlevel; if (Current_Environment != Current_Dungeon) mprint("How strange! No effect...."); else { newlevel = (int) parsenum("Warp to which level? "); if (newlevel >= MaxDungeonLevels || blessing < 0 || newlevel < 1) { mprint("You have been deflected!"); newlevel=random_range(MaxDungeonLevels - 1) + 1; } mprint("You dematerialize..."); change_level(Level->depth,newlevel,FALSE); } roomcheck(); }
/* * services */ static int services(int argc, char *argv[]) { struct servent *se; unsigned long id; char *proto; int i, rv; assert(argc > 1); assert(argv != NULL); #define SERVICESPRINT printfmtstrings(se->s_aliases, " ", " ", \ "%-16s %5d/%s", \ se->s_name, ntohs(se->s_port), se->s_proto) setservent(1); rv = RV_OK; if (argc == 2) { while ((se = getservent()) != NULL) SERVICESPRINT; } else { for (i = 2; i < argc; i++) { proto = strchr(argv[i], '/'); if (proto != NULL) *proto++ = '\0'; if (parsenum(argv[i], &id)) se = getservbyport(htons((u_short)id), proto); else se = getservbyname(argv[i], proto); if (se != NULL) SERVICESPRINT; else { rv = RV_NOTFOUND; break; } } } endservent(); return rv; }
/* info ::= num | num '=' attr* defn */ static Type* parseinfo(char *desc, char **pp) { int n1, n2; Type *t; char *attr; n1 = n2 = 0; parsenum(desc, &n1, &n2, &desc); t = typebynum(n1, n2); if(*desc != '='){ *pp = desc; return t; } desc++; if(fstack) fstack->list = mktl(t, fstack->list); while(parseattr(desc, &attr, &desc) >= 0){ if(*attr == 's') t->xsizeof = atoi(attr+1)/8; } return parsedefn(desc, t, pp); }
/* * passwd */ static int passwd(int argc, char *argv[]) { struct passwd *pw; unsigned long id; int i, rv; assert(argc > 1); assert(argv != NULL); #define PASSWDPRINT printf("%s:%s:%u:%u:%s:%s:%s\n", \ pw->pw_name, pw->pw_passwd, pw->pw_uid, \ pw->pw_gid, pw->pw_gecos, pw->pw_dir, pw->pw_shell) setpassent(1); rv = RV_OK; if (argc == 2) { while ((pw = getpwent()) != NULL) PASSWDPRINT; } else { for (i = 2; i < argc; i++) { if (parsenum(argv[i], &id)) pw = getpwuid((uid_t)id); else pw = getpwnam(argv[i]); if (pw != NULL) PASSWDPRINT; else { rv = RV_NOTFOUND; break; } } } endpwent(); return rv; }
/* * rpc */ static int rpc(int argc, char *argv[]) { struct rpcent *re; unsigned long id; int i, rv; assert(argc > 1); assert(argv != NULL); #define RPCPRINT printfmtstrings(re->r_aliases, " ", " ", \ "%-16s %6d", \ re->r_name, re->r_number) setrpcent(1); rv = RV_OK; if (argc == 2) { while ((re = getrpcent()) != NULL) RPCPRINT; } else { for (i = 2; i < argc; i++) { if (parsenum(argv[i], &id)) re = getrpcbynumber((int)id); else re = getrpcbyname(argv[i]); if (re != NULL) RPCPRINT; else { rv = RV_NOTFOUND; break; } } } endrpcent(); return rv; }
int parsetime(const char *s, struct dostime_t * const timep) { struct dostime_t t; int nums[4], items; int pm; assert(s); memset(nums, 0, sizeof(nums)); /* let default everything to zero */ /* Parse at maximum three numbers */ s = parsenum(s, 4, &items, nums); if (!s) /* general error */ return E_Syntax; /* 12 hour time format? */ pm = 0; /* no such flag */ switch(toupper(*s)) { case 'P': ++pm; /* post meridian */ case 'A': ++pm; /* ante meridian */ /* strip ?M or ?.M. */ if(toupper(s[1]) == 'M') s += 2; else if(memicmp(s + 1, ".M.", 3) == 0) s += 4; } if(*ltrimsp(s)) return E_Syntax; /* too many characters on line */ switch (items) { case 0: /* empty line --> always OK */ return E_Empty; case 1: /* single number --> error */ return E_Useage; #if 0 default: /* four numbers --> 1/100s, s, min, h */ /* else: 1/100s and/or s default to zero */ break; #endif } t.hour = nums[0]; t.minute = nums[1]; t.second = nums[2]; /* if missing defaults to previously set */ t.hsecond = nums[3]; /* values, aka 0 */ switch (pm) { case 2: /* post meridian */ if(t.hour != 12) t.hour += 12; break; case 1: /* antes meridian */ if (t.hour == 12) t.hour = 0; break; /* default: not specified --> nothing to do */ } if (t.hour >= 24 || t.minute >= 60 || t.second >= 60 || t.hsecond > 99) return E_Range; if(timep) memcpy(timep, &t, sizeof(t)); return E_None; }
void l_lift(void) { char response; int levelnum; int distance; int too_far = 0; Level->site[Player.x][Player.y].locchar = FLOOR; Level->site[Player.x][Player.y].p_locf = L_NO_OP; lset(Player.x, Player.y, CHANGED); print1("You walk onto a shimmering disk...."); print2("The disk vanishes, and a glow surrounds you."); print3("You feel weightless.... You feel ghostly...."); morewait(); clearmsg(); print1("Go up, down, or neither [u,d,ESCAPE] "); do response = (char) mcigetc(); while ((response != 'u') && (response != 'd') && (response != ESCAPE)); if (response != ESCAPE) { print1("How many levels?"); levelnum = (int) parsenum(""); if (levelnum > 6) { too_far = 1; levelnum = 6; } if (response == 'u' && Level->depth - levelnum < 1) { distance = levelnum - Level->depth; change_environment(E_COUNTRYSIDE); /* "you return to the countryside." */ if (distance > 0) { nprint1(".."); print2("...and keep going up! You hang in mid air..."); morewait(); print3("\"What goes up...\""); morewait(); print3("Yaaaaaaaah........"); p_damage(distance*10,NORMAL_DAMAGE,"a fall from a great height"); } return; } else if (response == 'd' && Level->depth + levelnum > MaxDungeonLevels) { too_far = 1; levelnum = MaxDungeonLevels - Level->depth; } if (levelnum == 0) { print1("Nothing happens."); return; } if (too_far) { print1("The lift gives out partway..."); print2("You rematerialize....."); } else print1("You rematerialize....."); change_level(Level->depth, (response=='d' ? Level->depth+levelnum : Level->depth-levelnum), FALSE); roomcheck(); } }
constexpr unsigned long long parsenum(char d,C...n){ return (d-'0')*pow10(sizeof...(n))+parsenum(n...); }
static void cb_snaplen(const char *arg) { opt_want_snaplen = (int)parsenum(arg, 0); }
/* addcom: create a new custom command */ int CmdHandler::addcom(char *out, struct command *c) { time_t cooldown; int opt; static struct l_option long_opts[] = { { "cooldown", REQ_ARG, 'c'}, { "help", NO_ARG, 'h' }, { 0, 0, 0 } }; if (!P_ALMOD(c->privileges)) { PERM_DENIED(out, c->nick, c->argv[0]); return EXIT_FAILURE; } if (!custom_cmds->active()) { snprintf(out, MAX_MSG, "%s: custom commands are " "currently disabled", c->argv[0]); return EXIT_FAILURE; } cooldown = 15; opt_init(); while ((opt = l_getopt_long(c->argc, c->argv, "c:", long_opts)) != EOF) { switch (opt) { case 'c': /* user provided a cooldown */ if (!parsenum(l_optarg, &cooldown)) { snprintf(out, MAX_MSG, "%s: invalid number: %s", c->argv[0], l_optarg); return EXIT_FAILURE; } if (cooldown < 0) { snprintf(out, MAX_MSG, "%s: cooldown cannot be " "negative", c->argv[0]); return EXIT_FAILURE; } break; case 'h': HELPMSG(out, CMDNAME, CMDUSAGE, CMDDESCR); return EXIT_SUCCESS; case '?': snprintf(out, MAX_MSG, "%s", l_opterr()); return EXIT_FAILURE; default: return EXIT_FAILURE; } } if (l_optind == c->argc) { USAGEMSG(out, CMDNAME, CMDUSAGE); return EXIT_FAILURE; } if (l_optind == c->argc - 1) { snprintf(out, MAX_MSG, "%s: no response provided for " "command $%s", c->argv[0], c->argv[l_optind]); return EXIT_FAILURE; } return create(out, custom_cmds, c, cooldown); }
int parsetime(char *s) { struct dostime_t t; int nums[4], items; int pm; assert(s); memset(nums, 0, sizeof(nums)); /* let default everything to zero */ /* Parse at maximum three numbers */ s = parsenum(s, 4, &items, nums); if (!s) /* general error */ return 0; /* 12 hour time format? */ pm = 0; /* no such flag */ switch (*strupr(s)) { case 'P': ++pm; /* post meridian */ case 'A': ++pm; /* ante meridian */ /* strip ?M or ?.M. */ if (s[1] == 'M') ++s; else if (memcmp(s + 1, ".M.", 3) == 0) s += 3; /* strip whitespaces */ while (isspace(*++s)) ; /* skip whitespaces */ } if (*s) return 0; /* too many characters on line */ switch (items) { case 0: /* empty line --> always OK */ return 1; case 1: /* single number --> error */ return 0; #if 0 default: /* four numbers --> 1/100s, s, min, h */ /* else: 1/100s and/or s default to zero */ break; #endif } t.hour = nums[0]; t.minute = nums[1]; t.second = nums[2]; t.hsecond = nums[3]; switch (pm) { case 2: /* post meridian */ if(t.hour != 12) t.hour += 12; break; case 1: /* antes meridian */ if (t.hour == 12) t.hour = 0; break; /* default: not specified --> nothing to do */ } if (t.hour > 23 || t.minute >= 60 || t.second >= 60 || t.hsecond > 99) return 0; _dos_settime(&t); return 1; }
/* mod: perform moderation commands */ int CmdHandler::mod(char *out, struct command *c) { char *s; const char *t; int action, lenflag; int64_t len; char reason[MAX_MSG]; char name[RSN_BUF]; int opt; static struct l_option long_opts[] = { { "ban", NO_ARG, 'b' }, { "help", NO_ARG, 'h' }, { "length", REQ_ARG, 'l' }, { "timeout", NO_ARG, 't' }, { 0, 0, 0 } }; if (!P_ALMOD(c->privileges)) { PERM_DENIED(out, c->nick, c->argv[0]); return EXIT_FAILURE; } opt_init(); action = lenflag = 0; len = 300; while ((opt = l_getopt_long(c->argc, c->argv, "bl:t", long_opts)) != EOF) { switch (opt) { case 'b': if (action) { snprintf(out, MAX_MSG, "%s: cannot both timeout" " and ban", c->argv[0]); return EXIT_FAILURE; } action = BAN; break; case 'h': HELPMSG(out, CMDNAME, CMDUSAGE, CMDDESCR); return EXIT_SUCCESS; case 'l': if (!parsenum(l_optarg, &len)) { snprintf(out, MAX_MSG, "%s: invalid number: %s", c->argv[0], l_optarg); return EXIT_FAILURE; } if (len < 0) { snprintf(out, MAX_MSG, "%s: length cannot be " "negative", c->argv[0]); return EXIT_FAILURE; } lenflag = 1; break; case 't': if (action) { snprintf(out, MAX_MSG, "%s: cannot both timeout" " and ban", c->argv[0]); return EXIT_FAILURE; } action = TIMEOUT; break; case '?': snprintf(out, MAX_MSG, "%s", l_opterr()); return EXIT_FAILURE; default: return EXIT_FAILURE; } } if (!action || l_optind == c->argc) { USAGEMSG(out, CMDNAME, CMDUSAGE); return EXIT_FAILURE; } if (lenflag && action != TIMEOUT) { snprintf(out, MAX_MSG, "%s: specifying length doesn't " "make sense for a ban", c->nick); return EXIT_FAILURE; } /* convert names to lower for lookup */ s = name; t = bot_name; while ((*s++ = tolower(*t++))) ; for (s = c->argv[l_optind]; *s; ++s) *s = tolower(*s); if (strcmp(c->argv[l_optind], name) == 0) { snprintf(out, MAX_MSG, "@%s, I'd rather not.", c->nick); return EXIT_SUCCESS; } if (strcmp(c->argv[l_optind], c->nick) == 0) { snprintf(out, MAX_MSG, "@%s, don't be silly!", c->nick); return EXIT_SUCCESS; } argvcat(reason, c->argc, c->argv, l_optind + 1, 1); /* attempt to perform the moderation action */ if (!moderator->mod_action(action, c->argv[l_optind], c->nick, reason, len)) { snprintf(out, MAX_MSG, "%s: user '%s' is not currently in the " "channel", c->argv[0], c->argv[l_optind]); return EXIT_FAILURE; } snprintf(out, MAX_MSG, "@%s, user '%s' has been %s", c->nick, c->argv[l_optind], action == BAN ? "banned" : "timed out"); if (*reason) { strcat(out, " for "); strcat(out, reason); } strcat(out, "."); return EXIT_SUCCESS; }
void parseopts(int argc, char **argv) { int c; /* initialize default option values */ psc_dynarray_init(&opts.exclude); psc_dynarray_init(&opts.files); psc_dynarray_init(&opts.filter); psc_dynarray_init(&opts.include); opts.progress = 1; opts.psync_path = "psync"; opts.rsh = "ssh " "-oControlPath=none " "-oCompression=no " "-oKbdInteractiveAuthentication=no " "-oNumberOfPasswordPrompts=1"; opts.streams = getnstreams(getnprocessors()); while ((c = getopt_long(argc, argv, "0468aB:bCcDdEEe:f:gHhIiKkLlmN:nOoPpqRrST:tuVvWxyz", longopts, NULL)) != -1) { switch (c) { case '0': opts.from0 = 1; break; case '4': opts.ipv4 = 1; break; case '6': opts.ipv6 = 1; break; case '8': opts._8_bit_output = 1; break; case 'a': opts.devices = 1; opts.group = 1; opts.links = 1; opts.owner = 1; opts.perms = 1; opts.recursive = 1; opts.specials = 1; opts.times = 1; break; case 'B': if (!parsesize(&opts.block_size, optarg, 1)) err(1, "-B %s", optarg); break; case 'b': opts.backup = 1; break; case 'C': opts.cvs_exclude = 1; break; case 'c': opts.checksum = 1; break; case 'D': opts.devices = 1; opts.specials = 1; break; case 'd': opts.dirs = 1; break; case 'E': opts.extended_attributes = 1; break; case 'e': opts.rsh = optarg; break; case 'f': push_filter(&opts.filter, optarg, FPT_INCL); break; case 'g': opts.group = 1; break; case 'H': opts.hard_links = 1; break; case 'h': opts.human_readable = 1; break; case 'I': opts.ignore_times = 1; break; case 'i': opts.itemize_changes = 1; break; case 'K': opts.keep_dirlinks = 1; break; case 'k': opts.copy_dirlinks = 1; break; case 'L': opts.copy_links = 1; break; case 'l': opts.links = 1; break; case 'm': opts.prune_empty_dirs = 1; break; case 'N': if (!parsenum(&opts.streams, optarg, 0, MAX_STREAMS)) err(1, "streams: %s", optarg); break; case 'n': opts.dry_run = 1; break; case 'O': opts.omit_dir_times = 1; break; case 'o': opts.owner = 1; break; case 'P': opts.progress = 1; opts.partial = 1; break; case 'p': opts.perms = 1; break; case 'q': opts.quiet = 1; break; case 'R': opts.relative = 1; break; case 'r': opts.recursive = 1; break; case 'S': opts.sparse = 1; break; case 'T': opts.temp_dir = optarg; break; case 't': opts.times = 1; break; case 'u': opts.update = 1; break; case 'V': fprintf(stderr, "psync version %d\n", PSYNC_VERSION); exit(0); break; case 'v': opts.verbose = 1; break; case 'W': opts.whole_file = 1; break; case 'x': opts.one_file_system = 1; break; case 'y': opts.fuzzy = 1; break; case 'z': opts.compress = 1; break; case OPT_ADDRESS: opts.address = optarg; break; case OPT_BWLIMIT: if (!parsesize(&opts.bwlimit, optarg, 1024)) err(1, "--bwlimit=%s", optarg); break; case OPT_CHMOD: opts.chmod = optarg; break; case OPT_COMPARE_DEST: opts.compare_dest = optarg; break; case OPT_COMPRESS_LEVEL: if (!parsenum(&opts.compress_level, optarg, 0, 10)) err(1, "--compress-level=%s", optarg); break; case OPT_COPY_DEST: opts.copy_dest = optarg; break; case OPT_EXCLUDE: push_filter(&opts.filter, optarg, FPT_EXCL); break; case OPT_EXCLUDE_FROM: pushfile(&opts.filter, optarg, push_filter, FPT_EXCL); break; case OPT_FILES_FROM: pushfile(&opts.files, optarg, push_files_from, FPT_INCL); break; case OPT_INCLUDE: push_filter(&opts.filter, optarg, FPT_INCL); break; case OPT_INCLUDE_FROM: pushfile(&opts.filter, optarg, push_filter, FPT_INCL); break; case OPT_LINK_DEST: opts.link_dest = optarg; break; case OPT_LOG_FILE: opts.log_file = optarg; break; case OPT_LOG_FILE_FORMAT: opts.log_file_format = optarg; break; case OPT_MAX_DELETE: if (!parsenum(&opts.max_delete, optarg, 0, INT_MAX)) err(1, "--max-delete=%s", optarg); break; case OPT_MAX_SIZE: if (!parsesize(&opts.max_size, optarg, 1)) err(1, "--max-size=%s", optarg); break; case OPT_MIN_SIZE: if (!parsesize(&opts.min_size, optarg, 1)) err(1, "--min-size=%s", optarg); break; case OPT_MODIFY_WINDOW: if (!parsenum(&opts.modify_window, optarg, 0, INT_MAX)) err(1, "--modify-window=%s", optarg); break; case OPT_ONLY_WRITE_BATCH:opts.write_batch = optarg; break; case OPT_OUT_FORMAT: opts.out_format = optarg; break; case OPT_PORT: if (!parsenum(&opts.port, optarg, 0, 65535)) err(1, "--port=%s", optarg); break; case OPT_PARTIAL_DIR: opts.partial_dir = optarg; break; case OPT_PASSWORD_FILE: opts.password_file = optarg; break; case OPT_PSYNC_PATH: opts.psync_path = optarg; break; case OPT_READ_BATCH: opts.read_batch = optarg; break; case OPT_SOCKOPTS: opts.sockopts = optarg; break; case OPT_SUFFIX: opts.suffix = optarg; break; case OPT_TIMEOUT: if (!parsenum(&opts.timeout, optarg, 0, INT_MAX)) err(1, "--timeout=%s", optarg); break; case OPT_WRITE_BATCH: opts.write_batch = optarg; break; /* psync specific options */ case OPT_DSTDIR: opts.dstdir = optarg; break; case OPT_PUPPET: if (!parsenum(&opts.puppet, optarg, 0, 1000000)) err(1, "--PUPPET=%s", optarg); break; case 0: break; default: warn("invalid option: -%c", c); usage(); } } }
static int gettarhead(struct tarhead *th) { int l, type; long long length; th->path = solv_free(th->path); th->ispax = 0; th->type = 0; th->length = 0; th->off = 0; th->end = 0; if (th->eof) return 0; for (;;) { int r = readblock(th->fp, th->blk); if (r) { if (feof(th->fp)) { th->eof = 1; return 0; } return -1; } if (th->blk[0] == 0) { th->eof = 1; return 0; } length = parsenum(th->blk + 124, 12); if (length < 0) return -1; type = 0; switch (th->blk[156]) { case 'S': case '0': type = 1; /* file */ break; case '1': /* hard link, special length magic... */ if (!th->ispax) length = 0; break; case '5': type = 2; /* dir */ break; case '2': case '3': case '4': case '6': length = 0; break; case 'X': case 'x': case 'L': { char *data, *pp; if (length < 1 || length >= 1024 * 1024) return -1; l = length; data = pp = solv_malloc(l + 512); for (; l > 0; l -= 512, pp += 512) if (readblock(th->fp, (unsigned char *)pp)) { solv_free(data); return -1; } type = 3; /* extension */ if (th->blk[156] == 'L') { solv_free(th->path); th->path = data; length = 0; break; } pp = data; while (length > 0) { int ll = 0; int l; for (l = 0; l < length && pp[l] >= '0' && pp[l] <= '9'; l++) ll = ll * 10 + (pp[l] - '0'); if (l == length || pp[l] != ' ' || ll < 1 || ll > length || pp[ll - 1] != '\n') { solv_free(data); return -1; } length -= ll; pp += l + 1; ll -= l + 1; pp[ll - 1] = 0; if (!strncmp(pp, "path=", 5)) { solv_free(th->path); th->path = solv_strdup(pp + 5); } pp += ll; } solv_free(data); th->ispax = 1; length = 0; break; } default: type = 3; /* extension */ break; } if ((type == 1 || type == 2) && !th->path) { char path[157]; memcpy(path, th->blk, 156); path[156] = 0; if (!memcmp(th->blk + 257, "ustar\0\060\060", 8) && !th->path && th->blk[345]) { /* POSIX ustar with prefix */ char prefix[156]; memcpy(prefix, th->blk + 345, 155); prefix[155] = 0; l = strlen(prefix); if (l && prefix[l - 1] == '/') prefix[l - 1] = 0; th->path = solv_dupjoin(prefix, "/", path); } else th->path = solv_dupjoin(path, 0, 0); } if (type == 1 || type == 2) { l = strlen(th->path); if (l && th->path[l - 1] == '/') { if (l > 1) th->path[l - 1] = 0; type = 2; } } if (type != 3) break; while (length > 0) { r = readblock(th->fp, th->blk); if (r) return r; length -= 512; } } th->type = type; th->length = length; return 1; }