if ( st->stateCondList.length() > 0 )
redFsm->bAnyConditions = true;
+
+ if ( st->eofTrans != 0 )
+ redFsm->bAnyEofTrans = true;
}
/* Assign ids to actions that are referenced. */
bAnyFromStateActions(false),
bAnyRegActions(false),
bAnyEofActions(false),
+ bAnyEofTrans(false),
bAnyActionGotos(false),
bAnyActionCalls(false),
bAnyActionRets(false),
bool bAnyFromStateActions;
bool bAnyRegActions;
bool bAnyEofActions;
+ bool bAnyEofTrans;
bool bAnyActionGotos;
bool bAnyActionCalls;
bool bAnyActionRets;
bool anyFromStateActions() { return bAnyFromStateActions; }
bool anyRegActions() { return bAnyRegActions; }
bool anyEofActions() { return bAnyEofActions; }
+ bool anyEofTrans() { return bAnyEofTrans; }
bool anyActionGotos() { return bAnyActionGotos; }
bool anyActionCalls() { return bAnyActionCalls; }
bool anyActionRets() { return bAnyActionRets; }
"\n";
}
+ if ( redFsm->anyEofTrans() ) {
+ OPEN_ARRAY( ARRAY_TYPE(redFsm->maxIndex+1), ET() );
+ EOF_TRANS();
+ CLOSE_ARRAY() <<
+ "\n";
+ }
+
STATE_IDS();
}
COND_TRANSLATE();
LOCATE_TRANS();
+
+ if ( redFsm->anyEofTrans() )
+ out << "_eof_trans:\n";
if ( redFsm->anyRegCurStateRef() )
out << " _ps = " << CS() << ";\n";
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " switch ( " << EA() << "[" << CS() << "] ) {\n";
- EOF_ACTION_SWITCH();
- SWITCH_DEFAULT() <<
- " }\n"
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " if ( " << ET() << "[" << CS() << "] > 0 ) {\n"
+ " _trans = " << ET() << "[" << CS() << "] - 1;\n"
+ " goto _eof_trans;\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " switch ( " << EA() << "[" << CS() << "] ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " switch ( " << EA() << "[" << CS() << "] ) {\n";
- EOF_ACTION_SWITCH();
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " switch ( " << CS() << " ) {\n";
+
+ for ( RedStateList::Iter st = redFsm->stateList; st.lte(); st++ ) {
+ if ( st->eofTrans != 0 )
+ out << " case " << st->id << ": goto tr" << st->eofTrans->id << ";\n";
+ }
+
SWITCH_DEFAULT() <<
- " }\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " switch ( " << EA() << "[" << CS() << "] ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
return out;
}
+std::ostream &FlatCodeGen::EOF_TRANS()
+{
+ out << "\t";
+ int totalStateNum = 0;
+ for ( RedStateList::Iter st = redFsm->stateList; st.lte(); st++ ) {
+ /* Write any eof action. */
+
+ long trans = 0;
+ if ( st->eofTrans != 0 )
+ trans = st->eofTrans->id+1;
+ out << trans;
+
+ if ( !st.last() ) {
+ out << ", ";
+ if ( ++totalStateNum % IALL == 0 )
+ out << "\n\t";
+ }
+ }
+ out << "\n";
+ return out;
+}
+
+
std::ostream &FlatCodeGen::COND_KEYS()
{
out << '\t';
"\n";
}
+ if ( redFsm->anyEofTrans() ) {
+ OPEN_ARRAY( ARRAY_TYPE(redFsm->maxIndex+1), ET() );
+ EOF_TRANS();
+ CLOSE_ARRAY() <<
+ "\n";
+ }
+
STATE_IDS();
}
LOCATE_TRANS();
+ if ( redFsm->anyEofTrans() )
+ out << "_eof_trans:\n";
+
if ( redFsm->anyRegCurStateRef() )
out << " _ps = " << CS() << ";\n";
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) << POINTER() << "__acts = " <<
- ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
- " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
- " while ( __nacts-- > 0 ) {\n"
- " switch ( *__acts++ ) {\n";
- EOF_ACTION_SWITCH();
- SWITCH_DEFAULT() <<
- " }\n"
- " }\n"
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " if ( " << ET() << "[" << CS() << "] > 0 ) {\n"
+ " _trans = " << ET() << "[" << CS() << "] - 1;\n"
+ " goto _eof_trans;\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) <<
+ POINTER() << "__acts = " <<
+ ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
+ " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
+ " while ( __nacts-- > 0 ) {\n"
+ " switch ( *__acts++ ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n"
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
-
if ( outLabelUsed )
out << " _out: {}\n";
std::ostream &TO_STATE_ACTIONS();
std::ostream &FROM_STATE_ACTIONS();
std::ostream &EOF_ACTIONS();
+ std::ostream &EOF_TRANS();
std::ostream &TRANS_TARGS();
std::ostream &TRANS_ACTIONS();
void LOCATE_TRANS();
string TSA() { return "_" + DATA_PREFIX() + "to_state_actions"; }
string FSA() { return "_" + DATA_PREFIX() + "from_state_actions"; }
string EA() { return "_" + DATA_PREFIX() + "eof_actions"; }
+ string ET() { return "_" + DATA_PREFIX() + "eof_trans"; }
string SP() { return "_" + DATA_PREFIX() + "key_spans"; }
string CSP() { return "_" + DATA_PREFIX() + "cond_key_spans"; }
string START() { return DATA_PREFIX() + "start"; }
"\n";
}
+ if ( redFsm->anyEofTrans() ) {
+ OPEN_ARRAY( ARRAY_TYPE(redFsm->maxIndex+1), ET() );
+ EOF_TRANS();
+ CLOSE_ARRAY() <<
+ "\n";
+ }
+
STATE_IDS();
}
out << "_match:\n";
- if ( redFsm->anyRegCurStateRef() )
- out << " _ps = " << CS() << ";\n";
-
if ( useIndicies )
out << " _trans = " << I() << "[_trans];\n";
+ if ( redFsm->anyEofTrans() )
+ out << "_eof_trans:\n";
+
+ if ( redFsm->anyRegCurStateRef() )
+ out << " _ps = " << CS() << ";\n";
+
out <<
" " << CS() << " = " << TT() << "[_trans];\n"
"\n";
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " switch ( " << EA() << "[" << CS() << "] ) {\n";
- EOF_ACTION_SWITCH();
- SWITCH_DEFAULT() <<
- " }\n"
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " if ( " << ET() << "[" << CS() << "] > 0 ) {\n"
+ " _trans = " << ET() << "[" << CS() << "] - 1;\n"
+ " goto _eof_trans;\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " switch ( " << EA() << "[" << CS() << "] ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) << POINTER() << "__acts = " <<
- ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
- " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
- " while ( __nacts-- > 0 ) {\n"
- " switch ( *__acts++ ) {\n";
- EOF_ACTION_SWITCH();
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " switch ( " << CS() << " ) {\n";
+
+ for ( RedStateList::Iter st = redFsm->stateList; st.lte(); st++ ) {
+ if ( st->eofTrans != 0 )
+ out << " case " << st->id << ": goto tr" << st->eofTrans->id << ";\n";
+ }
+
SWITCH_DEFAULT() <<
- " }\n"
- " }\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) <<
+ POINTER() << "__acts = " <<
+ ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
+ " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
+ " while ( __nacts-- > 0 ) {\n"
+ " switch ( *__acts++ ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n"
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
}
}
+ for ( RedStateList::Iter st = redFsm->stateList; st.lte(); st++ ) {
+ if ( st->eofTrans != 0 )
+ out << " case " << st->id << ": goto tr" << st->eofTrans->id << ";\n";
+ }
+
for ( ActionTableMap::Iter act = redFsm->actionMap; act.lte(); act++ ) {
if ( act->eofRefs != 0 ) {
for ( IntSet::Iter pst = *act->eofRefs; pst.lte(); pst++ )
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
" {\n"
return out;
}
+std::ostream &TabCodeGen::EOF_TRANS()
+{
+ out << "\t";
+ int totalStateNum = 0;
+ for ( RedStateList::Iter st = redFsm->stateList; st.lte(); st++ ) {
+ /* Write any eof action. */
+
+ long trans = 0;
+ if ( st->eofTrans != 0 )
+ trans = st->eofTrans->id+1;
+ out << trans;
+
+ if ( !st.last() ) {
+ out << ", ";
+ if ( ++totalStateNum % IALL == 0 )
+ out << "\n\t";
+ }
+ }
+ out << "\n";
+ return out;
+}
+
+
std::ostream &TabCodeGen::COND_KEYS()
{
out << '\t';
"\n";
}
+ if ( redFsm->anyEofTrans() ) {
+ OPEN_ARRAY( ARRAY_TYPE(redFsm->maxIndex+1), ET() );
+ EOF_TRANS();
+ CLOSE_ARRAY() <<
+ "\n";
+ }
+
STATE_IDS();
}
out << "_match:\n";
- if ( redFsm->anyRegCurStateRef() )
- out << " _ps = " << CS() << ";\n";
-
if ( useIndicies )
out << " _trans = " << I() << "[_trans];\n";
+
+ if ( redFsm->anyEofTrans() )
+ out << "_eof_trans:\n";
+
+ if ( redFsm->anyRegCurStateRef() )
+ out << " _ps = " << CS() << ";\n";
out <<
" " << CS() << " = " << TT() << "[_trans];\n"
if ( testEofUsed )
out << " _test_eof: {}\n";
- if ( redFsm->anyEofActions() ) {
+ if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) {
out <<
" if ( " << P() << " == " << EOFV() << " )\n"
- " {\n"
- " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) <<
- POINTER() << "__acts = " << ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
- " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
- " while ( __nacts-- > 0 ) {\n"
- " switch ( *__acts++ ) {\n";
- EOF_ACTION_SWITCH();
- SWITCH_DEFAULT() <<
- " }\n"
- " }\n"
+ " {\n";
+
+ if ( redFsm->anyEofTrans() ) {
+ out <<
+ " if ( " << ET() << "[" << CS() << "] > 0 ) {\n"
+ " _trans = " << ET() << "[" << CS() << "] - 1;\n"
+ " goto _eof_trans;\n"
+ " }\n";
+ }
+
+ if ( redFsm->anyEofActions() ) {
+ out <<
+ " " << PTR_CONST() << ARRAY_TYPE(redFsm->maxActArrItem) <<
+ POINTER() << "__acts = " <<
+ ARR_OFF( A(), EA() + "[" + CS() + "]" ) << ";\n"
+ " " << UINT() << " __nacts = " << CAST(UINT()) << " *__acts++;\n"
+ " while ( __nacts-- > 0 ) {\n"
+ " switch ( *__acts++ ) {\n";
+ EOF_ACTION_SWITCH();
+ SWITCH_DEFAULT() <<
+ " }\n"
+ " }\n";
+ }
+
+ out <<
" }\n"
"\n";
}
std::ostream &TO_STATE_ACTIONS();
std::ostream &FROM_STATE_ACTIONS();
std::ostream &EOF_ACTIONS();
+ std::ostream &EOF_TRANS();
std::ostream &TRANS_TARGS();
std::ostream &TRANS_ACTIONS();
std::ostream &TRANS_TARGS_WI();
'<> 'eof _ [repeat machine_expr_item]
end rule
+rule findScanner
+ match [machine_expr_item]
+ '|* _ [repeat scanner_item] '*|
+end rule
+
function findEof P [program]
replace [program]
_ [program]
[findEof4] [findEof5] [findEof6]
[findEof7] [findEof8] [findEof9]
[findEof10] [findEof11] [findEof12]
+ [findScanner]
by
'yes
end function
{
char *p = data;
char *pe = data + len;
+ char *eof = pe;
%% write exec;
"44. 44\n"
"44 . 44\n"
"44.44\n"
- "_hithere22\n"
- "\n"
+ "_hithere22"
);
test(
"0x98\n"
"0x\n"
"//\n"
- "/* * */\n"
+ "/* * */"
);
test(
<241>
<195> _hithere22
-P: 53
+P: 51
<193> '\''
<192> "\n\d'\""
<241>
<242> //
<242> /* * */
-P: 56
+P: 55
P: 1
PARSE ERROR
#endif
{
char *p = data;
char *pe = data + len;
+ char *eof = pe;
%% write exec;
}
"44. 44\n"
"44 . 44\n"
"44.44\n"
- "_hithere22\n"
- "\n"
+ "_hithere22"
);
test(
"0x98\n"
"0x\n"
"//\n"
- "/* * */\n"
+ "/* * */"
);
test(
*|;
}%%
/* _____INPUT_____
-"\"\\\"hi\" /!\n!/\n44 .44\n44. 44\n44 . 44\n44.44\n_hithere22\n\n"
-"'\\''\"\\n\\d'\\\"\"\nhi\n99\n.99\n99e-4\n->*\n||\n0x98\n0x\n//\n/! * !/\n"
+"\"\\\"hi\" /!\n!/\n44 .44\n44. 44\n44 . 44\n44.44\n_hithere22"
+"'\\''\"\\n\\d'\\\"\"\nhi\n99\n.99\n99e-4\n->*\n||\n0x98\n0x\n//\n/! * !/"
"'\n'\n"
_____INPUT_____ */
/* _____OUTPUT_____
%% write init;
char *p = buf;
char *pe = buf + len;
+ char *eof = pe;
%% write exec;
if ( cs == Scanner_error ) {
Scanner scanner;
scanner.run(
"//hello*/\n"
- "/*hi there*/ hello 0x88\n"
+ "/*hi there*/ hello 0x88"
);
return 0;
}
/* Read in a block. */
char *p = data;
char *pe = data + strlen( data );
+ char *eof = pe;
%% write exec;
if ( cs == RagelScan_error ) {
{
char *p = data;
char *pe = data + len;
+ char *eof = pe;
%% write exec;
- int have = 0;
- if ( tokstart != 0 ) {
- have = pe - tokstart;
- memmove( data, tokstart, have );
- }
- return have;
+ return 0;
}
int Scanner::finish( )
tokstart = 30
to: fc =
tokstart = 30
+to: fc =
+ tokstart = -1
#endif