1760Speter /* Copyright (c) 1979 Regents of the University of California */ 2760Speter 3*3828Speter static char sccsid[] = "@(#)nl.c 1.5 06/01/81"; 4760Speter 5760Speter #include "whoami.h" 6760Speter #include "0.h" 7760Speter #include "opcode.h" 8760Speter #include "objfmt.h" 9760Speter 10760Speter /* 11760Speter * NAMELIST SEGMENT DEFINITIONS 12760Speter */ 13760Speter struct nls { 14760Speter struct nl *nls_low; 15760Speter struct nl *nls_high; 16760Speter } ntab[MAXNL], *nlact; 17760Speter 18760Speter struct nl nl[INL]; 19760Speter struct nl *nlp = nl; 20760Speter struct nls *nlact = ntab; 21760Speter 22760Speter /* 23760Speter * all these strings must be places where people can find them 24760Speter * since lookup only looks at the string pointer, not the chars. 25760Speter * see, for example, pTreeInit. 26760Speter */ 27760Speter 28760Speter /* 29760Speter * built in constants 30760Speter */ 31760Speter char *in_consts[] = { 32760Speter "true" , 33760Speter "false" , 34760Speter "TRUE", 35760Speter "FALSE", 36760Speter "minint" , 37760Speter "maxint" , 38760Speter "minchar" , 39760Speter "maxchar" , 40760Speter "bell" , 41760Speter "tab" , 42760Speter 0 43760Speter }; 44760Speter 45760Speter /* 46760Speter * built in simple types 47760Speter */ 48760Speter char *in_types[] = 49760Speter { 50760Speter "boolean", 51760Speter "char", 52760Speter "integer", 53760Speter "real", 54760Speter "_nil", /* dummy name */ 55760Speter 0 56760Speter }; 57760Speter 58760Speter int in_rclasses[] = 59760Speter { 60760Speter TINT , 61760Speter TINT , 62760Speter TINT , 63760Speter TCHAR , 64760Speter TBOOL , 65760Speter TDOUBLE , 66760Speter 0 67760Speter }; 68760Speter 69760Speter long in_ranges[] = 70760Speter { 71760Speter -128L , 128L , 72760Speter -32768L , 32767L , 73760Speter -2147483648L , 2147483647L , 74760Speter 0L , 127L , 75760Speter 0L , 1L , 76760Speter 0L , 0L /* fake for reals */ 77760Speter }; 78760Speter 79760Speter /* 80760Speter * built in constructed types 81760Speter */ 82760Speter char *in_ctypes[] = { 83760Speter "Boolean" , 84760Speter "intset" , 85760Speter "alfa" , 86760Speter "text" , 87760Speter 0 88760Speter }; 89760Speter 90760Speter /* 91760Speter * built in variables 92760Speter */ 93760Speter char *in_vars[] = { 94760Speter "input" , 95760Speter "output" , 96760Speter 0 97760Speter }; 98760Speter 99760Speter /* 100760Speter * built in functions 101760Speter */ 102760Speter char *in_funcs[] = 103760Speter { 104760Speter "abs" , 105760Speter "arctan" , 106760Speter "card" , 107760Speter "chr" , 108760Speter "clock" , 109760Speter "cos" , 110760Speter "eof" , 111760Speter "eoln" , 112760Speter "eos" , 113760Speter "exp" , 114760Speter "expo" , 115760Speter "ln" , 116760Speter "odd" , 117760Speter "ord" , 118760Speter "pred" , 119760Speter "round" , 120760Speter "sin" , 121760Speter "sqr" , 122760Speter "sqrt" , 123760Speter "succ" , 124760Speter "trunc" , 125760Speter "undefined" , 126760Speter /* 127760Speter * Extensions 128760Speter */ 129760Speter "argc" , 130760Speter "random" , 131760Speter "seed" , 132760Speter "wallclock" , 133760Speter "sysclock" , 134760Speter 0 135760Speter }; 136760Speter 137760Speter /* 138760Speter * Built-in procedures 139760Speter */ 140760Speter char *in_procs[] = 141760Speter { 142760Speter "date" , 143760Speter "dispose" , 144760Speter "flush" , 145760Speter "get" , 146760Speter "getseg" , 147760Speter "halt" , 148760Speter "linelimit" , 149760Speter "message" , 150760Speter "new" , 151760Speter "pack" , 152760Speter "page" , 153760Speter "put" , 154760Speter "putseg" , 155760Speter "read" , 156760Speter "readln" , 157760Speter "remove" , 158760Speter "reset" , 159760Speter "rewrite" , 160760Speter "time" , 161760Speter "unpack" , 162760Speter "write" , 163760Speter "writeln" , 164760Speter /* 165760Speter * Extensions 166760Speter */ 167760Speter "argv" , 168760Speter "null" , 169760Speter "stlimit" , 170760Speter 0 171760Speter }; 172760Speter 173760Speter #ifndef PI0 174760Speter /* 175760Speter * and their opcodes 176760Speter */ 177760Speter int in_fops[] = 178760Speter { 179760Speter O_ABS2, 180760Speter O_ATAN, 181760Speter O_CARD|NSTAND, 182760Speter O_CHR2, 183760Speter O_CLCK|NSTAND, 184760Speter O_COS, 185760Speter O_EOF, 186760Speter O_EOLN, 187760Speter 0, 188760Speter O_EXP, 189760Speter O_EXPO|NSTAND, 190760Speter O_LN, 191760Speter O_ODD2, 192760Speter O_ORD2, 193760Speter O_PRED2, 194760Speter O_ROUND, 195760Speter O_SIN, 196760Speter O_SQR2, 197760Speter O_SQRT, 198760Speter O_SUCC2, 199760Speter O_TRUNC, 200760Speter O_UNDEF|NSTAND, 201760Speter /* 202760Speter * Extensions 203760Speter */ 204760Speter O_ARGC|NSTAND, 205760Speter O_RANDOM|NSTAND, 206760Speter O_SEED|NSTAND, 207760Speter O_WCLCK|NSTAND, 208760Speter O_SCLCK|NSTAND 209760Speter }; 210760Speter 211760Speter /* 212760Speter * Built-in procedures 213760Speter */ 214760Speter int in_pops[] = 215760Speter { 216760Speter O_DATE|NSTAND, 2171817Speter O_DISPOSE|NSTAND, 218760Speter O_FLUSH|NSTAND, 219760Speter O_GET, 220760Speter 0, 221760Speter O_HALT|NSTAND, 222760Speter O_LLIMIT|NSTAND, 223760Speter O_MESSAGE|NSTAND, 224760Speter O_NEW, 225760Speter O_PACK, 226760Speter O_PAGE, 227760Speter O_PUT, 228760Speter 0, 229760Speter O_READ4, 230760Speter O_READLN, 231760Speter O_REMOVE|NSTAND, 232760Speter O_RESET, 233760Speter O_REWRITE, 234760Speter O_TIME|NSTAND, 235760Speter O_UNPACK, 236760Speter O_WRITEF, 237760Speter O_WRITLN, 238760Speter /* 239760Speter * Extensions 240760Speter */ 241760Speter O_ARGV|NSTAND, 242760Speter O_ABORT|NSTAND, 243760Speter O_STLIM|NSTAND 244760Speter }; 245760Speter #endif 246760Speter 247760Speter /* 248760Speter * Initnl initializes the first namelist segment and then 249760Speter * initializes the name list for block 0. 250760Speter */ 251760Speter initnl() 252760Speter { 253760Speter register char **cp; 254760Speter register struct nl *np; 255760Speter struct nl *fp; 256760Speter int *ip; 257760Speter long *lp; 258760Speter 259760Speter #ifdef DEBUG 260760Speter if ( hp21mx ) 261760Speter { 262760Speter MININT = -32768.; 263760Speter MAXINT = 32767.; 264760Speter #ifndef PI0 265760Speter genmx(); 266760Speter #endif 267760Speter } 268760Speter #endif 269760Speter ntab[0].nls_low = nl; 270760Speter ntab[0].nls_high = &nl[INL]; 271760Speter defnl ( 0 , 0 , 0 , 0 ); 272760Speter 273760Speter /* 274760Speter * Types 275760Speter */ 276760Speter for ( cp = in_types ; *cp != 0 ; cp ++ ) 277760Speter hdefnl ( *cp , TYPE , nlp , 0 ); 278760Speter 279760Speter /* 280760Speter * Ranges 281760Speter */ 282760Speter lp = in_ranges; 283760Speter for ( ip = in_rclasses ; *ip != 0 ; ip ++ ) 284760Speter { 285760Speter np = defnl ( 0 , RANGE , nl+(*ip) , 0 ); 286760Speter nl[*ip].type = np; 287760Speter np -> range[0] = *lp ++ ; 288760Speter np -> range[1] = *lp ++ ; 289760Speter 290760Speter }; 291760Speter 292760Speter /* 293760Speter * built in constructed types 294760Speter */ 295760Speter 296760Speter cp = in_ctypes; 297760Speter /* 298760Speter * Boolean = boolean; 299760Speter */ 300760Speter hdefnl ( *cp++ , TYPE , nl+T1BOOL , 0 ); 301760Speter 302760Speter /* 303760Speter * intset = set of 0 .. 127; 304760Speter */ 305760Speter intset = *cp++; 306760Speter hdefnl( intset , TYPE , nlp+1 , 0 ); 307760Speter defnl ( 0 , SET , nlp+1 , 0 ); 308760Speter np = defnl ( 0 , RANGE , nl+TINT , 0 ); 309760Speter np -> range[0] = 0L; 310760Speter np -> range[1] = 127L; 311760Speter 312760Speter /* 313760Speter * alfa = array [ 1 .. 10 ] of char; 314760Speter */ 315760Speter np = defnl ( 0 , RANGE , nl+TINT , 0 ); 316760Speter np -> range[0] = 1L; 317760Speter np -> range[1] = 10L; 318760Speter defnl ( 0 , ARRAY , nl+T1CHAR , 1 ) -> chain = np; 319760Speter hdefnl ( *cp++ , TYPE , nlp-1 , 0 ); 320760Speter 321760Speter /* 322760Speter * text = file of char; 323760Speter */ 324760Speter hdefnl ( *cp++ , TYPE , nlp+1 , 0 ); 325760Speter np = defnl ( 0 , FILET , nl+T1CHAR , 0 ); 326760Speter np -> nl_flags |= NFILES; 327760Speter 328760Speter /* 329760Speter * input,output : text; 330760Speter */ 331760Speter cp = in_vars; 332760Speter # ifndef PI0 333760Speter input = hdefnl ( *cp++ , VAR , np , INPUT_OFF ); 334760Speter output = hdefnl ( *cp++ , VAR , np , OUTPUT_OFF ); 335760Speter # else 336760Speter input = hdefnl ( *cp++ , VAR , np , 0 ); 337760Speter output = hdefnl ( *cp++ , VAR , np , 0 ); 338760Speter # endif 339*3828Speter # ifdef PC 340*3828Speter input -> extra_flags |= NGLOBAL; 341*3828Speter output -> extra_flags |= NGLOBAL; 342*3828Speter # endif PC 343760Speter 344760Speter /* 345760Speter * built in constants 346760Speter */ 347760Speter cp = in_consts; 348760Speter np = hdefnl ( *cp++ , CONST , nl + TBOOL , 1 ); 349760Speter fp = hdefnl ( *cp++ , CONST , nl + TBOOL , 0 ); 350760Speter (nl + TBOOL)->chain = fp; 351760Speter fp->chain = np; 352760Speter np = hdefnl ( *cp++ , CONST , nl + TBOOL , 1 ); 353760Speter fp = hdefnl ( *cp++ , CONST , nl + TBOOL , 0 ); 354760Speter fp->chain = np; 355760Speter if (opt('s')) 356760Speter (nl + TBOOL)->chain = fp; 357760Speter hdefnl ( *cp++ , CONST , nl + T4INT , 0 ) -> range[0] = MININT; 358760Speter hdefnl ( *cp++ , CONST , nl + T4INT , 0 ) -> range[0] = MAXINT; 359760Speter hdefnl ( *cp++ , CONST , nl + T1CHAR , 0 ); 360760Speter hdefnl ( *cp++ , CONST , nl + T1CHAR , 127 ); 361760Speter hdefnl ( *cp++ , CONST , nl + T1CHAR , '\007' ); 362760Speter hdefnl ( *cp++ , CONST , nl + T1CHAR , '\t' ); 363760Speter 364760Speter /* 365760Speter * Built-in functions and procedures 366760Speter */ 367760Speter #ifndef PI0 368760Speter ip = in_fops; 369760Speter for ( cp = in_funcs ; *cp != 0 ; cp ++ ) 370760Speter hdefnl ( *cp , FUNC , 0 , * ip ++ ); 371760Speter ip = in_pops; 372760Speter for ( cp = in_procs ; *cp != 0 ; cp ++ ) 373760Speter hdefnl ( *cp , PROC , 0 , * ip ++ ); 374760Speter #else 375760Speter for ( cp = in_funcs ; *cp != 0 ; cp ++ ) 376760Speter hdefnl ( *cp , FUNC , 0 , 0 ); 377760Speter for ( cp = in_procs ; *cp != 0 , cp ++ ) 378760Speter hdefnl ( *cp , PROC , 0 , 0 ); 379760Speter #endif 380760Speter # ifdef PTREE 381760Speter pTreeInit(); 382760Speter # endif 383760Speter } 384760Speter 385760Speter struct nl * 386760Speter hdefnl(sym, cls, typ, val) 387760Speter { 388760Speter register struct nl *p; 389760Speter 390760Speter #ifndef PI1 391760Speter if (sym) 392760Speter hash(sym, 0); 393760Speter #endif 394760Speter p = defnl(sym, cls, typ, val); 395760Speter if (sym) 396760Speter enter(p); 397760Speter return (p); 398760Speter } 399760Speter 400760Speter /* 401760Speter * Free up the name list segments 402760Speter * at the end of a statement/proc/func 403760Speter * All segments are freed down to the one in which 404760Speter * p points. 405760Speter */ 406760Speter nlfree(p) 407760Speter struct nl *p; 408760Speter { 409760Speter 410760Speter nlp = p; 411760Speter while (nlact->nls_low > nlp || nlact->nls_high < nlp) { 412760Speter free(nlact->nls_low); 413760Speter nlact->nls_low = NIL; 414760Speter nlact->nls_high = NIL; 415760Speter --nlact; 416760Speter if (nlact < &ntab[0]) 417760Speter panic("nlfree"); 418760Speter } 419760Speter } 420760Speter 421760Speter 422760Speter char *VARIABLE = "variable"; 423760Speter 424760Speter char *classes[ ] = { 425760Speter "undefined", 426760Speter "constant", 427760Speter "type", 428760Speter "variable", /* VARIABLE */ 429760Speter "array", 430760Speter "pointer or file", 431760Speter "record", 432760Speter "field", 433760Speter "procedure", 434760Speter "function", 435760Speter "variable", /* VARIABLE */ 436760Speter "variable", /* VARIABLE */ 437760Speter "pointer", 438760Speter "file", 439760Speter "set", 440760Speter "subrange", 441760Speter "label", 442760Speter "withptr", 443760Speter "scalar", 444760Speter "string", 445760Speter "program", 4461197Speter "improper", 4471197Speter "variant", 4481197Speter "formal procedure", 4491197Speter "formal function" 450760Speter }; 451760Speter 452760Speter char *snark = "SNARK"; 453760Speter 454760Speter #ifdef PI 455760Speter #ifdef DEBUG 456760Speter char *ctext[] = 457760Speter { 458760Speter "BADUSE", 459760Speter "CONST", 460760Speter "TYPE", 461760Speter "VAR", 462760Speter "ARRAY", 463760Speter "PTRFILE", 464760Speter "RECORD", 465760Speter "FIELD", 466760Speter "PROC", 467760Speter "FUNC", 468760Speter "FVAR", 469760Speter "REF", 470760Speter "PTR", 471760Speter "FILET", 472760Speter "SET", 473760Speter "RANGE", 474760Speter "LABEL", 475760Speter "WITHPTR", 476760Speter "SCAL", 477760Speter "STR", 478760Speter "PROG", 479760Speter "IMPROPER", 4801197Speter "VARNT", 4811197Speter "FPROC", 4821197Speter "FFUNC" 483760Speter }; 484760Speter 485760Speter char *stars = "\t***"; 486760Speter 487760Speter /* 488760Speter * Dump the namelist from the 489760Speter * current nlp down to 'to'. 490760Speter * All the namelist is dumped if 491760Speter * to is NIL. 492760Speter */ 493760Speter dumpnl(to, rout) 494760Speter struct nl *to; 495760Speter { 496760Speter register struct nl *p; 497760Speter register int j; 498760Speter struct nls *nlsp; 499760Speter int i, v, head; 500760Speter 501760Speter if (opt('y') == 0) 502760Speter return; 503760Speter if (to != NIL) 504760Speter printf("\n\"%s\" Block=%d\n", rout, cbn); 505760Speter nlsp = nlact; 506760Speter head = NIL; 507760Speter for (p = nlp; p != to;) { 508760Speter if (p == nlsp->nls_low) { 509760Speter if (nlsp == &ntab[0]) 510760Speter break; 511760Speter nlsp--; 512760Speter p = nlsp->nls_high; 513760Speter } 514760Speter p--; 515760Speter if (head == NIL) { 516760Speter printf("\tName\tClass Bn+Flags\tType\tVal\tChn\n"); 517760Speter head++; 518760Speter } 519760Speter printf("%3d:", nloff(p)); 520760Speter if (p->symbol) 521760Speter printf("\t%.7s", p->symbol); 522760Speter else 523760Speter printf(stars); 524760Speter if (p->class) 525760Speter printf("\t%s", ctext[p->class]); 526760Speter else 527760Speter printf(stars); 528760Speter if (p->nl_flags) { 529760Speter pchr('\t'); 530760Speter if (p->nl_flags & 037) 531760Speter printf("%d ", p->nl_flags & 037); 532760Speter #ifndef PI0 533760Speter if (p->nl_flags & NMOD) 534760Speter pchr('M'); 535760Speter if (p->nl_flags & NUSED) 536760Speter pchr('U'); 537760Speter #endif 538760Speter if (p->nl_flags & NFILES) 539760Speter pchr('F'); 540760Speter } else 541760Speter printf(stars); 542760Speter if (p->type) 543760Speter printf("\t[%d]", nloff(p->type)); 544760Speter else 545760Speter printf(stars); 546760Speter v = p->value[0]; 547760Speter switch (p->class) { 548760Speter case TYPE: 549760Speter break; 550760Speter case VARNT: 551760Speter goto con; 552760Speter case CONST: 553760Speter switch (nloff(p->type)) { 554760Speter default: 555760Speter printf("\t%d", v); 556760Speter break; 557760Speter case TDOUBLE: 558760Speter printf("\t%f", p->real); 559760Speter break; 560760Speter case TINT: 561760Speter case T4INT: 562760Speter con: 563760Speter printf("\t%ld", p->range[0]); 564760Speter break; 565760Speter case TSTR: 566760Speter printf("\t'%s'", p->ptr[0]); 567760Speter break; 568760Speter } 569760Speter break; 570760Speter case VAR: 571760Speter case REF: 572760Speter case WITHPTR: 5731197Speter case FFUNC: 5741197Speter case FPROC: 575760Speter printf("\t%d,%d", cbn, v); 576760Speter break; 577760Speter case SCAL: 578760Speter case RANGE: 579760Speter printf("\t%ld..%ld", p->range[0], p->range[1]); 580760Speter break; 581760Speter case RECORD: 582760Speter printf("\t%d(%d)", v, p->value[NL_FLDSZ]); 583760Speter break; 584760Speter case FIELD: 585760Speter printf("\t%d", v); 586760Speter break; 587760Speter case STR: 588760Speter printf("\t|%d|", p->value[0]); 589760Speter break; 590760Speter case FVAR: 591760Speter case FUNC: 592760Speter case PROC: 593760Speter case PROG: 594760Speter if (cbn == 0) { 595760Speter printf("\t<%o>", p->value[0] & 0377); 596760Speter #ifndef PI0 597760Speter if (p->value[0] & NSTAND) 598760Speter printf("\tNSTAND"); 599760Speter #endif 600760Speter break; 601760Speter } 602760Speter v = p->value[1]; 603760Speter default: 604760Speter casedef: 605760Speter if (v) 606760Speter printf("\t<%d>", v); 607760Speter else 608760Speter printf(stars); 609760Speter } 610760Speter if (p->chain) 611760Speter printf("\t[%d]", nloff(p->chain)); 612760Speter switch (p->class) { 613760Speter case RECORD: 614760Speter if (p->ptr[NL_VARNT]) 615760Speter printf("\tVARNT=[%d]", nloff(p->ptr[NL_VARNT])); 616760Speter if (p->ptr[NL_TAG]) 617760Speter printf(" TAG=[%d]", nloff(p->ptr[NL_TAG])); 618760Speter break; 619760Speter case VARNT: 620760Speter printf("\tVTOREC=[%d]", nloff(p->ptr[NL_VTOREC])); 621760Speter break; 622760Speter } 623*3828Speter # ifdef PC 624*3828Speter if ( p -> extra_flags != 0 ) { 625*3828Speter pchr( '\t' ); 626*3828Speter if ( p -> extra_flags & NEXTERN ) 627*3828Speter printf( "NEXTERN " ); 628*3828Speter if ( p -> extra_flags & NLOCAL ) 629*3828Speter printf( "NLOCAL " ); 630*3828Speter if ( p -> extra_flags & NPARAM ) 631*3828Speter printf( "NPARAM " ); 632*3828Speter if ( p -> extra_flags & NGLOBAL ) 633*3828Speter printf( "NGLOBAL " ); 634*3828Speter if ( p -> extra_flags & NREGVAR ) 635*3828Speter printf( "NREGVAR " ); 636*3828Speter } 637*3828Speter # endif PC 638760Speter # ifdef PTREE 639760Speter pchr( '\t' ); 640760Speter pPrintPointer( stdout , "%s" , p -> inTree ); 641760Speter # endif 642760Speter pchr('\n'); 643760Speter } 644760Speter if (head == 0) 645760Speter printf("\tNo entries\n"); 646760Speter } 647760Speter #endif 648760Speter 649760Speter 650760Speter /* 651760Speter * Define a new name list entry 652760Speter * with initial symbol, class, type 653760Speter * and value[0] as given. A new name 654760Speter * list segment is allocated to hold 655760Speter * the next name list slot if necessary. 656760Speter */ 657760Speter struct nl * 658760Speter defnl(sym, cls, typ, val) 659760Speter char *sym; 660760Speter int cls; 661760Speter struct nl *typ; 662760Speter int val; 663760Speter { 664760Speter register struct nl *p; 665760Speter register int *q, i; 666760Speter char *cp; 667760Speter 668760Speter p = nlp; 669760Speter 670760Speter /* 671760Speter * Zero out this entry 672760Speter */ 673760Speter q = p; 674760Speter i = (sizeof *p)/(sizeof (int)); 675760Speter do 676760Speter *q++ = 0; 677760Speter while (--i); 678760Speter 679760Speter /* 680760Speter * Insert the values 681760Speter */ 682760Speter p->symbol = sym; 683760Speter p->class = cls; 684760Speter p->type = typ; 685760Speter p->nl_block = cbn; 686760Speter p->value[0] = val; 687760Speter 688760Speter /* 689760Speter * Insure that the next namelist 690760Speter * entry actually exists. This is 691760Speter * really not needed here, it would 692760Speter * suffice to do it at entry if we 693760Speter * need the slot. It is done this 694760Speter * way because, historically, nlp 695760Speter * always pointed at the next namelist 696760Speter * slot. 697760Speter */ 698760Speter nlp++; 699760Speter if (nlp >= nlact->nls_high) { 700760Speter i = NLINC; 701760Speter cp = malloc(NLINC * sizeof *nlp); 7021834Speter if (cp == 0) { 703760Speter i = NLINC / 2; 704760Speter cp = malloc((NLINC / 2) * sizeof *nlp); 705760Speter } 7061834Speter if (cp == 0) { 707760Speter error("Ran out of memory (defnl)"); 708760Speter pexit(DIED); 709760Speter } 710760Speter nlact++; 711760Speter if (nlact >= &ntab[MAXNL]) { 712760Speter error("Ran out of name list tables"); 713760Speter pexit(DIED); 714760Speter } 715760Speter nlp = cp; 716760Speter nlact->nls_low = nlp; 717760Speter nlact->nls_high = nlact->nls_low + i; 718760Speter } 719760Speter return (p); 720760Speter } 721760Speter 722760Speter /* 723760Speter * Make a duplicate of the argument 724760Speter * namelist entry for, e.g., type 725760Speter * declarations of the form 'type a = b' 726760Speter * and array indicies. 727760Speter */ 728760Speter struct nl * 729760Speter nlcopy(p) 730760Speter struct nl *p; 731760Speter { 732760Speter register int *p1, *p2, i; 733760Speter 734760Speter p1 = p; 735760Speter p = p2 = defnl(0, 0, 0, 0); 736760Speter i = (sizeof *p)/(sizeof (int)); 737760Speter do 738760Speter *p2++ = *p1++; 739760Speter while (--i); 740760Speter p->chain = NIL; 741760Speter return (p); 742760Speter } 743760Speter 744760Speter /* 745760Speter * Compute a namelist offset 746760Speter */ 747760Speter nloff(p) 748760Speter struct nl *p; 749760Speter { 750760Speter 751760Speter return (p - nl); 752760Speter } 753760Speter 754760Speter /* 755760Speter * Enter a symbol into the block 756760Speter * symbol table. Symbols are hashed 757760Speter * 64 ways based on low 6 bits of the 758760Speter * character pointer into the string 759760Speter * table. 760760Speter */ 761760Speter struct nl * 762760Speter enter(np) 763760Speter struct nl *np; 764760Speter { 765760Speter register struct nl *rp, *hp; 766760Speter register struct nl *p; 767760Speter int i; 768760Speter 769760Speter rp = np; 770760Speter if (rp == NIL) 771760Speter return (NIL); 772760Speter #ifndef PI1 773760Speter if (cbn > 0) 774760Speter if (rp->symbol == input->symbol || rp->symbol == output->symbol) 775760Speter error("Pre-defined files input and output must not be redefined"); 776760Speter #endif 777760Speter i = rp->symbol; 778760Speter i &= 077; 779760Speter hp = disptab[i]; 780760Speter if (rp->class != BADUSE && rp->class != FIELD) 781760Speter for (p = hp; p != NIL && (p->nl_block & 037) == cbn; p = p->nl_next) 782760Speter if (p->symbol == rp->symbol && p->class != BADUSE && p->class != FIELD) { 783760Speter #ifndef PI1 784760Speter error("%s is already defined in this block", rp->symbol); 785760Speter #endif 786760Speter break; 787760Speter 788760Speter } 789760Speter rp->nl_next = hp; 790760Speter disptab[i] = rp; 791760Speter return (rp); 792760Speter } 793760Speter #endif 794