📄 programgraphparser.cpp
字号:
{ program_builder->setCommand( for_init_command ); program_builder->proceedToNext( new ConditionTrue, mpositer.get_position().line - ln_offset ); } for_init_command = 0; // A for is nothing more than a while loop... std::pair<CommandInterface*, ConditionInterface*> comcon; comcon = conditionparser.getParseResultAsCommand(); program_builder->setCommand( comcon.first ); program_builder->startWhileStatement( comcon.second, mpositer.get_position().line - ln_offset ); delete mcondition; mcondition = 0; } void ProgramGraphParser::endforstatement() { // the last statement is a _conditional_ increment of the 'counter' if ( for_incr_command ) { program_builder->setCommand( for_incr_command ); // Since a valuechange does not add edges, we use this variant // to create one. program_builder->proceedToNext( new ConditionTrue, mpositer.get_position().line - ln_offset ); } for_incr_command = 0; program_builder->endWhileBlock(mpositer.get_position().line - ln_offset); } void ProgramGraphParser::seenprogramend() { // Fake a 'return' statement at the last line. program_builder->returnFunction( new ConditionTrue, mpositer.get_position().line - ln_offset ); program_builder->proceedToNext( mpositer.get_position().line - ln_offset ); program_list.push_back(program_builder->endFunction( mpositer.get_position().line - ln_offset ) ); // store the variables in the program's taskcontext object. valuechangeparser.store( context ); valuechangeparser.reset(); } std::vector< ProgramInterfacePtr > ProgramGraphParser::parse( iter_t& begin, iter_t end ) { // end is not used ! iter_t begin_copy = begin; skip_parser_t skip_parser = SKIP_PARSER; iter_pol_t iter_policy( skip_parser ); scanner_pol_t policies( iter_policy ); scanner_t scanner( begin, end, policies ); program_list.clear(); try { if ( ! production.parse( scanner ) ) { // This gets shown if we didn't even get the chance to throw an exception : cleanup(); throw file_parse_exception(new parse_exception_syntactic_error( " no valid input found." ), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } program_text = std::string( begin_copy, begin ); // begin is by reference. // set the program text in each program : for (std::vector<FunctionGraphPtr>::iterator it= program_list.begin();it!=program_list.end();++it) (*it)->setText( program_text ); this->cleanup(); std::vector<ProgramInterfacePtr> result; for (std::vector<FunctionGraphPtr>::iterator it= program_list.begin();it!=program_list.end();++it) result.push_back( *it ); program_list.clear(); return result; } // Catch Boost::Spirit exceptions catch( const parser_error<std::string, iter_t>& e ) { cleanup(); program_list.clear(); throw file_parse_exception( new parse_exception_syntactic_error( e.descriptor ), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } // Catch our Orocos exceptions catch( const parse_exception& e ) { cleanup(); program_list.clear(); throw file_parse_exception( e.copy(), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } } std::vector< ProgramInterfacePtr > ProgramGraphParser::parseFunction( iter_t& begin, iter_t end ) { // end is not used ! iter_t begin_copy = begin; skip_parser_t skip_parser = SKIP_PARSER; iter_pol_t iter_policy( skip_parser ); scanner_pol_t policies( iter_policy ); scanner_t scanner( begin, end, policies ); std::vector< ProgramInterfacePtr > function_list; try { if ( ! functions.parse( scanner ) ) { // This gets shown if we didn't even get the chance to throw an exception : cleanup(); throw file_parse_exception(new parse_exception_syntactic_error( " no valid input found." ), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } program_text = std::string( begin_copy, begin ); // begin is by reference. // set the program text in each function : for (funcmap::iterator it= mfuncs.begin();it!=mfuncs.end();++it) { it->second->setText( program_text ); // set text. function_list.push_back( it->second ); } this->cleanup(); return function_list; } // Catch Boost::Spirit exceptions catch( const parser_error<std::string, iter_t>& e ) { cleanup(); throw file_parse_exception( new parse_exception_syntactic_error( e.descriptor ), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } // Catch our Orocos exceptions catch( const parse_exception& e ) { cleanup(); throw file_parse_exception( e.copy(), mpositer.get_position().file, mpositer.get_position().line, mpositer.get_position().column ); } } void ProgramGraphParser::cleanup() { // after an exception, we can be in any state, so cleanup // all temp objects. delete argsparser; argsparser = 0; delete implcond; implcond = 0; delete mcondition; mcondition = 0; delete try_cond; try_cond = 0; delete for_init_command; for_init_command = 0; delete for_incr_command; for_incr_command = 0; // cleanup all functions : delete fcontext; fcontext = 0; if ( rootc == 0) return;// TaskContext* __f = rootc->getPeer("__functions");// if ( __f != 0 ) {// // first remove rootc from __f itself// rootc->disconnectPeers( __f->getName() );// delete __f;// } while ( ! mfuncs.empty() ) { mfuncs.erase( mfuncs.begin() ); } context = 0; valuechangeparser.reset(); commandparser.reset(); conditionparser.reset(); peerparser.reset(); } void ProgramGraphParser::seencommandcall() { // we get the data from commandparser CommandInterface* command; command = commandparser.getCommand(); implcond = commandparser.getImplTermCondition(); if ( !try_cmd ) { program_builder->setCommand( command ); } else { // try-wrap the asyn or dispatch command, store the result in try_cond. TryCommand* trycommand = new TryCommand( command ); // returns true if failure : TryCommandResult* tryresult = new TryCommandResult( trycommand->result(), true ); program_builder->setCommand( trycommand ); try_cond = tryresult; // go further if command failed or if command finished. implcond = new ConditionBinaryCompositeOR(try_cond->clone(), implcond ); } implcond_v.push_back(implcond); // store commandparser.reset(); } void ProgramGraphParser::seenandcall() { // retrieve a clone of the previous 'do' or 'and' command: CommandInterface* oldcmnd = program_builder->getCommand( program_builder->buildNode() )->clone(); assert(oldcmnd); // set composite command : (oldcmnd can not be zero) CommandInterface* compcmnd; // The implcond is already 'corrected' wrt result of evaluate(). implcond = commandparser.getImplTermCondition(); if ( !try_cmd ) compcmnd = new CommandBinary( oldcmnd, commandparser.getCommand() ); else { TryCommand* trycommand = new TryCommand( commandparser.getCommand() ); TryCommandResult* tryresult = new TryCommandResult( trycommand->result(), true ); compcmnd = new CommandBinary( oldcmnd, trycommand ); // chain the failure detections: if try_cond evaluates true, the catch phrase is executed // See : condition to enter the 'catch' block. try_cond = new ConditionBinaryCompositeOR( try_cond, tryresult ); // chain the implicit term. conditions: a command is implicitly done if it failed or // its implcond is true. // See : adding implicit term condition if no if .. then branches were defined. implcond = new ConditionBinaryCompositeOR( tryresult->clone(), implcond ); } program_builder->setCommand( compcmnd ); // this deletes the old command (hence the clone) ! implcond_v.push_back( implcond ); commandparser.reset(); } void ProgramGraphParser::seenvaluechange() { // some value changes generate a command, we need to add it to // the program. CommandInterface* ac = 0; std::vector<CommandInterface*> acv = valuechangeparser.assignCommands(); // and not forget to reset().. valuechangeparser.clear(); if ( acv.size() == 1) { ac = acv.front(); } else if (acv.size() > 1) { ac = new CommandComposite(acv); } if (ac) { program_builder->setCommand( ac ); // Since a valuechange does not add edges, we use this variant // to create one. program_builder->proceedToNext( new ConditionTrue, mpositer.get_position().line - ln_offset ); } } void ProgramGraphParser::seencallfunclabel( iter_t begin, iter_t end ) { // Used for "call xyz" // lookup mcallfunc seenfuncidentifier( begin, end ); assert( mcondition ); assert( mcallfunc ); program_builder->appendFunction( mcondition, mcallfunc, callfnargs); mcondition = 0; } void ProgramGraphParser::seencontinue( ) { // Used for "continue" assert ( mcondition ); // connect to next node under given condition. program_builder->addConditionEdge( mcondition, program_builder->nextNode() ); mcondition = 0; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -