Replace zone-with-no-pads test with isolated copper test.
The later is far more discriminating. Fixes https://gitlab.com/kicad/code/kicad/issues/11009
This commit is contained in:
parent
661488e932
commit
914e706023
|
@ -77,12 +77,12 @@ DRC_ITEM DRC_ITEM::edgeClearance( DRCE_EDGE_CLEARANCE,
|
|||
wxT( "copper_edge_clearance" ) );
|
||||
|
||||
DRC_ITEM DRC_ITEM::zonesIntersect( DRCE_ZONES_INTERSECT,
|
||||
_( "Copper areas intersect" ),
|
||||
_( "Copper zones intersect" ),
|
||||
wxT( "zones_intersect" ) );
|
||||
|
||||
DRC_ITEM DRC_ITEM::zoneHasEmptyNet( DRCE_ZONE_HAS_EMPTY_NET,
|
||||
_( "Copper zone net has no pads" ),
|
||||
wxT( "zone_has_empty_net" ) );
|
||||
DRC_ITEM DRC_ITEM::isolatedCopper( DRCE_ISOLATED_COPPER,
|
||||
_( "Isolated copper fill" ),
|
||||
wxT( "isolated_copper" ) );
|
||||
|
||||
DRC_ITEM DRC_ITEM::starvedThermal( DRCE_STARVED_THERMAL,
|
||||
_( "Thermal relief connection to zone incomplete" ),
|
||||
|
@ -292,7 +292,7 @@ std::vector<std::reference_wrapper<RC_ITEM>> DRC_ITEM::allItemTypes( {
|
|||
DRC_ITEM::heading_misc,
|
||||
DRC_ITEM::itemsNotAllowed,
|
||||
DRC_ITEM::zonesIntersect,
|
||||
DRC_ITEM::zoneHasEmptyNet,
|
||||
DRC_ITEM::isolatedCopper,
|
||||
DRC_ITEM::padstack,
|
||||
DRC_ITEM::pthInsideCourtyard,
|
||||
DRC_ITEM::npthInsideCourtyard,
|
||||
|
@ -318,7 +318,7 @@ std::shared_ptr<DRC_ITEM> DRC_ITEM::Create( int aErrorCode )
|
|||
case DRCE_TRACKS_CROSSING: return std::make_shared<DRC_ITEM>( tracksCrossing );
|
||||
case DRCE_EDGE_CLEARANCE: return std::make_shared<DRC_ITEM>( edgeClearance );
|
||||
case DRCE_ZONES_INTERSECT: return std::make_shared<DRC_ITEM>( zonesIntersect );
|
||||
case DRCE_ZONE_HAS_EMPTY_NET: return std::make_shared<DRC_ITEM>( zoneHasEmptyNet );
|
||||
case DRCE_ISOLATED_COPPER: return std::make_shared<DRC_ITEM>( isolatedCopper );
|
||||
case DRCE_STARVED_THERMAL: return std::make_shared<DRC_ITEM>( starvedThermal );
|
||||
case DRCE_DANGLING_VIA: return std::make_shared<DRC_ITEM>( viaDangling );
|
||||
case DRCE_DANGLING_TRACK: return std::make_shared<DRC_ITEM>( trackDangling );
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
* This program source code file is part of KiCad, a free EDA CAD application.
|
||||
*
|
||||
* Copyright (C) 2007 Dick Hollenbeck, dick@softplc.com
|
||||
* Copyright (C) 2018-2021 KiCad Developers, see AUTHORS.txt for contributors.
|
||||
* Copyright (C) 2018-2022 KiCad Developers, see AUTHORS.txt for contributors.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
|
@ -43,8 +43,8 @@ enum PCB_DRC_CODE {
|
|||
DRCE_CLEARANCE, // items are too close together
|
||||
DRCE_TRACKS_CROSSING, // tracks are crossing
|
||||
DRCE_EDGE_CLEARANCE, // a copper item is too close to the board edge
|
||||
DRCE_ZONES_INTERSECT, // copper area outlines intersect
|
||||
DRCE_ZONE_HAS_EMPTY_NET, // copper area has a net but no pads in nets, which is suspicious
|
||||
DRCE_ZONES_INTERSECT, // copper zone outlines intersect
|
||||
DRCE_ISOLATED_COPPER, // copper fill with no electrical connections
|
||||
DRCE_STARVED_THERMAL, // insufficient number of thermal spokes connected to zone
|
||||
DRCE_DANGLING_VIA, // via which isn't connected to anything
|
||||
DRCE_DANGLING_TRACK, // track with at least one end not connected to anything
|
||||
|
@ -156,7 +156,7 @@ private:
|
|||
static DRC_ITEM tracksCrossing;
|
||||
static DRC_ITEM edgeClearance;
|
||||
static DRC_ITEM zonesIntersect;
|
||||
static DRC_ITEM zoneHasEmptyNet;
|
||||
static DRC_ITEM isolatedCopper;
|
||||
static DRC_ITEM starvedThermal;
|
||||
static DRC_ITEM viaDangling;
|
||||
static DRC_ITEM trackDangling;
|
||||
|
|
|
@ -38,7 +38,7 @@
|
|||
Errors generated:
|
||||
- DRCE_DANGLING_TRACK
|
||||
- DRCE_DANGLING_VIA
|
||||
- DRCE_ZONE_HAS_EMPTY_NET
|
||||
- DRCE_ISOLATED_COPPER
|
||||
*/
|
||||
|
||||
class DRC_TEST_PROVIDER_CONNECTIVITY : public DRC_TEST_PROVIDER
|
||||
|
@ -74,14 +74,22 @@ bool DRC_TEST_PROVIDER_CONNECTIVITY::Run()
|
|||
BOARD* board = m_drcEngine->GetBoard();
|
||||
|
||||
std::shared_ptr<CONNECTIVITY_DATA> connectivity = board->GetConnectivity();
|
||||
std::vector<CN_ZONE_ISOLATED_ISLAND_LIST> islandsList;
|
||||
|
||||
for( ZONE* zone : board->Zones() )
|
||||
{
|
||||
if( !zone->GetIsRuleArea() )
|
||||
islandsList.emplace_back( CN_ZONE_ISOLATED_ISLAND_LIST( zone ) );
|
||||
}
|
||||
|
||||
// Rebuild just in case. This really needs to be reliable.
|
||||
connectivity->Clear();
|
||||
connectivity->Build( board, m_drcEngine->GetProgressReporter() );
|
||||
connectivity->FindIsolatedCopperIslands( islandsList );
|
||||
|
||||
int delta = 100; // This is the number of tests between 2 calls to the progress bar
|
||||
int ii = 0;
|
||||
int count = board->Tracks().size() + board->Zones().size();
|
||||
int count = board->Tracks().size() + islandsList.size();
|
||||
|
||||
ii += count; // We gave half of this phase to CONNECTIVITY_DATA::Build()
|
||||
count += count;
|
||||
|
@ -99,7 +107,7 @@ bool DRC_TEST_PROVIDER_CONNECTIVITY::Run()
|
|||
continue;
|
||||
|
||||
if( !reportProgress( ii++, count, delta ) )
|
||||
break;
|
||||
return false; // DRC cancelled
|
||||
|
||||
// Test for dangling items
|
||||
int code = track->Type() == PCB_VIA_T ? DRCE_DANGLING_VIA : DRCE_DANGLING_TRACK;
|
||||
|
@ -114,28 +122,30 @@ bool DRC_TEST_PROVIDER_CONNECTIVITY::Run()
|
|||
}
|
||||
|
||||
/* test starved zones */
|
||||
for( ZONE* zone : board->Zones() )
|
||||
for( CN_ZONE_ISOLATED_ISLAND_LIST& zone : islandsList )
|
||||
{
|
||||
if( m_drcEngine->IsErrorLimitExceeded( DRCE_ZONE_HAS_EMPTY_NET ) )
|
||||
if( m_drcEngine->IsErrorLimitExceeded( DRCE_ISOLATED_COPPER ) )
|
||||
break;
|
||||
|
||||
if( !zone->IsOnCopperLayer() )
|
||||
continue;
|
||||
|
||||
if( !reportProgress( ii++, count, delta ) )
|
||||
return false; // DRC cancelled
|
||||
|
||||
int netcode = zone->GetNetCode();
|
||||
// a netcode < 0 or > 0 and no pad in net is a error or strange
|
||||
// perhaps a "dead" net, which happens when all pads in this net were removed
|
||||
// Remark: a netcode < 0 should not happen (this is more a bug somewhere)
|
||||
int pads_in_net = ( netcode > 0 ) ? connectivity->GetPadCount( netcode ) : 1;
|
||||
|
||||
if( ( netcode < 0 ) || pads_in_net == 0 )
|
||||
for( PCB_LAYER_ID layer : zone.m_zone->GetLayerSet().Seq() )
|
||||
{
|
||||
std::shared_ptr<DRC_ITEM> drcItem = DRC_ITEM::Create( DRCE_ZONE_HAS_EMPTY_NET );
|
||||
drcItem->SetItems( zone );
|
||||
reportViolation( drcItem, zone->GetPosition(), zone->GetLayer() );
|
||||
if( !zone.m_islands.count( layer ) )
|
||||
continue;
|
||||
|
||||
std::shared_ptr<SHAPE_POLY_SET> poly = zone.m_zone->GetFilledPolysList( layer );
|
||||
|
||||
for( int idx : zone.m_islands.at( layer ) )
|
||||
{
|
||||
if( m_drcEngine->IsErrorLimitExceeded( DRCE_ISOLATED_COPPER ) )
|
||||
break;
|
||||
|
||||
std::shared_ptr<DRC_ITEM> drcItem = DRC_ITEM::Create( DRCE_ISOLATED_COPPER );
|
||||
drcItem->SetItems( zone.m_zone );
|
||||
reportViolation( drcItem, poly->Outline( idx ).CPoint( 0 ), layer );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue