diff --git a/pcbnew/drc/drc_engine.cpp b/pcbnew/drc/drc_engine.cpp index c8e04ee4fd..e3265c244c 100644 --- a/pcbnew/drc/drc_engine.cpp +++ b/pcbnew/drc/drc_engine.cpp @@ -837,9 +837,9 @@ static int matchDpSuffix( const wxString& aNetName, wxString& aComplementNet, } -int DRC_ENGINE::IsNetADiffPair( BOARD* aBoard, int aNet, int& aNetP, int& aNetN ) +int DRC_ENGINE::IsNetADiffPair( BOARD* aBoard, NETINFO_ITEM* aNet, int& aNetP, int& aNetN ) { - wxString refName = aBoard->FindNet( aNet )->GetNetname(); + wxString refName = aNet->GetNetname(); wxString dummy, coupledNetName; if( int polarity = matchDpSuffix( refName, coupledNetName, dummy ) ) @@ -851,13 +851,13 @@ int DRC_ENGINE::IsNetADiffPair( BOARD* aBoard, int aNet, int& aNetP, int& aNetN if( polarity > 0 ) { - aNetP = aNet; + aNetP = aNet->GetNet(); aNetN = net->GetNet(); } else { aNetP = net->GetNet(); - aNetN = aNet; + aNetN = aNet->GetNet(); } return true; diff --git a/pcbnew/drc/drc_engine.h b/pcbnew/drc/drc_engine.h index 8736be070c..d15af28b53 100644 --- a/pcbnew/drc/drc_engine.h +++ b/pcbnew/drc/drc_engine.h @@ -40,6 +40,7 @@ class ZONE_CONTAINER; class MARKER_PCB; class NETCLASS; class NETLIST; +class NETINFO_ITEM; class PROGRESS_REPORTER; class REPORTER; @@ -177,7 +178,7 @@ public: DRC_TEST_PROVIDER* GetTestProvider( const wxString& name ) const; - static int IsNetADiffPair( BOARD* aBoard, int aNet, int& aNetP, int& aNetN ); + static int IsNetADiffPair( BOARD* aBoard, NETINFO_ITEM* aNet, int& aNetP, int& aNetN ); private: void addRule( DRC_RULE* rule ) diff --git a/pcbnew/drc/drc_test_provider_diff_pair_coupling.cpp b/pcbnew/drc/drc_test_provider_diff_pair_coupling.cpp index 3e1a6ab0a4..90db1acc92 100644 --- a/pcbnew/drc/drc_test_provider_diff_pair_coupling.cpp +++ b/pcbnew/drc/drc_test_provider_diff_pair_coupling.cpp @@ -278,34 +278,36 @@ bool test::DRC_TEST_PROVIDER_DIFF_PAIR_COUPLING::Run() [&]( BOARD_ITEM *item ) -> bool { DIFF_PAIR_KEY key; - auto citem = static_cast( item ); - int refNet = citem->GetNetCode(); + BOARD_CONNECTED_ITEM* citem = static_cast( item ); + NETINFO_ITEM* refNet = citem->GetNet(); - if( !DRC_ENGINE::IsNetADiffPair( m_board, refNet, key.netP, key.netN ) ) // not our business - return true; - - drc_dbg(10, "eval dp %p\n", item ); - - const DRC_CONSTRAINT_TYPE_T constraintsToCheck[] = { - DRC_CONSTRAINT_TYPE_DIFF_PAIR_GAP, - DRC_CONSTRAINT_TYPE_DIFF_PAIR_MAX_UNCOUPLED - }; - - for( int i = 0; i < 2; i++ ) + if( refNet && DRC_ENGINE::IsNetADiffPair( m_board, refNet, key.netP, key.netN ) ) { - auto constraint = m_drcEngine->EvalRulesForItems( constraintsToCheck[i], item, nullptr, item->GetLayer() ); + drc_dbg( 10, "eval dp %p\n", item ); - if( constraint.IsNull() ) - continue; + const DRC_CONSTRAINT_TYPE_T constraintsToCheck[] = { + DRC_CONSTRAINT_TYPE_DIFF_PAIR_GAP, + DRC_CONSTRAINT_TYPE_DIFF_PAIR_MAX_UNCOUPLED + }; - drc_dbg(10, "cns %d item %p\n", constraintsToCheck[i], item ); + for( int i = 0; i < 2; i++ ) + { + auto constraint = m_drcEngine->EvalRulesForItems( constraintsToCheck[i], + item, nullptr, + item->GetLayer() ); - key.parentRule = constraint.GetParentRule(); + if( constraint.IsNull() ) + continue; - if( refNet == key.netN ) - dpRuleMatches[key].itemsN.insert( citem ); - else - dpRuleMatches[key].itemsP.insert( citem ); + drc_dbg( 10, "cns %d item %p\n", constraintsToCheck[i], item ); + + key.parentRule = constraint.GetParentRule(); + + if( refNet->GetNet() == key.netN ) + dpRuleMatches[key].itemsN.insert( citem ); + else + dpRuleMatches[key].itemsP.insert( citem ); + } } return true; diff --git a/pcbnew/pcb_expr_evaluator.cpp b/pcbnew/pcb_expr_evaluator.cpp index 3d2354835b..f06214effc 100644 --- a/pcbnew/pcb_expr_evaluator.cpp +++ b/pcbnew/pcb_expr_evaluator.cpp @@ -335,12 +335,12 @@ static void isDiffPair( LIBEVAL::CONTEXT* aCtx, void* self ) result->Set( 0.0 ); aCtx->Push( result ); - if( item->IsConnected() ) + if( item && item->IsConnected() ) { - int net = static_cast( item )->GetNetCode(); - int net_p, net_n; + NETINFO_ITEM* netinfo = static_cast( item )->GetNet(); + int dummy_p, dummy_n; - if( DRC_ENGINE::IsNetADiffPair( item->GetBoard(), net, net_p, net_n ) ) + if( netinfo && DRC_ENGINE::IsNetADiffPair( item->GetBoard(), netinfo, dummy_p, dummy_n ) ) result->Set( 1.0 ); } } diff --git a/pcbnew/tools/pcb_editor_control.cpp b/pcbnew/tools/pcb_editor_control.cpp index 5d3ba78382..514a9e6aad 100644 --- a/pcbnew/tools/pcb_editor_control.cpp +++ b/pcbnew/tools/pcb_editor_control.cpp @@ -374,22 +374,39 @@ int PCB_EDITOR_CONTROL::RepairBoard( const TOOL_EVENT& aEvent ) wxString details; /******************************* - * Repair duplicate IDs + * Repair duplicate IDs and missing nets */ std::set ids; int duplicates = 0; - auto processItem = [&]( EDA_ITEM* aItem ) - { - if( ids.count( aItem->m_Uuid ) ) - { - duplicates++; - const_cast( aItem->m_Uuid ) = KIID(); - } + auto processItem = + [&]( EDA_ITEM* aItem ) + { + if( ids.count( aItem->m_Uuid ) ) + { + duplicates++; + const_cast( aItem->m_Uuid ) = KIID(); + } - ids.insert( aItem->m_Uuid ); - }; + ids.insert( aItem->m_Uuid ); + + BOARD_CONNECTED_ITEM* cItem = dynamic_cast( aItem ); + + if( cItem && cItem->GetNetCode() ) + { + NETINFO_ITEM* netinfo = cItem->GetNet(); + + if( netinfo && !board()->FindNet( netinfo->GetNetname() ) ) + { + board()->Add( netinfo ); + + details += wxString::Format( _( "Orphaned net %s re-parented.\n" ), + netinfo->GetNetname() ); + errors++; + } + } + }; // Module IDs are the most important, so give them the first crack at "owning" a particular // KIID. @@ -421,6 +438,9 @@ int PCB_EDITOR_CONTROL::RepairBoard( const TOOL_EVENT& aEvent ) for( ZONE_CONTAINER* zone : module->Zones() ) processItem( zone ); + + for( PCB_GROUP* group : module->Groups() ) + processItem( group ); } for( BOARD_ITEM* drawing : board()->Drawings() ) @@ -432,6 +452,9 @@ int PCB_EDITOR_CONTROL::RepairBoard( const TOOL_EVENT& aEvent ) for( MARKER_PCB* marker : board()->Markers() ) processItem( marker ); + for( PCB_GROUP* group : board()->Groups() ) + processItem( group ); + if( duplicates ) { errors += duplicates;