Commit e53b79ec authored by Simon Morlat's avatar Simon Morlat

optimizations. parsing time around 5ms for a SIP register.

parent a45ed80d
...@@ -176,16 +176,20 @@ shared_ptr<Loop> Foundation::loop(){ ...@@ -176,16 +176,20 @@ shared_ptr<Loop> Foundation::loop(){
return make_shared<Loop>(); return make_shared<Loop>();
} }
/* Literal::Literal(const string& lit) : mLiteral(tolower(lit)){
* TODO: could be optimized() with strcmp with a specialized Recognizer ! mLiteralSize=mLiteral.size();
*/ }
shared_ptr<Recognizer> Utils::literal(const string & lt){
shared_ptr<Sequence> seq=Foundation::sequence(); size_t Literal::_feed(const shared_ptr< ParserContextBase >& ctx, const string& input, size_t pos){
size_t i; size_t i;
for (i=0;i<lt.size();++i){ for(i=0;i<mLiteralSize;++i){
seq->addRecognizer(Foundation::charRecognizer(lt[i],false)); if (::tolower(input[pos+i])!=mLiteral[i]) return string::npos;
} }
return seq; return mLiteralSize;
}
shared_ptr<Recognizer> Utils::literal(const string & lt){
return make_shared<Literal>(lt);
} }
shared_ptr<Recognizer> Utils::char_range(int begin, int end){ shared_ptr<Recognizer> Utils::char_range(int begin, int end){
...@@ -253,12 +257,20 @@ void Grammar::_extendRule(const string &argname, const shared_ptr<Recognizer> &r ...@@ -253,12 +257,20 @@ void Grammar::_extendRule(const string &argname, const shared_ptr<Recognizer> &r
} }
} }
shared_ptr<Recognizer> Grammar::getRule(const string &argname){ shared_ptr<Recognizer> Grammar::findRule(const string &argname){
shared_ptr<Recognizer> ret;
string name=tolower(argname); string name=tolower(argname);
auto it=mRules.find(name); auto it=mRules.find(name);
if (it!=mRules.end()){ if (it!=mRules.end()){
shared_ptr<RecognizerPointer> pointer=dynamic_pointer_cast<RecognizerPointer>((*it).second); return (*it).second;
}
return NULL;
}
shared_ptr<Recognizer> Grammar::getRule(const string &argname){
shared_ptr<Recognizer> ret=findRule(argname);
if (ret){
shared_ptr<RecognizerPointer> pointer=dynamic_pointer_cast<RecognizerPointer>(ret);
if (pointer){ if (pointer){
if (pointer->getPointed()){/*if pointer is defined return the pointed value directly*/ if (pointer->getPointed()){/*if pointer is defined return the pointed value directly*/
return pointer->getPointed(); return pointer->getPointed();
...@@ -266,9 +278,10 @@ shared_ptr<Recognizer> Grammar::getRule(const string &argname){ ...@@ -266,9 +278,10 @@ shared_ptr<Recognizer> Grammar::getRule(const string &argname){
return pointer; return pointer;
} }
} }
return (*it).second; return ret;
}else{/*the rule doesn't exist yet: return a pointer*/ }else{/*the rule doesn't exist yet: return a pointer*/
ret=make_shared<RecognizerPointer>(); ret=make_shared<RecognizerPointer>();
string name=tolower(argname);
ret->setName(string("@")+name); ret->setName(string("@")+name);
mRules[name]=ret; mRules[name]=ret;
} }
......
...@@ -38,15 +38,6 @@ private: ...@@ -38,15 +38,6 @@ private:
bool mCaseSensitive; bool mCaseSensitive;
}; };
/*this is an optimization of a selector with multiple individual char recognizer*/
class CharRange : public Recognizer{
public:
CharRange(int begin, int end);
private:
virtual size_t _feed(const shared_ptr<ParserContextBase> &ctx, const string &input, size_t pos);
int mBegin,mEnd;
};
class Selector : public Recognizer{ class Selector : public Recognizer{
public: public:
Selector(); Selector();
...@@ -92,6 +83,24 @@ public: ...@@ -92,6 +83,24 @@ public:
static shared_ptr<Loop> loop(); static shared_ptr<Loop> loop();
}; };
/*this is an optimization of a selector with multiple individual char recognizer*/
class CharRange : public Recognizer{
public:
CharRange(int begin, int end);
private:
virtual size_t _feed(const shared_ptr<ParserContextBase> &ctx, const string &input, size_t pos);
int mBegin,mEnd;
};
class Literal : public Recognizer{
public:
Literal(const string &lit);
private:
virtual size_t _feed(const shared_ptr<ParserContextBase> &ctx, const string &input, size_t pos);
string mLiteral;
size_t mLiteralSize;
};
class Utils{ class Utils{
public: public:
static shared_ptr<Recognizer> literal(const string & lt); static shared_ptr<Recognizer> literal(const string & lt);
...@@ -125,6 +134,10 @@ public: ...@@ -125,6 +134,10 @@ public:
_extendRule(name, rule); _extendRule(name, rule);
return rule; return rule;
} }
shared_ptr<Recognizer> findRule(const string &name);
/*
* getRule() never returns NULL. If the rule is not (yet) defined, it returns an undefined pointer, that will be set later if the rule gets defined.
**/
shared_ptr<Recognizer> getRule(const string &name); shared_ptr<Recognizer> getRule(const string &name);
bool isComplete()const; bool isComplete()const;
int getNumRules()const; int getNumRules()const;
......
...@@ -78,8 +78,8 @@ HandlerContext<_parserElementT>::HandlerContext(const shared_ptr<ParserHandlerBa ...@@ -78,8 +78,8 @@ HandlerContext<_parserElementT>::HandlerContext(const shared_ptr<ParserHandlerBa
} }
template <typename _parserElementT> template <typename _parserElementT>
void HandlerContext<_parserElementT>::setChild(const string &subrule_name, size_t begin, size_t count, const shared_ptr<HandlerContext<_parserElementT>> &child){ void HandlerContext<_parserElementT>::setChild(unsigned int subrule_id, size_t begin, size_t count, const shared_ptr<HandlerContext<_parserElementT>> &child){
auto collector=mHandler->getCollector(subrule_name); auto collector=mHandler->getCollector(subrule_id);
if (collector){ if (collector){
mAssignments.push_back(Assignment<_parserElementT>(collector, begin, count, child)); mAssignments.push_back(Assignment<_parserElementT>(collector, begin, count, child));
} }
...@@ -126,12 +126,17 @@ ParserHandlerBase<_parserElementT>::ParserHandlerBase(const Parser<_parserElemen ...@@ -126,12 +126,17 @@ ParserHandlerBase<_parserElementT>::ParserHandlerBase(const Parser<_parserElemen
template <typename _parserElementT> template <typename _parserElementT>
void ParserHandlerBase<_parserElementT>::installCollector(const string &rulename, const shared_ptr<AbstractCollector<_parserElementT>> &collector){ void ParserHandlerBase<_parserElementT>::installCollector(const string &rulename, const shared_ptr<AbstractCollector<_parserElementT>> &collector){
mCollectors[tolower(rulename)]=collector; shared_ptr<Recognizer> rec=mParser.mGrammar->findRule(rulename);
if (!rec){
cerr<<"There is no rule '"<<rulename<<"' in the grammar."<<endl;
return;
}
mCollectors[rec->getId()]=collector;
} }
template <typename _parserElementT> template <typename _parserElementT>
const shared_ptr<AbstractCollector<_parserElementT>> & ParserHandlerBase<_parserElementT>::getCollector(const string &rulename)const{ const shared_ptr<AbstractCollector<_parserElementT>> & ParserHandlerBase<_parserElementT>::getCollector(unsigned int rule_id)const{
auto it=mCollectors.find(rulename); auto it=mCollectors.find(rule_id);
if (it!=mCollectors.end()) return (*it).second; if (it!=mCollectors.end()) return (*it).second;
return mParser.mNullCollector; return mParser.mNullCollector;
} }
...@@ -157,7 +162,7 @@ template <typename _parserElementT> ...@@ -157,7 +162,7 @@ template <typename _parserElementT>
ParserLocalContext ParserContext<_parserElementT>::_beginParse(const shared_ptr<Recognizer> &rec){ ParserLocalContext ParserContext<_parserElementT>::_beginParse(const shared_ptr<Recognizer> &rec){
shared_ptr<HandlerContextBase> ctx; shared_ptr<HandlerContextBase> ctx;
auto h=mParser.getHandler(rec->getName()); auto h=mParser.getHandler(rec->getId());
if (h){ if (h){
ctx=h->createContext(); ctx=h->createContext();
mHandlerStack.push_back(static_pointer_cast<HandlerContext<_parserElementT>>(ctx)); mHandlerStack.push_back(static_pointer_cast<HandlerContext<_parserElementT>>(ctx));
...@@ -172,7 +177,7 @@ void ParserContext<_parserElementT>::_endParse(const ParserLocalContext &localct ...@@ -172,7 +177,7 @@ void ParserContext<_parserElementT>::_endParse(const ParserLocalContext &localct
if (count!=string::npos && count>0){ if (count!=string::npos && count>0){
if (!mHandlerStack.empty()){ if (!mHandlerStack.empty()){
/*assign object to parent */ /*assign object to parent */
mHandlerStack.back()->setChild(localctx.mRecognizer->getName(), begin, count, mHandlerStack.back()->setChild(localctx.mRecognizer->getId(), begin, count,
static_pointer_cast<HandlerContext< _parserElementT >> (localctx.mHandlerContext)); static_pointer_cast<HandlerContext< _parserElementT >> (localctx.mHandlerContext));
}else{ }else{
...@@ -183,7 +188,7 @@ void ParserContext<_parserElementT>::_endParse(const ParserLocalContext &localct ...@@ -183,7 +188,7 @@ void ParserContext<_parserElementT>::_endParse(const ParserLocalContext &localct
}else{ }else{
if (count!=string::npos && count>0){ if (count!=string::npos && count>0){
/*assign string to parent */ /*assign string to parent */
mHandlerStack.back()->setChild(localctx.mRecognizer->getName(), begin, count, NULL); mHandlerStack.back()->setChild(localctx.mRecognizer->getId(), begin, count, NULL);
}else{ }else{
mHandlerStack.back()->undoAssignments(localctx.mAssignmentPos); mHandlerStack.back()->undoAssignments(localctx.mAssignmentPos);
} }
...@@ -270,15 +275,20 @@ Parser<_parserElementT>::Parser(const shared_ptr<Grammar> &grammar) : mGrammar(g ...@@ -270,15 +275,20 @@ Parser<_parserElementT>::Parser(const shared_ptr<Grammar> &grammar) : mGrammar(g
} }
template <typename _parserElementT> template <typename _parserElementT>
shared_ptr<ParserHandlerBase<_parserElementT>> &Parser<_parserElementT>::getHandler(const string &rulename){ shared_ptr<ParserHandlerBase<_parserElementT>> &Parser<_parserElementT>::getHandler(unsigned int rule_id){
auto it=mHandlers.find(rulename); auto it=mHandlers.find(rule_id);
if (it==mHandlers.end()) return mNullHandler; if (it==mHandlers.end()) return mNullHandler;
return (*it).second; return (*it).second;
} }
template <typename _parserElementT> template <typename _parserElementT>
void Parser<_parserElementT>::installHandler(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler){ void Parser<_parserElementT>::installHandler(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler){
mHandlers[handler->getRulename()]=handler; shared_ptr<Recognizer> rec=mGrammar->findRule(handler->getRulename());
if (rec==NULL){
cerr<<"There is no rule '"<<handler->getRulename()<<"' in the grammar."<<endl;
return;
}
mHandlers[rec->getId()]=handler;
} }
template <typename _parserElementT> template <typename _parserElementT>
......
...@@ -62,9 +62,9 @@ public: ...@@ -62,9 +62,9 @@ public:
} }
protected: protected:
void installCollector(const string &rulename, const shared_ptr<AbstractCollector<_parserElementT>> &collector); void installCollector(const string &rulename, const shared_ptr<AbstractCollector<_parserElementT>> &collector);
const shared_ptr<AbstractCollector<_parserElementT>> &getCollector(const string &rulename)const; const shared_ptr<AbstractCollector<_parserElementT>> &getCollector(unsigned int rule_id)const;
private: private:
map<string, shared_ptr<AbstractCollector<_parserElementT>> > mCollectors; map<unsigned int, shared_ptr<AbstractCollector<_parserElementT>> > mCollectors;
const Parser<_parserElementT> &mParser; const Parser<_parserElementT> &mParser;
string mRulename; string mRulename;
}; };
...@@ -121,7 +121,7 @@ template <typename _parserElementT> ...@@ -121,7 +121,7 @@ template <typename _parserElementT>
class HandlerContext : public HandlerContextBase{ class HandlerContext : public HandlerContextBase{
public: public:
HandlerContext(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler); HandlerContext(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler);
void setChild(const string &subrule_name, size_t begin, size_t count, const shared_ptr<HandlerContext> &child); void setChild(unsigned int subrule_id, size_t begin, size_t count, const shared_ptr<HandlerContext> &child);
_parserElementT realize(const string &input, size_t begin, size_t count); _parserElementT realize(const string &input, size_t begin, size_t count);
shared_ptr<HandlerContext<_parserElementT>> branch(); shared_ptr<HandlerContext<_parserElementT>> branch();
void merge(const shared_ptr<HandlerContext<_parserElementT>> &other); void merge(const shared_ptr<HandlerContext<_parserElementT>> &other);
...@@ -195,10 +195,10 @@ public: ...@@ -195,10 +195,10 @@ public:
} }
_parserElementT parseInput(const string &rulename, const string &input, size_t *parsed_size); _parserElementT parseInput(const string &rulename, const string &input, size_t *parsed_size);
private: private:
shared_ptr<ParserHandlerBase<_parserElementT>> &getHandler(const string &rulename); shared_ptr<ParserHandlerBase<_parserElementT>> &getHandler(unsigned int);
void installHandler(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler); void installHandler(const shared_ptr<ParserHandlerBase<_parserElementT>> &handler);
shared_ptr<Grammar> mGrammar; shared_ptr<Grammar> mGrammar;
map<string, shared_ptr<ParserHandlerBase<_parserElementT>>> mHandlers; map<unsigned int, shared_ptr<ParserHandlerBase<_parserElementT>>> mHandlers;
shared_ptr<ParserHandlerBase<_parserElementT>> mNullHandler; shared_ptr<ParserHandlerBase<_parserElementT>> mNullHandler;
shared_ptr<AbstractCollector<_parserElementT>> mNullCollector; shared_ptr<AbstractCollector<_parserElementT>> mNullCollector;
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment