diff --git a/common/dsnlexer.cpp b/common/dsnlexer.cpp index 151fa6d405..66fb642bd8 100644 --- a/common/dsnlexer.cpp +++ b/common/dsnlexer.cpp @@ -192,6 +192,18 @@ wxString DSNLEXER::GetTokenString( int aTok ) } +bool DSNLEXER::IsSymbol( int aTok ) +{ + // This is static and not inline to reduce code space. + + // if aTok is >= 0, then it is a coincidental match to a keyword. + return aTok==DSN_SYMBOL + || aTok==DSN_STRING + || aTok>=0 + ; +} + + void DSNLEXER::ThrowIOError( wxString aText, int charOffset ) throw (IOError) { // append to aText, do not overwrite @@ -235,6 +247,39 @@ void DSNLEXER::Unexpected( const wxString& text ) throw( IOError ) } +void DSNLEXER::NeedLEFT() throw( IOError ) +{ + int tok = NextTok(); + if( tok != DSN_LEFT ) + Expecting( DSN_LEFT ); +} + + +void DSNLEXER::NeedRIGHT() throw( IOError ) +{ + int tok = NextTok(); + if( tok != DSN_RIGHT ) + Expecting( DSN_RIGHT ); +} + + +int DSNLEXER::NeedSYMBOL() throw( IOError ) +{ + int tok = NextTok(); + if( !IsSymbol( tok ) ) + Expecting( DSN_SYMBOL ); + return tok; +} + + +int DSNLEXER::NeedSYMBOLorNUMBER() throw( IOError ) +{ + int tok = NextTok(); + if( !IsSymbol( tok ) && tok!=DSN_NUMBER ) + Expecting( _("symbol|number") ); + return tok; +} + /** * Function isspace * strips the upper bits of the int to ensure the value passed to ::isspace() is diff --git a/eeschema/template_fieldnames.cpp b/eeschema/template_fieldnames.cpp index a4a4fd01b1..daa21419db 100644 --- a/eeschema/template_fieldnames.cpp +++ b/eeschema/template_fieldnames.cpp @@ -50,35 +50,29 @@ void TEMPLATE_FIELDNAME::Parse( DSNLEXER* in ) throw( IOError ) { TFIELD_T tok; - if( (tok = (TFIELD_T) in->NextTok()) != T_LEFT ) - in->Expecting( T_LEFT ); + in->NeedLEFT(); // begin (name ...) if( (tok = (TFIELD_T) in->NextTok()) != T_name ) in->Expecting( T_name ); - if( (tok = (TFIELD_T) in->NextTok()) != T_SYMBOL && tok!=T_STRING ) - in->Expecting( _("field's name") ); + in->NeedSYMBOLorNUMBER(); m_Name = CONV_FROM_UTF8( in->CurText() ); - if( (tok = (TFIELD_T) in->NextTok()) != T_RIGHT ) - in->Expecting( T_RIGHT ); + in->NeedRIGHT(); // end (name ...) while( (tok = (TFIELD_T) in->NextTok() ) != T_RIGHT && tok != T_EOF ) { + // "visible" has no '(' prefix, "value" does, so T_LEFT is optional. if( tok == T_LEFT ) tok = (TFIELD_T) in->NextTok(); switch( tok ) { case T_value: - if( (tok = (TFIELD_T) in->NextTok()) != T_SYMBOL && tok!=T_STRING ) - in->Expecting( _("field's value") ); - + in->NeedSYMBOLorNUMBER(); m_Value = CONV_FROM_UTF8( in->CurText() ); - - if( (tok = (TFIELD_T) in->NextTok()) != T_RIGHT ) - in->Expecting( T_RIGHT ); + in->NeedRIGHT(); break; case T_visible: @@ -86,7 +80,7 @@ void TEMPLATE_FIELDNAME::Parse( DSNLEXER* in ) throw( IOError ) break; default: - in->Unexpected( CONV_FROM_UTF8( in->CurText() ) ); + in->Expecting( wxT( "value|visible" ) ); break; } } diff --git a/include/dsnlexer.h b/include/dsnlexer.h index 363b44d259..acda44614a 100644 --- a/include/dsnlexer.h +++ b/include/dsnlexer.h @@ -208,10 +208,9 @@ public: return old; } - /** * Function NextTok - * returns the next token found in the input file or T_EOF when reaching + * returns the next token found in the input file or DSN_EOF when reaching * the end of file. Users should wrap this function to return an enum * to aid in grammar debugging while running under a debugger, but leave * this lower level function returning an int (so the enum does not collide @@ -221,6 +220,13 @@ public: */ int NextTok() throw (IOError); + /** + * Function IsSymbol + * tests a token to see if it is a symbol. This means it cannot be a + * special delimiter character such as DSN_LEFT, DSN_RIGHT, DSN_QUOTE, etc. It may + * however, coincidentally match a keyword and still be a symbol. + */ + static bool IsSymbol( int aTok ); /** * Function ThrowIOError @@ -264,6 +270,42 @@ public: */ void Unexpected( const wxString& aErrorMsg ) throw( IOError ); + /** + * Function NeedLEFT + * calls NextTok() and then verifies that the token read in is a DSN_LEFT. + * If it is not, an IOError is thrown. + * @throw IOError, if the next token is not a DSN_LEFT + */ + void NeedLEFT() throw( IOError ); + + /** + * Function NeedRIGHT + * calls NextTok() and then verifies that the token read in is a DSN_RIGHT. + * If it is not, an IOError is thrown. + * @throw IOError, if the next token is not a DSN_RIGHT + */ + void NeedRIGHT() throw( IOError ); + + /** + * Function NeedSYMBOL + * calls NextTok() and then verifies that the token read in + * satisfies bool IsSymbol(). + * If not, an IOError is thrown. + * @return int - the actual token read in. + * @throw IOError, if the next token does not satisfy IsSymbol() + */ + int NeedSYMBOL() throw( IOError ); + + /** + * Function NeedSYMBOLorNUMBER + * calls NextTok() and then verifies that the token read in + * satisfies bool IsSymbol() or tok==DSN_NUMBER. + * If not, an IOError is thrown. + * @return int - the actual token read in. + * @throw IOError, if the next token does not satisfy the above test + */ + int NeedSYMBOLorNUMBER() throw( IOError ); + /** * Function GetTokenText * returns the C string representation of a DSN_T value. diff --git a/pcbnew/specctra.cpp b/pcbnew/specctra.cpp index f2eee90bd9..13b52b618e 100644 --- a/pcbnew/specctra.cpp +++ b/pcbnew/specctra.cpp @@ -547,21 +547,12 @@ void SPECCTRA_DB::ThrowIOError( const wxChar* fmt, ... ) throw( IOError ) } -void SPECCTRA_DB::expecting( DSN_T aTok ) throw( IOError ) -{ - lexer->Expecting( aTok ); -} - void SPECCTRA_DB::expecting( const char* text ) throw( IOError ) { wxString errText = CONV_FROM_UTF8( text ); lexer->Expecting( errText ); } -void SPECCTRA_DB::unexpected( DSN_T aTok ) throw( IOError ) -{ - lexer->Unexpected( aTok ); -} void SPECCTRA_DB::unexpected( const char* text ) throw( IOError ) { @@ -576,47 +567,6 @@ DSN_T SPECCTRA_DB::nextTok() return ret; } - -bool SPECCTRA_DB::isSymbol( DSN_T aTok ) -{ - // if aTok is >= 0, then it might be a coincidental match to a keyword. - return aTok==T_SYMBOL - || aTok==T_STRING - || aTok>=0 - ; -} - - -void SPECCTRA_DB::needLEFT() throw( IOError ) -{ - DSN_T tok = nextTok(); - if( tok != T_LEFT ) - expecting( T_LEFT ); -} - -void SPECCTRA_DB::needRIGHT() throw( IOError ) -{ - DSN_T tok = nextTok(); - if( tok != T_RIGHT ) - expecting( T_RIGHT ); -} - -DSN_T SPECCTRA_DB::needSYMBOL() throw( IOError ) -{ - DSN_T tok = nextTok(); - if( !isSymbol( tok ) ) - expecting( T_SYMBOL ); - return tok; -} - -DSN_T SPECCTRA_DB::needSYMBOLorNUMBER() throw( IOError ) -{ - DSN_T tok = nextTok(); - if( !isSymbol( tok ) && tok!=T_NUMBER ) - expecting( "symbol|number" ); - return tok; -} - void SPECCTRA_DB::readCOMPnPIN( std::string* component_id, std::string* pin_id ) throw( IOError ) { DSN_T tok; diff --git a/pcbnew/specctra.h b/pcbnew/specctra.h index 7039c4cf65..4b27d03988 100644 --- a/pcbnew/specctra.h +++ b/pcbnew/specctra.h @@ -4039,15 +4039,16 @@ class SPECCTRA_DB : public OUTPUTFORMATTER */ DSN_T nextTok(); - /** * Function isSymbol * tests a token to see if it is a symbol. This means it cannot be a * special delimiter character such as T_LEFT, T_RIGHT, T_QUOTE, etc. It may * however, coincidentally match a keyword and still be a symbol. */ - static bool isSymbol( DSN_T aTok ); - + static bool isSymbol( DSN_T aTok ) + { + return DSNLEXER::IsSymbol( aTok ); + } /** * Function needLEFT @@ -4055,7 +4056,10 @@ class SPECCTRA_DB : public OUTPUTFORMATTER * If it is not, an IOError is thrown. * @throw IOError, if the next token is not a T_LEFT */ - void needLEFT() throw( IOError ); + void needLEFT() throw( IOError ) + { + lexer->NeedLEFT(); + } /** * Function needRIGHT @@ -4063,7 +4067,10 @@ class SPECCTRA_DB : public OUTPUTFORMATTER * If it is not, an IOError is thrown. * @throw IOError, if the next token is not a T_RIGHT */ - void needRIGHT() throw( IOError ); + void needRIGHT() throw( IOError ) + { + lexer->NeedRIGHT(); + } /** * Function needSYMBOL @@ -4073,7 +4080,10 @@ class SPECCTRA_DB : public OUTPUTFORMATTER * @return DSN_T - the actual token read in. * @throw IOError, if the next token does not satisfy isSymbol() */ - DSN_T needSYMBOL() throw( IOError ); + DSN_T needSYMBOL() throw( IOError ) + { + return (DSN_T) lexer->NeedSYMBOL(); + } /** * Function needSYMBOLorNUMBER @@ -4083,7 +4093,10 @@ class SPECCTRA_DB : public OUTPUTFORMATTER * @return DSN_T - the actual token read in. * @throw IOError, if the next token does not satisfy the above test */ - DSN_T needSYMBOLorNUMBER() throw( IOError ); + DSN_T needSYMBOLorNUMBER() throw( IOError ) + { + return (DSN_T) lexer->NeedSYMBOLorNUMBER(); + } /** * Function readCOMPnPIN @@ -4127,9 +4140,15 @@ class SPECCTRA_DB : public OUTPUTFORMATTER * @param int is the token type which was expected at the current input location. * @throw IOError with the location within the input file of the problem. */ - void expecting( DSN_T aTok ) throw( IOError ); + void expecting( DSN_T aTok ) throw( IOError ) + { + lexer->Expecting( aTok ); + } + void unexpected( DSN_T aTok ) throw( IOError ) + { + lexer->Unexpected( aTok ); + } void expecting( const char* text ) throw( IOError ); - void unexpected( DSN_T aTok ) throw( IOError ); void unexpected( const char* text ) throw( IOError ); void doPCB( PCB* growth ) throw(IOError);