Multiple connectivity algo crash fixes:

- ratsnest crash on single-pad nets
- connectivity crash on adding new net codes
This commit is contained in:
Tomasz Włostowski 2017-07-01 23:54:17 +02:00
parent 1c5ace4b7a
commit 1936b45a0f
3 changed files with 39 additions and 17 deletions

View File

@ -203,7 +203,7 @@ void CN_CONNECTIVITY_ALGO::markItemNetAsDirty( const BOARD_ITEM* aItem )
if( aItem->IsConnected() ) if( aItem->IsConnected() )
{ {
auto citem = static_cast<const BOARD_CONNECTED_ITEM*>( aItem ); auto citem = static_cast<const BOARD_CONNECTED_ITEM*>( aItem );
markNetAsDirty( citem->GetNetCode() ); MarkNetAsDirty( citem->GetNetCode() );
} }
else else
{ {
@ -212,7 +212,7 @@ void CN_CONNECTIVITY_ALGO::markItemNetAsDirty( const BOARD_ITEM* aItem )
auto mod = static_cast <const MODULE*>( aItem ); auto mod = static_cast <const MODULE*>( aItem );
for( D_PAD* pad = mod->PadsList(); pad; pad = pad->Next() ) for( D_PAD* pad = mod->PadsList(); pad; pad = pad->Next() )
markNetAsDirty( pad->GetNetCode() ); MarkNetAsDirty( pad->GetNetCode() );
} }
} }
} }
@ -224,6 +224,11 @@ bool CN_CONNECTIVITY_ALGO::Add( BOARD_ITEM* aItem )
switch( aItem->Type() ) switch( aItem->Type() )
{ {
case PCB_NETINFO_T:
{
MarkNetAsDirty( static_cast<NETINFO_ITEM*>( aItem )->GetNet() );
break;
}
case PCB_MODULE_T: case PCB_MODULE_T:
for( auto pad : static_cast<MODULE*>( aItem ) -> Pads() ) for( auto pad : static_cast<MODULE*>( aItem ) -> Pads() )
{ {
@ -762,7 +767,7 @@ void CN_CONNECTIVITY_ALGO::propagateConnections()
if( item->CanChangeNet() ) if( item->CanChangeNet() )
{ {
item->Parent()->SetNetCode( cluster->OriginNet() ); item->Parent()->SetNetCode( cluster->OriginNet() );
markNetAsDirty( cluster->OriginNet() ); MarkNetAsDirty( cluster->OriginNet() );
n_changed++; n_changed++;
} }
} }
@ -826,9 +831,9 @@ const CN_CONNECTIVITY_ALGO::CLUSTERS& CN_CONNECTIVITY_ALGO::GetClusters()
} }
void CN_CONNECTIVITY_ALGO::markNetAsDirty( int aNet ) void CN_CONNECTIVITY_ALGO::MarkNetAsDirty( int aNet )
{ {
if( aNet <= 0 ) if( aNet < 0 )
return; return;
if( (int) m_dirtyNets.size() <= aNet ) if( (int) m_dirtyNets.size() <= aNet )

View File

@ -823,7 +823,6 @@ public:
bool addConnectedItem( BOARD_CONNECTED_ITEM* aItem ); bool addConnectedItem( BOARD_CONNECTED_ITEM* aItem );
bool isDirty() const; bool isDirty() const;
void markNetAsDirty( int aNet );
void markItemNetAsDirty( const BOARD_ITEM* aItem ); void markItemNetAsDirty( const BOARD_ITEM* aItem );
public: public:
@ -838,6 +837,9 @@ public:
bool IsNetDirty( int aNet ) const bool IsNetDirty( int aNet ) const
{ {
if( aNet < 0 )
return false;
return m_dirtyNets[ aNet ]; return m_dirtyNets[ aNet ];
} }
@ -885,6 +887,9 @@ public:
void ForEachAnchor( std::function<void(CN_ANCHOR_PTR)> aFunc ); void ForEachAnchor( std::function<void(CN_ANCHOR_PTR)> aFunc );
void ForEachItem( std::function<void(CN_ITEM*)> aFunc ); void ForEachItem( std::function<void(CN_ITEM*)> aFunc );
void MarkNetAsDirty( int aNet );
}; };
bool operator<( const CN_ANCHOR_PTR a, const CN_ANCHOR_PTR b ); bool operator<( const CN_ANCHOR_PTR a, const CN_ANCHOR_PTR b );

View File

@ -235,7 +235,18 @@ public:
for( int i = prevId; i < id; i++ ) for( int i = prevId; i < id; i++ )
anchorChains[prevId].push_back( m_allNodes[ i ] ); anchorChains[prevId].push_back( m_allNodes[ i ] );
if( triNodes.size() == 1 )
{
return mstEdges;
}
else if( triNodes.size() == 2 )
{
auto src = m_allNodes[ triNodes[0]->Id() ];
auto dst = m_allNodes[ triNodes[1]->Id() ];
mstEdges.emplace_back( src, dst, getDistance( src, dst ) );
}
else
{
hed::TRIANGULATION triangulator; hed::TRIANGULATION triangulator;
triangulator.CreateDelaunay( triNodes.begin(), triNodes.end() ); triangulator.CreateDelaunay( triNodes.begin(), triNodes.end() );
triangulator.GetEdges( triangEdges ); triangulator.GetEdges( triangEdges );
@ -247,6 +258,7 @@ public:
mstEdges.emplace_back( src, dst, getDistance( src, dst ) ); mstEdges.emplace_back( src, dst, getDistance( src, dst ) );
} }
}
for( unsigned int i = 0; i < anchorChains.size(); i++ ) for( unsigned int i = 0; i < anchorChains.size(); i++ )
{ {