1798Speter /* Copyright (c) 1979 Regents of the University of California */ 2798Speter 3798Speter /* 4798Speter * Yacc grammar for UNIX Pascal 5798Speter * 6798Speter * This grammar is processed by the commands in the shell script 7798Speter * "gram" to yield parse tables and semantic routines in the file 8798Speter * "y.tab.c" and a header defining the lexical tokens in "yy.h". 9798Speter * 10798Speter * In order for the syntactic error recovery possible with this 11798Speter * grammar to work, the grammar must be processed by a yacc which 12798Speter * has been modified to fully enumerate possibilities in states 13798Speter * which involve the symbol "error". 14798Speter * The parser used for Pascal also uses a different encoding of 15798Speter * the test entries in the action table which speeds the parse. 16798Speter * A version of yacc which will work for Pascal is included on 17798Speter * the distribution table as "eyacc". 18798Speter * 19798Speter * The "gram" script also makes the following changes to the "y.tab.c" 20798Speter * file: 21798Speter * 22798Speter * 1) Causes yyval to be declared int *. 23798Speter * 24798Speter * 2) Loads the variable yypv into a register as yyYpv so that 25798Speter * the arguments $1, ... are available as yyYpv[1] etc. 26798Speter * This produces much smaller code in the semantic actions. 27798Speter * 28798Speter * 3) Deletes the unused array yysterm. 29798Speter * 30798Speter * 4) Moves the declarations up to the flag line containing 31798Speter * '##' to the file yy.h so that the routines which use 32798Speter * these "magic numbers" don't have to all be compiled at 33798Speter * the same time. 34798Speter * 35798Speter * 5) Creates the semantic restriction checking routine yyEactr 36804Speter * by processing action lines containing `@@'. 37798Speter * 38798Speter * This compiler uses a different version of the yacc parser, a 39798Speter * different yyerror which is called yerror, and requires more 40798Speter * lookahead sets than normally provided by yacc. 41798Speter * 42798Speter * Source for the yacc used with this grammar is included on 43798Speter * distribution tapes. 44798Speter */ 45798Speter 46798Speter /* 47798Speter * TERMINAL DECLARATIONS 48798Speter * 49798Speter * Some of the terminal declarations are out of the most natural 50798Speter * alphabetic order because the error recovery 51798Speter * will guess the first of equal cost non-terminals. 52798Speter * This makes, e.g. YTO preferable to YDOWNTO. 53798Speter */ 54798Speter 55798Speter %term 56798Speter YAND YARRAY YBEGIN YCASE 57798Speter YCONST YDIV YDO YDOTDOT 58798Speter YTO YELSE YEND YFILE 59798Speter YFOR YFORWARD YFUNCTION YGOTO 60798Speter YID YIF YIN YINT 61798Speter YLABEL YMOD YNOT YNUMB 62798Speter YOF YOR YPACKED YNIL 63798Speter YPROCEDURE YPROG YRECORD YREPEAT 64798Speter YSET YSTRING YTHEN YDOWNTO 65798Speter YTYPE YUNTIL YVAR YWHILE 66798Speter YWITH YBINT YOCT YHEX 67*837Speter YASSERT YCASELAB YILLCH YEXTERN 68*837Speter YLAST 69798Speter 70798Speter /* 71798Speter * PRECEDENCE DECLARATIONS 72798Speter * 73798Speter * Highest precedence is the unary logical NOT. 74798Speter * Next are the multiplying operators, signified by '*'. 75798Speter * Lower still are the binary adding operators, signified by '+'. 76798Speter * Finally, at lowest precedence and non-associative are the relationals. 77798Speter */ 78798Speter 79798Speter %binary '<' '=' '>' YIN 80798Speter %left '+' '-' YOR '|' 81798Speter %left UNARYSIGN 82798Speter %left '*' '/' YDIV YMOD YAND '&' 83798Speter %left YNOT 84798Speter 85798Speter %{ 86798Speter /* 87798Speter * GLOBALS FOR ACTIONS 88798Speter */ 89798Speter 90798Speter /* Copyright (c) 1979 Regents of the University of California */ 91798Speter 92*837Speter /* static char sccsid[] = "@(#)pas.y 1.3 09/02/80"; */ 93798Speter 94798Speter /* 95798Speter * The following line marks the end of the yacc 96798Speter * Constant definitions which are removed from 97798Speter * y.tab.c and placed in the file y.tab.h. 98798Speter */ 99798Speter ## 100798Speter /* Copyright (c) 1979 Regents of the University of California */ 101798Speter 102*837Speter static char sccsid[] = "@(#)pas.y 1.3 09/02/80"; 103798Speter 104798Speter #include "whoami.h" 105798Speter #include "0.h" 106798Speter #include "yy.h" 107798Speter #include "tree.h" 108798Speter 109798Speter #ifdef PI 110798Speter #define lineof(l) l 111798Speter #define line2of(l) l 112798Speter #endif 113798Speter 114798Speter %} 115798Speter 116798Speter %% 117798Speter 118798Speter /* 119798Speter * PRODUCTIONS 120798Speter */ 121798Speter 122798Speter goal: 123*837Speter prog_hedr decls block '.' 124*837Speter = funcend($1, $3, lineof($4)); 125798Speter | 126*837Speter decls 127798Speter = segend(); 128798Speter ; 129798Speter 130798Speter 131798Speter prog_hedr: 132798Speter YPROG YID '(' id_list ')' ';' 133798Speter = $$ = funcbody(funchdr(tree5(T_PROG, lineof($1), $2, fixlist($4), NIL))); 134798Speter | 135798Speter YPROG error 136798Speter = { 137798Speter yyPerror("Malformed program statement", PPROG); 138798Speter /* 139798Speter * Should make a program statement 140798Speter * with "input" and "output" here. 141798Speter */ 142798Speter $$ = funcbody(funchdr(tree5(T_PROG, lineof($1), NIL, NIL, NIL))); 143798Speter } 144798Speter ; 145798Speter block: 146798Speter YBEGIN stat_list YEND 147798Speter = { 148798Speter $$ = tree3(T_BSTL, lineof($1), fixlist($2)); 149798Speter if ($3 < 0) 150798Speter brerror($1, "begin"); 151798Speter } 152798Speter ; 153798Speter 154798Speter 155798Speter /* 156798Speter * DECLARATION PART 157798Speter */ 158798Speter decls: 159798Speter decls decl 160798Speter = trfree(); 161798Speter | 162798Speter decls error 163798Speter = { 164798Speter Derror: 165798Speter constend(), typeend(), varend(), trfree(); 166798Speter yyPerror("Malformed declaration", PDECL); 167798Speter } 168798Speter | 169798Speter /* lambda */ 170798Speter = trfree(); 171798Speter ; 172798Speter 173798Speter decl: 174798Speter labels 175798Speter | 176798Speter const_decl 177798Speter = constend(); 178798Speter | 179798Speter type_decl 180798Speter = typeend(); 181798Speter | 182798Speter var_decl 183798Speter = varend(); 184*837Speter | 185*837Speter proc_decl 186798Speter ; 187798Speter 188798Speter /* 189798Speter * LABEL PART 190798Speter */ 191798Speter 192798Speter labels: 193798Speter YLABEL label_decl ';' 194798Speter = label(fixlist($2), lineof($1)); 195798Speter ; 196798Speter label_decl: 197798Speter YINT 198798Speter = $$ = newlist($1 == NIL ? NIL : *hash($1, 1)); 199798Speter | 200798Speter label_decl ',' YINT 201798Speter = $$ = addlist($1, $3 == NIL ? NIL : *hash($3, 1)); 202798Speter ; 203798Speter 204798Speter /* 205798Speter * CONST PART 206798Speter */ 207798Speter 208798Speter const_decl: 209798Speter YCONST YID '=' const ';' 210798Speter = constbeg($1, line2of($2)), const(lineof($3), $2, $4); 211798Speter | 212798Speter const_decl YID '=' const ';' 213798Speter = const(lineof($3), $2, $4); 214798Speter | 215798Speter YCONST error 216798Speter = { 217798Speter constbeg($1, line2of($1)); 218798Speter Cerror: 219798Speter yyPerror("Malformed const declaration", PDECL); 220798Speter } 221798Speter | 222798Speter const_decl error 223798Speter = goto Cerror; 224798Speter ; 225798Speter 226798Speter /* 227798Speter * TYPE PART 228798Speter */ 229798Speter 230798Speter type_decl: 231798Speter YTYPE YID '=' type ';' 232798Speter = typebeg($1, line2of($2)), type(lineof($3), $2, $4); 233798Speter | 234798Speter type_decl YID '=' type ';' 235798Speter = type(lineof($3), $2, $4); 236798Speter | 237798Speter YTYPE error 238798Speter = { 239798Speter typebeg($1, line2of($1)); 240798Speter Terror: 241798Speter yyPerror("Malformed type declaration", PDECL); 242798Speter } 243798Speter | 244798Speter type_decl error 245798Speter = goto Terror; 246798Speter ; 247798Speter 248798Speter /* 249798Speter * VAR PART 250798Speter */ 251798Speter 252798Speter var_decl: 253798Speter YVAR id_list ':' type ';' 254798Speter = varbeg($1, line2of($3)), var(lineof($3), fixlist($2), $4); 255798Speter | 256798Speter var_decl id_list ':' type ';' 257798Speter = var(lineof($3), fixlist($2), $4); 258798Speter | 259798Speter YVAR error 260798Speter = { 261798Speter varbeg($1, line2of($1)); 262798Speter Verror: 263798Speter yyPerror("Malformed var declaration", PDECL); 264798Speter } 265798Speter | 266798Speter var_decl error 267798Speter = goto Verror; 268798Speter ; 269798Speter 270798Speter /* 271798Speter * PROCEDURE AND FUNCTION DECLARATION PART 272798Speter */ 273798Speter 274*837Speter proc_decl: 275798Speter phead YFORWARD ';' 276798Speter = funcfwd($1); 277798Speter | 278798Speter phead YEXTERN ';' 279798Speter = funcext($1); 280798Speter | 281*837Speter pheadres decls block ';' 282*837Speter = funcend($1, $3, lineof($4)); 283798Speter ; 284798Speter pheadres: 285798Speter phead 286798Speter = funcbody($1); 287798Speter ; 288798Speter phead: 289798Speter porf YID params ftype ';' 290798Speter = $$ = funchdr(tree5($1, lineof($5), $2, $3, $4)); 291798Speter ; 292798Speter porf: 293798Speter YPROCEDURE 294798Speter = $$ = T_PDEC; 295798Speter | 296798Speter YFUNCTION 297798Speter = $$ = T_FDEC; 298798Speter ; 299798Speter params: 300798Speter '(' param_list ')' 301798Speter = $$ = fixlist($2); 302798Speter | 303798Speter /* lambda */ 304798Speter = $$ = NIL; 305798Speter ; 306798Speter 307798Speter /* 308798Speter * PARAMETERS 309798Speter */ 310798Speter 311798Speter param: 312798Speter id_list ':' type 313798Speter = $$ = tree3(T_PVAL, fixlist($1), $3); 314798Speter | 315798Speter YVAR id_list ':' type 316798Speter = $$ = tree3(T_PVAR, fixlist($2), $4); 317798Speter | 318798Speter YFUNCTION id_list ':' type 319798Speter = $$ = tree3(T_PFUNC, fixlist($2), $4); 320798Speter | 321798Speter YPROCEDURE id_list 322798Speter = $$ = tree2(T_PPROC, fixlist($2)); 323798Speter ; 324798Speter ftype: 325798Speter ':' type 326798Speter = $$ = $2; 327798Speter | 328798Speter /* lambda */ 329798Speter = $$ = NIL; 330798Speter ; 331798Speter param_list: 332798Speter param 333798Speter = $$ = newlist($1); 334798Speter | 335798Speter param_list ';' param 336798Speter = $$ = addlist($1, $3); 337798Speter ; 338798Speter 339798Speter /* 340798Speter * CONSTANTS 341798Speter */ 342798Speter 343798Speter const: 344798Speter YSTRING 345798Speter = $$ = tree2(T_CSTRNG, $1); 346798Speter | 347798Speter number 348798Speter | 349798Speter '+' number 350798Speter = $$ = tree2(T_PLUSC, $2); 351798Speter | 352798Speter '-' number 353798Speter = $$ = tree2(T_MINUSC, $2); 354798Speter ; 355798Speter number: 356798Speter const_id 357798Speter = $$ = tree2(T_ID, $1); 358798Speter | 359798Speter YINT 360798Speter = $$ = tree2(T_CINT, $1); 361798Speter | 362798Speter YBINT 363798Speter = $$ = tree2(T_CBINT, $1); 364798Speter | 365798Speter YNUMB 366798Speter = $$ = tree2(T_CFINT, $1); 367798Speter ; 368798Speter const_list: 369798Speter const 370798Speter = $$ = newlist($1); 371798Speter | 372798Speter const_list ',' const 373798Speter = $$ = addlist($1, $3); 374798Speter ; 375798Speter 376798Speter /* 377798Speter * TYPES 378798Speter */ 379798Speter 380798Speter type: 381798Speter simple_type 382798Speter | 383798Speter '^' YID 384798Speter = $$ = tree3(T_TYPTR, lineof($1), tree2(T_ID, $2)); 385798Speter | 386798Speter struct_type 387798Speter | 388798Speter YPACKED struct_type 389798Speter = $$ = tree3(T_TYPACK, lineof($1), $2); 390798Speter ; 391798Speter simple_type: 392798Speter type_id 393798Speter | 394798Speter '(' id_list ')' 395798Speter = $$ = tree3(T_TYSCAL, lineof($1), fixlist($2)); 396798Speter | 397798Speter const YDOTDOT const 398798Speter = $$ = tree4(T_TYRANG, lineof($2), $1, $3); 399798Speter ; 400798Speter struct_type: 401798Speter YARRAY '[' simple_type_list ']' YOF type 402798Speter = $$ = tree4(T_TYARY, lineof($1), fixlist($3), $6); 403798Speter | 404798Speter YFILE YOF type 405798Speter = $$ = tree3(T_TYFILE, lineof($1), $3); 406798Speter | 407798Speter YSET YOF simple_type 408798Speter = $$ = tree3(T_TYSET, lineof($1), $3); 409798Speter | 410798Speter YRECORD field_list YEND 411798Speter = { 412798Speter $$ = setuptyrec( lineof( $1 ) , $2 ); 413798Speter if ($3 < 0) 414798Speter brerror($1, "record"); 415798Speter } 416798Speter ; 417798Speter simple_type_list: 418798Speter simple_type 419798Speter = $$ = newlist($1); 420798Speter | 421798Speter simple_type_list ',' simple_type 422798Speter = $$ = addlist($1, $3); 423798Speter ; 424798Speter 425798Speter /* 426798Speter * RECORD TYPE 427798Speter */ 428798Speter field_list: 429798Speter fixed_part variant_part 430798Speter = $$ = tree4(T_FLDLST, lineof(NIL), fixlist($1), $2); 431798Speter ; 432798Speter fixed_part: 433798Speter field 434798Speter = $$ = newlist($1); 435798Speter | 436798Speter fixed_part ';' field 437798Speter = $$ = addlist($1, $3); 438798Speter | 439798Speter fixed_part error 440798Speter = yyPerror("Malformed record declaration", PDECL); 441798Speter ; 442798Speter field: 443798Speter /* lambda */ 444798Speter = $$ = NIL; 445798Speter | 446798Speter id_list ':' type 447798Speter = $$ = tree4(T_RFIELD, lineof($2), fixlist($1), $3); 448798Speter ; 449798Speter 450798Speter variant_part: 451798Speter /* lambda */ 452798Speter = $$ = NIL; 453798Speter | 454798Speter YCASE type_id YOF variant_list 455798Speter = $$ = tree5(T_TYVARPT, lineof($1), NIL, $2, fixlist($4)); 456798Speter | 457798Speter YCASE YID ':' type_id YOF variant_list 458798Speter = $$ = tree5(T_TYVARPT, lineof($1), $2, $4, fixlist($6)); 459798Speter ; 460798Speter variant_list: 461798Speter variant 462798Speter = $$ = newlist($1); 463798Speter | 464798Speter variant_list ';' variant 465798Speter = $$ = addlist($1, $3); 466798Speter | 467798Speter variant_list error 468798Speter = yyPerror("Malformed record declaration", PDECL); 469798Speter ; 470798Speter variant: 471798Speter /* lambda */ 472798Speter = $$ = NIL; 473798Speter | 474798Speter const_list ':' '(' field_list ')' 475798Speter = $$ = tree4(T_TYVARNT, lineof($2), fixlist($1), $4); 476798Speter | 477798Speter const_list ':' '(' ')' 478798Speter = $$ = tree4(T_TYVARNT, lineof($2), fixlist($1), NIL); 479798Speter ; 480798Speter 481798Speter /* 482798Speter * STATEMENT LIST 483798Speter */ 484798Speter 485798Speter stat_list: 486798Speter stat 487798Speter = $$ = newlist($1); 488798Speter | 489798Speter stat_lsth stat 490798Speter = { 491798Speter if ((p = $1) != NIL && (q = p[1])[0] == T_IFX) { 492798Speter q[0] = T_IFEL; 493798Speter q[4] = $2; 494798Speter } else 495798Speter $$ = addlist($1, $2); 496798Speter } 497798Speter ; 498798Speter 499798Speter stat_lsth: 500798Speter stat_list ';' 501798Speter = if ((q = $1) != NIL && (p = q[1]) != NIL && p[0] == T_IF) { 502798Speter if (yychar < 0) 503798Speter yychar = yylex(); 504798Speter if (yyshifts >= 2 && yychar == YELSE) { 505798Speter recovered(); 506798Speter copy(&Y, &OY, sizeof Y); 507798Speter yerror("Deleted ';' before keyword else"); 508798Speter yychar = yylex(); 509798Speter p[0] = T_IFX; 510798Speter } 511798Speter } 512798Speter ; 513798Speter 514798Speter /* 515798Speter * CASE STATEMENT LIST 516798Speter */ 517798Speter 518798Speter cstat_list: 519798Speter cstat 520798Speter = $$ = newlist($1); 521798Speter | 522798Speter cstat_list ';' cstat 523798Speter = $$ = addlist($1, $3); 524798Speter | 525798Speter error 526798Speter = { 527798Speter $$ = NIL; 528798Speter Kerror: 529798Speter yyPerror("Malformed statement in case", PSTAT); 530798Speter } 531798Speter | 532798Speter cstat_list error 533798Speter = goto Kerror; 534798Speter ; 535798Speter 536798Speter cstat: 537798Speter const_list ':' stat 538798Speter = $$ = tree4(T_CSTAT, lineof($2), fixlist($1), $3); 539798Speter | 540798Speter YCASELAB stat 541798Speter = $$ = tree4(T_CSTAT, lineof($1), NIL, $2); 542798Speter | 543798Speter /* lambda */ 544798Speter = $$ = NIL; 545798Speter ; 546798Speter 547798Speter /* 548798Speter * STATEMENT 549798Speter */ 550798Speter 551798Speter stat: 552798Speter /* lambda */ 553798Speter = $$ = NIL; 554798Speter | 555798Speter YINT ':' stat 556798Speter = $$ = tree4(T_LABEL, lineof($2), $1 == NIL ? NIL : *hash($1, 1), $3); 557798Speter | 558798Speter proc_id 559798Speter = $$ = tree4(T_PCALL, lineof(yyline), $1, NIL); 560798Speter | 561798Speter proc_id '(' wexpr_list ')' 562798Speter = $$ = tree4(T_PCALL, lineof($2), $1, fixlist($3)); 563798Speter | 564798Speter YID error 565798Speter = goto NSerror; 566798Speter | 567798Speter assign 568798Speter | 569798Speter YBEGIN stat_list YEND 570798Speter = { 571798Speter $$ = tree3(T_BLOCK, lineof($1), fixlist($2)); 572798Speter if ($3 < 0) 573798Speter brerror($1, "begin"); 574798Speter } 575798Speter | 576798Speter YCASE expr YOF cstat_list YEND 577798Speter = { 578798Speter $$ = tree4(T_CASE, lineof($1), $2, fixlist($4)); 579798Speter if ($5 < 0) 580798Speter brerror($1, "case"); 581798Speter } 582798Speter | 583798Speter YWITH var_list YDO stat 584798Speter = $$ = tree4(T_WITH, lineof($1), fixlist($2), $4); 585798Speter | 586798Speter YWHILE expr YDO stat 587798Speter = $$ = tree4(T_WHILE, lineof($1), $2, $4); 588798Speter | 589798Speter YREPEAT stat_list YUNTIL expr 590798Speter = $$ = tree4(T_REPEAT, lineof($3), fixlist($2), $4); 591798Speter | 592798Speter YFOR assign YTO expr YDO stat 593798Speter = $$ = tree5(T_FORU, lineof($1), $2, $4, $6); 594798Speter | 595798Speter YFOR assign YDOWNTO expr YDO stat 596798Speter = $$ = tree5(T_FORD, lineof($1), $2, $4, $6); 597798Speter | 598798Speter YGOTO YINT 599798Speter = $$ = tree3(T_GOTO, lineof($1), *hash($2, 1)); 600798Speter | 601798Speter YIF expr YTHEN stat 602798Speter = $$ = tree5(T_IF, lineof($1), $2, $4, NIL); 603798Speter | 604798Speter YIF expr YTHEN stat YELSE stat 605798Speter = $$ = tree5(T_IFEL, lineof($1), $2, $4, $6); 606798Speter | 607798Speter YIF expr YTHEN stat YELSE 608798Speter = $$ = tree5(T_IFEL, lineof($1), $2, $4, NIL); 609798Speter | 610798Speter YASSERT '(' expr ')' 611798Speter = $$ = tree3(T_ASRT, lineof($1), $3); 612798Speter | 613798Speter error 614798Speter = { 615798Speter NSerror: 616798Speter $$ = NIL; 617798Speter Serror: 618798Speter yyPerror("Malformed statement", PSTAT); 619798Speter } 620798Speter ; 621798Speter assign: 622798Speter variable ':' '=' expr 623798Speter = $$ = tree4(T_ASGN, lineof($2), $1, $4); 624798Speter ; 625798Speter 626798Speter /* 627798Speter * EXPRESSION 628798Speter */ 629798Speter 630798Speter expr: 631798Speter error 632798Speter = { 633798Speter NEerror: 634798Speter $$ = NIL; 635798Speter Eerror: 636798Speter yyPerror("Missing/malformed expression", PEXPR); 637798Speter } 638798Speter | 639798Speter expr relop expr %prec '<' 640798Speter = $$ = tree4($2, $1[1] == SAWCON ? $3[1] : $1[1], $1, $3); 641798Speter | 642798Speter '+' expr %prec UNARYSIGN 643798Speter = $$ = tree3(T_PLUS, $2[1], $2); 644798Speter | 645798Speter '-' expr %prec UNARYSIGN 646798Speter = $$ = tree3(T_MINUS, $2[1], $2); 647798Speter | 648798Speter expr addop expr %prec '+' 649798Speter = $$ = tree4($2, $1[1] == SAWCON ? $3[1] : $1[1], $1, $3); 650798Speter | 651798Speter expr divop expr %prec '*' 652798Speter = $$ = tree4($2, $1[1] == SAWCON ? $3[1] : $1[1], $1, $3); 653798Speter | 654798Speter YNIL 655798Speter = $$ = tree2(T_NIL, NOCON); 656798Speter | 657798Speter YSTRING 658798Speter = $$ = tree3(T_STRNG, SAWCON, $1); 659798Speter | 660798Speter YINT 661798Speter = $$ = tree3(T_INT, NOCON, $1); 662798Speter | 663798Speter YBINT 664798Speter = $$ = tree3(T_BINT, NOCON, $1); 665798Speter | 666798Speter YNUMB 667798Speter = $$ = tree3(T_FINT, NOCON, $1); 668798Speter | 669798Speter variable 670798Speter | 671798Speter YID error 672798Speter = goto NEerror; 673798Speter | 674798Speter func_id '(' wexpr_list ')' 675798Speter = $$ = tree4(T_FCALL, NOCON, $1, fixlist($3)); 676798Speter | 677798Speter '(' expr ')' 678798Speter = $$ = $2; 679798Speter | 680798Speter negop expr %prec YNOT 681798Speter = $$ = tree3(T_NOT, NOCON, $2); 682798Speter | 683798Speter '[' element_list ']' 684798Speter = $$ = tree3(T_CSET, SAWCON, fixlist($2)); 685798Speter | 686798Speter '[' ']' 687798Speter = $$ = tree3(T_CSET, SAWCON, NIL); 688798Speter ; 689798Speter 690798Speter element_list: 691798Speter element 692798Speter = $$ = newlist($1); 693798Speter | 694798Speter element_list ',' element 695798Speter = $$ = addlist($1, $3); 696798Speter ; 697798Speter element: 698798Speter expr 699798Speter | 700798Speter expr YDOTDOT expr 701798Speter = $$ = tree3(T_RANG, $1, $3); 702798Speter ; 703798Speter 704798Speter /* 705798Speter * QUALIFIED VARIABLES 706798Speter */ 707798Speter 708798Speter variable: 709798Speter YID 710798Speter = { 711804Speter @@ return (identis(var, VAR)); 712798Speter $$ = setupvar($1, NIL); 713798Speter } 714798Speter | 715798Speter qual_var 716798Speter = $1[3] = fixlist($1[3]); 717798Speter ; 718798Speter qual_var: 719798Speter array_id '[' expr_list ']' 720798Speter = $$ = setupvar($1, tree2(T_ARY, fixlist($3))); 721798Speter | 722798Speter qual_var '[' expr_list ']' 723798Speter = $1[3] = addlist($1[3], tree2(T_ARY, fixlist($3))); 724798Speter | 725798Speter record_id '.' field_id 726798Speter = $$ = setupvar($1, setupfield($3, NIL)); 727798Speter | 728798Speter qual_var '.' field_id 729798Speter = $1[3] = addlist($1[3], setupfield($3, NIL)); 730798Speter | 731798Speter ptr_id '^' 732798Speter = $$ = setupvar($1, tree1(T_PTR)); 733798Speter | 734798Speter qual_var '^' 735798Speter = $1[3] = addlist($1[3], tree1(T_PTR)); 736798Speter ; 737798Speter 738798Speter /* 739798Speter * Expression with write widths 740798Speter */ 741798Speter wexpr: 742798Speter expr 743798Speter | 744798Speter expr ':' expr 745798Speter = $$ = tree4(T_WEXP, $1, $3, NIL); 746798Speter | 747798Speter expr ':' expr ':' expr 748798Speter = $$ = tree4(T_WEXP, $1, $3, $5); 749798Speter | 750798Speter expr octhex 751798Speter = $$ = tree4(T_WEXP, $1, NIL, $2); 752798Speter | 753798Speter expr ':' expr octhex 754798Speter = $$ = tree4(T_WEXP, $1, $3, $4); 755798Speter ; 756798Speter octhex: 757798Speter YOCT 758798Speter = $$ = OCT; 759798Speter | 760798Speter YHEX 761798Speter = $$ = HEX; 762798Speter ; 763798Speter 764798Speter expr_list: 765798Speter expr 766798Speter = $$ = newlist($1); 767798Speter | 768798Speter expr_list ',' expr 769798Speter = $$ = addlist($1, $3); 770798Speter ; 771798Speter 772798Speter wexpr_list: 773798Speter wexpr 774798Speter = $$ = newlist($1); 775798Speter | 776798Speter wexpr_list ',' wexpr 777798Speter = $$ = addlist($1, $3); 778798Speter ; 779798Speter 780798Speter /* 781798Speter * OPERATORS 782798Speter */ 783798Speter 784798Speter relop: 785798Speter '=' = $$ = T_EQ; 786798Speter | 787798Speter '<' = $$ = T_LT; 788798Speter | 789798Speter '>' = $$ = T_GT; 790798Speter | 791798Speter '<' '>' = $$ = T_NE; 792798Speter | 793798Speter '<' '=' = $$ = T_LE; 794798Speter | 795798Speter '>' '=' = $$ = T_GE; 796798Speter | 797798Speter YIN = $$ = T_IN; 798798Speter ; 799798Speter addop: 800798Speter '+' = $$ = T_ADD; 801798Speter | 802798Speter '-' = $$ = T_SUB; 803798Speter | 804798Speter YOR = $$ = T_OR; 805798Speter | 806798Speter '|' = $$ = T_OR; 807798Speter ; 808798Speter divop: 809798Speter '*' = $$ = T_MULT; 810798Speter | 811798Speter '/' = $$ = T_DIVD; 812798Speter | 813798Speter YDIV = $$ = T_DIV; 814798Speter | 815798Speter YMOD = $$ = T_MOD; 816798Speter | 817798Speter YAND = $$ = T_AND; 818798Speter | 819798Speter '&' = $$ = T_AND; 820798Speter ; 821798Speter 822798Speter negop: 823798Speter YNOT 824798Speter | 825798Speter '~' 826798Speter ; 827798Speter 828798Speter /* 829798Speter * LISTS 830798Speter */ 831798Speter 832798Speter var_list: 833798Speter variable 834798Speter = $$ = newlist($1); 835798Speter | 836798Speter var_list ',' variable 837798Speter = $$ = addlist($1, $3); 838798Speter ; 839798Speter 840798Speter id_list: 841798Speter YID 842798Speter = $$ = newlist($1); 843798Speter | 844798Speter id_list ',' YID 845798Speter = $$ = addlist($1, $3); 846798Speter ; 847798Speter 848798Speter /* 849798Speter * Identifier productions with semantic restrictions 850798Speter * 851804Speter * For these productions, the characters @@ signify 852798Speter * that the associated C statement is to provide 853798Speter * the semantic restriction for this reduction. 854798Speter * These lines are made into a procedure yyEactr, similar to 855798Speter * yyactr, which determines whether the corresponding reduction 856798Speter * is permitted, or whether an error is to be signaled. 857798Speter * A zero return from yyEactr is considered an error. 858798Speter * YyEactr is called with an argument "var" giving the string 859798Speter * name of the variable in question, essentially $1, although 860798Speter * $1 will not work because yyEactr is called from loccor in 861798Speter * the recovery routines. 862798Speter */ 863798Speter 864798Speter const_id: 865798Speter YID 866804Speter = @@ return (identis(var, CONST)); 867798Speter ; 868798Speter type_id: 869798Speter YID 870798Speter = { 871804Speter @@ return (identis(var, TYPE)); 872798Speter $$ = tree3(T_TYID, lineof(yyline), $1); 873798Speter } 874798Speter ; 875798Speter var_id: 876798Speter YID 877804Speter = @@ return (identis(var, VAR)); 878798Speter ; 879798Speter array_id: 880798Speter YID 881804Speter = @@ return (identis(var, ARRAY)); 882798Speter ; 883798Speter ptr_id: 884798Speter YID 885804Speter = @@ return (identis(var, PTRFILE)); 886798Speter ; 887798Speter record_id: 888798Speter YID 889804Speter = @@ return (identis(var, RECORD)); 890798Speter ; 891798Speter field_id: 892798Speter YID 893804Speter = @@ return (identis(var, FIELD)); 894798Speter ; 895798Speter proc_id: 896798Speter YID 897804Speter = @@ return (identis(var, PROC)); 898798Speter ; 899798Speter func_id: 900798Speter YID 901804Speter = @@ return (identis(var, FUNC)); 902798Speter ; 903