binloop.cc (ragel-7.0.0.10) | : | binloop.cc (ragel-7.0.0.11) | ||
---|---|---|---|---|
/* | /* | |||
* Copyright 2001-2014 Adrian Thurston <thurston@colm.net> | * Copyright 2018-2018 Adrian Thurston <thurston@colm.net> | |||
* | * | |||
* Permission is hereby granted, free of charge, to any person obtaining a copy | * Permission is hereby granted, free of charge, to any person obtaining a copy | |||
* of this software and associated documentation files (the "Software"), to | * of this software and associated documentation files (the "Software"), to | |||
* deal in the Software without restriction, including without limitation the | * deal in the Software without restriction, including without limitation the | |||
* rights to use, copy, modify, merge, publish, distribute, sublicense, and/or | * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or | |||
* sell copies of the Software, and to permit persons to whom the Software is | * sell copies of the Software, and to permit persons to whom the Software is | |||
* furnished to do so, subject to the following conditions: | * furnished to do so, subject to the following conditions: | |||
* | * | |||
* The above copyright notice and this permission notice shall be included in al l | * The above copyright notice and this permission notice shall be included in al l | |||
* copies or substantial portions of the Software. | * copies or substantial portions of the Software. | |||
* | * | |||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | |||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | |||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | |||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | |||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | |||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | |||
* SOFTWARE. | * SOFTWARE. | |||
*/ | */ | |||
#include "ragel.h" | #include "actloop.h" | |||
#include "binloop.h" | ||||
#include "redfsm.h" | #include "redfsm.h" | |||
#include "gendata.h" | #include "gendata.h" | |||
#include "inputdata.h" | ||||
#include "parsedata.h" | ||||
BinaryLoopGoto::BinaryLoopGoto( const CodeGenArgs &args ) | void ActLoop::FROM_STATE_ACTION( RedStateAp *state ) | |||
: | ||||
Binary( args ) | ||||
{} | ||||
/* Determine if we should use indicies or not. */ | ||||
void BinaryLoopGoto::calcIndexSize() | ||||
{ | { | |||
// long long sizeWithInds = | int act = 0; | |||
// indicies.size() + | if ( state->fromStateAction != 0 ) | |||
// transCondSpacesWi.size() + | act = state->fromStateAction->location+1; | |||
// transOffsetsWi.size() + | fromStateActions.value( act ); | |||
// transLengthsWi.size(); | ||||
// long long sizeWithoutInds = | ||||
// transCondSpaces.size() + | ||||
// transOffsets.size() + | ||||
// transLengths.size(); | ||||
///* If using indicies reduces the size, use them. */ | ||||
//useIndicies = sizeWithInds < sizeWithoutInds; | ||||
useIndicies = false; | ||||
} | ||||
void BinaryLoopGoto::tableDataPass() | ||||
{ | ||||
taActions(); | ||||
taKeyOffsets(); | ||||
taSingleLens(); | ||||
taRangeLens(); | ||||
taIndexOffsets(); | ||||
taIndicies(); | ||||
taTransCondSpacesWi(); | ||||
taTransOffsetsWi(); | ||||
taTransLengthsWi(); | ||||
taTransCondSpaces(); | ||||
taTransOffsets(); | ||||
taTransLengths(); | ||||
taCondTargs(); | ||||
taCondActions(); | ||||
taToStateActions(); | ||||
taFromStateActions(); | ||||
taEofActions(); | ||||
taEofTransDirect(); | ||||
taEofTransIndexed(); | ||||
taKeys(); | ||||
taCondKeys(); | ||||
taNfaTargs(); | ||||
taNfaOffsets(); | ||||
taNfaPushActions(); | ||||
taNfaPopTrans(); | ||||
} | ||||
void BinaryLoopGoto::genAnalysis() | ||||
{ | ||||
redFsm->sortByStateId(); | ||||
/* Choose default transitions and the single transition. */ | ||||
redFsm->chooseDefaultSpan(); | ||||
/* Choose the singles. */ | ||||
redFsm->moveSelectTransToSingle(); | ||||
/* If any errors have occured in the input file then don't write anything | ||||
. */ | ||||
if ( red->id->errorCount > 0 ) | ||||
return; | ||||
/* Anlayze Machine will find the final action reference counts, among oth | ||||
er | ||||
* things. We will use these in reporting the usage of fsm directives in | ||||
* action code. */ | ||||
red->analyzeMachine(); | ||||
setKeyType(); | ||||
/* Run the analysis pass over the table data. */ | ||||
setTableState( TableArray::AnalyzePass ); | ||||
tableDataPass(); | ||||
/* Determine if we should use indicies. */ | ||||
calcIndexSize(); | ||||
/* Switch the tables over to the code gen mode. */ | ||||
setTableState( TableArray::GeneratePass ); | ||||
} | } | |||
void BinaryLoopGoto::COND_ACTION( RedCondPair *cond ) | void ActLoop::COND_ACTION( RedCondPair *cond ) | |||
{ | { | |||
int act = 0; | int act = 0; | |||
if ( cond->action != 0 ) | if ( cond->action != 0 ) | |||
act = cond->action->location+1; | act = cond->action->location+1; | |||
condActions.value( act ); | condActions.value( act ); | |||
} | } | |||
void BinaryLoopGoto::TO_STATE_ACTION( RedStateAp *state ) | void ActLoop::TO_STATE_ACTION( RedStateAp *state ) | |||
{ | { | |||
int act = 0; | int act = 0; | |||
if ( state->toStateAction != 0 ) | if ( state->toStateAction != 0 ) | |||
act = state->toStateAction->location+1; | act = state->toStateAction->location+1; | |||
toStateActions.value( act ); | toStateActions.value( act ); | |||
} | } | |||
void BinaryLoopGoto::FROM_STATE_ACTION( RedStateAp *state ) | void ActLoop::EOF_ACTION( RedStateAp *state ) | |||
{ | ||||
int act = 0; | ||||
if ( state->fromStateAction != 0 ) | ||||
act = state->fromStateAction->location+1; | ||||
fromStateActions.value( act ); | ||||
} | ||||
void BinaryLoopGoto::EOF_ACTION( RedStateAp *state ) | ||||
{ | { | |||
int act = 0; | int act = 0; | |||
if ( state->eofAction != 0 ) | if ( state->eofAction != 0 ) | |||
act = state->eofAction->location+1; | act = state->eofAction->location+1; | |||
eofActions.value( act ); | eofActions.value( act ); | |||
} | } | |||
void BinaryLoopGoto::NFA_PUSH_ACTION( RedNfaTarg *targ ) | void ActLoop::NFA_PUSH_ACTION( RedNfaTarg *targ ) | |||
{ | { | |||
int act = 0; | int act = 0; | |||
if ( targ->push != 0 ) | if ( targ->push != 0 ) | |||
act = targ->push->actListId+1; | act = targ->push->actListId+1; | |||
nfaPushActions.value( act ); | nfaPushActions.value( act ); | |||
} | } | |||
void BinaryLoopGoto::NFA_POP_TEST( RedNfaTarg *targ ) | void ActLoop::NFA_POP_TEST( RedNfaTarg *targ ) | |||
{ | { | |||
int act = 0; | int act = 0; | |||
if ( targ->popTest != 0 ) | if ( targ->popTest != 0 ) | |||
act = targ->popTest->actListId+1; | act = targ->popTest->actListId+1; | |||
nfaPopTrans.value( act ); | nfaPopTrans.value( act ); | |||
} | } | |||
std::ostream &BinaryLoopGoto::TO_STATE_ACTION_SWITCH() | std::ostream &ActLoop::FROM_STATE_ACTION_SWITCH() | |||
{ | { | |||
/* Walk the list of functions, printing the cases. */ | /* Walk the list of functions, printing the cases. */ | |||
for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | |||
/* Write out referenced actions. */ | /* Write out referenced actions. */ | |||
if ( act->numToStateRefs > 0 ) { | if ( act->numFromStateRefs > 0 ) { | |||
/* Write the case label, the action and the case break. * / | /* Write the case label, the action and the case break. * / | |||
out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | |||
ACTION( out, act, IlOpts( 0, false, false ) ); | ACTION( out, act, IlOpts( 0, false, false ) ); | |||
out << "\n\t" << CEND() << "}\n"; | out << "\n\t" << CEND() << "}\n"; | |||
} | } | |||
} | } | |||
return out; | return out; | |||
} | } | |||
std::ostream &BinaryLoopGoto::FROM_STATE_ACTION_SWITCH() | std::ostream &ActLoop::ACTION_SWITCH() | |||
{ | { | |||
/* Walk the list of functions, printing the cases. */ | /* Walk the list of functions, printing the cases. */ | |||
for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | |||
/* Write out referenced actions. */ | /* Write out referenced actions. */ | |||
if ( act->numFromStateRefs > 0 ) { | if ( act->numTransRefs > 0 ) { | |||
/* Write the case label, the action and the case break. * / | /* Write the case label, the action and the case break. * / | |||
out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | |||
ACTION( out, act, IlOpts( 0, false, false ) ); | ACTION( out, act, IlOpts( 0, false, false ) ); | |||
out << "\n\t" << CEND() << "}\n"; | out << "\n\t" << CEND() << "}\n"; | |||
} | } | |||
} | } | |||
return out; | return out; | |||
} | } | |||
std::ostream &BinaryLoopGoto::EOF_ACTION_SWITCH() | std::ostream &ActLoop::TO_STATE_ACTION_SWITCH() | |||
{ | { | |||
/* Walk the list of functions, printing the cases. */ | /* Walk the list of functions, printing the cases. */ | |||
for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | |||
/* Write out referenced actions. */ | /* Write out referenced actions. */ | |||
if ( act->numEofRefs > 0 ) { | if ( act->numToStateRefs > 0 ) { | |||
/* Write the case label, the action and the case break. * / | /* Write the case label, the action and the case break. * / | |||
out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | |||
ACTION( out, act, IlOpts( 0, true, false ) ); | ACTION( out, act, IlOpts( 0, false, false ) ); | |||
out << "\n\t" << CEND() << "}\n"; | out << "\n\t" << CEND() << "}\n"; | |||
} | } | |||
} | } | |||
return out; | return out; | |||
} | } | |||
std::ostream &BinaryLoopGoto::ACTION_SWITCH() | std::ostream &ActLoop::EOF_ACTION_SWITCH() | |||
{ | { | |||
/* Walk the list of functions, printing the cases. */ | /* Walk the list of functions, printing the cases. */ | |||
for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | for ( GenActionList::Iter act = red->actionList; act.lte(); act++ ) { | |||
/* Write out referenced actions. */ | /* Write out referenced actions. */ | |||
if ( act->numTransRefs > 0 ) { | if ( act->numEofRefs > 0 ) { | |||
/* Write the case label, the action and the case break. * / | /* Write the case label, the action and the case break. * / | |||
out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | out << "\t " << CASE( STR( act->actionId ) ) << " {\n"; | |||
ACTION( out, act, IlOpts( 0, false, false ) ); | ACTION( out, act, IlOpts( 0, true, false ) ); | |||
out << "\n\t" << CEND() << "}\n"; | out << "\n\t" << CEND() << "}\n"; | |||
} | } | |||
} | } | |||
return out; | return out; | |||
} | } | |||
void BinaryLoopGoto::writeData() | void ActLoop::FROM_STATE_ACTIONS() | |||
{ | ||||
/* If there are any transtion functions then output the array. If there | ||||
* are none, don't bother emitting an empty array that won't be used. */ | ||||
if ( redFsm->anyActions() ) | ||||
taActions(); | ||||
taKeyOffsets(); | ||||
taKeys(); | ||||
taSingleLens(); | ||||
taRangeLens(); | ||||
taIndexOffsets(); | ||||
if ( useIndicies ) { | ||||
taIndicies(); | ||||
taTransCondSpacesWi(); | ||||
taTransOffsetsWi(); | ||||
taTransLengthsWi(); | ||||
} | ||||
else { | ||||
taTransCondSpaces(); | ||||
taTransOffsets(); | ||||
taTransLengths(); | ||||
} | ||||
taCondKeys(); | ||||
taCondTargs(); | ||||
taCondActions(); | ||||
if ( redFsm->anyToStateActions() ) | ||||
taToStateActions(); | ||||
if ( redFsm->anyFromStateActions() ) | ||||
taFromStateActions(); | ||||
if ( redFsm->anyEofActions() ) | ||||
taEofActions(); | ||||
if ( redFsm->anyEofTrans() ) { | ||||
taEofTransIndexed(); | ||||
taEofTransDirect(); | ||||
} | ||||
taNfaTargs(); | ||||
taNfaOffsets(); | ||||
taNfaPushActions(); | ||||
taNfaPopTrans(); | ||||
STATE_IDS(); | ||||
} | ||||
void BinaryLoopGoto::NFA_FROM_STATE_ACTION_EXEC() | ||||
{ | { | |||
if ( redFsm->anyFromStateActions() ) { | if ( redFsm->anyFromStateActions() ) { | |||
out << | out << | |||
" _acts = " << OFFSET( ARR_REF( actions ), ARR_REF( | " " << acts << " = " << OFFSET( ARR_REF( actions ), | |||
fromStateActions ) + "[nfa_bp[nfa_len].state]" ) << ";\n" | ARR_REF( fromStateActions ) + "[" + vCS() + "]" ) << ";\n" | |||
" _nacts = " << CAST( UINT() ) << DEREF( ARR_REF( a | " " << nacts << " = " << CAST(UINT()) << DEREF( ARR | |||
ctions ), "_acts" ) << ";\n" | _REF( actions ), "" + string(acts) + "" ) << ";\n" | |||
" _acts += 1;\n" | " " << acts << " += 1;\n" | |||
" while ( _nacts > 0 ) {\n" | " while ( " << nacts << " > 0 ) {\n" | |||
" switch ( " << DEREF( ARR_REF( actions ), | " switch ( " << DEREF( ARR_REF( actions ), | |||
"_acts" ) << " ) {\n"; | "" + string(acts) + "" ) << " ) {\n"; | |||
FROM_STATE_ACTION_SWITCH() << | FROM_STATE_ACTION_SWITCH() << | |||
" }\n" | " }\n" | |||
" _nacts -= 1;\n" | " " << nacts << " -= 1;\n" | |||
" _acts += 1;\n" | " " << acts << " += 1;\n" | |||
" }\n" | " }\n" | |||
"\n"; | "\n"; | |||
} | } | |||
} | } | |||
void BinaryLoopGoto::writeExec() | void ActLoop::REG_ACTIONS( std::string cond ) | |||
{ | { | |||
testEofUsed = false; | ||||
outLabelUsed = false; | ||||
out << | ||||
" {\n" | ||||
" int _klen;\n"; | ||||
if ( redFsm->anyRegCurStateRef() ) | ||||
out << " int _ps;\n"; | ||||
out << | out << | |||
" " << UINT() << " _trans = 0;\n" | " " << acts << " = " << OFFSET( ARR_REF( actions ), ARR_REF | |||
" " << UINT() << " _cond = 0;\n"; | ( condActions ) + "[" + cond + "]" ) << ";\n" | |||
" " << nacts << " = " << CAST( UINT() ) << DEREF( ARR_REF( | ||||
if ( redFsm->anyRegNbreak() ) | actions ), "" + string(acts) + "" ) << ";\n" | |||
out << " int _nbreak;\n"; | " " << acts << " += 1;\n" | |||
" while ( " << nacts << " > 0 ) {\n" | ||||
if ( redFsm->anyToStateActions() || redFsm->anyRegActions() | " switch ( " << DEREF( ARR_REF( actions ), "" + str | |||
|| redFsm->anyFromStateActions() ) | ing(acts) + "" ) << " )\n" | |||
{ | " {\n"; | |||
out << | ACTION_SWITCH() << | |||
" " << INDEX( ARR_TYPE( actions ), "_acts" ) << ";\ | " }\n" | |||
n" | " " << nacts << " -= 1;\n" | |||
" " << UINT() << " _nacts;\n"; | " " << acts << " += 1;\n" | |||
} | " }\n" | |||
out << | ||||
" " << INDEX( ALPH_TYPE(), "_keys" ) << ";\n" | ||||
" " << INDEX( ARR_TYPE( condKeys ), "_ckeys" ) << ";\n" | ||||
" int _cpc;\n" | ||||
" " << ENTRY() << " {\n" | ||||
"\n"; | ||||
if ( !noEnd ) { | ||||
testEofUsed = true; | ||||
out << | ||||
" if ( " << P() << " == " << PE() << " )\n" | ||||
" goto _test_eof;\n"; | ||||
} | ||||
if ( redFsm->errState != 0 ) { | ||||
outLabelUsed = true; | ||||
out << | ||||
" if ( " << vCS() << " == " << redFsm->errState->id | ||||
<< " )\n" | ||||
" goto _out;\n"; | ||||
} | ||||
out << LABEL( "_resume" ) << " {\n"; | ||||
if ( redFsm->anyFromStateActions() ) { | ||||
out << | ||||
" _acts = " << OFFSET( ARR_REF( actions ), ARR_REF | ||||
( fromStateActions ) + | ||||
"[" + vCS() + "]" ) << ";\n" | ||||
" _nacts = " << CAST(UINT()) << DEREF( ARR_REF( act | ||||
ions ), "_acts" ) << ";\n" | ||||
" _acts += 1;\n" | ||||
" while ( _nacts > 0 ) {\n" | ||||
" switch ( " << DEREF( ARR_REF( actions ), | ||||
"_acts" ) << " ) {\n"; | ||||
FROM_STATE_ACTION_SWITCH() << | ||||
" }\n" | ||||
" _nacts -= 1;\n" | ||||
" _acts += 1;\n" | ||||
" }\n" | ||||
"\n"; | ||||
} | ||||
NFA_PUSH(); | ||||
LOCATE_TRANS(); | ||||
out << "}\n"; | ||||
out << LABEL( "_match" ) << " {\n"; | ||||
if ( useIndicies ) | ||||
out << " _trans = " << ARR_REF( indicies ) << "[_trans];\n | ||||
"; | ||||
LOCATE_COND(); | ||||
out << "}\n"; | ||||
out << LABEL( "_match_cond" ) << " {\n"; | ||||
if ( redFsm->anyRegCurStateRef() ) | ||||
out << " _ps = " << vCS() << ";\n"; | ||||
out << | ||||
" " << vCS() << " = " << CAST( "int" ) << ARR_REF( condTarg | ||||
s ) << "[_cond];\n" | ||||
"\n"; | "\n"; | |||
} | ||||
if ( redFsm->anyRegActions() ) { | void ActLoop::TO_STATE_ACTIONS() | |||
out << | { | |||
" if ( " << ARR_REF( condActions ) << "[_cond] == 0 | ||||
)\n" | ||||
" goto _again;\n" | ||||
"\n"; | ||||
if ( redFsm->anyRegNbreak() ) | ||||
out << " _nbreak = 0;\n"; | ||||
out << | ||||
" _acts = " << OFFSET( ARR_REF( actions ), ARR_REF( | ||||
condActions ) + "[_cond]" ) << ";\n" | ||||
" _nacts = " << CAST( UINT() ) << DEREF( ARR_REF( a | ||||
ctions ), "_acts" ) << ";\n" | ||||
" _acts += 1;\n" | ||||
" while ( _nacts > 0 )\n {\n" | ||||
" switch ( " << DEREF( ARR_REF( actions ), | ||||
"_acts" ) << " )\n" | ||||
" {\n"; | ||||
ACTION_SWITCH() << | ||||
" }\n" | ||||
" _nacts -= 1;\n" | ||||
" _acts += 1;\n" | ||||
" }\n" | ||||
"\n"; | ||||
if ( redFsm->anyRegNbreak() ) { | ||||
out << | ||||
" if ( _nbreak == 1 )\n" | ||||
" goto _out;\n"; | ||||
outLabelUsed = true; | ||||
} | ||||
out << "\n"; | ||||
} | ||||
// if ( redFsm->anyRegActions() || redFsm->anyActionGotos() || | ||||
// redFsm->anyActionCalls() || redFsm->anyActionRets() ) | ||||
out << "}\n"; | ||||
out << LABEL( "_again" ) << " {\n"; | ||||
if ( redFsm->anyToStateActions() ) { | if ( redFsm->anyToStateActions() ) { | |||
out << | out << | |||
" _acts = " << OFFSET( ARR_REF( actions ), ARR_REF( | " " << acts << " = " << OFFSET( ARR_REF( actions ), | |||
toStateActions ) + | ARR_REF( toStateActions ) + "[" + vCS() + "]" ) << ";\n" | |||
"[" + vCS() + "]" ) << ";\n" | " " << nacts << " = " << CAST(UINT()) << DEREF( ARR | |||
" _nacts = " << CAST(UINT()) << DEREF( ARR_REF( act | _REF( actions ), "" + string(acts) + "" ) << ";\n" | |||
ions ), "_acts" ) << ";\n" | " " << acts << " += 1;\n" | |||
" _acts += 1;\n" | " while ( " << nacts << " > 0 ) {\n" | |||
" while ( _nacts > 0 ) {\n" | " switch ( " << DEREF( ARR_REF( actions ), | |||
" switch ( " << DEREF( ARR_REF( actions ), | "" + string(acts) + "" ) << " ) {\n"; | |||
"_acts" ) << " ) {\n"; | ||||
TO_STATE_ACTION_SWITCH() << | TO_STATE_ACTION_SWITCH() << | |||
" }\n" | " }\n" | |||
" _nacts -= 1;\n" | " " << nacts << " -= 1;\n" | |||
" _acts += 1;\n" | " " << acts << " += 1;\n" | |||
" }\n" | " }\n" | |||
"\n"; | "\n"; | |||
} | } | |||
} | ||||
if ( redFsm->errState != 0 ) { | void ActLoop::EOF_ACTIONS() | |||
outLabelUsed = true; | { | |||
out << | if ( redFsm->anyEofActions() ) { | |||
" if ( " << vCS() << " == " << redFsm->errState->id | ||||
<< " )\n" | ||||
" goto _out;\n"; | ||||
} | ||||
if ( !noEnd ) { | ||||
out << | ||||
" " << P() << " += 1;\n" | ||||
" if ( " << P() << " != " << PE() << " )\n" | ||||
" goto _resume;\n"; | ||||
} | ||||
else { | ||||
out << | out << | |||
" " << P() << " += 1;\n" | " " << INDEX( ARR_TYPE( actions ), "__acts" ) << "; | |||
" goto _resume;\n"; | \n" | |||
" " << UINT() << " __nacts;\n" | ||||
" __acts = " << OFFSET( ARR_REF( actions ), ARR_REF | ||||
( eofActions ) + "[" + vCS() + "]" ) << ";\n" | ||||
" __nacts = " << CAST(UINT()) << DEREF( ARR_REF( ac | ||||
tions ), "__acts" ) << ";\n" | ||||
" __acts += 1;\n" | ||||
" while ( __nacts > 0 ) {\n" | ||||
" switch ( " << DEREF( ARR_REF( actions ), | ||||
"__acts" ) << " ) {\n"; | ||||
EOF_ACTION_SWITCH() << | ||||
" }\n" | ||||
" __nacts -= 1;\n" | ||||
" __acts += 1;\n" | ||||
" }\n"; | ||||
} | } | |||
} | ||||
if ( testEofUsed ) | void ActLoop::NFA_FROM_STATE_ACTION_EXEC() | |||
out << "}\n" << LABEL( "_test_eof" ) << " { {}\n"; | { | |||
if ( redFsm->anyFromStateActions() ) { | ||||
if ( redFsm->anyEofTrans() || redFsm->anyEofActions() ) { | ||||
out << | ||||
" if ( " << P() << " == " << vEOF() << " )\n" | ||||
" {\n"; | ||||
if ( redFsm->anyEofTrans() ) { | ||||
TableArray &eofTrans = useIndicies ? eofTransIndexed : eo | ||||
fTransDirect; | ||||
out << | ||||
" if ( " << ARR_REF( eofTrans ) << "[" << v | ||||
CS() << "] > 0 ) {\n" | ||||
" _trans = " << CAST(UINT()) << ARR | ||||
_REF( eofTrans ) << "[" << vCS() << "] - 1;\n" | ||||
" _cond = " << CAST(UINT()) << ARR_ | ||||
REF( transOffsets ) << "[_trans];\n" | ||||
" goto _match_cond;\n" | ||||
" }\n"; | ||||
} | ||||
if ( redFsm->anyEofActions() ) { | ||||
out << | ||||
" " << INDEX( ARR_TYPE( actions ), "__acts" | ||||
) << ";\n" | ||||
" " << UINT() << " __nacts;\n" | ||||
" __acts = " << OFFSET( ARR_REF( actions ), | ||||
ARR_REF( eofActions ) + "[" + vCS() + "]" ) << ";\n" | ||||
" __nacts = " << CAST(UINT()) << DEREF( ARR | ||||
_REF( actions ), "__acts" ) << ";\n" | ||||
" __acts += 1;\n" | ||||
" while ( __nacts > 0 ) {\n" | ||||
" switch ( " << DEREF( ARR_REF( act | ||||
ions ), "__acts" ) << " ) {\n"; | ||||
EOF_ACTION_SWITCH() << | ||||
" }\n" | ||||
" __nacts -= 1;\n" | ||||
" __acts += 1;\n" | ||||
" }\n"; | ||||
} | ||||
out << | out << | |||
" " << acts << " = " << OFFSET( ARR_REF( actions ), | ||||
ARR_REF( fromStateActions ) + "[nfa_bp[nfa_len].state]" ) << ";\n" | ||||
" " << nacts << " = " << CAST( UINT() ) << DEREF( A | ||||
RR_REF( actions ), "" + string(acts) + "" ) << ";\n" | ||||
" " << acts << " += 1;\n" | ||||
" while ( " << nacts << " > 0 ) {\n" | ||||
" switch ( " << DEREF( ARR_REF( actions ), | ||||
"" + string(acts) + "" ) << " ) {\n"; | ||||
FROM_STATE_ACTION_SWITCH() << | ||||
" }\n" | ||||
" " << nacts << " -= 1;\n" | ||||
" " << acts << " += 1;\n" | ||||
" }\n" | " }\n" | |||
"\n"; | "\n"; | |||
} | } | |||
if ( outLabelUsed ) | ||||
out << "}\n" << LABEL( "_out" ) << " { {}\n"; | ||||
/* The entry loop. */ | ||||
out << "}\n}\n"; | ||||
NFA_POP(); | ||||
/* The execute block. */ | ||||
out << " }\n"; | ||||
} | } | |||
End of changes. 37 change blocks. | ||||
395 lines changed or deleted | 97 lines changed or added |