Fix netlist error when editing schematic symbols in place.
Fixes https://gitlab.com/kicad/code/kicad/-/issues/8798
This commit is contained in:
parent
5155093ec0
commit
f485ba9338
|
@ -72,7 +72,10 @@ wxString NETLIST_EXPORTER_BASE::MakeCommandLine( const wxString& aFormatString,
|
|||
|
||||
SCH_SYMBOL* NETLIST_EXPORTER_BASE::findNextSymbol( EDA_ITEM* aItem, SCH_SHEET_PATH* aSheetPath )
|
||||
{
|
||||
wxString ref;
|
||||
wxCHECK( aItem, nullptr );
|
||||
wxCHECK( aSheetPath, nullptr );
|
||||
|
||||
wxString ref;
|
||||
|
||||
if( aItem->Type() != SCH_SYMBOL_T )
|
||||
return nullptr;
|
||||
|
@ -87,16 +90,16 @@ SCH_SYMBOL* NETLIST_EXPORTER_BASE::findNextSymbol( EDA_ITEM* aItem, SCH_SHEET_PA
|
|||
if( ref[0] == wxChar( '#' ) )
|
||||
return nullptr;
|
||||
|
||||
// if( symbol->m_FlagControlMulti == 1 )
|
||||
// continue; /* yes */
|
||||
// removed because with multiple instances of one schematic (several sheets pointing to
|
||||
// 1 screen), this will be erroneously be toggled.
|
||||
SCH_SCREEN* screen = aSheetPath->LastScreen();
|
||||
|
||||
if( !symbol->GetLibSymbolRef() )
|
||||
return nullptr;
|
||||
wxCHECK( screen, nullptr );
|
||||
|
||||
LIB_SYMBOL* libSymbol = screen->GetLibSymbols()[ symbol->GetSchSymbolLibraryName() ];
|
||||
|
||||
wxCHECK( libSymbol, nullptr );
|
||||
|
||||
// If symbol is a "multi parts per package" type
|
||||
if( symbol->GetLibSymbolRef()->GetUnitCount() > 1 )
|
||||
if( libSymbol->GetUnitCount() > 1 )
|
||||
{
|
||||
// test if this reference has already been processed, and if so skip
|
||||
if( m_referencesAlreadyFound.Lookup( ref ) )
|
||||
|
@ -104,7 +107,7 @@ SCH_SYMBOL* NETLIST_EXPORTER_BASE::findNextSymbol( EDA_ITEM* aItem, SCH_SHEET_PA
|
|||
}
|
||||
|
||||
// record the usage of this library symbol entry.
|
||||
m_libParts.insert( symbol->GetLibSymbolRef().get() ); // rejects non-unique pointers
|
||||
m_libParts.insert( libSymbol ); // rejects non-unique pointers
|
||||
|
||||
return symbol;
|
||||
}
|
||||
|
|
|
@ -90,72 +90,6 @@ struct PIN_INFO
|
|||
*/
|
||||
class NETLIST_EXPORTER_BASE
|
||||
{
|
||||
protected:
|
||||
/// Used to temporarily store and filter the list of pins of a schematic symbol when
|
||||
/// generating schematic symbol data in netlist (comp section). No ownership of members.
|
||||
/// TODO(snh): Descope this object
|
||||
std::vector<PIN_INFO> m_sortedSymbolPinList;
|
||||
|
||||
/// Used for "multiple symbols per package" symbols to avoid processing a lib symbol more than
|
||||
/// once
|
||||
UNIQUE_STRINGS m_referencesAlreadyFound;
|
||||
|
||||
/// unique library symbols used. LIB_SYMBOL items are sorted by names
|
||||
std::set<LIB_SYMBOL*, LIB_SYMBOL_LESS_THAN> m_libParts;
|
||||
|
||||
/// The schematic we're generating a netlist for
|
||||
SCHEMATIC_IFACE* m_schematic;
|
||||
|
||||
/// The schematic's CurrentSheet when we entered. Restore on exiting.
|
||||
SCH_SHEET_PATH m_savedCurrentSheet;
|
||||
|
||||
/**
|
||||
* Find a symbol from the DrawList and builds its pin list in m_sortedSymbolPinList.
|
||||
*
|
||||
* This list is sorted by pin number. The symbol is the next actual symbol after \a aSymbol.
|
||||
* Power symbols and virtual symbols that have their reference designators starting with
|
||||
* '#' are skipped.
|
||||
* if aKeepUnconnectedPins = false, unconnected pins will be removed from list
|
||||
* but usually we need all pins in netlists.
|
||||
*/
|
||||
void CreatePinList( SCH_SYMBOL* aSymbol, SCH_SHEET_PATH* aSheetPath,
|
||||
bool aKeepUnconnectedPins );
|
||||
|
||||
/**
|
||||
* Check if the given symbol should be processed for netlisting.
|
||||
*
|
||||
* Prevent processing multi-unit symbols more than once, etc.
|
||||
*
|
||||
* @param aItem is a symbol to check
|
||||
* @param aSheetPath is the sheet to check the symbol for
|
||||
* @return the symbol if it should be processed, or nullptr
|
||||
*/
|
||||
SCH_SYMBOL* findNextSymbol( EDA_ITEM* aItem, SCH_SHEET_PATH* aSheetPath );
|
||||
|
||||
/**
|
||||
* Erase duplicate pins from m_sortedSymbolPinList (i.e. set pointer in this list to NULL).
|
||||
*
|
||||
* (This is a list of pins found in the whole schematic, for a single symbol.) These
|
||||
* duplicate pins were put in list because some pins (power pins...) are found more than
|
||||
* once when in "multiple symbols per package" symbols. For instance, a 74ls00 has 4 symbols,
|
||||
* and therefore the VCC pin and GND pin appears 4 times in the list.
|
||||
* Note: this list *MUST* be sorted by pin number (.m_PinNum member value)
|
||||
* Also set the m_Flag member of "removed" NETLIST_OBJECT pin item to 1
|
||||
*/
|
||||
void eraseDuplicatePins();
|
||||
|
||||
/**
|
||||
* Find all units for symbols with multiple symbols per package.
|
||||
*
|
||||
* Search the entire design for all units of \a aSymbol based on matching reference
|
||||
* designator, and for each unit, add all its pins to the temporary sorted pin list,
|
||||
* m_sortedSymbolPinList.
|
||||
* if aKeepUnconnectedPins = false, unconnected pins will be removed from list
|
||||
* but usually we need all pins in netlists.
|
||||
*/
|
||||
void findAllUnitsOfSymbol( SCH_SYMBOL* aSchSymbol, LIB_SYMBOL* aLibSymbol,
|
||||
SCH_SHEET_PATH* aSheetPath, bool aKeepUnconnectedPins );
|
||||
|
||||
public:
|
||||
/**
|
||||
* @param aMasterList we take ownership of this here.
|
||||
|
@ -213,6 +147,72 @@ public:
|
|||
static wxString MakeCommandLine( const wxString& aFormatString, const wxString& aNetlistFile,
|
||||
const wxString& aFinalFile,
|
||||
const wxString& aProjectDirectory );
|
||||
|
||||
protected:
|
||||
/**
|
||||
* Find a symbol from the DrawList and builds its pin list in m_sortedSymbolPinList.
|
||||
*
|
||||
* This list is sorted by pin number. The symbol is the next actual symbol after \a aSymbol.
|
||||
* Power symbols and virtual symbols that have their reference designators starting with
|
||||
* '#' are skipped.
|
||||
* if aKeepUnconnectedPins = false, unconnected pins will be removed from list
|
||||
* but usually we need all pins in netlists.
|
||||
*/
|
||||
void CreatePinList( SCH_SYMBOL* aSymbol, SCH_SHEET_PATH* aSheetPath,
|
||||
bool aKeepUnconnectedPins );
|
||||
|
||||
/**
|
||||
* Check if the given symbol should be processed for netlisting.
|
||||
*
|
||||
* Prevent processing multi-unit symbols more than once, etc.
|
||||
*
|
||||
* @param aItem is a symbol to check
|
||||
* @param aSheetPath is the sheet to check the symbol for
|
||||
* @return the symbol if it should be processed, or nullptr
|
||||
*/
|
||||
SCH_SYMBOL* findNextSymbol( EDA_ITEM* aItem, SCH_SHEET_PATH* aSheetPath );
|
||||
|
||||
/**
|
||||
* Erase duplicate pins from m_sortedSymbolPinList (i.e. set pointer in this list to NULL).
|
||||
*
|
||||
* (This is a list of pins found in the whole schematic, for a single symbol.) These
|
||||
* duplicate pins were put in list because some pins (power pins...) are found more than
|
||||
* once when in "multiple symbols per package" symbols. For instance, a 74ls00 has 4 symbols,
|
||||
* and therefore the VCC pin and GND pin appears 4 times in the list.
|
||||
* Note: this list *MUST* be sorted by pin number (.m_PinNum member value)
|
||||
* Also set the m_Flag member of "removed" NETLIST_OBJECT pin item to 1
|
||||
*/
|
||||
void eraseDuplicatePins();
|
||||
|
||||
/**
|
||||
* Find all units for symbols with multiple symbols per package.
|
||||
*
|
||||
* Search the entire design for all units of \a aSymbol based on matching reference
|
||||
* designator, and for each unit, add all its pins to the temporary sorted pin list,
|
||||
* m_sortedSymbolPinList.
|
||||
* if aKeepUnconnectedPins = false, unconnected pins will be removed from list
|
||||
* but usually we need all pins in netlists.
|
||||
*/
|
||||
void findAllUnitsOfSymbol( SCH_SYMBOL* aSchSymbol, LIB_SYMBOL* aLibSymbol,
|
||||
SCH_SHEET_PATH* aSheetPath, bool aKeepUnconnectedPins );
|
||||
|
||||
/// Used to temporarily store and filter the list of pins of a schematic symbol when
|
||||
/// generating schematic symbol data in netlist (comp section). No ownership of members.
|
||||
/// TODO(snh): Descope this object
|
||||
std::vector<PIN_INFO> m_sortedSymbolPinList;
|
||||
|
||||
/// Used for "multiple symbols per package" symbols to avoid processing a lib symbol more than
|
||||
/// once
|
||||
UNIQUE_STRINGS m_referencesAlreadyFound;
|
||||
|
||||
/// unique library symbols used. LIB_SYMBOL items are sorted by names
|
||||
std::set<LIB_SYMBOL*, LIB_SYMBOL_LESS_THAN> m_libParts;
|
||||
|
||||
/// The schematic we're generating a netlist for
|
||||
SCHEMATIC_IFACE* m_schematic;
|
||||
|
||||
/// The schematic's CurrentSheet when we entered. Restore on exiting.
|
||||
SCH_SHEET_PATH m_savedCurrentSheet;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -297,12 +297,23 @@ XNODE* NETLIST_EXPORTER_XML::makeSymbols( unsigned aCtl )
|
|||
// "logical" library name, which is in anticipation of a better search algorithm
|
||||
// for parts based on "logical_lib.part" and where logical_lib is merely the library
|
||||
// name minus path and extension.
|
||||
if( symbol->GetLibSymbolRef() )
|
||||
xlibsource->AddAttribute( "lib",
|
||||
symbol->GetLibSymbolRef()->GetLibId().GetLibNickname() );
|
||||
wxString libName;
|
||||
wxString partName;
|
||||
|
||||
if( symbol->UseLibIdLookup() )
|
||||
{
|
||||
libName = symbol->GetLibId().GetLibNickname();
|
||||
partName = symbol->GetLibId().GetLibItemName();
|
||||
}
|
||||
else
|
||||
{
|
||||
partName = symbol->GetSchSymbolLibraryName();
|
||||
}
|
||||
|
||||
xlibsource->AddAttribute( "lib", libName );
|
||||
|
||||
// We only want the symbol name, not the full LIB_ID.
|
||||
xlibsource->AddAttribute( "part", symbol->GetLibId().GetLibItemName() );
|
||||
xlibsource->AddAttribute( "part", partName );
|
||||
|
||||
xlibsource->AddAttribute( "description", symbol->GetDescription() );
|
||||
|
||||
|
|
|
@ -178,16 +178,27 @@ void SCH_SCREEN::Append( SCH_ITEM* aItem )
|
|||
int cnt = 1;
|
||||
wxString newName;
|
||||
|
||||
newName.Printf( "%s_%d", symbol->GetLibId().Format().wx_str(), cnt );
|
||||
newName.Printf( "%s_%d", symbol->GetLibId().GetUniStringLibItemName(),
|
||||
cnt );
|
||||
|
||||
while( m_libSymbols.find( newName ) != m_libSymbols.end() )
|
||||
{
|
||||
cnt += 1;
|
||||
newName.Printf( "%s_%d", symbol->GetLibId().Format().wx_str(), cnt );
|
||||
newName.Printf( "%s_%d", symbol->GetLibId().GetUniStringLibItemName(),
|
||||
cnt );
|
||||
}
|
||||
|
||||
// Update the schematic symbol library link as this symbol only exists
|
||||
// in the schematic.
|
||||
symbol->SetSchSymbolLibraryName( newName );
|
||||
m_libSymbols[newName] = new LIB_SYMBOL( *symbol->GetLibSymbolRef() );
|
||||
|
||||
LIB_SYMBOL* newLibSymbol = new LIB_SYMBOL( *symbol->GetLibSymbolRef() );
|
||||
LIB_ID newLibId( wxEmptyString, newName );
|
||||
|
||||
newLibSymbol->SetLibId( newLibId );
|
||||
newLibSymbol->SetName( newName );
|
||||
symbol->SetLibSymbol( newLibSymbol->Flatten().release() );
|
||||
m_libSymbols[newName] = newLibSymbol;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue