Fix possible crash and issues when a incorrect fp lib table is loaded:

correct lines are loaded, and pcbnew / eeschema is no more aborted.
Fixes: lp:1701627
https://bugs.launchpad.net/kicad/+bug/1701627
This commit is contained in:
jean-pierre charras 2017-07-12 18:41:10 +02:00
parent 459fd9e584
commit c93ab4d5da
4 changed files with 26 additions and 11 deletions

View File

@ -68,12 +68,14 @@ FP_LIB_TABLE::FP_LIB_TABLE( FP_LIB_TABLE* aFallBackTable ) :
void FP_LIB_TABLE::Parse( LIB_TABLE_LEXER* in ) void FP_LIB_TABLE::Parse( LIB_TABLE_LEXER* in )
{ {
T tok; T tok;
wxString errMsg; // to collect error messages
// This table may be nested within a larger s-expression, or not. // This table may be nested within a larger s-expression, or not.
// Allow for parser of that optional containing s-epression to have looked ahead. // Allow for parser of that optional containing s-epression to have looked ahead.
if( in->CurTok() != T_fp_lib_table ) if( in->CurTok() != T_fp_lib_table )
{ {
in->NeedLEFT(); in->NeedLEFT();
if( ( tok = in->NextTok() ) != T_fp_lib_table ) if( ( tok = in->NextTok() ) != T_fp_lib_table )
in->Expecting( T_fp_lib_table ); in->Expecting( T_fp_lib_table );
} }
@ -88,10 +90,6 @@ void FP_LIB_TABLE::Parse( LIB_TABLE_LEXER* in )
if( tok != T_LEFT ) if( tok != T_LEFT )
in->Expecting( T_LEFT ); in->Expecting( T_LEFT );
// in case there is a "row integrity" error, tell where later.
int lineNum = in->CurLineNumber();
int offset = in->CurOffset();
if( ( tok = in->NextTok() ) != T_lib ) if( ( tok = in->NextTok() ) != T_lib )
in->Expecting( T_lib ); in->Expecting( T_lib );
@ -175,14 +173,22 @@ void FP_LIB_TABLE::Parse( LIB_TABLE_LEXER* in )
// use doReplace in InsertRow(). (However a fallBack table can have a // use doReplace in InsertRow(). (However a fallBack table can have a
// conflicting nickName and ours will supercede that one since in // conflicting nickName and ours will supercede that one since in
// FindLib() we search this table before any fall back.) // FindLib() we search this table before any fall back.)
wxString nickname = row->GetNickName(); // store it to be able to used it
// after row deletion if an error occurs
if( !InsertRow( row.release() ) ) if( !InsertRow( row.release() ) )
{ {
wxString msg = wxString::Format( wxString msg = wxString::Format(
_( "'%s' is a duplicate footprint library nickName" ), _( "'%s' is a duplicate footprint library nickName" ),
GetChars( row->GetNickName() ) ); GetChars( nickname ) );
THROW_PARSE_ERROR( msg, in->CurSource(), in->CurLine(), lineNum, offset ); if( !errMsg.IsEmpty() )
errMsg << '\n';
errMsg << msg;
} }
} }
if( !errMsg.IsEmpty() )
THROW_IO_ERROR( errMsg );
} }

View File

@ -264,12 +264,16 @@ bool IFACE::OnKifaceStart( PGM_BASE* aProgram, int aCtlBits )
} }
catch( const IO_ERROR& ioe ) catch( const IO_ERROR& ioe )
{ {
// if we are here, a incorrect global symbol library table was found.
// Incorrect global symbol library table is not a fatal error:
// the user just has to edit the (partially) loaded table.
wxString msg = wxString::Format( _( wxString msg = wxString::Format( _(
"An error occurred attempting to load the global symbol library table:\n\n%s" ), "An error occurred attempting to load the global symbol library table:"
"\n\n%s\n\n"
"Please edit this global symbol library table in Preferences menu" ),
GetChars( ioe.What() ) GetChars( ioe.What() )
); );
DisplayError( NULL, msg ); DisplayError( NULL, msg );
return false;
} }
return true; return true;

View File

@ -185,11 +185,13 @@ void SYMBOL_LIB_TABLE::Parse( LIB_TABLE_LEXER* in )
// use doReplace in InsertRow(). (However a fallBack table can have a // use doReplace in InsertRow(). (However a fallBack table can have a
// conflicting nickName and ours will supercede that one since in // conflicting nickName and ours will supercede that one since in
// FindLib() we search this table before any fall back.) // FindLib() we search this table before any fall back.)
wxString nickname = row->GetNickName(); // store it to be able to used it
// after row deletion if an error occurs
if( !InsertRow( row.release() ) ) if( !InsertRow( row.release() ) )
{ {
wxString msg = wxString::Format( wxString msg = wxString::Format(
_( "'%s' is a duplicate symbol library nickname" ), _( "'%s' is a duplicate symbol library nickname" ),
GetChars( row->GetNickName() ) ); GetChars( nickname ) );
THROW_PARSE_ERROR( msg, in->CurSource(), in->CurLine(), lineNum, offset ); THROW_PARSE_ERROR( msg, in->CurSource(), in->CurLine(), lineNum, offset );
} }
} }

View File

@ -354,13 +354,16 @@ bool IFACE::OnKifaceStart( PGM_BASE* aProgram, int aCtlBits )
} }
catch( const IO_ERROR& ioe ) catch( const IO_ERROR& ioe )
{ {
// if we are here, a incorrect global footprint library table was found.
// Incorrect global footprint library table is not a fatal error:
// the user just has to edit the (partially) loaded table.
wxString msg = wxString::Format( _( wxString msg = wxString::Format( _(
"An error occurred attempting to load the global footprint library " "An error occurred attempting to load the global footprint library "
"table:\n\n%s" ), "table:\n\n%s\n\n"
"Please edit this global footprint library table in Preferences menu" ),
GetChars( ioe.What() ) GetChars( ioe.What() )
); );
DisplayError( NULL, msg ); DisplayError( NULL, msg );
return false;
} }
#if defined(KICAD_SCRIPTING) #if defined(KICAD_SCRIPTING)