1 /* 2 * awk.h -- Definitions for gawk. 3 */ 4 5 /* 6 * Copyright (C) 1986, 1988, 1989, 1991-2000 the Free Software Foundation, Inc. 7 * 8 * This file is part of GAWK, the GNU implementation of the 9 * AWK Programming Language. 10 * 11 * GAWK is free software; you can redistribute it and/or modify 12 * it under the terms of the GNU General Public License as published by 13 * the Free Software Foundation; either version 2 of the License, or 14 * (at your option) any later version. 15 * 16 * GAWK is distributed in the hope that it will be useful, 17 * but WITHOUT ANY WARRANTY; without even the implied warranty of 18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19 * GNU General Public License for more details. 20 * 21 * You should have received a copy of the GNU General Public License 22 * along with this program; if not, write to the Free Software 23 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA 24 * 25 * $FreeBSD: src/contrib/awk/awk.h,v 1.5.2.1 2001/01/23 22:08:30 asmodai Exp $ 26 * $DragonFly: src/contrib/awk/Attic/awk.h,v 1.2 2003/06/17 04:23:58 dillon Exp $ 27 */ 28 29 /* ------------------------------ Includes ------------------------------ */ 30 31 /* 32 * config.h absolutely, positively, *M*U*S*T* be included before 33 * any system headers. Otherwise, extreme death, destruction 34 * and loss of life results. 35 * 36 * Well, OK, gawk just won't work on systems using egcs and LFS. But 37 * that's almost as bad. 38 */ 39 #ifdef HAVE_CONFIG_H 40 #include <config.h> 41 #endif 42 43 #ifndef _GNU_SOURCE 44 #define _GNU_SOURCE 1 /* enable GNU extensions */ 45 #endif /* _GNU_SOURCE */ 46 47 #include <stdio.h> 48 #include <assert.h> 49 #ifdef HAVE_LIMITS_H 50 #include <limits.h> 51 #endif /* HAVE_LIMITS_H */ 52 #include <ctype.h> 53 #include <setjmp.h> 54 #ifdef HAVE_LOCALE_H 55 #include <locale.h> 56 #endif /* HAVE_LOCALE_H */ 57 #if defined(HAVE_STDARG_H) && defined(__STDC__) && __STDC__ 58 #include <stdarg.h> 59 #else 60 #include <varargs.h> 61 #endif 62 #include <signal.h> 63 #include <time.h> 64 #include <errno.h> 65 #if ! defined(errno) && ! defined(MSDOS) && ! defined(OS2) 66 extern int errno; 67 #endif 68 #ifdef HAVE_SIGNUM_H 69 #include <signum.h> 70 #endif 71 72 /* ----------------- System dependencies (with more includes) -----------*/ 73 74 /* This section is the messiest one in the file, not a lot that can be done */ 75 76 /* First, get the ctype stuff right; from Jim Meyering */ 77 #if defined(STDC_HEADERS) || (!defined(isascii) && !defined(HAVE_ISASCII)) 78 #define ISASCII(c) 1 79 #else 80 #define ISASCII(c) isascii(c) 81 #endif 82 83 #ifdef isblank 84 #define ISBLANK(c) (ISASCII(c) && isblank(c)) 85 #else 86 #define ISBLANK(c) ((c) == ' ' || (c) == '\t') 87 #endif 88 #ifdef isgraph 89 #define ISGRAPH(c) (ISASCII(c) && isgraph(c)) 90 #else 91 #define ISGRAPH(c) (ISASCII(c) && isprint(c) && !isspace(c)) 92 #endif 93 94 #define ISPRINT(c) (ISASCII (c) && isprint (c)) 95 #define ISDIGIT(c) (ISASCII (c) && isdigit (c)) 96 #define ISALNUM(c) (ISASCII (c) && isalnum (c)) 97 #define ISALPHA(c) (ISASCII (c) && isalpha (c)) 98 #define ISCNTRL(c) (ISASCII (c) && iscntrl (c)) 99 #define ISLOWER(c) (ISASCII (c) && islower (c)) 100 #define ISPUNCT(c) (ISASCII (c) && ispunct (c)) 101 #define ISSPACE(c) (ISASCII (c) && isspace (c)) 102 #define ISUPPER(c) (ISASCII (c) && isupper (c)) 103 #define ISXDIGIT(c) (ISASCII (c) && isxdigit (c)) 104 105 106 #ifdef __STDC__ 107 #define P(s) s 108 #define MALLOC_ARG_T size_t 109 #else /* not __STDC__ */ 110 #define P(s) () 111 #define MALLOC_ARG_T unsigned 112 #define volatile 113 #define const 114 #endif /* not __STDC__ */ 115 116 #if ! defined(VMS) || (! defined(VAXC) && ! defined(__DECC)) 117 #include <sys/types.h> 118 #include <sys/stat.h> 119 #else /* VMS w/ VAXC or DECC */ 120 #include <types.h> 121 #include <stat.h> 122 #include <file.h> /* avoid <fcntl.h> in io.c */ 123 #ifdef __DECC 124 /* DEC C implies DECC$SHR, which doesn't have the %g problem of VAXCRTL */ 125 #undef GFMT_WORKAROUND 126 #endif 127 #endif /* VMS w/ VAXC or DECC */ 128 129 #ifdef STDC_HEADERS 130 #include <stdlib.h> 131 #else /* not STDC_HEADERS */ 132 #include "protos.h" 133 #endif /* not STDC_HEADERS */ 134 135 #ifdef HAVE_STRING_H 136 #include <string.h> 137 #ifdef NEED_MEMORY_H 138 #include <memory.h> 139 #endif /* NEED_MEMORY_H */ 140 #else /* not HAVE_STRING_H */ 141 #ifdef HAVE_STRINGS_H 142 #include <strings.h> 143 #endif /* HAVE_STRINGS_H */ 144 #endif /* not HAVE_STRING_H */ 145 146 #ifdef NeXT 147 #if __GNUC__ < 2 || __GNUC_MINOR__ < 7 148 #include <libc.h> 149 #endif 150 #undef atof 151 #define getopt GNU_getopt 152 #define GFMT_WORKAROUND 153 #endif /* NeXT */ 154 155 #if defined(atarist) || defined(VMS) 156 #include <unixlib.h> 157 #endif /* atarist || VMS */ 158 159 #if HAVE_UNISTD_H 160 #include <unistd.h> 161 #endif /* HAVE_UNISTD_H */ 162 163 #ifndef HAVE_VPRINTF 164 /* if you don't have vprintf, try this and cross your fingers. */ 165 #ifdef HAVE_DOPRNT 166 #define vfprintf(fp,fmt,arg) _doprnt((fmt), (arg), (fp)) 167 #else /* not HAVE_DOPRNT */ 168 you 169 lose 170 #endif /* not HAVE_DOPRNT */ 171 #endif /* HAVE_VPRINTF */ 172 173 #ifndef HAVE_SETLOCALE 174 #define setlocale(locale, val) /* nothing */ 175 #endif /* HAVE_SETLOCALE */ 176 177 #ifdef VMS 178 #include "vms/redirect.h" 179 #endif /*VMS*/ 180 181 #ifdef atarist 182 #include "atari/redirect.h" 183 #endif 184 185 #define GNU_REGEX 186 #ifdef GNU_REGEX 187 #ifdef __FreeBSD__ 188 #include <gnuregex.h> 189 #else 190 #include "regex.h" 191 #endif 192 #include "dfa.h" 193 typedef struct Regexp { 194 struct re_pattern_buffer pat; 195 struct re_registers regs; 196 struct dfa dfareg; 197 int dfa; 198 } Regexp; 199 #define RESTART(rp,s) (rp)->regs.start[0] 200 #define REEND(rp,s) (rp)->regs.end[0] 201 #define SUBPATSTART(rp,s,n) (rp)->regs.start[n] 202 #define SUBPATEND(rp,s,n) (rp)->regs.end[n] 203 #endif /* GNU_REGEX */ 204 205 /* ------------------ Constants, Structures, Typedefs ------------------ */ 206 207 #ifndef AWKNUM 208 #define AWKNUM double 209 #endif 210 211 #ifndef TRUE 212 /* a bit hackneyed, but what the heck */ 213 #define TRUE 1 214 #define FALSE 0 215 #endif 216 217 /* Figure out what '\a' really is. */ 218 #ifdef __STDC__ 219 #define BELL '\a' /* sure makes life easy, don't it? */ 220 #else 221 # if 'z' - 'a' == 25 /* ascii */ 222 # if 'a' != 97 /* machine is dumb enough to use mark parity */ 223 # define BELL '\207' 224 # else 225 # define BELL '\07' 226 # endif 227 # else 228 # define BELL '\057' 229 # endif 230 #endif 231 232 typedef enum nodevals { 233 /* illegal entry == 0 */ 234 Node_illegal, 235 236 /* binary operators lnode and rnode are the expressions to work on */ 237 Node_times, 238 Node_quotient, 239 Node_mod, 240 Node_plus, 241 Node_minus, 242 Node_cond_pair, /* conditional pair (see Node_line_range) */ 243 Node_subscript, 244 Node_concat, 245 Node_exp, 246 247 /* unary operators subnode is the expression to work on */ 248 Node_preincrement, 249 Node_predecrement, 250 Node_postincrement, 251 Node_postdecrement, 252 Node_unary_minus, 253 Node_field_spec, 254 255 /* assignments lnode is the var to assign to, rnode is the exp */ 256 Node_assign, 257 Node_assign_times, 258 Node_assign_quotient, 259 Node_assign_mod, 260 Node_assign_plus, 261 Node_assign_minus, 262 Node_assign_exp, 263 264 /* boolean binaries lnode and rnode are expressions */ 265 Node_and, 266 Node_or, 267 268 /* binary relationals compares lnode and rnode */ 269 Node_equal, 270 Node_notequal, 271 Node_less, 272 Node_greater, 273 Node_leq, 274 Node_geq, 275 Node_match, 276 Node_nomatch, 277 278 /* unary relationals works on subnode */ 279 Node_not, 280 281 /* program structures */ 282 Node_rule_list, /* lnode is a rule, rnode is rest of list */ 283 Node_rule_node, /* lnode is pattern, rnode is statement */ 284 Node_statement_list, /* lnode is statement, rnode is more list */ 285 Node_if_branches, /* lnode is to run on true, rnode on false */ 286 Node_expression_list, /* lnode is an exp, rnode is more list */ 287 Node_param_list, /* lnode is a variable, rnode is more list */ 288 289 /* keywords */ 290 Node_K_if, /* lnode is conditonal, rnode is if_branches */ 291 Node_K_while, /* lnode is condtional, rnode is stuff to run */ 292 Node_K_for, /* lnode is for_struct, rnode is stuff to run */ 293 Node_K_arrayfor, /* lnode is for_struct, rnode is stuff to run */ 294 Node_K_break, /* no subs */ 295 Node_K_continue, /* no subs */ 296 Node_K_print, /* lnode is exp_list, rnode is redirect */ 297 Node_K_printf, /* lnode is exp_list, rnode is redirect */ 298 Node_K_next, /* no subs */ 299 Node_K_exit, /* subnode is return value, or NULL */ 300 Node_K_do, /* lnode is conditional, rnode stuff to run */ 301 Node_K_return, /* lnode is return value */ 302 Node_K_delete, /* lnode is array, rnode is subscript */ 303 Node_K_delete_loop, /* lnode is array, rnode is subscript */ 304 Node_K_getline, /* lnode is opt var, rnode is redirection */ 305 Node_K_function, /* lnode is statement list, rnode is params */ 306 Node_K_nextfile, /* no subs */ 307 308 /* I/O redirection for print statements */ 309 Node_redirect_output, /* subnode is where to redirect */ 310 Node_redirect_append, /* subnode is where to redirect */ 311 Node_redirect_pipe, /* subnode is where to redirect */ 312 Node_redirect_pipein, /* subnode is where to redirect */ 313 Node_redirect_input, /* subnode is where to redirect */ 314 315 /* Variables */ 316 Node_var, /* rnode is value, lnode is array stuff */ 317 Node_var_array, /* array is ptr to elements, asize num of eles */ 318 Node_val, /* node is a value - type in flags */ 319 320 /* Builtins subnode is explist to work on, proc is func to call */ 321 Node_builtin, 322 323 /* 324 * pattern: conditional ',' conditional ; lnode of Node_line_range 325 * is the two conditionals (Node_cond_pair), other word (rnode place) 326 * is a flag indicating whether or not this range has been entered. 327 */ 328 Node_line_range, 329 330 /* 331 * boolean test of membership in array lnode is string-valued 332 * expression rnode is array name 333 */ 334 Node_in_array, 335 336 Node_func, /* lnode is param. list, rnode is body */ 337 Node_func_call, /* lnode is name, rnode is argument list */ 338 339 Node_cond_exp, /* lnode is conditonal, rnode is if_branches */ 340 Node_regex, /* a regexp, text, compiled, flags, etc */ 341 Node_hashnode, /* an identifier in the symbol table */ 342 Node_ahash, /* an array element */ 343 Node_array_ref, /* array passed by ref as parameter */ 344 Node_NF, /* variables recognized in the grammar */ 345 Node_NR, 346 Node_FNR, 347 Node_FS, 348 Node_RS, 349 Node_FIELDWIDTHS, 350 Node_IGNORECASE, 351 Node_OFS, 352 Node_ORS, 353 Node_OFMT, 354 Node_CONVFMT, 355 Node_final /* sentry value, not legal */ 356 } NODETYPE; 357 358 /* 359 * NOTE - this struct is a rather kludgey -- it is packed to minimize 360 * space usage, at the expense of cleanliness. Alter at own risk. 361 */ 362 typedef struct exp_node { 363 union { 364 struct { 365 union { 366 struct exp_node *lptr; 367 char *param_name; 368 long ll; 369 } l; 370 union { 371 struct exp_node *rptr; 372 struct exp_node *(*pptr)(); 373 Regexp *preg; 374 struct for_loop_header *hd; 375 struct exp_node **av; 376 int r_ent; /* range entered */ 377 } r; 378 union { 379 struct exp_node *extra; 380 long xl; 381 } x; 382 char *name; 383 short number; 384 unsigned char reflags; 385 # define CASE 1 386 # define CONST 2 387 # define FS_DFLT 4 388 } nodep; 389 struct { 390 AWKNUM fltnum; /* this is here for optimal packing of 391 * the structure on many machines 392 */ 393 char *sp; 394 size_t slen; 395 long sref; 396 int idx; 397 } val; 398 struct { 399 struct exp_node *next; 400 char *name; 401 size_t length; 402 struct exp_node *value; 403 } hash; 404 #define hnext sub.hash.next 405 #define hname sub.hash.name 406 #define hlength sub.hash.length 407 #define hvalue sub.hash.value 408 struct { 409 struct exp_node *next; 410 struct exp_node *name; 411 struct exp_node *value; 412 } ahash; 413 #define ahnext sub.ahash.next 414 #define ahname sub.ahash.name 415 #define ahvalue sub.ahash.value 416 } sub; 417 NODETYPE type; 418 unsigned short flags; 419 # define MALLOC 1 /* can be free'd */ 420 # define TEMP 2 /* should be free'd */ 421 # define PERM 4 /* can't be free'd */ 422 # define STRING 8 /* assigned as string */ 423 # define STR 16 /* string value is current */ 424 # define NUM 32 /* numeric value is current */ 425 # define NUMBER 64 /* assigned as number */ 426 # define MAYBE_NUM 128 /* user input: if NUMERIC then 427 * a NUMBER */ 428 # define ARRAYMAXED 256 /* array is at max size */ 429 # define SCALAR 512 /* used as scalar, can't be array */ 430 # define FUNC 1024 /* this parameter is really a 431 * function name; see awk.y */ 432 # define FIELD 2048 /* this is a field */ 433 434 char *vname; /* variable's name */ 435 } NODE; 436 437 #define lnode sub.nodep.l.lptr 438 #define nextp sub.nodep.l.lptr 439 #define rnode sub.nodep.r.rptr 440 #define source_file sub.nodep.name 441 #define source_line sub.nodep.number 442 #define param_cnt sub.nodep.number 443 #define param sub.nodep.l.param_name 444 445 #define subnode lnode 446 #define proc sub.nodep.r.pptr 447 448 #define re_reg sub.nodep.r.preg 449 #define re_flags sub.nodep.reflags 450 #define re_text lnode 451 #define re_exp sub.nodep.x.extra 452 #define re_cnt sub.nodep.number 453 454 #define forsub lnode 455 #define forloop rnode->sub.nodep.r.hd 456 457 #define stptr sub.val.sp 458 #define stlen sub.val.slen 459 #define stref sub.val.sref 460 #define stfmt sub.val.idx 461 462 #define numbr sub.val.fltnum 463 464 #define var_value lnode 465 #define var_array sub.nodep.r.av 466 #define array_size sub.nodep.l.ll 467 #define table_size sub.nodep.x.xl 468 469 #define orig_array sub.nodep.x.extra 470 471 #define condpair lnode 472 #define triggered sub.nodep.r.r_ent 473 474 /* a regular for loop */ 475 typedef struct for_loop_header { 476 NODE *init; 477 NODE *cond; 478 NODE *incr; 479 } FOR_LOOP_HEADER; 480 481 /* for "for(iggy in foo) {" */ 482 struct search { 483 NODE *sym; 484 size_t idx; 485 NODE *bucket; 486 NODE *retval; 487 }; 488 489 /* for faster input, bypass stdio */ 490 typedef struct iobuf { 491 const char *name; 492 int fd; 493 char *buf; 494 char *off; 495 char *end; 496 size_t size; /* this will be determined by an fstat() call */ 497 int cnt; 498 long secsiz; 499 int flag; 500 # define IOP_IS_TTY 1 501 # define IOP_IS_INTERNAL 2 502 # define IOP_NO_FREE 4 503 # define IOP_MMAPPED 8 504 # define IOP_NOFREE_OBJ 16 505 int (*getrec)(); 506 } IOBUF; 507 508 typedef void (*Func_ptr)(); 509 510 /* structure used to dynamically maintain a linked-list of open files/pipes */ 511 struct redirect { 512 unsigned int flag; 513 # define RED_FILE 1 514 # define RED_PIPE 2 515 # define RED_READ 4 516 # define RED_WRITE 8 517 # define RED_APPEND 16 518 # define RED_NOBUF 32 519 # define RED_USED 64 /* closed temporarily to reuse fd */ 520 # define RED_EOF 128 521 char *value; 522 FILE *fp; 523 FILE *ifp; /* input fp, needed for PIPES_SIMULATED */ 524 IOBUF *iop; 525 int pid; 526 int status; 527 struct redirect *prev; 528 struct redirect *next; 529 }; 530 531 /* structure for our source, either a command line string or a source file */ 532 struct src { 533 enum srctype { CMDLINE = 1, SOURCEFILE } stype; 534 char *val; 535 }; 536 537 /* longjmp return codes, must be nonzero */ 538 /* Continue means either for loop/while continue, or next input record */ 539 #define TAG_CONTINUE 1 540 /* Break means either for/while break, or stop reading input */ 541 #define TAG_BREAK 2 542 /* Return means return from a function call; leave value in ret_node */ 543 #define TAG_RETURN 3 544 545 #ifndef LONG_MAX 546 #define LONG_MAX ((long)(~(1L << (sizeof (long) * 8 - 1)))) 547 #endif 548 #ifndef ULONG_MAX 549 #define ULONG_MAX (~(unsigned long)0) 550 #endif 551 #ifndef LONG_MIN 552 #define LONG_MIN ((long)(-LONG_MAX - 1L)) 553 #endif 554 #define HUGE LONG_MAX 555 556 /* -------------------------- External variables -------------------------- */ 557 /* gawk builtin variables */ 558 extern long NF; 559 extern long NR; 560 extern long FNR; 561 extern int IGNORECASE; 562 extern int RS_is_null; 563 extern char *OFS; 564 extern int OFSlen; 565 extern char *ORS; 566 extern int ORSlen; 567 extern char *OFMT; 568 extern char *CONVFMT; 569 extern int CONVFMTidx; 570 extern int OFMTidx; 571 extern NODE *CONVFMT_node, *FIELDWIDTHS_node, *FILENAME_node; 572 extern NODE *FNR_node, *FS_node, *IGNORECASE_node, *NF_node; 573 extern NODE *NR_node, *OFMT_node, *OFS_node, *ORS_node, *RLENGTH_node; 574 extern NODE *RSTART_node, *RS_node, *RT_node, *SUBSEP_node; 575 extern NODE **stack_ptr; 576 extern NODE *Nnull_string; 577 extern NODE **fields_arr; 578 extern int sourceline; 579 extern char *source; 580 extern NODE *expression_value; 581 582 #if __GNUC__ < 2 583 extern NODE *_t; /* used as temporary in tree_eval */ 584 #endif 585 586 extern NODE *nextfree; 587 extern int field0_valid; 588 extern int do_traditional; 589 extern int do_posix; 590 extern int do_lint; 591 extern int do_lint_old; 592 extern int do_intervals; 593 extern int in_begin_rule; 594 extern int in_end_rule; 595 596 extern const char *myname; 597 598 extern char quote; 599 extern char *defpath; 600 extern char envsep; 601 602 extern char casetable[]; /* for case-independent regexp matching */ 603 604 /* ------------------------- Pseudo-functions ------------------------- */ 605 606 #define is_identchar(c) (isalnum(c) || (c) == '_') 607 #define isnondecimal(str) (((str)[0]) == '0' && (ISDIGIT((str)[1]) \ 608 || (str)[1] == 'x' || (str)[1] == 'X')) 609 610 #ifdef MPROF 611 #define getnode(n) emalloc(n, NODE *, sizeof(NODE), "getnode") 612 #define freenode(n) free(n) 613 #else /* not MPROF */ 614 #define getnode(n) if (nextfree) n = nextfree, nextfree = nextfree->nextp;\ 615 else n = more_nodes() 616 #define freenode(n) ((n)->flags &= ~SCALAR, (n)->nextp = nextfree, nextfree = (n)) 617 #endif /* not MPROF */ 618 619 #ifdef DEBUG 620 #undef freenode 621 #define get_lhs(p, a) r_get_lhs((p), (a)) 622 #define m_tree_eval(t, iscond) r_tree_eval(t, iscond) 623 #else 624 #define get_lhs(p, a) ((p)->type == Node_var ? (&(p)->var_value) : \ 625 r_get_lhs((p), (a))) 626 #if __GNUC__ >= 2 627 #define m_tree_eval(t, iscond) \ 628 ({NODE * _t = (t); \ 629 if (_t == NULL) \ 630 _t = Nnull_string; \ 631 else { \ 632 switch(_t->type) { \ 633 case Node_val: \ 634 break; \ 635 case Node_var: \ 636 _t = _t->var_value; \ 637 break; \ 638 default: \ 639 _t = r_tree_eval(_t, iscond);\ 640 break; \ 641 } \ 642 } \ 643 _t;}) 644 #else 645 #define m_tree_eval(t, iscond) (_t = (t), _t == NULL ? Nnull_string : \ 646 (_t->type == Node_param_list ? \ 647 r_tree_eval(_t, iscond) : \ 648 (_t->type == Node_val ? _t : \ 649 (_t->type == Node_var ? _t->var_value : \ 650 r_tree_eval(_t, iscond))))) 651 #endif /* __GNUC__ */ 652 #endif /* not DEBUG */ 653 #define tree_eval(t) m_tree_eval(t, FALSE) 654 655 #define make_number(x) mk_number((x), (unsigned int)(MALLOC|NUM|NUMBER)) 656 #define tmp_number(x) mk_number((x), (unsigned int)(MALLOC|TEMP|NUM|NUMBER)) 657 658 #define free_temp(n) do { if ((n)->flags&TEMP) { unref(n); }} while (FALSE) 659 #define make_string(s, l) make_str_node((s), (size_t) (l), FALSE) 660 #define SCAN 1 661 #define ALREADY_MALLOCED 2 662 663 #define cant_happen() r_fatal("internal error line %d, file: %s", \ 664 __LINE__, __FILE__); 665 666 #ifdef HAVE_STRINGIZE 667 #define emalloc(var,ty,x,str) (void)((var=(ty)malloc((MALLOC_ARG_T)(x))) ||\ 668 (fatal("%s: %s: can't allocate memory (%s)",\ 669 (str), #var, strerror(errno)),0)) 670 #define erealloc(var,ty,x,str) (void)((var=(ty)realloc((char *)var,\ 671 (MALLOC_ARG_T)(x))) ||\ 672 (fatal("%s: %s: can't allocate memory (%s)",\ 673 (str), #var, strerror(errno)),0)) 674 #else /* HAVE_STRINGIZE */ 675 #define emalloc(var,ty,x,str) (void)((var=(ty)malloc((MALLOC_ARG_T)(x))) ||\ 676 (fatal("%s: %s: can't allocate memory (%s)",\ 677 (str), "var", strerror(errno)),0)) 678 #define erealloc(var,ty,x,str) (void)((var=(ty)realloc((char *)var,\ 679 (MALLOC_ARG_T)(x))) ||\ 680 (fatal("%s: %s: can't allocate memory (%s)",\ 681 (str), "var", strerror(errno)),0)) 682 #endif /* HAVE_STRINGIZE */ 683 684 #ifdef DEBUG 685 #define force_number r_force_number 686 #define force_string r_force_string 687 #else /* not DEBUG */ 688 #ifdef lint 689 extern AWKNUM force_number(); 690 #endif 691 #if __GNUC__ >= 2 692 #define force_number(n) ({NODE *_tn = (n);\ 693 (_tn->flags & NUM) ?_tn->numbr : r_force_number(_tn);}) 694 #define force_string(s) ({NODE *_ts = (s);\ 695 ((_ts->flags & STR) && \ 696 (_ts->stfmt == -1 || _ts->stfmt == CONVFMTidx)) ?\ 697 _ts : r_force_string(_ts);}) 698 #else 699 #ifdef MSDOS 700 extern double _msc51bug; 701 #define force_number(n) (_msc51bug=(_t = (n),\ 702 (_t->flags & NUM) ? _t->numbr : r_force_number(_t))) 703 #else /* not MSDOS */ 704 #define force_number(n) (_t = (n),\ 705 (_t->flags & NUM) ? _t->numbr : r_force_number(_t)) 706 #endif /* not MSDOS */ 707 #define force_string(s) (_t = (s),((_t->flags & STR) && \ 708 (_t->stfmt == -1 || \ 709 _t->stfmt == CONVFMTidx))? \ 710 _t : r_force_string(_t)) 711 #endif /* not __GNUC__ */ 712 #endif /* not DEBUG */ 713 714 #define STREQ(a,b) (*(a) == *(b) && strcmp((a), (b)) == 0) 715 #define STREQN(a,b,n) ((n) && *(a)== *(b) && \ 716 strncmp((a), (b), (size_t) (n)) == 0) 717 718 #define fatal set_loc(__FILE__, __LINE__), r_fatal 719 720 /* ------------- Function prototypes or defs (as appropriate) ------------- */ 721 722 /* array.c */ 723 extern NODE *concat_exp P((NODE *tree)); 724 extern void assoc_clear P((NODE *symbol)); 725 extern unsigned int hash P((const char *s, size_t len, unsigned long hsize)); 726 extern int in_array P((NODE *symbol, NODE *subs)); 727 extern NODE **assoc_lookup P((NODE *symbol, NODE *subs)); 728 extern void do_delete P((NODE *symbol, NODE *tree)); 729 extern void do_delete_loop P((NODE *symbol, NODE *tree)); 730 extern void assoc_scan P((NODE *symbol, struct search *lookat)); 731 extern void assoc_next P((struct search *lookat)); 732 extern NODE *assoc_dump P((NODE *symbol)); 733 extern NODE *do_adump P((NODE *tree)); 734 /* awktab.c */ 735 extern char *tokexpand P((void)); 736 extern NODE *node P((NODE *left, NODETYPE op, NODE *right)); 737 extern NODE *install P((char *name, NODE *value)); 738 extern NODE *lookup P((const char *name)); 739 extern NODE *variable P((char *name, int can_free, NODETYPE type)); 740 extern int yyparse P((void)); 741 extern NODE *stopme P((NODE *tree)); 742 /* builtin.c */ 743 extern double double_to_int P((double d)); 744 extern NODE *do_exp P((NODE *tree)); 745 extern NODE *do_fflush P((NODE *tree)); 746 extern NODE *do_index P((NODE *tree)); 747 extern NODE *do_int P((NODE *tree)); 748 extern NODE *do_length P((NODE *tree)); 749 extern NODE *do_log P((NODE *tree)); 750 extern NODE *do_sprintf P((NODE *tree)); 751 extern void do_printf P((NODE *tree)); 752 extern void print_simple P((NODE *tree, FILE *fp)); 753 extern NODE *do_sqrt P((NODE *tree)); 754 extern NODE *do_substr P((NODE *tree)); 755 extern NODE *do_strftime P((NODE *tree)); 756 extern NODE *do_systime P((NODE *tree)); 757 extern NODE *do_system P((NODE *tree)); 758 extern void do_print P((NODE *tree)); 759 extern NODE *do_tolower P((NODE *tree)); 760 extern NODE *do_toupper P((NODE *tree)); 761 extern NODE *do_atan2 P((NODE *tree)); 762 extern NODE *do_sin P((NODE *tree)); 763 extern NODE *do_cos P((NODE *tree)); 764 extern NODE *do_rand P((NODE *tree)); 765 extern NODE *do_srand P((NODE *tree)); 766 extern NODE *do_match P((NODE *tree)); 767 extern NODE *do_gsub P((NODE *tree)); 768 extern NODE *do_sub P((NODE *tree)); 769 extern NODE *do_gensub P((NODE *tree)); 770 #ifdef BITOPS 771 extern NODE *do_lshift P((NODE *tree)); 772 extern NODE *do_rshift P((NODE *tree)); 773 extern NODE *do_and P((NODE *tree)); 774 extern NODE *do_or P((NODE *tree)); 775 extern NODE *do_xor P((NODE *tree)); 776 extern NODE *do_compl P((NODE *tree)); 777 extern NODE *do_strtonum P((NODE *tree)); 778 #endif /* BITOPS */ 779 #if defined(BITOPS) || defined(NONDECDATA) 780 extern AWKNUM nondec2awknum P((char *str, size_t len)); 781 #endif /* defined(BITOPS) || defined(NONDECDATA) */ 782 /* eval.c */ 783 extern int interpret P((NODE *volatile tree)); 784 extern NODE *r_tree_eval P((NODE *tree, int iscond)); 785 extern int cmp_nodes P((NODE *t1, NODE *t2)); 786 extern NODE **r_get_lhs P((NODE *ptr, Func_ptr *assign)); 787 extern void set_IGNORECASE P((void)); 788 void set_OFS P((void)); 789 void set_ORS P((void)); 790 void set_OFMT P((void)); 791 void set_CONVFMT P((void)); 792 extern char *flags2str P((int)); 793 /* field.c */ 794 extern void init_fields P((void)); 795 extern void set_record P((char *buf, int cnt, int freeold)); 796 extern void reset_record P((void)); 797 extern void set_NF P((void)); 798 extern NODE **get_field P((long num, Func_ptr *assign)); 799 extern NODE *do_split P((NODE *tree)); 800 extern void set_FS P((void)); 801 extern void set_FS_if_not_FIELDWIDTHS P((void)); 802 extern void set_RS P((void)); 803 extern void set_FIELDWIDTHS P((void)); 804 extern int using_fieldwidths P((void)); 805 /* gawkmisc.c */ 806 extern char *gawk_name P((const char *filespec)); 807 extern void os_arg_fixup P((int *argcp, char ***argvp)); 808 extern int os_devopen P((const char *name, int flag)); 809 extern int optimal_bufsize P((int fd, struct stat *sbuf)); 810 extern int ispath P((const char *file)); 811 extern int isdirpunct P((int c)); 812 /* io.c */ 813 extern void set_FNR P((void)); 814 extern void set_NR P((void)); 815 extern void do_input P((void)); 816 extern struct redirect *redirect P((NODE *tree, int *errflg)); 817 extern NODE *do_close P((NODE *tree)); 818 extern int flush_io P((void)); 819 extern int close_io P((void)); 820 extern int devopen P((const char *name, const char *mode)); 821 extern int pathopen P((const char *file)); 822 extern NODE *do_getline P((NODE *tree)); 823 extern void do_nextfile P((void)); 824 extern struct redirect *getredirect P((char *str, int len)); 825 /* main.c */ 826 extern int main P((int argc, char **argv)); 827 extern void load_environ P((void)); 828 extern char *arg_assign P((char *arg)); 829 extern RETSIGTYPE catchsig P((int sig, int code)); 830 /* msg.c */ 831 extern void err P((const char *s, const char *emsg, va_list argp)); 832 #if _MSC_VER == 510 833 extern void msg P((va_list va_alist, ...)); 834 extern void error P((va_list va_alist, ...)); 835 extern void warning P((va_list va_alist, ...)); 836 extern void set_loc P((char *file, int line)); 837 extern void r_fatal P((va_list va_alist, ...)); 838 #else 839 #if defined(HAVE_STDARG_H) && defined(__STDC__) && __STDC__ 840 extern void msg (char *mesg, ...); 841 extern void error (char *mesg, ...); 842 extern void warning (char *mesg, ...); 843 extern void set_loc (char *file, int line); 844 extern void r_fatal (char *mesg, ...); 845 #else 846 extern void msg (); 847 extern void error (); 848 extern void warning (); 849 extern void set_loc (); 850 extern void r_fatal (); 851 #endif 852 #endif 853 /* node.c */ 854 extern AWKNUM r_force_number P((NODE *n)); 855 extern NODE *format_val P((char *format, int index, NODE *s)); 856 extern NODE *r_force_string P((NODE *s)); 857 extern NODE *dupnode P((NODE *n)); 858 extern NODE *mk_number P((AWKNUM x, unsigned int flags)); 859 extern NODE *make_str_node P((char *s, size_t len, int scan )); 860 extern NODE *tmp_string P((char *s, size_t len )); 861 extern NODE *more_nodes P((void)); 862 #ifdef DEBUG 863 extern void freenode P((NODE *it)); 864 #endif 865 extern void unref P((NODE *tmp)); 866 extern int parse_escape P((char **string_ptr)); 867 /* re.c */ 868 extern Regexp *make_regexp P((char *s, size_t len, int ignorecase, int dfa)); 869 extern int research P((Regexp *rp, char *str, int start, 870 size_t len, int need_start)); 871 extern void refree P((Regexp *rp)); 872 extern void reg_error P((const char *s)); 873 extern Regexp *re_update P((NODE *t)); 874 extern void resyntax P((int syntax)); 875 extern void resetup P((void)); 876 extern int avoid_dfa P((NODE *re, char *str, size_t len)); /* temporary */ 877 878 /* strncasecmp.c */ 879 extern int strncasecmp P((const char *s1, const char *s2, register size_t n)); 880 881 #if defined(atarist) 882 #if defined(PIPES_SIMULATED) 883 /* atari/tmpnam.c */ 884 extern char *tmpnam P((char *buf)); 885 extern char *tempnam P((const char *path, const char *base)); 886 #else 887 #include <wait.h> 888 #endif 889 #include <fcntl.h> 890 #define INVALID_HANDLE (__SMALLEST_VALID_HANDLE - 1) 891 #else 892 #define INVALID_HANDLE (-1) 893 #endif /* atarist */ 894 895 #ifndef STATIC 896 #define STATIC static 897 #endif 898 899 #ifdef C_ALLOCA 900 /* The __hpux check is to avoid conflicts with bison's definition of 901 alloca() in awktab.c.*/ 902 #if (defined(__STDC__) && __STDC__) || defined (__hpux) 903 extern void *alloca P((unsigned)); 904 #else 905 extern char *alloca P((unsigned)); 906 #endif 907 #endif 908