diff options
| author | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2007-01-01 23:51:30 +0000 |
|---|---|---|
| committer | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2007-01-01 23:51:30 +0000 |
| commit | f47f1260c1562ffbed0534a00f6946af1dda4e09 (patch) | |
| tree | 232224d85ecc50c7204fa96f0fce43eb70bca586 | |
| parent | a1d5274ff00fa15246a788150635a3f576899eae (diff) | |
| download | busybox-w32-f47f1260c1562ffbed0534a00f6946af1dda4e09.tar.gz busybox-w32-f47f1260c1562ffbed0534a00f6946af1dda4e09.tar.bz2 busybox-w32-f47f1260c1562ffbed0534a00f6946af1dda4e09.zip | |
awk: style cleanup. A lot of rw data moved to ro
(still has quite a lot of statics etc...).
getopt32-ification.
git-svn-id: svn://busybox.net/trunk/busybox@17125 69ca8d6d-28ef-0310-b511-8ec308f3f277
| -rw-r--r-- | editors/awk.c | 587 |
1 files changed, 293 insertions, 294 deletions
diff --git a/editors/awk.c b/editors/awk.c index 5a500aa83..97e78163c 100644 --- a/editors/awk.c +++ b/editors/awk.c | |||
| @@ -77,10 +77,10 @@ typedef struct hash_item_s { | |||
| 77 | } hash_item; | 77 | } hash_item; |
| 78 | 78 | ||
| 79 | typedef struct xhash_s { | 79 | typedef struct xhash_s { |
| 80 | unsigned int nel; /* num of elements */ | 80 | unsigned nel; /* num of elements */ |
| 81 | unsigned int csize; /* current hash size */ | 81 | unsigned csize; /* current hash size */ |
| 82 | unsigned int nprime; /* next hash size in PRIMES[] */ | 82 | unsigned nprime; /* next hash size in PRIMES[] */ |
| 83 | unsigned int glen; /* summary length of item names */ | 83 | unsigned glen; /* summary length of item names */ |
| 84 | struct hash_item_s **items; | 84 | struct hash_item_s **items; |
| 85 | } xhash; | 85 | } xhash; |
| 86 | 86 | ||
| @@ -260,88 +260,87 @@ enum { | |||
| 260 | 260 | ||
| 261 | #define OC_B OC_BUILTIN | 261 | #define OC_B OC_BUILTIN |
| 262 | 262 | ||
| 263 | static char * const tokenlist = | 263 | static const char tokenlist[] = |
| 264 | "\1(" NTC | 264 | "\1(" NTC |
| 265 | "\1)" NTC | 265 | "\1)" NTC |
| 266 | "\1/" NTC /* REGEXP */ | 266 | "\1/" NTC /* REGEXP */ |
| 267 | "\2>>" "\1>" "\1|" NTC /* OUTRDR */ | 267 | "\2>>" "\1>" "\1|" NTC /* OUTRDR */ |
| 268 | "\2++" "\2--" NTC /* UOPPOST */ | 268 | "\2++" "\2--" NTC /* UOPPOST */ |
| 269 | "\2++" "\2--" "\1$" NTC /* UOPPRE1 */ | 269 | "\2++" "\2--" "\1$" NTC /* UOPPRE1 */ |
| 270 | "\2==" "\1=" "\2+=" "\2-=" /* BINOPX */ | 270 | "\2==" "\1=" "\2+=" "\2-=" /* BINOPX */ |
| 271 | "\2*=" "\2/=" "\2%=" "\2^=" | 271 | "\2*=" "\2/=" "\2%=" "\2^=" |
| 272 | "\1+" "\1-" "\3**=" "\2**" | 272 | "\1+" "\1-" "\3**=" "\2**" |
| 273 | "\1/" "\1%" "\1^" "\1*" | 273 | "\1/" "\1%" "\1^" "\1*" |
| 274 | "\2!=" "\2>=" "\2<=" "\1>" | 274 | "\2!=" "\2>=" "\2<=" "\1>" |
| 275 | "\1<" "\2!~" "\1~" "\2&&" | 275 | "\1<" "\2!~" "\1~" "\2&&" |
| 276 | "\2||" "\1?" "\1:" NTC | 276 | "\2||" "\1?" "\1:" NTC |
| 277 | "\2in" NTC | 277 | "\2in" NTC |
| 278 | "\1," NTC | 278 | "\1," NTC |
| 279 | "\1|" NTC | 279 | "\1|" NTC |
| 280 | "\1+" "\1-" "\1!" NTC /* UOPPRE2 */ | 280 | "\1+" "\1-" "\1!" NTC /* UOPPRE2 */ |
| 281 | "\1]" NTC | 281 | "\1]" NTC |
| 282 | "\1{" NTC | 282 | "\1{" NTC |
| 283 | "\1}" NTC | 283 | "\1}" NTC |
| 284 | "\1;" NTC | 284 | "\1;" NTC |
| 285 | "\1\n" NTC | 285 | "\1\n" NTC |
| 286 | "\2if" "\2do" "\3for" "\5break" /* STATX */ | 286 | "\2if" "\2do" "\3for" "\5break" /* STATX */ |
| 287 | "\10continue" "\6delete" "\5print" | 287 | "\10continue" "\6delete" "\5print" |
| 288 | "\6printf" "\4next" "\10nextfile" | 288 | "\6printf" "\4next" "\10nextfile" |
| 289 | "\6return" "\4exit" NTC | 289 | "\6return" "\4exit" NTC |
| 290 | "\5while" NTC | 290 | "\5while" NTC |
| 291 | "\4else" NTC | 291 | "\4else" NTC |
| 292 | 292 | ||
| 293 | "\3and" "\5compl" "\6lshift" "\2or" | 293 | "\3and" "\5compl" "\6lshift" "\2or" |
| 294 | "\6rshift" "\3xor" | 294 | "\6rshift" "\3xor" |
| 295 | "\5close" "\6system" "\6fflush" "\5atan2" /* BUILTIN */ | 295 | "\5close" "\6system" "\6fflush" "\5atan2" /* BUILTIN */ |
| 296 | "\3cos" "\3exp" "\3int" "\3log" | 296 | "\3cos" "\3exp" "\3int" "\3log" |
| 297 | "\4rand" "\3sin" "\4sqrt" "\5srand" | 297 | "\4rand" "\3sin" "\4sqrt" "\5srand" |
| 298 | "\6gensub" "\4gsub" "\5index" "\6length" | 298 | "\6gensub" "\4gsub" "\5index" "\6length" |
| 299 | "\5match" "\5split" "\7sprintf" "\3sub" | 299 | "\5match" "\5split" "\7sprintf" "\3sub" |
| 300 | "\6substr" "\7systime" "\10strftime" | 300 | "\6substr" "\7systime" "\10strftime" |
| 301 | "\7tolower" "\7toupper" NTC | 301 | "\7tolower" "\7toupper" NTC |
| 302 | "\7getline" NTC | 302 | "\7getline" NTC |
| 303 | "\4func" "\10function" NTC | 303 | "\4func" "\10function" NTC |
| 304 | "\5BEGIN" NTC | 304 | "\5BEGIN" NTC |
| 305 | "\3END" "\0" | 305 | "\3END" "\0" |
| 306 | ; | 306 | ; |
| 307 | 307 | ||
| 308 | static const uint32_t tokeninfo[] = { | 308 | static const uint32_t tokeninfo[] = { |
| 309 | |||
| 310 | 0, | 309 | 0, |
| 311 | 0, | 310 | 0, |
| 312 | OC_REGEXP, | 311 | OC_REGEXP, |
| 313 | xS|'a', xS|'w', xS|'|', | 312 | xS|'a', xS|'w', xS|'|', |
| 314 | OC_UNARY|xV|P(9)|'p', OC_UNARY|xV|P(9)|'m', | 313 | OC_UNARY|xV|P(9)|'p', OC_UNARY|xV|P(9)|'m', |
| 315 | OC_UNARY|xV|P(9)|'P', OC_UNARY|xV|P(9)|'M', | 314 | OC_UNARY|xV|P(9)|'P', OC_UNARY|xV|P(9)|'M', |
| 316 | OC_FIELD|xV|P(5), | 315 | OC_FIELD|xV|P(5), |
| 317 | OC_COMPARE|VV|P(39)|5, OC_MOVE|VV|P(74), | 316 | OC_COMPARE|VV|P(39)|5, OC_MOVE|VV|P(74), |
| 318 | OC_REPLACE|NV|P(74)|'+', OC_REPLACE|NV|P(74)|'-', | 317 | OC_REPLACE|NV|P(74)|'+', OC_REPLACE|NV|P(74)|'-', |
| 319 | OC_REPLACE|NV|P(74)|'*', OC_REPLACE|NV|P(74)|'/', | 318 | OC_REPLACE|NV|P(74)|'*', OC_REPLACE|NV|P(74)|'/', |
| 320 | OC_REPLACE|NV|P(74)|'%', OC_REPLACE|NV|P(74)|'&', | 319 | OC_REPLACE|NV|P(74)|'%', OC_REPLACE|NV|P(74)|'&', |
| 321 | OC_BINARY|NV|P(29)|'+', OC_BINARY|NV|P(29)|'-', | 320 | OC_BINARY|NV|P(29)|'+', OC_BINARY|NV|P(29)|'-', |
| 322 | OC_REPLACE|NV|P(74)|'&', OC_BINARY|NV|P(15)|'&', | 321 | OC_REPLACE|NV|P(74)|'&', OC_BINARY|NV|P(15)|'&', |
| 323 | OC_BINARY|NV|P(25)|'/', OC_BINARY|NV|P(25)|'%', | 322 | OC_BINARY|NV|P(25)|'/', OC_BINARY|NV|P(25)|'%', |
| 324 | OC_BINARY|NV|P(15)|'&', OC_BINARY|NV|P(25)|'*', | 323 | OC_BINARY|NV|P(15)|'&', OC_BINARY|NV|P(25)|'*', |
| 325 | OC_COMPARE|VV|P(39)|4, OC_COMPARE|VV|P(39)|3, | 324 | OC_COMPARE|VV|P(39)|4, OC_COMPARE|VV|P(39)|3, |
| 326 | OC_COMPARE|VV|P(39)|0, OC_COMPARE|VV|P(39)|1, | 325 | OC_COMPARE|VV|P(39)|0, OC_COMPARE|VV|P(39)|1, |
| 327 | OC_COMPARE|VV|P(39)|2, OC_MATCH|Sx|P(45)|'!', | 326 | OC_COMPARE|VV|P(39)|2, OC_MATCH|Sx|P(45)|'!', |
| 328 | OC_MATCH|Sx|P(45)|'~', OC_LAND|Vx|P(55), | 327 | OC_MATCH|Sx|P(45)|'~', OC_LAND|Vx|P(55), |
| 329 | OC_LOR|Vx|P(59), OC_TERNARY|Vx|P(64)|'?', | 328 | OC_LOR|Vx|P(59), OC_TERNARY|Vx|P(64)|'?', |
| 330 | OC_COLON|xx|P(67)|':', | 329 | OC_COLON|xx|P(67)|':', |
| 331 | OC_IN|SV|P(49), | 330 | OC_IN|SV|P(49), |
| 332 | OC_COMMA|SS|P(80), | 331 | OC_COMMA|SS|P(80), |
| 333 | OC_PGETLINE|SV|P(37), | 332 | OC_PGETLINE|SV|P(37), |
| 334 | OC_UNARY|xV|P(19)|'+', OC_UNARY|xV|P(19)|'-', | 333 | OC_UNARY|xV|P(19)|'+', OC_UNARY|xV|P(19)|'-', |
| 335 | OC_UNARY|xV|P(19)|'!', | 334 | OC_UNARY|xV|P(19)|'!', |
| 336 | 0, | 335 | 0, |
| 337 | 0, | 336 | 0, |
| 338 | 0, | 337 | 0, |
| 339 | 0, | 338 | 0, |
| 340 | 0, | 339 | 0, |
| 341 | ST_IF, ST_DO, ST_FOR, OC_BREAK, | 340 | ST_IF, ST_DO, ST_FOR, OC_BREAK, |
| 342 | OC_CONTINUE, OC_DELETE|Vx, OC_PRINT, | 341 | OC_CONTINUE, OC_DELETE|Vx, OC_PRINT, |
| 343 | OC_PRINTF, OC_NEXT, OC_NEXTFILE, | 342 | OC_PRINTF, OC_NEXT, OC_NEXTFILE, |
| 344 | OC_RETURN|Vx, OC_EXIT|Nx, | 343 | OC_RETURN|Vx, OC_EXIT|Nx, |
| 345 | ST_WHILE, | 344 | ST_WHILE, |
| 346 | 0, | 345 | 0, |
| 347 | 346 | ||
| @@ -363,32 +362,32 @@ static const uint32_t tokeninfo[] = { | |||
| 363 | /* internal variable names and their initial values */ | 362 | /* internal variable names and their initial values */ |
| 364 | /* asterisk marks SPECIAL vars; $ is just no-named Field0 */ | 363 | /* asterisk marks SPECIAL vars; $ is just no-named Field0 */ |
| 365 | enum { | 364 | enum { |
| 366 | CONVFMT=0, OFMT, FS, OFS, | 365 | CONVFMT=0, OFMT, FS, OFS, |
| 367 | ORS, RS, RT, FILENAME, | 366 | ORS, RS, RT, FILENAME, |
| 368 | SUBSEP, ARGIND, ARGC, ARGV, | 367 | SUBSEP, ARGIND, ARGC, ARGV, |
| 369 | ERRNO, FNR, | 368 | ERRNO, FNR, |
| 370 | NR, NF, IGNORECASE, | 369 | NR, NF, IGNORECASE, |
| 371 | ENVIRON, F0, _intvarcount_ | 370 | ENVIRON, F0, _intvarcount_ |
| 372 | }; | 371 | }; |
| 373 | 372 | ||
| 374 | static char * vNames = | 373 | static const char vNames[] = |
| 375 | "CONVFMT\0" "OFMT\0" "FS\0*" "OFS\0" | 374 | "CONVFMT\0" "OFMT\0" "FS\0*" "OFS\0" |
| 376 | "ORS\0" "RS\0*" "RT\0" "FILENAME\0" | 375 | "ORS\0" "RS\0*" "RT\0" "FILENAME\0" |
| 377 | "SUBSEP\0" "ARGIND\0" "ARGC\0" "ARGV\0" | 376 | "SUBSEP\0" "ARGIND\0" "ARGC\0" "ARGV\0" |
| 378 | "ERRNO\0" "FNR\0" | 377 | "ERRNO\0" "FNR\0" |
| 379 | "NR\0" "NF\0*" "IGNORECASE\0*" | 378 | "NR\0" "NF\0*" "IGNORECASE\0*" |
| 380 | "ENVIRON\0" "$\0*" "\0"; | 379 | "ENVIRON\0" "$\0*" "\0"; |
| 381 | 380 | ||
| 382 | static char * vValues = | 381 | static const char vValues[] = |
| 383 | "%.6g\0" "%.6g\0" " \0" " \0" | 382 | "%.6g\0" "%.6g\0" " \0" " \0" |
| 384 | "\n\0" "\n\0" "\0" "\0" | 383 | "\n\0" "\n\0" "\0" "\0" |
| 385 | "\034\0" | 384 | "\034\0" |
| 386 | "\377"; | 385 | "\377"; |
| 387 | 386 | ||
| 388 | /* hash size may grow to these values */ | 387 | /* hash size may grow to these values */ |
| 389 | #define FIRST_PRIME 61; | 388 | #define FIRST_PRIME 61; |
| 390 | static const unsigned int PRIMES[] = { 251, 1021, 4093, 16381, 65521 }; | 389 | static const unsigned PRIMES[] = { 251, 1021, 4093, 16381, 65521 }; |
| 391 | enum { NPRIMES = sizeof(PRIMES) / sizeof(unsigned int) }; | 390 | enum { NPRIMES = sizeof(PRIMES) / sizeof(unsigned) }; |
| 392 | 391 | ||
| 393 | /* globals */ | 392 | /* globals */ |
| 394 | 393 | ||
| @@ -441,10 +440,15 @@ static const char EMSG_TOO_FEW_ARGS[] = "Too few arguments for builtin"; | |||
| 441 | static const char EMSG_NOT_ARRAY[] = "Not an array"; | 440 | static const char EMSG_NOT_ARRAY[] = "Not an array"; |
| 442 | static const char EMSG_POSSIBLE_ERROR[] = "Possible syntax error"; | 441 | static const char EMSG_POSSIBLE_ERROR[] = "Possible syntax error"; |
| 443 | static const char EMSG_UNDEF_FUNC[] = "Call to undefined function"; | 442 | static const char EMSG_UNDEF_FUNC[] = "Call to undefined function"; |
| 444 | #ifndef CONFIG_FEATURE_AWK_MATH | 443 | #if !ENABLE_FEATURE_AWK_MATH |
| 445 | static const char EMSG_NO_MATH[] = "Math support is not compiled in"; | 444 | static const char EMSG_NO_MATH[] = "Math support is not compiled in"; |
| 446 | #endif | 445 | #endif |
| 447 | 446 | ||
| 447 | static void zero_out_var(var * vp) | ||
| 448 | { | ||
| 449 | memset(vp, 0, sizeof(*vp)); | ||
| 450 | } | ||
| 451 | |||
| 448 | static void syntax_error(const char * const message) ATTRIBUTE_NORETURN; | 452 | static void syntax_error(const char * const message) ATTRIBUTE_NORETURN; |
| 449 | static void syntax_error(const char * const message) | 453 | static void syntax_error(const char * const message) |
| 450 | { | 454 | { |
| @@ -456,11 +460,11 @@ static void syntax_error(const char * const message) | |||
| 456 | 460 | ||
| 457 | /* ---- hash stuff ---- */ | 461 | /* ---- hash stuff ---- */ |
| 458 | 462 | ||
| 459 | static unsigned int hashidx(const char *name) | 463 | static unsigned hashidx(const char *name) |
| 460 | { | 464 | { |
| 461 | unsigned int idx=0; | 465 | unsigned idx = 0; |
| 462 | 466 | ||
| 463 | while (*name) idx = *name++ + (idx << 6) - idx; | 467 | while (*name) idx = *name++ + (idx << 6) - idx; |
| 464 | return idx; | 468 | return idx; |
| 465 | } | 469 | } |
| 466 | 470 | ||
| @@ -493,7 +497,7 @@ static void *hash_search(xhash *hash, const char *name) | |||
| 493 | /* grow hash if it becomes too big */ | 497 | /* grow hash if it becomes too big */ |
| 494 | static void hash_rebuild(xhash *hash) | 498 | static void hash_rebuild(xhash *hash) |
| 495 | { | 499 | { |
| 496 | unsigned int newsize, i, idx; | 500 | unsigned newsize, i, idx; |
| 497 | hash_item **newitems, *hi, *thi; | 501 | hash_item **newitems, *hi, *thi; |
| 498 | 502 | ||
| 499 | if (hash->nprime == NPRIMES) | 503 | if (hash->nprime == NPRIMES) |
| @@ -522,7 +526,7 @@ static void hash_rebuild(xhash *hash) | |||
| 522 | static void *hash_find(xhash *hash, const char *name) | 526 | static void *hash_find(xhash *hash, const char *name) |
| 523 | { | 527 | { |
| 524 | hash_item *hi; | 528 | hash_item *hi; |
| 525 | unsigned int idx; | 529 | unsigned idx; |
| 526 | int l; | 530 | int l; |
| 527 | 531 | ||
| 528 | hi = hash_search(hash, name); | 532 | hi = hash_search(hash, name); |
| @@ -542,10 +546,10 @@ static void *hash_find(xhash *hash, const char *name) | |||
| 542 | return &(hi->data); | 546 | return &(hi->data); |
| 543 | } | 547 | } |
| 544 | 548 | ||
| 545 | #define findvar(hash, name) (var *) hash_find ( (hash) , (name) ) | 549 | #define findvar(hash, name) ((var*) hash_find((hash) , (name))) |
| 546 | #define newvar(name) (var *) hash_find ( vhash , (name) ) | 550 | #define newvar(name) ((var*) hash_find(vhash , (name))) |
| 547 | #define newfile(name) (rstream *) hash_find ( fdhash , (name) ) | 551 | #define newfile(name) ((rstream*)hash_find(fdhash ,(name))) |
| 548 | #define newfunc(name) (func *) hash_find ( fnhash , (name) ) | 552 | #define newfunc(name) ((func*) hash_find(fnhash , (name))) |
| 549 | 553 | ||
| 550 | static void hash_remove(xhash *hash, const char *name) | 554 | static void hash_remove(xhash *hash, const char *name) |
| 551 | { | 555 | { |
| @@ -582,7 +586,7 @@ static char *nextword(char **s) | |||
| 582 | { | 586 | { |
| 583 | char *p = *s; | 587 | char *p = *s; |
| 584 | 588 | ||
| 585 | while (*(*s)++) ; | 589 | while (*(*s)++) /* */; |
| 586 | 590 | ||
| 587 | return p; | 591 | return p; |
| 588 | } | 592 | } |
| @@ -626,7 +630,7 @@ static xhash *iamarray(var *v) | |||
| 626 | 630 | ||
| 627 | static void clear_array(xhash *array) | 631 | static void clear_array(xhash *array) |
| 628 | { | 632 | { |
| 629 | unsigned int i; | 633 | unsigned i; |
| 630 | hash_item *hi, *thi; | 634 | hash_item *hi, *thi; |
| 631 | 635 | ||
| 632 | for (i=0; i<array->csize; i++) { | 636 | for (i=0; i<array->csize; i++) { |
| @@ -833,14 +837,15 @@ static void nvfree(var *v) | |||
| 833 | */ | 837 | */ |
| 834 | static uint32_t next_token(uint32_t expected) | 838 | static uint32_t next_token(uint32_t expected) |
| 835 | { | 839 | { |
| 840 | static int concat_inserted; | ||
| 841 | static uint32_t save_tclass, save_info; | ||
| 842 | static uint32_t ltclass = TC_OPTERM; | ||
| 843 | |||
| 836 | char *p, *pp, *s; | 844 | char *p, *pp, *s; |
| 837 | char *tl; | 845 | const char *tl; |
| 838 | uint32_t tc; | 846 | uint32_t tc; |
| 839 | const uint32_t *ti; | 847 | const uint32_t *ti; |
| 840 | int l; | 848 | int l; |
| 841 | static int concat_inserted; | ||
| 842 | static uint32_t save_tclass, save_info; | ||
| 843 | static uint32_t ltclass = TC_OPTERM; | ||
| 844 | 849 | ||
| 845 | if (t.rollback) { | 850 | if (t.rollback) { |
| 846 | 851 | ||
| @@ -930,7 +935,7 @@ static uint32_t next_token(uint32_t expected) | |||
| 930 | tl += l; | 935 | tl += l; |
| 931 | } | 936 | } |
| 932 | 937 | ||
| 933 | if (! *tl) { | 938 | if (!*tl) { |
| 934 | /* it's a name (var/array/function), | 939 | /* it's a name (var/array/function), |
| 935 | * otherwise it's something wrong | 940 | * otherwise it's something wrong |
| 936 | */ | 941 | */ |
| @@ -1072,8 +1077,8 @@ static node *parse_expr(uint32_t iexp) | |||
| 1072 | /* one should be very careful with switch on tclass - | 1077 | /* one should be very careful with switch on tclass - |
| 1073 | * only simple tclasses should be used! */ | 1078 | * only simple tclasses should be used! */ |
| 1074 | switch (tc) { | 1079 | switch (tc) { |
| 1075 | case TC_VARIABLE: | 1080 | case TC_VARIABLE: |
| 1076 | case TC_ARRAY: | 1081 | case TC_ARRAY: |
| 1077 | cn->info = OC_VAR; | 1082 | cn->info = OC_VAR; |
| 1078 | if ((v = hash_search(ahash, t.string)) != NULL) { | 1083 | if ((v = hash_search(ahash, t.string)) != NULL) { |
| 1079 | cn->info = OC_FNARG; | 1084 | cn->info = OC_FNARG; |
| @@ -1087,8 +1092,8 @@ static node *parse_expr(uint32_t iexp) | |||
| 1087 | } | 1092 | } |
| 1088 | break; | 1093 | break; |
| 1089 | 1094 | ||
| 1090 | case TC_NUMBER: | 1095 | case TC_NUMBER: |
| 1091 | case TC_STRING: | 1096 | case TC_STRING: |
| 1092 | cn->info = OC_VAR; | 1097 | cn->info = OC_VAR; |
| 1093 | v = cn->l.v = xzalloc(sizeof(var)); | 1098 | v = cn->l.v = xzalloc(sizeof(var)); |
| 1094 | if (tc & TC_NUMBER) | 1099 | if (tc & TC_NUMBER) |
| @@ -1097,27 +1102,27 @@ static node *parse_expr(uint32_t iexp) | |||
| 1097 | setvar_s(v, t.string); | 1102 | setvar_s(v, t.string); |
| 1098 | break; | 1103 | break; |
| 1099 | 1104 | ||
| 1100 | case TC_REGEXP: | 1105 | case TC_REGEXP: |
| 1101 | mk_re_node(t.string, cn, xzalloc(sizeof(regex_t)*2)); | 1106 | mk_re_node(t.string, cn, xzalloc(sizeof(regex_t)*2)); |
| 1102 | break; | 1107 | break; |
| 1103 | 1108 | ||
| 1104 | case TC_FUNCTION: | 1109 | case TC_FUNCTION: |
| 1105 | cn->info = OC_FUNC; | 1110 | cn->info = OC_FUNC; |
| 1106 | cn->r.f = newfunc(t.string); | 1111 | cn->r.f = newfunc(t.string); |
| 1107 | cn->l.n = condition(); | 1112 | cn->l.n = condition(); |
| 1108 | break; | 1113 | break; |
| 1109 | 1114 | ||
| 1110 | case TC_SEQSTART: | 1115 | case TC_SEQSTART: |
| 1111 | cn = vn->r.n = parse_expr(TC_SEQTERM); | 1116 | cn = vn->r.n = parse_expr(TC_SEQTERM); |
| 1112 | cn->a.n = vn; | 1117 | cn->a.n = vn; |
| 1113 | break; | 1118 | break; |
| 1114 | 1119 | ||
| 1115 | case TC_GETLINE: | 1120 | case TC_GETLINE: |
| 1116 | glptr = cn; | 1121 | glptr = cn; |
| 1117 | xtc = TC_OPERAND | TC_UOPPRE | TC_BINOP | iexp; | 1122 | xtc = TC_OPERAND | TC_UOPPRE | TC_BINOP | iexp; |
| 1118 | break; | 1123 | break; |
| 1119 | 1124 | ||
| 1120 | case TC_BUILTIN: | 1125 | case TC_BUILTIN: |
| 1121 | cn->l.n = condition(); | 1126 | cn->l.n = condition(); |
| 1122 | break; | 1127 | break; |
| 1123 | } | 1128 | } |
| @@ -1403,8 +1408,8 @@ static void fsrealloc(int size) | |||
| 1403 | if (size >= maxfields) { | 1408 | if (size >= maxfields) { |
| 1404 | i = maxfields; | 1409 | i = maxfields; |
| 1405 | maxfields = size + 16; | 1410 | maxfields = size + 16; |
| 1406 | Fields = (var *)xrealloc(Fields, maxfields * sizeof(var)); | 1411 | Fields = xrealloc(Fields, maxfields * sizeof(var)); |
| 1407 | for (; i<maxfields; i++) { | 1412 | for (; i < maxfields; i++) { |
| 1408 | Fields[i].type = VF_SPECIAL; | 1413 | Fields[i].type = VF_SPECIAL; |
| 1409 | Fields[i].string = NULL; | 1414 | Fields[i].string = NULL; |
| 1410 | } | 1415 | } |
| @@ -1420,7 +1425,7 @@ static void fsrealloc(int size) | |||
| 1420 | 1425 | ||
| 1421 | static int awk_split(char *s, node *spl, char **slist) | 1426 | static int awk_split(char *s, node *spl, char **slist) |
| 1422 | { | 1427 | { |
| 1423 | int l, n=0; | 1428 | int l, n = 0; |
| 1424 | char c[4]; | 1429 | char c[4]; |
| 1425 | char *s1; | 1430 | char *s1; |
| 1426 | regmatch_t pmatch[2]; | 1431 | regmatch_t pmatch[2]; |
| @@ -1441,11 +1446,11 @@ static int awk_split(char *s, node *spl, char **slist) | |||
| 1441 | if (pmatch[0].rm_eo == 0) { l++; pmatch[0].rm_eo++; } | 1446 | if (pmatch[0].rm_eo == 0) { l++; pmatch[0].rm_eo++; } |
| 1442 | } else { | 1447 | } else { |
| 1443 | pmatch[0].rm_eo = l; | 1448 | pmatch[0].rm_eo = l; |
| 1444 | if (*(s+l)) pmatch[0].rm_eo++; | 1449 | if (s[l]) pmatch[0].rm_eo++; |
| 1445 | } | 1450 | } |
| 1446 | 1451 | ||
| 1447 | memcpy(s1, s, l); | 1452 | memcpy(s1, s, l); |
| 1448 | *(s1+l) = '\0'; | 1453 | s1[l] = '\0'; |
| 1449 | nextword(&s1); | 1454 | nextword(&s1); |
| 1450 | s += pmatch[0].rm_eo; | 1455 | s += pmatch[0].rm_eo; |
| 1451 | n++; | 1456 | n++; |
| @@ -1494,7 +1499,7 @@ static void split_f0(void) | |||
| 1494 | n = awk_split(getvar_s(V[F0]), &fsplitter.n, &fstrings); | 1499 | n = awk_split(getvar_s(V[F0]), &fsplitter.n, &fstrings); |
| 1495 | fsrealloc(n); | 1500 | fsrealloc(n); |
| 1496 | s = fstrings; | 1501 | s = fstrings; |
| 1497 | for (i=0; i<n; i++) { | 1502 | for (i = 0; i < n; i++) { |
| 1498 | Fields[i].string = nextword(&s); | 1503 | Fields[i].string = nextword(&s); |
| 1499 | Fields[i].type |= (VF_FSTR | VF_USER | VF_DIRTY); | 1504 | Fields[i].type |= (VF_FSTR | VF_USER | VF_DIRTY); |
| 1500 | } | 1505 | } |
| @@ -1610,7 +1615,8 @@ static int hashwalk_next(var *v) | |||
| 1610 | /* evaluate node, return 1 when result is true, 0 otherwise */ | 1615 | /* evaluate node, return 1 when result is true, 0 otherwise */ |
| 1611 | static int ptest(node *pattern) | 1616 | static int ptest(node *pattern) |
| 1612 | { | 1617 | { |
| 1613 | static var v; | 1618 | static var v; /* static: to save stack space? */ |
| 1619 | |||
| 1614 | return istrue(evaluate(pattern, &v)); | 1620 | return istrue(evaluate(pattern, &v)); |
| 1615 | } | 1621 | } |
| 1616 | 1622 | ||
| @@ -1710,14 +1716,14 @@ static int awk_getline(rstream *rsm, var *v) | |||
| 1710 | 1716 | ||
| 1711 | static int fmt_num(char *b, int size, const char *format, double n, int int_as_int) | 1717 | static int fmt_num(char *b, int size, const char *format, double n, int int_as_int) |
| 1712 | { | 1718 | { |
| 1713 | int r=0; | 1719 | int r = 0; |
| 1714 | char c; | 1720 | char c; |
| 1715 | const char *s=format; | 1721 | const char *s = format; |
| 1716 | 1722 | ||
| 1717 | if (int_as_int && n == (int)n) { | 1723 | if (int_as_int && n == (int)n) { |
| 1718 | r = snprintf(b, size, "%d", (int)n); | 1724 | r = snprintf(b, size, "%d", (int)n); |
| 1719 | } else { | 1725 | } else { |
| 1720 | do { c = *s; } while (*s && *++s); | 1726 | do { c = *s; } while (c && *++s); |
| 1721 | if (strchr("diouxX", c)) { | 1727 | if (strchr("diouxX", c)) { |
| 1722 | r = snprintf(b, size, format, (int)n); | 1728 | r = snprintf(b, size, format, (int)n); |
| 1723 | } else if (strchr("eEfgG", c)) { | 1729 | } else if (strchr("eEfgG", c)) { |
| @@ -1751,15 +1757,17 @@ static char *awk_printf(node *n) | |||
| 1751 | f++; | 1757 | f++; |
| 1752 | 1758 | ||
| 1753 | incr = (f - s) + MAXVARFMT; | 1759 | incr = (f - s) + MAXVARFMT; |
| 1754 | qrealloc(&b, incr+i, &bsize); | 1760 | qrealloc(&b, incr + i, &bsize); |
| 1755 | c = *f; if (c != '\0') f++; | 1761 | c = *f; |
| 1756 | c1 = *f ; *f = '\0'; | 1762 | if (c != '\0') f++; |
| 1763 | c1 = *f; | ||
| 1764 | *f = '\0'; | ||
| 1757 | arg = evaluate(nextarg(&n), v); | 1765 | arg = evaluate(nextarg(&n), v); |
| 1758 | 1766 | ||
| 1759 | j = i; | 1767 | j = i; |
| 1760 | if (c == 'c' || !c) { | 1768 | if (c == 'c' || !c) { |
| 1761 | i += sprintf(b+i, s, | 1769 | i += sprintf(b+i, s, is_numeric(arg) ? |
| 1762 | is_numeric(arg) ? (char)getvar_i(arg) : *getvar_s(arg)); | 1770 | (char)getvar_i(arg) : *getvar_s(arg)); |
| 1763 | 1771 | ||
| 1764 | } else if (c == 's') { | 1772 | } else if (c == 's') { |
| 1765 | s1 = getvar_s(arg); | 1773 | s1 = getvar_s(arg); |
| @@ -1776,7 +1784,7 @@ static char *awk_printf(node *n) | |||
| 1776 | 1784 | ||
| 1777 | } | 1785 | } |
| 1778 | 1786 | ||
| 1779 | b = xrealloc(b, i+1); | 1787 | b = xrealloc(b, i + 1); |
| 1780 | free(fmt); | 1788 | free(fmt); |
| 1781 | nvfree(v); | 1789 | nvfree(v); |
| 1782 | b[i] = '\0'; | 1790 | b[i] = '\0'; |
| @@ -1890,15 +1898,15 @@ static var *exec_builtin(node *op, var *res) | |||
| 1890 | 1898 | ||
| 1891 | switch (info & OPNMASK) { | 1899 | switch (info & OPNMASK) { |
| 1892 | 1900 | ||
| 1893 | case B_a2: | 1901 | case B_a2: |
| 1894 | #ifdef CONFIG_FEATURE_AWK_MATH | 1902 | #if ENABLE_FEATURE_AWK_MATH |
| 1895 | setvar_i(res, atan2(getvar_i(av[i]), getvar_i(av[1]))); | 1903 | setvar_i(res, atan2(getvar_i(av[i]), getvar_i(av[1]))); |
| 1896 | #else | 1904 | #else |
| 1897 | runtime_error(EMSG_NO_MATH); | 1905 | runtime_error(EMSG_NO_MATH); |
| 1898 | #endif | 1906 | #endif |
| 1899 | break; | 1907 | break; |
| 1900 | 1908 | ||
| 1901 | case B_sp: | 1909 | case B_sp: |
| 1902 | if (nargs > 2) { | 1910 | if (nargs > 2) { |
| 1903 | spl = (an[2]->info & OPCLSMASK) == OC_REGEXP ? | 1911 | spl = (an[2]->info & OPCLSMASK) == OC_REGEXP ? |
| 1904 | an[2] : mk_splitter(getvar_s(evaluate(an[2], &tv[2])), &tspl); | 1912 | an[2] : mk_splitter(getvar_s(evaluate(an[2], &tv[2])), &tspl); |
| @@ -1915,7 +1923,7 @@ static var *exec_builtin(node *op, var *res) | |||
| 1915 | setvar_i(res, n); | 1923 | setvar_i(res, n); |
| 1916 | break; | 1924 | break; |
| 1917 | 1925 | ||
| 1918 | case B_ss: | 1926 | case B_ss: |
| 1919 | l = strlen(as[0]); | 1927 | l = strlen(as[0]); |
| 1920 | i = getvar_i(av[1]) - 1; | 1928 | i = getvar_i(av[1]) - 1; |
| 1921 | if (i>l) i=l; if (i<0) i=0; | 1929 | if (i>l) i=l; if (i<0) i=0; |
| @@ -1927,35 +1935,35 @@ static var *exec_builtin(node *op, var *res) | |||
| 1927 | setvar_p(res, s); | 1935 | setvar_p(res, s); |
| 1928 | break; | 1936 | break; |
| 1929 | 1937 | ||
| 1930 | case B_an: | 1938 | case B_an: |
| 1931 | setvar_i(res, (long)getvar_i(av[0]) & (long)getvar_i(av[1])); | 1939 | setvar_i(res, (long)getvar_i(av[0]) & (long)getvar_i(av[1])); |
| 1932 | break; | 1940 | break; |
| 1933 | 1941 | ||
| 1934 | case B_co: | 1942 | case B_co: |
| 1935 | setvar_i(res, ~(long)getvar_i(av[0])); | 1943 | setvar_i(res, ~(long)getvar_i(av[0])); |
| 1936 | break; | 1944 | break; |
| 1937 | 1945 | ||
| 1938 | case B_ls: | 1946 | case B_ls: |
| 1939 | setvar_i(res, (long)getvar_i(av[0]) << (long)getvar_i(av[1])); | 1947 | setvar_i(res, (long)getvar_i(av[0]) << (long)getvar_i(av[1])); |
| 1940 | break; | 1948 | break; |
| 1941 | 1949 | ||
| 1942 | case B_or: | 1950 | case B_or: |
| 1943 | setvar_i(res, (long)getvar_i(av[0]) | (long)getvar_i(av[1])); | 1951 | setvar_i(res, (long)getvar_i(av[0]) | (long)getvar_i(av[1])); |
| 1944 | break; | 1952 | break; |
| 1945 | 1953 | ||
| 1946 | case B_rs: | 1954 | case B_rs: |
| 1947 | setvar_i(res, (long)((unsigned long)getvar_i(av[0]) >> (unsigned long)getvar_i(av[1]))); | 1955 | setvar_i(res, (long)((unsigned long)getvar_i(av[0]) >> (unsigned long)getvar_i(av[1]))); |
| 1948 | break; | 1956 | break; |
| 1949 | 1957 | ||
| 1950 | case B_xo: | 1958 | case B_xo: |
| 1951 | setvar_i(res, (long)getvar_i(av[0]) ^ (long)getvar_i(av[1])); | 1959 | setvar_i(res, (long)getvar_i(av[0]) ^ (long)getvar_i(av[1])); |
| 1952 | break; | 1960 | break; |
| 1953 | 1961 | ||
| 1954 | case B_lo: | 1962 | case B_lo: |
| 1955 | to_xxx = tolower; | 1963 | to_xxx = tolower; |
| 1956 | goto lo_cont; | 1964 | goto lo_cont; |
| 1957 | 1965 | ||
| 1958 | case B_up: | 1966 | case B_up: |
| 1959 | to_xxx = toupper; | 1967 | to_xxx = toupper; |
| 1960 | lo_cont: | 1968 | lo_cont: |
| 1961 | s1 = s = xstrdup(as[0]); | 1969 | s1 = s = xstrdup(as[0]); |
| @@ -1966,7 +1974,7 @@ lo_cont: | |||
| 1966 | setvar_p(res, s); | 1974 | setvar_p(res, s); |
| 1967 | break; | 1975 | break; |
| 1968 | 1976 | ||
| 1969 | case B_ix: | 1977 | case B_ix: |
| 1970 | n = 0; | 1978 | n = 0; |
| 1971 | ll = strlen(as[1]); | 1979 | ll = strlen(as[1]); |
| 1972 | l = strlen(as[0]) - ll; | 1980 | l = strlen(as[0]) - ll; |
| @@ -1989,7 +1997,7 @@ lo_cont: | |||
| 1989 | setvar_i(res, n); | 1997 | setvar_i(res, n); |
| 1990 | break; | 1998 | break; |
| 1991 | 1999 | ||
| 1992 | case B_ti: | 2000 | case B_ti: |
| 1993 | if (nargs > 1) | 2001 | if (nargs > 1) |
| 1994 | tt = getvar_i(av[1]); | 2002 | tt = getvar_i(av[1]); |
| 1995 | else | 2003 | else |
| @@ -2000,7 +2008,7 @@ lo_cont: | |||
| 2000 | setvar_s(res, buf); | 2008 | setvar_s(res, buf); |
| 2001 | break; | 2009 | break; |
| 2002 | 2010 | ||
| 2003 | case B_ma: | 2011 | case B_ma: |
| 2004 | re = as_regex(an[1], &sreg); | 2012 | re = as_regex(an[1], &sreg); |
| 2005 | n = regexec(re, as[0], 1, pmatch, 0); | 2013 | n = regexec(re, as[0], 1, pmatch, 0); |
| 2006 | if (n == 0) { | 2014 | if (n == 0) { |
| @@ -2016,15 +2024,15 @@ lo_cont: | |||
| 2016 | if (re == &sreg) regfree(re); | 2024 | if (re == &sreg) regfree(re); |
| 2017 | break; | 2025 | break; |
| 2018 | 2026 | ||
| 2019 | case B_ge: | 2027 | case B_ge: |
| 2020 | awk_sub(an[0], as[1], getvar_i(av[2]), av[3], res, TRUE); | 2028 | awk_sub(an[0], as[1], getvar_i(av[2]), av[3], res, TRUE); |
| 2021 | break; | 2029 | break; |
| 2022 | 2030 | ||
| 2023 | case B_gs: | 2031 | case B_gs: |
| 2024 | setvar_i(res, awk_sub(an[0], as[1], 0, av[2], av[2], FALSE)); | 2032 | setvar_i(res, awk_sub(an[0], as[1], 0, av[2], av[2], FALSE)); |
| 2025 | break; | 2033 | break; |
| 2026 | 2034 | ||
| 2027 | case B_su: | 2035 | case B_su: |
| 2028 | setvar_i(res, awk_sub(an[0], as[1], 1, av[2], av[2], FALSE)); | 2036 | setvar_i(res, awk_sub(an[0], as[1], 1, av[2], av[2], FALSE)); |
| 2029 | break; | 2037 | break; |
| 2030 | } | 2038 | } |
| @@ -2043,7 +2051,7 @@ static var *evaluate(node *op, var *res) | |||
| 2043 | { | 2051 | { |
| 2044 | /* This procedure is recursive so we should count every byte */ | 2052 | /* This procedure is recursive so we should count every byte */ |
| 2045 | static var *fnargs = NULL; | 2053 | static var *fnargs = NULL; |
| 2046 | static unsigned int seed = 1; | 2054 | static unsigned seed = 1; |
| 2047 | static regex_t sreg; | 2055 | static regex_t sreg; |
| 2048 | node *op1; | 2056 | node *op1; |
| 2049 | var *v1; | 2057 | var *v1; |
| @@ -2088,7 +2096,7 @@ static var *evaluate(node *op, var *res) | |||
| 2088 | /* -- iterative node type -- */ | 2096 | /* -- iterative node type -- */ |
| 2089 | 2097 | ||
| 2090 | /* test pattern */ | 2098 | /* test pattern */ |
| 2091 | case XC( OC_TEST ): | 2099 | case XC( OC_TEST ): |
| 2092 | if ((op1->info & OPCLSMASK) == OC_COMMA) { | 2100 | if ((op1->info & OPCLSMASK) == OC_COMMA) { |
| 2093 | /* it's range pattern */ | 2101 | /* it's range pattern */ |
| 2094 | if ((opinfo & OF_CHECKED) || ptest(op1->l.n)) { | 2102 | if ((opinfo & OF_CHECKED) || ptest(op1->l.n)) { |
| @@ -2106,26 +2114,26 @@ static var *evaluate(node *op, var *res) | |||
| 2106 | break; | 2114 | break; |
| 2107 | 2115 | ||
| 2108 | /* just evaluate an expression, also used as unconditional jump */ | 2116 | /* just evaluate an expression, also used as unconditional jump */ |
| 2109 | case XC( OC_EXEC ): | 2117 | case XC( OC_EXEC ): |
| 2110 | break; | 2118 | break; |
| 2111 | 2119 | ||
| 2112 | /* branch, used in if-else and various loops */ | 2120 | /* branch, used in if-else and various loops */ |
| 2113 | case XC( OC_BR ): | 2121 | case XC( OC_BR ): |
| 2114 | op = istrue(L.v) ? op->a.n : op->r.n; | 2122 | op = istrue(L.v) ? op->a.n : op->r.n; |
| 2115 | break; | 2123 | break; |
| 2116 | 2124 | ||
| 2117 | /* initialize for-in loop */ | 2125 | /* initialize for-in loop */ |
| 2118 | case XC( OC_WALKINIT ): | 2126 | case XC( OC_WALKINIT ): |
| 2119 | hashwalk_init(L.v, iamarray(R.v)); | 2127 | hashwalk_init(L.v, iamarray(R.v)); |
| 2120 | break; | 2128 | break; |
| 2121 | 2129 | ||
| 2122 | /* get next array item */ | 2130 | /* get next array item */ |
| 2123 | case XC( OC_WALKNEXT ): | 2131 | case XC( OC_WALKNEXT ): |
| 2124 | op = hashwalk_next(L.v) ? op->a.n : op->r.n; | 2132 | op = hashwalk_next(L.v) ? op->a.n : op->r.n; |
| 2125 | break; | 2133 | break; |
| 2126 | 2134 | ||
| 2127 | case XC( OC_PRINT ): | 2135 | case XC( OC_PRINT ): |
| 2128 | case XC( OC_PRINTF ): | 2136 | case XC( OC_PRINTF ): |
| 2129 | X.F = stdout; | 2137 | X.F = stdout; |
| 2130 | if (op->r.n) { | 2138 | if (op->r.n) { |
| 2131 | X.rsm = newfile(R.s); | 2139 | X.rsm = newfile(R.s); |
| @@ -2168,7 +2176,7 @@ static var *evaluate(node *op, var *res) | |||
| 2168 | fflush(X.F); | 2176 | fflush(X.F); |
| 2169 | break; | 2177 | break; |
| 2170 | 2178 | ||
| 2171 | case XC( OC_DELETE ): | 2179 | case XC( OC_DELETE ): |
| 2172 | X.info = op1->info & OPCLSMASK; | 2180 | X.info = op1->info & OPCLSMASK; |
| 2173 | if (X.info == OC_VAR) { | 2181 | if (X.info == OC_VAR) { |
| 2174 | R.v = op1->l.v; | 2182 | R.v = op1->l.v; |
| @@ -2187,50 +2195,50 @@ static var *evaluate(node *op, var *res) | |||
| 2187 | } | 2195 | } |
| 2188 | break; | 2196 | break; |
| 2189 | 2197 | ||
| 2190 | case XC( OC_NEWSOURCE ): | 2198 | case XC( OC_NEWSOURCE ): |
| 2191 | programname = op->l.s; | 2199 | programname = op->l.s; |
| 2192 | break; | 2200 | break; |
| 2193 | 2201 | ||
| 2194 | case XC( OC_RETURN ): | 2202 | case XC( OC_RETURN ): |
| 2195 | copyvar(res, L.v); | 2203 | copyvar(res, L.v); |
| 2196 | break; | 2204 | break; |
| 2197 | 2205 | ||
| 2198 | case XC( OC_NEXTFILE ): | 2206 | case XC( OC_NEXTFILE ): |
| 2199 | nextfile = TRUE; | 2207 | nextfile = TRUE; |
| 2200 | case XC( OC_NEXT ): | 2208 | case XC( OC_NEXT ): |
| 2201 | nextrec = TRUE; | 2209 | nextrec = TRUE; |
| 2202 | case XC( OC_DONE ): | 2210 | case XC( OC_DONE ): |
| 2203 | clrvar(res); | 2211 | clrvar(res); |
| 2204 | break; | 2212 | break; |
| 2205 | 2213 | ||
| 2206 | case XC( OC_EXIT ): | 2214 | case XC( OC_EXIT ): |
| 2207 | awk_exit(L.d); | 2215 | awk_exit(L.d); |
| 2208 | 2216 | ||
| 2209 | /* -- recursive node type -- */ | 2217 | /* -- recursive node type -- */ |
| 2210 | 2218 | ||
| 2211 | case XC( OC_VAR ): | 2219 | case XC( OC_VAR ): |
| 2212 | L.v = op->l.v; | 2220 | L.v = op->l.v; |
| 2213 | if (L.v == V[NF]) | 2221 | if (L.v == V[NF]) |
| 2214 | split_f0(); | 2222 | split_f0(); |
| 2215 | goto v_cont; | 2223 | goto v_cont; |
| 2216 | 2224 | ||
| 2217 | case XC( OC_FNARG ): | 2225 | case XC( OC_FNARG ): |
| 2218 | L.v = &fnargs[op->l.i]; | 2226 | L.v = &fnargs[op->l.i]; |
| 2219 | 2227 | ||
| 2220 | v_cont: | 2228 | v_cont: |
| 2221 | res = (op->r.n) ? findvar(iamarray(L.v), R.s) : L.v; | 2229 | res = (op->r.n) ? findvar(iamarray(L.v), R.s) : L.v; |
| 2222 | break; | 2230 | break; |
| 2223 | 2231 | ||
| 2224 | case XC( OC_IN ): | 2232 | case XC( OC_IN ): |
| 2225 | setvar_i(res, hash_search(iamarray(R.v), L.s) ? 1 : 0); | 2233 | setvar_i(res, hash_search(iamarray(R.v), L.s) ? 1 : 0); |
| 2226 | break; | 2234 | break; |
| 2227 | 2235 | ||
| 2228 | case XC( OC_REGEXP ): | 2236 | case XC( OC_REGEXP ): |
| 2229 | op1 = op; | 2237 | op1 = op; |
| 2230 | L.s = getvar_s(V[F0]); | 2238 | L.s = getvar_s(V[F0]); |
| 2231 | goto re_cont; | 2239 | goto re_cont; |
| 2232 | 2240 | ||
| 2233 | case XC( OC_MATCH ): | 2241 | case XC( OC_MATCH ): |
| 2234 | op1 = op->r.n; | 2242 | op1 = op->r.n; |
| 2235 | re_cont: | 2243 | re_cont: |
| 2236 | X.re = as_regex(op1, &sreg); | 2244 | X.re = as_regex(op1, &sreg); |
| @@ -2239,7 +2247,7 @@ re_cont: | |||
| 2239 | setvar_i(res, (R.i == 0 ? 1 : 0) ^ (opn == '!' ? 1 : 0)); | 2247 | setvar_i(res, (R.i == 0 ? 1 : 0) ^ (opn == '!' ? 1 : 0)); |
| 2240 | break; | 2248 | break; |
| 2241 | 2249 | ||
| 2242 | case XC( OC_MOVE ): | 2250 | case XC( OC_MOVE ): |
| 2243 | /* if source is a temporary string, jusk relink it to dest */ | 2251 | /* if source is a temporary string, jusk relink it to dest */ |
| 2244 | if (R.v == v1+1 && R.v->string) { | 2252 | if (R.v == v1+1 && R.v->string) { |
| 2245 | res = setvar_p(L.v, R.v->string); | 2253 | res = setvar_p(L.v, R.v->string); |
| @@ -2249,13 +2257,13 @@ re_cont: | |||
| 2249 | } | 2257 | } |
| 2250 | break; | 2258 | break; |
| 2251 | 2259 | ||
| 2252 | case XC( OC_TERNARY ): | 2260 | case XC( OC_TERNARY ): |
| 2253 | if ((op->r.n->info & OPCLSMASK) != OC_COLON) | 2261 | if ((op->r.n->info & OPCLSMASK) != OC_COLON) |
| 2254 | runtime_error(EMSG_POSSIBLE_ERROR); | 2262 | runtime_error(EMSG_POSSIBLE_ERROR); |
| 2255 | res = evaluate(istrue(L.v) ? op->r.n->l.n : op->r.n->r.n, res); | 2263 | res = evaluate(istrue(L.v) ? op->r.n->l.n : op->r.n->r.n, res); |
| 2256 | break; | 2264 | break; |
| 2257 | 2265 | ||
| 2258 | case XC( OC_FUNC ): | 2266 | case XC( OC_FUNC ): |
| 2259 | if (! op->r.f->body.first) | 2267 | if (! op->r.f->body.first) |
| 2260 | runtime_error(EMSG_UNDEF_FUNC); | 2268 | runtime_error(EMSG_UNDEF_FUNC); |
| 2261 | 2269 | ||
| @@ -2280,8 +2288,8 @@ re_cont: | |||
| 2280 | fnargs = R.v; | 2288 | fnargs = R.v; |
| 2281 | break; | 2289 | break; |
| 2282 | 2290 | ||
| 2283 | case XC( OC_GETLINE ): | 2291 | case XC( OC_GETLINE ): |
| 2284 | case XC( OC_PGETLINE ): | 2292 | case XC( OC_PGETLINE ): |
| 2285 | if (op1) { | 2293 | if (op1) { |
| 2286 | X.rsm = newfile(L.s); | 2294 | X.rsm = newfile(L.s); |
| 2287 | if (! X.rsm->F) { | 2295 | if (! X.rsm->F) { |
| @@ -2317,70 +2325,70 @@ re_cont: | |||
| 2317 | break; | 2325 | break; |
| 2318 | 2326 | ||
| 2319 | /* simple builtins */ | 2327 | /* simple builtins */ |
| 2320 | case XC( OC_FBLTIN ): | 2328 | case XC( OC_FBLTIN ): |
| 2321 | switch (opn) { | 2329 | switch (opn) { |
| 2322 | 2330 | ||
| 2323 | case F_in: | 2331 | case F_in: |
| 2324 | R.d = (int)L.d; | 2332 | R.d = (int)L.d; |
| 2325 | break; | 2333 | break; |
| 2326 | 2334 | ||
| 2327 | case F_rn: | 2335 | case F_rn: |
| 2328 | R.d = (double)rand() / (double)RAND_MAX; | 2336 | R.d = (double)rand() / (double)RAND_MAX; |
| 2329 | break; | 2337 | break; |
| 2330 | 2338 | ||
| 2331 | #ifdef CONFIG_FEATURE_AWK_MATH | 2339 | #if ENABLE_FEATURE_AWK_MATH |
| 2332 | case F_co: | 2340 | case F_co: |
| 2333 | R.d = cos(L.d); | 2341 | R.d = cos(L.d); |
| 2334 | break; | 2342 | break; |
| 2335 | 2343 | ||
| 2336 | case F_ex: | 2344 | case F_ex: |
| 2337 | R.d = exp(L.d); | 2345 | R.d = exp(L.d); |
| 2338 | break; | 2346 | break; |
| 2339 | 2347 | ||
| 2340 | case F_lg: | 2348 | case F_lg: |
| 2341 | R.d = log(L.d); | 2349 | R.d = log(L.d); |
| 2342 | break; | 2350 | break; |
| 2343 | 2351 | ||
| 2344 | case F_si: | 2352 | case F_si: |
| 2345 | R.d = sin(L.d); | 2353 | R.d = sin(L.d); |
| 2346 | break; | 2354 | break; |
| 2347 | 2355 | ||
| 2348 | case F_sq: | 2356 | case F_sq: |
| 2349 | R.d = sqrt(L.d); | 2357 | R.d = sqrt(L.d); |
| 2350 | break; | 2358 | break; |
| 2351 | #else | 2359 | #else |
| 2352 | case F_co: | 2360 | case F_co: |
| 2353 | case F_ex: | 2361 | case F_ex: |
| 2354 | case F_lg: | 2362 | case F_lg: |
| 2355 | case F_si: | 2363 | case F_si: |
| 2356 | case F_sq: | 2364 | case F_sq: |
| 2357 | runtime_error(EMSG_NO_MATH); | 2365 | runtime_error(EMSG_NO_MATH); |
| 2358 | break; | 2366 | break; |
| 2359 | #endif | 2367 | #endif |
| 2360 | 2368 | ||
| 2361 | case F_sr: | 2369 | case F_sr: |
| 2362 | R.d = (double)seed; | 2370 | R.d = (double)seed; |
| 2363 | seed = op1 ? (unsigned int)L.d : (unsigned int)time(NULL); | 2371 | seed = op1 ? (unsigned)L.d : (unsigned)time(NULL); |
| 2364 | srand(seed); | 2372 | srand(seed); |
| 2365 | break; | 2373 | break; |
| 2366 | 2374 | ||
| 2367 | case F_ti: | 2375 | case F_ti: |
| 2368 | R.d = time(NULL); | 2376 | R.d = time(NULL); |
| 2369 | break; | 2377 | break; |
| 2370 | 2378 | ||
| 2371 | case F_le: | 2379 | case F_le: |
| 2372 | if (! op1) | 2380 | if (! op1) |
| 2373 | L.s = getvar_s(V[F0]); | 2381 | L.s = getvar_s(V[F0]); |
| 2374 | R.d = strlen(L.s); | 2382 | R.d = strlen(L.s); |
| 2375 | break; | 2383 | break; |
| 2376 | 2384 | ||
| 2377 | case F_sy: | 2385 | case F_sy: |
| 2378 | fflush(NULL); | 2386 | fflush(NULL); |
| 2379 | R.d = (ENABLE_FEATURE_ALLOW_EXEC && L.s && *L.s) | 2387 | R.d = (ENABLE_FEATURE_ALLOW_EXEC && L.s && *L.s) |
| 2380 | ? (system(L.s) >> 8) : 0; | 2388 | ? (system(L.s) >> 8) : 0; |
| 2381 | break; | 2389 | break; |
| 2382 | 2390 | ||
| 2383 | case F_ff: | 2391 | case F_ff: |
| 2384 | if (! op1) | 2392 | if (! op1) |
| 2385 | fflush(stdout); | 2393 | fflush(stdout); |
| 2386 | else { | 2394 | else { |
| @@ -2393,7 +2401,7 @@ re_cont: | |||
| 2393 | } | 2401 | } |
| 2394 | break; | 2402 | break; |
| 2395 | 2403 | ||
| 2396 | case F_cl: | 2404 | case F_cl: |
| 2397 | X.rsm = (rstream *)hash_search(fdhash, L.s); | 2405 | X.rsm = (rstream *)hash_search(fdhash, L.s); |
| 2398 | if (X.rsm) { | 2406 | if (X.rsm) { |
| 2399 | R.i = X.rsm->is_pipe ? pclose(X.rsm->F) : fclose(X.rsm->F); | 2407 | R.i = X.rsm->is_pipe ? pclose(X.rsm->F) : fclose(X.rsm->F); |
| @@ -2408,43 +2416,43 @@ re_cont: | |||
| 2408 | setvar_i(res, R.d); | 2416 | setvar_i(res, R.d); |
| 2409 | break; | 2417 | break; |
| 2410 | 2418 | ||
| 2411 | case XC( OC_BUILTIN ): | 2419 | case XC( OC_BUILTIN ): |
| 2412 | res = exec_builtin(op, res); | 2420 | res = exec_builtin(op, res); |
| 2413 | break; | 2421 | break; |
| 2414 | 2422 | ||
| 2415 | case XC( OC_SPRINTF ): | 2423 | case XC( OC_SPRINTF ): |
| 2416 | setvar_p(res, awk_printf(op1)); | 2424 | setvar_p(res, awk_printf(op1)); |
| 2417 | break; | 2425 | break; |
| 2418 | 2426 | ||
| 2419 | case XC( OC_UNARY ): | 2427 | case XC( OC_UNARY ): |
| 2420 | X.v = R.v; | 2428 | X.v = R.v; |
| 2421 | L.d = R.d = getvar_i(R.v); | 2429 | L.d = R.d = getvar_i(R.v); |
| 2422 | switch (opn) { | 2430 | switch (opn) { |
| 2423 | case 'P': | 2431 | case 'P': |
| 2424 | L.d = ++R.d; | 2432 | L.d = ++R.d; |
| 2425 | goto r_op_change; | 2433 | goto r_op_change; |
| 2426 | case 'p': | 2434 | case 'p': |
| 2427 | R.d++; | 2435 | R.d++; |
| 2428 | goto r_op_change; | 2436 | goto r_op_change; |
| 2429 | case 'M': | 2437 | case 'M': |
| 2430 | L.d = --R.d; | 2438 | L.d = --R.d; |
| 2431 | goto r_op_change; | 2439 | goto r_op_change; |
| 2432 | case 'm': | 2440 | case 'm': |
| 2433 | R.d--; | 2441 | R.d--; |
| 2434 | goto r_op_change; | 2442 | goto r_op_change; |
| 2435 | case '!': | 2443 | case '!': |
| 2436 | L.d = istrue(X.v) ? 0 : 1; | 2444 | L.d = istrue(X.v) ? 0 : 1; |
| 2437 | break; | 2445 | break; |
| 2438 | case '-': | 2446 | case '-': |
| 2439 | L.d = -R.d; | 2447 | L.d = -R.d; |
| 2440 | break; | 2448 | break; |
| 2441 | r_op_change: | 2449 | r_op_change: |
| 2442 | setvar_i(X.v, R.d); | 2450 | setvar_i(X.v, R.d); |
| 2443 | } | 2451 | } |
| 2444 | setvar_i(res, L.d); | 2452 | setvar_i(res, L.d); |
| 2445 | break; | 2453 | break; |
| 2446 | 2454 | ||
| 2447 | case XC( OC_FIELD ): | 2455 | case XC( OC_FIELD ): |
| 2448 | R.i = (int)getvar_i(R.v); | 2456 | R.i = (int)getvar_i(R.v); |
| 2449 | if (R.i == 0) { | 2457 | if (R.i == 0) { |
| 2450 | res = V[F0]; | 2458 | res = V[F0]; |
| @@ -2458,53 +2466,53 @@ re_cont: | |||
| 2458 | break; | 2466 | break; |
| 2459 | 2467 | ||
| 2460 | /* concatenation (" ") and index joining (",") */ | 2468 | /* concatenation (" ") and index joining (",") */ |
| 2461 | case XC( OC_CONCAT ): | 2469 | case XC( OC_CONCAT ): |
| 2462 | case XC( OC_COMMA ): | 2470 | case XC( OC_COMMA ): |
| 2463 | opn = strlen(L.s) + strlen(R.s) + 2; | 2471 | opn = strlen(L.s) + strlen(R.s) + 2; |
| 2464 | X.s = xmalloc(opn); | 2472 | X.s = xmalloc(opn); |
| 2465 | strcpy(X.s, L.s); | 2473 | strcpy(X.s, L.s); |
| 2466 | if ((opinfo & OPCLSMASK) == OC_COMMA) { | 2474 | if ((opinfo & OPCLSMASK) == OC_COMMA) { |
| 2467 | L.s = getvar_s(V[SUBSEP]); | 2475 | L.s = getvar_s(V[SUBSEP]); |
| 2468 | X.s = (char *)xrealloc(X.s, opn + strlen(L.s)); | 2476 | X.s = xrealloc(X.s, opn + strlen(L.s)); |
| 2469 | strcat(X.s, L.s); | 2477 | strcat(X.s, L.s); |
| 2470 | } | 2478 | } |
| 2471 | strcat(X.s, R.s); | 2479 | strcat(X.s, R.s); |
| 2472 | setvar_p(res, X.s); | 2480 | setvar_p(res, X.s); |
| 2473 | break; | 2481 | break; |
| 2474 | 2482 | ||
| 2475 | case XC( OC_LAND ): | 2483 | case XC( OC_LAND ): |
| 2476 | setvar_i(res, istrue(L.v) ? ptest(op->r.n) : 0); | 2484 | setvar_i(res, istrue(L.v) ? ptest(op->r.n) : 0); |
| 2477 | break; | 2485 | break; |
| 2478 | 2486 | ||
| 2479 | case XC( OC_LOR ): | 2487 | case XC( OC_LOR ): |
| 2480 | setvar_i(res, istrue(L.v) ? 1 : ptest(op->r.n)); | 2488 | setvar_i(res, istrue(L.v) ? 1 : ptest(op->r.n)); |
| 2481 | break; | 2489 | break; |
| 2482 | 2490 | ||
| 2483 | case XC( OC_BINARY ): | 2491 | case XC( OC_BINARY ): |
| 2484 | case XC( OC_REPLACE ): | 2492 | case XC( OC_REPLACE ): |
| 2485 | R.d = getvar_i(R.v); | 2493 | R.d = getvar_i(R.v); |
| 2486 | switch (opn) { | 2494 | switch (opn) { |
| 2487 | case '+': | 2495 | case '+': |
| 2488 | L.d += R.d; | 2496 | L.d += R.d; |
| 2489 | break; | 2497 | break; |
| 2490 | case '-': | 2498 | case '-': |
| 2491 | L.d -= R.d; | 2499 | L.d -= R.d; |
| 2492 | break; | 2500 | break; |
| 2493 | case '*': | 2501 | case '*': |
| 2494 | L.d *= R.d; | 2502 | L.d *= R.d; |
| 2495 | break; | 2503 | break; |
| 2496 | case '/': | 2504 | case '/': |
| 2497 | if (R.d == 0) runtime_error(EMSG_DIV_BY_ZERO); | 2505 | if (R.d == 0) runtime_error(EMSG_DIV_BY_ZERO); |
| 2498 | L.d /= R.d; | 2506 | L.d /= R.d; |
| 2499 | break; | 2507 | break; |
| 2500 | case '&': | 2508 | case '&': |
| 2501 | #ifdef CONFIG_FEATURE_AWK_MATH | 2509 | #if ENABLE_FEATURE_AWK_MATH |
| 2502 | L.d = pow(L.d, R.d); | 2510 | L.d = pow(L.d, R.d); |
| 2503 | #else | 2511 | #else |
| 2504 | runtime_error(EMSG_NO_MATH); | 2512 | runtime_error(EMSG_NO_MATH); |
| 2505 | #endif | 2513 | #endif |
| 2506 | break; | 2514 | break; |
| 2507 | case '%': | 2515 | case '%': |
| 2508 | if (R.d == 0) runtime_error(EMSG_DIV_BY_ZERO); | 2516 | if (R.d == 0) runtime_error(EMSG_DIV_BY_ZERO); |
| 2509 | L.d -= (int)(L.d / R.d) * R.d; | 2517 | L.d -= (int)(L.d / R.d) * R.d; |
| 2510 | break; | 2518 | break; |
| @@ -2512,7 +2520,7 @@ re_cont: | |||
| 2512 | res = setvar_i(((opinfo&OPCLSMASK) == OC_BINARY) ? res : X.v, L.d); | 2520 | res = setvar_i(((opinfo&OPCLSMASK) == OC_BINARY) ? res : X.v, L.d); |
| 2513 | break; | 2521 | break; |
| 2514 | 2522 | ||
| 2515 | case XC( OC_COMPARE ): | 2523 | case XC( OC_COMPARE ): |
| 2516 | if (is_numeric(L.v) && is_numeric(R.v)) { | 2524 | if (is_numeric(L.v) && is_numeric(R.v)) { |
| 2517 | L.d = getvar_i(L.v) - getvar_i(R.v); | 2525 | L.d = getvar_i(L.v) - getvar_i(R.v); |
| 2518 | } else { | 2526 | } else { |
| @@ -2521,20 +2529,20 @@ re_cont: | |||
| 2521 | L.d = icase ? strcasecmp(L.s, R.s) : strcmp(L.s, R.s); | 2529 | L.d = icase ? strcasecmp(L.s, R.s) : strcmp(L.s, R.s); |
| 2522 | } | 2530 | } |
| 2523 | switch (opn & 0xfe) { | 2531 | switch (opn & 0xfe) { |
| 2524 | case 0: | 2532 | case 0: |
| 2525 | R.i = (L.d > 0); | 2533 | R.i = (L.d > 0); |
| 2526 | break; | 2534 | break; |
| 2527 | case 2: | 2535 | case 2: |
| 2528 | R.i = (L.d >= 0); | 2536 | R.i = (L.d >= 0); |
| 2529 | break; | 2537 | break; |
| 2530 | case 4: | 2538 | case 4: |
| 2531 | R.i = (L.d == 0); | 2539 | R.i = (L.d == 0); |
| 2532 | break; | 2540 | break; |
| 2533 | } | 2541 | } |
| 2534 | setvar_i(res, (opn & 0x1 ? R.i : !R.i) ? 1 : 0); | 2542 | setvar_i(res, (opn & 0x1 ? R.i : !R.i) ? 1 : 0); |
| 2535 | break; | 2543 | break; |
| 2536 | 2544 | ||
| 2537 | default: | 2545 | default: |
| 2538 | runtime_error(EMSG_POSSIBLE_ERROR); | 2546 | runtime_error(EMSG_POSSIBLE_ERROR); |
| 2539 | } | 2547 | } |
| 2540 | if ((opinfo & OPCLSMASK) <= SHIFT_TIL_THIS) | 2548 | if ((opinfo & OPCLSMASK) <= SHIFT_TIL_THIS) |
| @@ -2553,18 +2561,20 @@ re_cont: | |||
| 2553 | 2561 | ||
| 2554 | static int awk_exit(int r) | 2562 | static int awk_exit(int r) |
| 2555 | { | 2563 | { |
| 2556 | unsigned int i; | 2564 | var tv; |
| 2565 | unsigned i; | ||
| 2557 | hash_item *hi; | 2566 | hash_item *hi; |
| 2558 | static var tv; | ||
| 2559 | 2567 | ||
| 2560 | if (! exiting) { | 2568 | zero_out_var(&tv); |
| 2569 | |||
| 2570 | if (!exiting) { | ||
| 2561 | exiting = TRUE; | 2571 | exiting = TRUE; |
| 2562 | nextrec = FALSE; | 2572 | nextrec = FALSE; |
| 2563 | evaluate(endseq.first, &tv); | 2573 | evaluate(endseq.first, &tv); |
| 2564 | } | 2574 | } |
| 2565 | 2575 | ||
| 2566 | /* waiting for children */ | 2576 | /* waiting for children */ |
| 2567 | for (i=0; i<fdhash->csize; i++) { | 2577 | for (i = 0; i < fdhash->csize; i++) { |
| 2568 | hi = fdhash->items[i]; | 2578 | hi = fdhash->items[i]; |
| 2569 | while (hi) { | 2579 | while (hi) { |
| 2570 | if (hi->data.rs.F && hi->data.rs.is_pipe) | 2580 | if (hi->data.rs.F && hi->data.rs.is_pipe) |
| @@ -2635,18 +2645,17 @@ int awk_main(int argc, char **argv) | |||
| 2635 | { | 2645 | { |
| 2636 | unsigned opt; | 2646 | unsigned opt; |
| 2637 | char *opt_F, *opt_v, *opt_W; | 2647 | char *opt_F, *opt_v, *opt_W; |
| 2638 | char *s, *s1; | 2648 | int i, j, flen; |
| 2639 | int i, j, c, flen; | ||
| 2640 | var *v; | 2649 | var *v; |
| 2641 | static var tv; | 2650 | var tv; |
| 2642 | char **envp; | 2651 | char **envp; |
| 2643 | static int from_file = FALSE; | 2652 | char *vnames = (char *)vNames; /* cheat */ |
| 2644 | rstream *rsm; | 2653 | char *vvalues = (char *)vValues; |
| 2645 | FILE *F, *stdfiles[3]; | 2654 | |
| 2646 | static char * stdnames = "/dev/stdin\0/dev/stdout\0/dev/stderr"; | 2655 | zero_out_var(&tv); |
| 2647 | 2656 | ||
| 2648 | /* allocate global buffer */ | 2657 | /* allocate global buffer */ |
| 2649 | buf = xmalloc(MAXVARFMT+1); | 2658 | buf = xmalloc(MAXVARFMT + 1); |
| 2650 | 2659 | ||
| 2651 | vhash = hash_init(); | 2660 | vhash = hash_init(); |
| 2652 | ahash = hash_init(); | 2661 | ahash = hash_init(); |
| @@ -2654,98 +2663,90 @@ int awk_main(int argc, char **argv) | |||
| 2654 | fnhash = hash_init(); | 2663 | fnhash = hash_init(); |
| 2655 | 2664 | ||
| 2656 | /* initialize variables */ | 2665 | /* initialize variables */ |
| 2657 | for (i=0; *vNames; i++) { | 2666 | for (i = 0; *vnames; i++) { |
| 2658 | V[i] = v = newvar(nextword(&vNames)); | 2667 | V[i] = v = newvar(nextword(&vnames)); |
| 2659 | if (*vValues != '\377') | 2668 | if (*vvalues != '\377') |
| 2660 | setvar_s(v, nextword(&vValues)); | 2669 | setvar_s(v, nextword(&vvalues)); |
| 2661 | else | 2670 | else |
| 2662 | setvar_i(v, 0); | 2671 | setvar_i(v, 0); |
| 2663 | 2672 | ||
| 2664 | if (*vNames == '*') { | 2673 | if (*vnames == '*') { |
| 2665 | v->type |= VF_SPECIAL; | 2674 | v->type |= VF_SPECIAL; |
| 2666 | vNames++; | 2675 | vnames++; |
| 2667 | } | 2676 | } |
| 2668 | } | 2677 | } |
| 2669 | 2678 | ||
| 2670 | handle_special(V[FS]); | 2679 | handle_special(V[FS]); |
| 2671 | handle_special(V[RS]); | 2680 | handle_special(V[RS]); |
| 2672 | 2681 | ||
| 2673 | stdfiles[0] = stdin; | 2682 | newfile("/dev/stdin")->F = stdin; |
| 2674 | stdfiles[1] = stdout; | 2683 | newfile("/dev/stdout")->F = stdout; |
| 2675 | stdfiles[2] = stderr; | 2684 | newfile("/dev/stderr")->F = stderr; |
| 2676 | for (i=0; i<3; i++) { | ||
| 2677 | rsm = newfile(nextword(&stdnames)); | ||
| 2678 | rsm->F = stdfiles[i]; | ||
| 2679 | } | ||
| 2680 | 2685 | ||
| 2681 | for (envp=environ; *envp; envp++) { | 2686 | for (envp = environ; *envp; envp++) { |
| 2682 | s = xstrdup(*envp); | 2687 | char *s = xstrdup(*envp); |
| 2683 | s1 = strchr(s, '='); | 2688 | char *s1 = strchr(s, '='); |
| 2684 | if (!s1) { | 2689 | if (s1) { |
| 2685 | goto keep_going; | 2690 | *s1++ = '\0'; |
| 2691 | setvar_u(findvar(iamarray(V[ENVIRON]), s), s1); | ||
| 2686 | } | 2692 | } |
| 2687 | *(s1++) = '\0'; | ||
| 2688 | setvar_u(findvar(iamarray(V[ENVIRON]), s), s1); | ||
| 2689 | keep_going: | ||
| 2690 | free(s); | 2693 | free(s); |
| 2691 | } | 2694 | } |
| 2692 | 2695 | ||
| 2693 | opt = getopt32(argc, argv, "F:v:f:W:", &opt_F, &opt_v, &programname, &opt_W); | 2696 | opt = getopt32(argc, argv, "F:v:f:W:", &opt_F, &opt_v, &programname, &opt_W); |
| 2697 | argv += optind; | ||
| 2698 | argc -= optind; | ||
| 2694 | if (opt & 0x1) setvar_s(V[FS], opt_F); // -F | 2699 | if (opt & 0x1) setvar_s(V[FS], opt_F); // -F |
| 2695 | if (opt & 0x2) if (!is_assignment(opt_v)) bb_show_usage(); // -v | 2700 | if (opt & 0x2) if (!is_assignment(opt_v)) bb_show_usage(); // -v |
| 2696 | if (opt & 0x4) { // -f | 2701 | if (opt & 0x4) { // -f |
| 2697 | from_file = TRUE; | 2702 | char *s = s; /* die, gcc, die */ |
| 2698 | F = afopen(programname, "r"); | 2703 | FILE *from_file = afopen(programname, "r"); |
| 2699 | s = NULL; | ||
| 2700 | /* one byte is reserved for some trick in next_token */ | 2704 | /* one byte is reserved for some trick in next_token */ |
| 2701 | if (fseek(F, 0, SEEK_END) == 0) { | 2705 | if (fseek(from_file, 0, SEEK_END) == 0) { |
| 2702 | flen = ftell(F); | 2706 | flen = ftell(from_file); |
| 2703 | s = xmalloc(flen+4); | 2707 | s = xmalloc(flen + 4); |
| 2704 | fseek(F, 0, SEEK_SET); | 2708 | fseek(from_file, 0, SEEK_SET); |
| 2705 | i = 1 + fread(s+1, 1, flen, F); | 2709 | i = 1 + fread(s + 1, 1, flen, from_file); |
| 2706 | } else { | 2710 | } else { |
| 2707 | for (i=j=1; j>0; i+=j) { | 2711 | for (i = j = 1; j > 0; i += j) { |
| 2708 | s = (char *)xrealloc(s, i+4096); | 2712 | s = xrealloc(s, i + 4096); |
| 2709 | j = fread(s+i, 1, 4094, F); | 2713 | j = fread(s + i, 1, 4094, from_file); |
| 2710 | } | 2714 | } |
| 2711 | } | 2715 | } |
| 2712 | s[i] = '\0'; | 2716 | s[i] = '\0'; |
| 2713 | fclose(F); | 2717 | fclose(from_file); |
| 2714 | parse_program(s+1); | 2718 | parse_program(s + 1); |
| 2715 | free(s); | 2719 | free(s); |
| 2716 | } | 2720 | } else { // no -f: take program from 1st parameter |
| 2717 | if (opt & 0x8) // -W | 2721 | if (!argc) |
| 2718 | bb_error_msg("warning: unrecognized option '-W %s' ignored", opt_W); | ||
| 2719 | |||
| 2720 | if (!from_file) { | ||
| 2721 | if (argc == optind) | ||
| 2722 | bb_show_usage(); | 2722 | bb_show_usage(); |
| 2723 | programname = "cmd. line"; | 2723 | programname = "cmd. line"; |
| 2724 | parse_program(argv[optind++]); | 2724 | parse_program(*argv++); |
| 2725 | 2725 | argc--; | |
| 2726 | } | 2726 | } |
| 2727 | if (opt & 0x8) // -W | ||
| 2728 | bb_error_msg("warning: unrecognized option '-W %s' ignored", opt_W); | ||
| 2727 | 2729 | ||
| 2728 | /* fill in ARGV array */ | 2730 | /* fill in ARGV array */ |
| 2729 | setvar_i(V[ARGC], argc - optind + 1); | 2731 | setvar_i(V[ARGC], argc + 1); |
| 2730 | setari_u(V[ARGV], 0, "awk"); | 2732 | setari_u(V[ARGV], 0, "awk"); |
| 2731 | for (i = optind; i < argc; i++) | 2733 | i = 0; |
| 2732 | setari_u(V[ARGV], i+1-optind, argv[i]); | 2734 | while (*argv) |
| 2735 | setari_u(V[ARGV], ++i, *argv++); | ||
| 2733 | 2736 | ||
| 2734 | evaluate(beginseq.first, &tv); | 2737 | evaluate(beginseq.first, &tv); |
| 2735 | if (! mainseq.first && ! endseq.first) | 2738 | if (!mainseq.first && !endseq.first) |
| 2736 | awk_exit(EXIT_SUCCESS); | 2739 | awk_exit(EXIT_SUCCESS); |
| 2737 | 2740 | ||
| 2738 | /* input file could already be opened in BEGIN block */ | 2741 | /* input file could already be opened in BEGIN block */ |
| 2739 | if (! iF) iF = next_input_file(); | 2742 | if (!iF) iF = next_input_file(); |
| 2740 | 2743 | ||
| 2741 | /* passing through input files */ | 2744 | /* passing through input files */ |
| 2742 | while (iF) { | 2745 | while (iF) { |
| 2743 | |||
| 2744 | nextfile = FALSE; | 2746 | nextfile = FALSE; |
| 2745 | setvar_i(V[FNR], 0); | 2747 | setvar_i(V[FNR], 0); |
| 2746 | 2748 | ||
| 2747 | while ((c = awk_getline(iF, V[F0])) > 0) { | 2749 | while ((i = awk_getline(iF, V[F0])) > 0) { |
| 2748 | |||
| 2749 | nextrec = FALSE; | 2750 | nextrec = FALSE; |
| 2750 | incvar(V[NR]); | 2751 | incvar(V[NR]); |
| 2751 | incvar(V[FNR]); | 2752 | incvar(V[FNR]); |
| @@ -2755,14 +2756,12 @@ keep_going: | |||
| 2755 | break; | 2756 | break; |
| 2756 | } | 2757 | } |
| 2757 | 2758 | ||
| 2758 | if (c < 0) | 2759 | if (i < 0) |
| 2759 | runtime_error(strerror(errno)); | 2760 | runtime_error(strerror(errno)); |
| 2760 | 2761 | ||
| 2761 | iF = next_input_file(); | 2762 | iF = next_input_file(); |
| 2762 | |||
| 2763 | } | 2763 | } |
| 2764 | 2764 | ||
| 2765 | awk_exit(EXIT_SUCCESS); | 2765 | awk_exit(EXIT_SUCCESS); |
| 2766 | 2766 | /*return 0;*/ | |
| 2767 | return 0; | ||
| 2768 | } | 2767 | } |
