2
* SORCERER Version 1.00B
10
/* 23-Sep-97 thm Accomodate user who needs to redefine ZZLEXBUFSIZE */
13
#define ZZLEXBUFSIZE 8000
15
#include "pcctscfg.h" /* MR20 G. Hobbelt __USE_PROTOS #define */
21
int token; char text[MaxAtom+1], label[MaxRuleName+1]; \
22
char *action; /* if action node, here is ptr to it */ \
24
char init_action; /* set if Action and 1st action of alt */ \
25
int file; int line; /* set for BLOCK, ALT, nonterm nodes */ \
26
int upper_range; /* only if T1..T2 found */ \
27
GLA *start_state; /* ptr into GLA for this block */ \
28
int no_copy; /* copy input ptr to output ptr? */ \
29
ListNode *refvars; /* any ref vars defined for this rule */ \
30
unsigned char is_root; /* this token is a root #( A ... ) */
31
#define zzcr_ast(node, cur, _tok, _text) \
32
{(node)->token=_tok; strncpy((node)->text, _text,MaxAtom);}
35
extern int define_num;
39
/* MR20 G. Hobbelt Fix for Borland C++ 4.x & 5.x compiling with ALL warnings enabled */
40
#if defined(__TURBOC__)
41
#pragma warn -aus /* unused assignment of 'xxx' */
57
scarf_to_end_of_func_call(void)
59
scarf_to_end_of_func_call()
62
static char func_call_str[MaxAtom+1];
65
p = &func_call_str[0];
68
if ( zzchar==')' ) { *p++ = zzchar; *p++ = '\0'; zzadvance(); return func_call_str; }
71
*p++ = zzchar; zzadvance();
74
if ( zzchar=='\\' ) { *p++ = zzchar; zzadvance(); }
75
*p++ = zzchar; zzadvance();
78
*p++ = zzchar; zzadvance();
84
void /* MR9 23-Sep-97 Eliminate complaint about no return value */
86
lisp( AST *tree, FILE *output )
93
while ( tree != NULL )
95
if ( tree->down != NULL ) fprintf(output," (");
96
if ( tree->text[0]!='\0' ) {
97
fprintf(output, " \"");
98
if ( tree->label[0]!='\0' ) fprintf(output, "%s:", tree->label);
99
switch ( tree->token ) {
104
fprintf(output, "%s", tree->text);
107
fprintf(output, "%s[%s]", zztokens[tree->token], tree->text);
109
fprintf(output, "\"");
112
fprintf(output, " %s", zztokens[tree->token]);
114
lisp(tree->down, output);
115
if ( tree->down != NULL ) fprintf(output," )");
122
zzmk_ast(AST *node, int token)
124
zzmk_ast(node, token)
135
read_sor_desc(FILE *f)
144
ANTLR(sordesc(&root), f);
146
if ( found_error ) return NULL;
149
fprintf(stderr, "Internal Represenation of Tree Grammar:\n");
151
fprintf(stderr, "\n");
154
last_valid_token = token_type;
155
end_of_input = token_type++;/* end of input token type is 1 + last real token */
156
epsilon = token_type++; /* epsilon token type is 2 + last real token */
157
wild_card = token_type++; /* wild_card_token is 3 + last real token */
158
token_association(end_of_input, "$");
159
token_association(epsilon, "[Ep]");
160
token_association(wild_card, ".");
162
zzdouble_link(root, NULL, NULL);
164
if ( root!=NULL ) build_GLA(root);
167
fprintf(stderr, "Internal Represenation of Grammar Lookahead Automaton:\n");
169
fprintf(stderr, "\n");
176
#token RExpr "\"" << zzmode(START); >>
177
#token "\n|\r|\r\n" << /* MR16a */
179
warn("eoln found in string");
182
#token "\\~[]" << zzmore(); >>
183
#token "~[\n\r\"\\]+" << zzmore(); >> /* MR16a */
185
#lexclass ACTION_STRINGS
186
#token "\"" << zzmode(ACTIONS); zzmore(); >>
187
#token "\n|\r|\r\n" << /* MR16a */
189
warn("eoln found in string (in user action)");
192
#token "\\~[]" << zzmore(); >>
193
#token "~[\n\r\"\\]+" << zzmore(); >> /* MR16a */
195
#lexclass ACTION_CHARS
196
#token "'" << zzmode(ACTIONS); zzmore(); >>
197
#token "\n|\r|\r\n" << /* MR16a */
199
warn("eoln found in char literal (in user action)");
202
#token "\\~[]" << zzmore(); >>
203
#token "~[\n\r'\\]+" << zzmore(); >> /* MR16a */
205
#lexclass ACTION_COMMENTS
206
#token "\*/" << zzmode(ACTIONS); zzmore(); >>
207
#token "\*" << zzmore(); >>
208
#token "\n|\r|\r\n" << zzline++; zzmore(); >> /* MR16a */
209
#token "~[\n\r\*]+" << zzmore(); >> /* MR16a */
211
#lexclass ACTION_CPP_COMMENTS
212
#token "\n|\r|\r\n" << zzline++; zzmode(ACTIONS); zzmore(); >> /* MR16a */
213
#token "~[\n\r]+" << zzmore(); >> /* MR16a */
215
#lexclass CPP_COMMENTS
216
#token "\n|\r|\r\n" << zzline++; zzmode(START); zzskip(); >> /* MR16a */
217
#token "~[\n\r]+" << zzskip(); >> /* MR16a */
220
#token "\*/" << zzmode(START); zzskip(); >>
221
#token "\*" << zzskip(); >>
222
#token "\n|\r|\r\n" << zzline++; zzskip(); >> /* MR16a */
223
#token "~[\n\r\*]+" << zzskip(); >> /* MR16a */
225
#lexclass REFVAR_SCARF /* everything until a ')' */
226
#token "~[\)]+ \)" <<{
229
zzbegexpr[strlen(zzbegexpr)-1] = '\0';
230
rf=refVarRec(zzbegexpr);
231
list_add(&AllRefVars, rf);
232
list_add(&RefVars, rf);
233
zzmode(ACTIONS); zzmore(); zzreplstr("");
237
* This lexical class accepts actions of type [..] and <<..>>
239
* It translates the following special items:
241
* #[args] --> "ast_node(args)" add "classname::" for C++, however.
242
* #[] --> "ast_empty_node()"
243
* #( root, child1, ..., childn )
244
--> "ast_make(root, child1, ...., childn, NULL)"
247
* Things for reference variables are also recognized:
257
* A stack is used to nest action terminators because they can be nested
258
* like crazy: << #[#[..],..] >>
261
#token Action "\>\>" << /* these do not nest */
269
err( eMsgd("action buffer overflow; size %d",ZZLEXBUFSIZE));
272
#token PassAction "\]" << if ( topint() == ']' ) {
274
if ( istackempty() ) /* terminate action */
281
err( eMsgd("parameter buffer overflow; size %d",ZZLEXBUFSIZE));
285
/* terminate #[..] */
290
else if ( topint() == '|' ) { /* end of simple [...] */
296
#token "\n|\r|\r\n" << zzline++; zzmore(); >> /* MR16a */
297
#token "\>" << zzmore(); >>
298
#token "#[_a-zA-Z][_a-zA-Z0-9]*"
300
if ( !(strcmp(zzbegexpr, "#ifdef")==0 ||
301
strcmp(zzbegexpr, "#else")==0 ||
302
strcmp(zzbegexpr, "#endif")==0 ||
303
strcmp(zzbegexpr, "#ifndef")==0 ||
304
strcmp(zzbegexpr, "#if")==0 ||
305
strcmp(zzbegexpr, "#define")==0 ||
306
strcmp(zzbegexpr, "#pragma")==0 ||
307
strcmp(zzbegexpr, "#undef")==0 ||
308
strcmp(zzbegexpr, "#import")==0 ||
309
strcmp(zzbegexpr, "#line")==0 ||
310
strcmp(zzbegexpr, "#include")==0 ||
311
strcmp(zzbegexpr, "#error")==0) )
313
static char buf[100];
315
warn("#id used in nontransform mode; # ignored");
316
sprintf(buf, "%s", zzbegexpr+1);
320
{warn("#id used in action outside of rule; ignored");}
321
else if ( strcmp(zzbegexpr+1,CurRule)==0 )
322
strcpy(buf, "(*_result)");
329
if ( GenCPP ) zzreplstr("new SORAST");
330
else zzreplstr("ast_empty_node()");
333
#token "#\(\)" << zzreplstr("NULL"); zzmore(); >>
336
if ( GenCPP ) zzreplstr("new SORAST(");
337
else zzreplstr("ast_node(");
342
if ( GenCPP ) zzreplstr("PCCTS_AST::make(");
343
else zzreplstr("ast_make(");
346
#token "#" << zzmore(); >>
350
else if ( topint()==')' ) {
353
else if ( topint()=='}' ) {
355
/* terminate #(..) */
356
zzreplstr(", NULL)");
361
pushint('|'); /* look for '|' to terminate simple [...] */
369
#token "\\\]" << zzreplstr("]"); zzmore(); >>
370
#token "\\\)" << zzreplstr(")"); zzmore(); >>
371
#token "\\>" << zzreplstr(">"); zzmore(); >>
374
#token "'" << zzmode(ACTION_CHARS); zzmore();>>
375
#token "\"" << zzmode(ACTION_STRINGS); zzmore();>>
376
#token "\\#" << zzreplstr("#"); zzmore(); >>
377
/*#token "\\\\" << zzmore(); >> /* need this for some reason */
378
#token "\\~[\]\)>#]" << zzmore(); >> /* escaped char, always ignore */
379
#token "/" << zzmore(); >>
380
#token "/\*" << zzmode(ACTION_COMMENTS); zzmore(); >>
381
#token "\*/" << err("Missing /*; found dangling */ in action"); zzmore(); >>
382
#token "//" << zzmode(ACTION_CPP_COMMENTS); zzmore(); >>
384
#token "\@\(" <<zzmode(REFVAR_SCARF); zzmore(); zzreplstr("");>>
387
zzmore(); if ( !GenCPP ) zzreplstr("_parser->");
390
#token "[a-zA-Z_]+\(" <<
391
if ( (GenCPP && strcmp(zzbegexpr,"ast_scan(")==0) ||
392
(!GenCPP && strcmp(zzbegexpr,"ast_scan(")==0) ) {
393
char *args=scarf_to_end_of_func_call();
394
zzreplstr(cvt_token_str(zzbegexpr, args));
397
else { pushint(')'); zzmore(); }
399
#token "[a-zA-Z_]+" << zzmore(); >>
400
#token "~[a-zA-Z_\n\r\)\(\\#\>\]\[\"'/\@]+" << zzmore(); >> /* MR16a */
403
#token "[\t\ ]+" << zzskip(); >> /* Ignore White */
404
#token "\n|\r|\n\r" << zzline++; zzskip(); >> /* Track Line # */ /* MR16a */
405
#token "\[" << zzmode(ACTIONS); zzmore();
408
#token "\<\<" << action_file=CurFile; action_line=zzline;
409
zzmode(ACTIONS); zzmore();
412
#token "\"" << zzmode(STRINGS); zzmore(); >>
413
#token "/\*" << zzmode(COMMENTS); zzskip(); >>
414
#token "\*/" << err("Missing /*; found dangling */"); zzskip(); >>
415
#token "//" << zzmode(CPP_COMMENTS); zzskip(); >>
416
#token "\>\>" << err("Missing <<; found dangling \>\>"); zzskip(); >>
418
<< /* L o o k F o r A n o t h e r F i l e */
421
new_input = NextFile();
422
if ( new_input != NULL ) {
426
/*zzadvance(); ** Get 1st char of this file */
427
zzskip(); /* Skip the Eof (@) char i.e continue */
432
#token Header "#header"
433
#token Tokdef "#tokdefs"
434
#token BLOCK /* used only as place-holder in intermediate tree */
435
#token ALT /* used only as place-holder in intermediate tree */
436
#token LABEL ":" /* used only as place-holder in intermediate tree */
437
#token OPT "\{" /* These are labeled so we can ref them in trees */
438
#token POS_CLOSURE "\+"
446
#errclass "atomic-element" { WILD NonTerm Token }
447
#errclass "rule-header" { PassAction LABEL "\<" "\>" }
450
* Build trees for a sorcerer description
458
if ( he==0 && !Inline && !GenCPP ) warnNoFL("missing #header statement");
459
if ( he>1 ) warnNoFL("extra #header statement");
460
if ( to>1 ) warnNoFL("extra #tokdef statement");
463
<<list_add(&before_actions, actiondup(LATEXT(1)));>>
468
if ( CurClassName[0]!='\0' )
469
list_add(&class_actions, actiondup(LATEXT(1)));
471
list_add(&before_actions, actiondup(LATEXT(1)));
477
if ( CurClassName[0]!='\0' )
478
list_add(&class_actions, actiondup(LATEXT(1)));
480
list_add(&before_actions, actiondup(LATEXT(1)));
483
{ "\}"! // end of class def
485
if ( CurClassName[0]=='\0' )
486
err("missing class definition for trailing '}'");
490
<<list_add(&after_actions, actiondup(LATEXT(1)));>>
496
header: "#header"! Action! <<header_action = actiondup(LATEXT(1));>>
500
tokdef: "#tokdefs"! RExpr!
503
zzantlr_state st; FILE *f; struct zzdlg_state dst;
504
strcpy(tokdefs_file, LATEXT(1));
505
strcpy(tokdefs_file, tokdefs_file+1); /* remove quotes */
506
tokdefs_file[strlen(tokdefs_file)-1] = '\0';
507
zzsave_antlr_state(&st);
508
zzsave_dlg_state(&dst);
510
f = fopen(tokdefs_file, "r");
511
if ( f==NULL ) {found_error=1; err(eMsg1("cannot open token defs file '%s'", tokdefs_file));}
512
else {ANTLRm(enum_file(&dumb), f, PARSE_ENUM_FILE);}
513
zzrestore_antlr_state(&st);
514
zzrestore_dlg_state(&dst);
522
( NonTerm <<strncpy(CurClassName,LATEXT(1),MaxAtom);>>
523
| Token <<strncpy(CurClassName,LATEXT(1),MaxAtom);>>
525
<<if ( !GenCPP ) { err("class meta-op used without C++ option"); }>>
530
* Create a rule tree:
532
* NonTerm[arg_action, ret_val_action]
537
rule: <<SymEntry *p; int trouble=0, no_copy=0;>>
543
p = (SymEntry *) hash_get(symbols, $1.text);
545
p = (SymEntry *) hash_add(symbols, $1.text, (Entry *) newSymEntry($1.text));
550
else if ( p->token != NonTerm ) {
551
err(eMsg2("rule definition clashes with %s definition: '%s'", zztokens[p->token], p->str));
557
err(eMsg1("rule multiply defined: '%s'", $1.text));
565
{ "!"! <<if (!trouble) #0->no_copy=no_copy=1;>> }
566
( { "\<"! } PassAction! <<if (!trouble) p->args = actiondup(LATEXT(1));>>
569
{ "\>"! PassAction! <<if (!trouble) p->rt = actiondup(LATEXT(1));>>
575
if ( !trouble ) #0->refvars = RefVars;
579
if ( trouble ) #0 = NULL;
585
/* Create a tree for a block:
590
* alt1 ---> alt2 ---> ... ---> altn
593
: <<int line=zzline, file=CurFile;>>
595
( "\|"! alt[$no_copy]
598
#0 = #( #[BLOCK], #0 );
605
/* Create a tree for an alternative:
610
* e1 ---> e2 ---> ... ---> en
613
: <<int line=zzline, file=CurFile; int local_no_copy=0;>>
614
{ "!"! <<local_no_copy=1;>> }
616
( labeled_element[$no_copy||local_no_copy]
617
| element[$no_copy||local_no_copy]
618
| tree[$no_copy||local_no_copy]
622
#0 = #( #[ALT], #0 );
629
/* a rule ref looks like:
634
* arg_action ---> ret_val_action
636
* Blocks that have a suffix look like this:
643
* Optional blocks look like:
650
* Predicates are like actions except they have a root: #( PRED_OP Action )
653
: <</**** SymEntry *p; **** MR10 ****/ int file,line; int local_no_copy=0;>>
655
| <<file = CurFile; line=zzline;>>
657
{ "!"! <<local_no_copy = 1;>> }
658
{ { "\<"! } PassAction <<#0->in = 1;>> }
659
{ "\>"! PassAction <<#0->out = 1;>> }
660
<<#0->file = file; #0->line=line;>>
661
<<#0->no_copy = $no_copy || local_no_copy;>>
662
| <<file = CurFile; line=zzline;>>
663
Action <<#1->action = actiondup(LATEXT(1));>>
664
{ "?"^ } <<#0->file = file; #0->line=line;>>
665
| <<file = CurFile; line=zzline;>>
666
"\("! block[$no_copy] "\)"!
669
| "?"^ <<found_guess_block=1;>>
672
<<#0->file = file; #0->line=line;>>
673
| "\{"^ block[$no_copy] "\}"!
674
| <<file = CurFile; line=zzline;>>
676
{ "!"! <<local_no_copy = 1;>> }
677
<<#0->no_copy = $no_copy || local_no_copy;>>
678
<<#0->file = file; #0->line=line;>>
682
/* labels on an element look like: #( LABEL element ) */
683
labeled_element[int no_copy]
684
: <<Attrib label; int file,line; SymEntry *s; int local_no_copy=0;>>
685
( Token! <<label = $1;>>
686
| NonTerm! <<label = $1;>>
689
s = (SymEntry *) hash_get(symbols, label.text);
691
s = (SymEntry *) hash_add(symbols, label.text, (Entry *) newSymEntry(label.text));
694
else if ( s->token!=LABEL ) {
695
err(eMsg2("label definition clashes with %s definition: '%s'", zztokens[s->token], label.text));
699
( <<file = CurFile; line=zzline;>>
700
token[$no_copy] <<strcpy(#1->label, label.text);>>
701
<<#0->file = file; #0->line=line;>>
702
| <<file = CurFile; line=zzline;>>
703
NonTerm^ <<strcpy(#1->label, label.text);>>
704
{ "!"! <<local_no_copy = 1;>> }
705
{ { "\<"! } PassAction <<#0->in = 1;>> }
706
{ "\>"! PassAction <<#0->out = 1;>> }
707
<<#0->file = file; #0->line=line;>>
708
<<#0->no_copy = $no_copy || local_no_copy;>>
709
| <<file = CurFile; line=zzline;>>
710
"." <<strcpy(#1->label, label.text);>>
711
{ "!"! <<local_no_copy = 1;>> }
712
<<#0->no_copy = $no_copy || local_no_copy;>>
713
<<#0->file = file; #0->line=line;>>
714
| ("\|" | ";" | PassAction | Action | Eof | "\(" | "\{" | "\)" | "\}" | "#\(")
716
err("cannot label this grammar construct");
724
: <<SymEntry *p; int file, line; int local_no_copy=0;>>
725
<<file = CurFile; line=zzline;>>
727
<<#0->file = file; #0->line=line;>>
728
<<define_token($1.text);>>
730
{ "!"! <<local_no_copy=1;>>}
732
if ( !UserDefdTokens ) {
733
err("range operator is illegal without #tokdefs directive");
736
p = define_token($2.text);
737
require(p!=NULL, "token: hash table is broken");
738
#0->upper_range = p->token_type;
741
| "!"! <<local_no_copy=1;>>
743
<<#0->no_copy = $no_copy||local_no_copy;>>
746
/* A tree description looks like:
751
* root ---> sibling1 ---> ... ---> siblingn
754
: <<Attrib label; SymEntry *p, *s; int local_no_copy=0; AST *t=NULL;>>
757
<<define_token($1.text);>>
758
{ ".."! Token! /* inline rather than 'token' because must be root */
759
{ "!"! <<local_no_copy=1;>>}
761
if ( !UserDefdTokens ) {
762
err("range operator is illegal without #tokdefs directive");
765
p = define_token($2.text);
766
require(p!=NULL, "element: hash table is broken");
767
t->upper_range = p->token_type;
770
| "!"! <<local_no_copy=1;>>
772
<<t->no_copy = $no_copy||local_no_copy; t->is_root = 1;>>
774
{ "!"! <<local_no_copy = 1;>> }
775
<<#1->no_copy = $no_copy || local_no_copy; #1->is_root = 1;>>
776
| ( Token! <<label = $1;>>
777
| NonTerm! <<label = $1;>>
780
s = (SymEntry *) hash_get(symbols, label.text);
782
s = (SymEntry *) hash_add(symbols, label.text, (Entry *) newSymEntry(label.text));
785
else if ( s->token!=LABEL ) {
786
err(eMsg2("label definition clashes with %s definition: '%s'", zztokens[s->token], label.text));
790
( Token^ <<strcpy(#1->label, label.text); t = #1;>>
791
<<define_token($1.text);>>
792
{ ".."! Token! /* inline rather than 'token' because must be root */
793
{ "!"! <<local_no_copy=1;>>}
795
if ( !UserDefdTokens ) {
796
err("range operator is illegal without #tokdefs directive");
799
p = define_token($2.text);
800
require(p!=NULL, "element: hash table is broken");
801
t->upper_range = p->token_type;
804
| "!"! <<local_no_copy=1;>>
806
<<t->no_copy = $no_copy||local_no_copy;>>
807
| "."^ <<strcpy(#1->label, label.text);>>
808
{ "!"! <<local_no_copy = 1;>> }
809
<<#1->no_copy = $no_copy || local_no_copy;>>
813
( labeled_element[$no_copy] | element[$no_copy] | tree[$no_copy] )*
818
#token NonTerm "[a-z] [A-Za-z0-9_]*"
819
#token Token "[A-Z] [A-Za-z0-9_]*"
820
#token "#[A-Za-z0-9_]*" <<warn(eMsg1("unknown meta-op: %s",LATEXT(1))); zzskip(); >>
822
/* # t o k d e f s s t u f f */
824
#lexclass TOK_DEF_COMMENTS
825
#token "\*/" << zzmode(PARSE_ENUM_FILE); zzmore(); >>
826
#token "\*" << zzmore(); >>
827
#token "\n|\r|\r\n" << zzline++; zzmore(); >> /* MR16a */
828
#token "~[\n\r\*]+" << zzmore(); >> /* MR16a */
830
#lexclass TOK_DEF_CPP_COMMENTS
831
#token "\n|\r|\r\n" << zzline++; zzmode(PARSE_ENUM_FILE); zzskip(); >> /* MR16a */
832
#token "~[\n\r]+" << zzskip(); >> /* MR16a */
834
#lexclass PARSE_ENUM_FILE
836
#token "[\t\ ]+" << zzskip(); >> /* Ignore White */
837
#token "\n|\r|\r\n" << zzline++; zzskip(); >> /* Track Line # */ /* MR16a */
838
#token "//" << zzmode(TOK_DEF_CPP_COMMENTS); zzmore(); >>
839
#token "/\*" << zzmode(TOK_DEF_COMMENTS); zzmore(); >>
840
#token "#ifndef" << >>
841
#token "#ifdef" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>
842
#token "#else" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>
845
#token "#endif" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>
846
#token "@" << /*zzmode(START); zzskip();*/ >>
849
: <<SymEntry *p=NULL;>>
851
{ "#define" ID /* ignore if it smells like a gate */
852
/* First #define after the first #ifndef (if any) is ignored */
861
: <<int maxt= -1; /**** char *t; **** MR10 ****/ SymEntry *p; int ignore=0;>>
865
p = (SymEntry *) hash_get(symbols, $2.text);
867
p = (SymEntry *) hash_add(symbols, $2.text,
868
(Entry *) newSymEntry($2.text));
869
require(p!=NULL, "can't add to sym tab");
871
list_add(&token_list, (void *)p);
872
set_orel(p->token_type, &referenced_tokens);
876
err(eMsg1("redefinition of token %s; ignored",$2.text));
883
p->token_type = atoi($3.text);
884
token_association(p->token_type, p->str);
885
/* fprintf(stderr, "#token %s=%d\n", p->str, p->token_type);*/
886
if ( p->token_type>maxt ) maxt=p->token_type;
891
<<token_type = maxt + 1;>> /* record max defined token */
895
: <<int maxt = -1, v= -1; /**** char *t; **** MR10 ****/ SymEntry *p; int ignore=0;>>
900
p = (SymEntry *) hash_get(symbols, $4.text);
902
p = (SymEntry *) hash_add(symbols, $4.text,
903
(Entry *) newSymEntry($4.text));
904
require(p!=NULL, "can't add to sym tab");
906
list_add(&token_list, (void *)p);
907
set_orel(p->token_type, &referenced_tokens);
911
err(eMsg1("redefinition of token %s; ignored",$4.text));
915
( "=" INT <<v=atoi($2.text);>>
920
/* fprintf(stderr, "#token %s=%d\n", p->str, v);*/
921
if ( v>maxt ) maxt=v;
923
token_association(p->token_type, p->str);
928
{ "DLGminToken" { "=" INT } /* 1.33MR6 compatibility */
929
| "DLGmaxToken" { "=" INT } /* 1.33MR6 compatibility */
932
p = (SymEntry *) hash_get(symbols, $1.text);
934
p = (SymEntry *) hash_add(symbols, $1.text,
935
(Entry *) newSymEntry($1.text));
936
require(p!=NULL, "can't add to sym tab");
938
list_add(&token_list, (void *)p);
939
set_orel(p->token_type, &referenced_tokens);
943
err(eMsg1("redefinition of token %s; ignored",$1.text));
947
( "=" INT <<v=atoi($2.text);>>
952
/* fprintf(stderr, "#token %s=%d\n", p->str, v);*/
953
if ( v>maxt ) maxt=v;
955
token_association(p->token_type, p->str);
963
<<token_type = maxt + 1;>> /* record max defined token */
967
#token ID "[a-zA-Z_][_a-zA-Z0-9]*"
972
/* SORCERER-specific syntax error message generator
973
* (define USER_ZZSYN when compiling so don't get 2 definitions)
977
zzsyn(char *text, int tok, char *egroup, SetWordType *eset, int etok, int k, char *bad_text)
979
zzsyn(text, tok, egroup, eset, etok, k, bad_text)
980
char *text, *egroup, *bad_text;
987
fprintf(stderr, ErrHdr, FileStr[CurFile]!=NULL?FileStr[CurFile]:"stdin", zzline);
988
fprintf(stderr, " syntax error at \"%s\"", (tok==zzEOF_TOKEN)?"EOF":text);
989
if ( !etok && !eset ) {fprintf(stderr, "\n"); return;}
990
if ( k==1 ) fprintf(stderr, " missing");
993
fprintf(stderr, "; \"%s\" not", bad_text);
994
if ( zzset_deg(eset)>1 ) fprintf(stderr, " in");
996
if ( zzset_deg(eset)>0 ) zzedecode(eset);
997
else fprintf(stderr, " %s", zztokens[etok]);
998
if ( strlen(egroup) > (size_t)0 ) fprintf(stderr, " in %s", egroup);
999
fprintf(stderr, "\n");
1004
define_token(char *text)
1012
p = (SymEntry *) hash_get(symbols, text);
1014
if ( UserDefdTokens ) {
1015
err(eMsg1("implicit token definition of '%s' not allowed with #tokdefs",text));
1017
p = (SymEntry *) hash_add(symbols, text, (Entry *) newSymEntry(text));
1019
p->token_type = token_type++;
1020
token_association(p->token_type, p->str);
1021
list_add(&token_list, (void *)p);
1022
set_orel(p->token_type, &referenced_tokens);
1025
if ( p->token!=Token )
1026
err(eMsg2("token definition clashes with %s definition: '%s'", zztokens[p->token], text));