📄 lempar.c
字号:
/*** Find the appropriate action for a parser given the non-terminal** look-ahead token iLookAhead.**** If the look-ahead token is YYNOCODE, then check to see if the action is** independent of the look-ahead. If it is, return the action, otherwise** return YY_NO_ACTION.*/static int yy_find_reduce_action( int stateno, /* Current state number */ YYCODETYPE iLookAhead /* The look-ahead token */){ int i; /* int stateno = pParser->yystack[pParser->yyidx].stateno; */ if( stateno>YY_REDUCE_MAX || (i = yy_reduce_ofst[stateno])==YY_REDUCE_USE_DFLT ){ return yy_default[stateno]; } if( iLookAhead==YYNOCODE ){ return YY_NO_ACTION; } i += iLookAhead; if( i<0 || i>=YY_SZ_ACTTAB || yy_lookahead[i]!=iLookAhead ){ return yy_default[stateno]; }else{ return yy_action[i]; }}/*** The following routine is called if the stack overflows.*/static void yyStackOverflow(yyParser *yypParser, YYMINORTYPE *yypMinor){ ParseARG_FETCH; yypParser->yyidx--;#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sStack Overflow!\n",yyTracePrompt); }#endif while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will execute if the parser ** stack every overflows */%% ParseARG_STORE; /* Suppress warning about unused %extra_argument var */}/*** Perform a shift action.*/static void yy_shift( yyParser *yypParser, /* The parser to be shifted */ int yyNewState, /* The new state to shift in */ int yyMajor, /* The major token to shift in */ YYMINORTYPE *yypMinor /* Pointer ot the minor token to shift in */){ yyStackEntry *yytos; yypParser->yyidx++;#if YYSTACKDEPTH>0 if( yypParser->yyidx>=YYSTACKDEPTH ){ yyStackOverflow(yypParser, yypMinor); return; }#else if( yypParser->yyidx>=yypParser->yystksz ){ yyGrowStack(yypParser); if( yypParser->yyidx>=yypParser->yystksz ){ yyStackOverflow(yypParser, yypMinor); return; } }#endif yytos = &yypParser->yystack[yypParser->yyidx]; yytos->stateno = yyNewState; yytos->major = yyMajor; yytos->minor = *yypMinor;#ifndef NDEBUG if( yyTraceFILE && yypParser->yyidx>0 ){ int i; fprintf(yyTraceFILE,"%sShift %d\n",yyTracePrompt,yyNewState); fprintf(yyTraceFILE,"%sStack:",yyTracePrompt); for(i=1; i<=yypParser->yyidx; i++) fprintf(yyTraceFILE," %s",yyTokenName[yypParser->yystack[i].major]); fprintf(yyTraceFILE,"\n"); }#endif}/* The following table contains information about every rule that** is used during the reduce.*/static const struct { YYCODETYPE lhs; /* Symbol on the left-hand side of the rule */ unsigned char nrhs; /* Number of right-hand side symbols in the rule */} yyRuleInfo[] = {%%};static void yy_accept(yyParser*); /* Forward Declaration *//*** Perform a reduce action and the shift that must immediately** follow the reduce.*/static void yy_reduce( yyParser *yypParser, /* The parser */ int yyruleno /* Number of the rule by which to reduce */){ int yygoto; /* The next state */ int yyact; /* The next action */ YYMINORTYPE yygotominor; /* The LHS of the rule reduced */ yyStackEntry *yymsp; /* The top of the parser's stack */ int yysize; /* Amount to pop the stack */ ParseARG_FETCH; yymsp = &yypParser->yystack[yypParser->yyidx];#ifndef NDEBUG if( yyTraceFILE && yyruleno>=0 && yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) ){ fprintf(yyTraceFILE, "%sReduce [%s].\n", yyTracePrompt, yyRuleName[yyruleno]); }#endif /* NDEBUG */ /* Silence complaints from purify about yygotominor being uninitialized ** in some cases when it is copied into the stack after the following ** switch. yygotominor is uninitialized when a rule reduces that does ** not set the value of its left-hand side nonterminal. Leaving the ** value of the nonterminal uninitialized is utterly harmless as long ** as the value is never used. So really the only thing this code ** accomplishes is to quieten purify. ** ** 2007-01-16: The wireshark project (www.wireshark.org) reports that ** without this code, their parser segfaults. I'm not sure what there ** parser is doing to make this happen. This is the second bug report ** from wireshark this week. Clearly they are stressing Lemon in ways ** that it has not been previously stressed... (SQLite ticket #2172) */ memset(&yygotominor, 0, sizeof(yygotominor)); switch( yyruleno ){ /* Beginning here are the reduction cases. A typical example ** follows: ** case 0: ** #line <lineno> <grammarfile> ** { ... } // User supplied code ** #line <lineno> <thisfile> ** break; */%% }; yygoto = yyRuleInfo[yyruleno].lhs; yysize = yyRuleInfo[yyruleno].nrhs; yypParser->yyidx -= yysize; yyact = yy_find_reduce_action(yymsp[-yysize].stateno,yygoto); if( yyact < YYNSTATE ){#ifdef NDEBUG /* If we are not debugging and the reduce action popped at least ** one element off the stack, then we can push the new element back ** onto the stack here, and skip the stack overflow test in yy_shift(). ** That gives a significant speed improvement. */ if( yysize ){ yypParser->yyidx++; yymsp -= yysize-1; yymsp->stateno = yyact; yymsp->major = yygoto; yymsp->minor = yygotominor; }else#endif { yy_shift(yypParser,yyact,yygoto,&yygotominor); } }else if( yyact == YYNSTATE + YYNRULE + 1 ){ yy_accept(yypParser); }}/*** The following code executes when the parse fails*/static void yy_parse_failed( yyParser *yypParser /* The parser */){ ParseARG_FETCH;#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sFail!\n",yyTracePrompt); }#endif while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will be executed whenever the ** parser fails */%% ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */}/*** The following code executes when a syntax error first occurs.*/static void yy_syntax_error( yyParser *yypParser, /* The parser */ int yymajor, /* The major type of the error token */ YYMINORTYPE yyminor /* The minor type of the error token */){ ParseARG_FETCH;#define TOKEN (yyminor.yy0)%% ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */}/*** The following is executed when the parser accepts*/static void yy_accept( yyParser *yypParser /* The parser */){ ParseARG_FETCH;#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sAccept!\n",yyTracePrompt); }#endif while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will be executed whenever the ** parser accepts */%% ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */}/* The main parser program.** The first argument is a pointer to a structure obtained from** "ParseAlloc" which describes the current state of the parser.** The second argument is the major token number. The third is** the minor token. The fourth optional argument is whatever the** user wants (and specified in the grammar) and is available for** use by the action routines.**** Inputs:** <ul>** <li> A pointer to the parser (an opaque structure.)** <li> The major token number.** <li> The minor token number.** <li> An option argument of a grammar-specified type.** </ul>**** Outputs:** None.*/void Parse( void *yyp, /* The parser */ int yymajor, /* The major token code number */ ParseTOKENTYPE yyminor /* The value for the token */ ParseARG_PDECL /* Optional %extra_argument parameter */){ YYMINORTYPE yyminorunion; int yyact; /* The parser action. */ int yyendofinput; /* True if we are at the end of input */ int yyerrorhit = 0; /* True if yymajor has invoked an error */ yyParser *yypParser; /* The parser */ /* (re)initialize the parser, if necessary */ yypParser = (yyParser*)yyp; if( yypParser->yyidx<0 ){#if YYSTACKDEPTH<=0 if( yypParser->yystksz <=0 ){ memset(&yyminorunion, 0, sizeof(yyminorunion)); yyStackOverflow(yypParser, &yyminorunion); return; }#endif yypParser->yyidx = 0; yypParser->yyerrcnt = -1; yypParser->yystack[0].stateno = 0; yypParser->yystack[0].major = 0; } yyminorunion.yy0 = yyminor; yyendofinput = (yymajor==0); ParseARG_STORE;#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sInput %s\n",yyTracePrompt,yyTokenName[yymajor]); }#endif do{ yyact = yy_find_shift_action(yypParser,yymajor); if( yyact<YYNSTATE ){ yy_shift(yypParser,yyact,yymajor,&yyminorunion); yypParser->yyerrcnt--; if( yyendofinput && yypParser->yyidx>=0 ){ yymajor = 0; }else{ yymajor = YYNOCODE; } }else if( yyact < YYNSTATE + YYNRULE ){ yy_reduce(yypParser,yyact-YYNSTATE); }else if( yyact == YY_ERROR_ACTION ){ int yymx;#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sSyntax Error!\n",yyTracePrompt); }#endif#ifdef YYERRORSYMBOL /* A syntax error has occurred. ** The response to an error depends upon whether or not the ** grammar defines an error token "ERROR". ** ** This is what we do if the grammar does define ERROR: ** ** * Call the %syntax_error function. ** ** * Begin popping the stack until we enter a state where ** it is legal to shift the error symbol, then shift ** the error symbol. ** ** * Set the error count to three. ** ** * Begin accepting and shifting new tokens. No new error ** processing will occur until three tokens have been ** shifted successfully. ** */ if( yypParser->yyerrcnt<0 ){ yy_syntax_error(yypParser,yymajor,yyminorunion); } yymx = yypParser->yystack[yypParser->yyidx].major; if( yymx==YYERRORSYMBOL || yyerrorhit ){#ifndef NDEBUG if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sDiscard input token %s\n", yyTracePrompt,yyTokenName[yymajor]); }#endif yy_destructor(yymajor,&yyminorunion); yymajor = YYNOCODE; }else{ while( yypParser->yyidx >= 0 && yymx != YYERRORSYMBOL && (yyact = yy_find_reduce_action( yypParser->yystack[yypParser->yyidx].stateno, YYERRORSYMBOL)) >= YYNSTATE ){ yy_pop_parser_stack(yypParser); } if( yypParser->yyidx < 0 || yymajor==0 ){ yy_destructor(yymajor,&yyminorunion); yy_parse_failed(yypParser); yymajor = YYNOCODE; }else if( yymx!=YYERRORSYMBOL ){ YYMINORTYPE u2; u2.YYERRSYMDT = 0; yy_shift(yypParser,yyact,YYERRORSYMBOL,&u2); } } yypParser->yyerrcnt = 3; yyerrorhit = 1;#else /* YYERRORSYMBOL is not defined */ /* This is what we do if the grammar does not define ERROR: ** ** * Report an error message, and throw away the input token. ** ** * If the input token is $, then fail the parse. ** ** As before, subsequent error messages are suppressed until ** three input tokens have been successfully shifted. */ if( yypParser->yyerrcnt<=0 ){ yy_syntax_error(yypParser,yymajor,yyminorunion); } yypParser->yyerrcnt = 3; yy_destructor(yymajor,&yyminorunion); if( yyendofinput ){ yy_parse_failed(yypParser); } yymajor = YYNOCODE;#endif }else{ yy_accept(yypParser); yymajor = YYNOCODE; } }while( yymajor!=YYNOCODE && yypParser->yyidx>=0 ); return;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -