Skip to content

Commit 746586d

Browse files
authored
Merge pull request #9010 from gadfort/add-connect-to-pads-to-grid
pdn: add ability to connect to straps from pads
2 parents 3b1e99d + aab386d commit 746586d

20 files changed

+88591
-22
lines changed

src/pdn/README.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,8 @@ set_voltage_domain
6464
[-region region_name]
6565
[-secondary_power secondary_power_net]
6666
[-switched_power switched_power_net]
67+
[-connect_to_pad_layers layers]
68+
[-connect_to_pads]
6769
```
6870

6971
#### Options
@@ -76,6 +78,8 @@ set_voltage_domain
7678
| `[-region]` | Specifies a region of the design occupied by this voltage domain. |
7779
| `[-secondary_power]` | Specifies the name of the secondary power net for this voltage domain. |
7880
| `[-switched_power]` | Specifies the name of the switched power net for switched power domains. |
81+
| `[-connect_to_pad_layers]` | Restrict the pad pins layers to this list. |
82+
| `[-connect_to_pads]` | The core side of the pad pins will be connected to the grid. |
7983

8084
### Define Power Grids
8185

src/pdn/include/pdn/PdnGen.hh

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,8 @@ class PdnGen
9898
const std::vector<odb::dbTechLayer*>& generate_obstructions,
9999
PowerCell* powercell,
100100
odb::dbNet* powercontrol,
101-
const char* powercontrolnetwork);
101+
const char* powercontrolnetwork,
102+
const std::vector<odb::dbTechLayer*>& pad_pin_layers);
102103
void makeInstanceGrid(
103104
VoltageDomain* domain,
104105
const std::string& name,

src/pdn/src/PdnGen.cc

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -421,7 +421,8 @@ void PdnGen::makeCoreGrid(
421421
const std::vector<odb::dbTechLayer*>& generate_obstructions,
422422
PowerCell* powercell,
423423
odb::dbNet* powercontrol,
424-
const char* powercontrolnetwork)
424+
const char* powercontrolnetwork,
425+
const std::vector<odb::dbTechLayer*>& pad_pin_layers)
425426
{
426427
auto grid = std::make_unique<CoreGrid>(
427428
domain, name, starts_with == POWER, generate_obstructions);
@@ -450,6 +451,9 @@ void PdnGen::makeCoreGrid(
450451
GridSwitchedPower::fromString(powercontrolnetwork, logger_)));
451452
}
452453
}
454+
if (!pad_pin_layers.empty()) {
455+
grid->setupDirectConnect(pad_pin_layers);
456+
}
453457
domain->addGrid(std::move(grid));
454458
}
455459

@@ -574,6 +578,13 @@ void PdnGen::makeRing(Grid* grid,
574578
if (!pad_pin_layers.empty() && grid->type() == Grid::Core) {
575579
auto* core_grid = static_cast<CoreGrid*>(grid);
576580
core_grid->setupDirectConnect(pad_pin_layers);
581+
for (const auto& comp : core_grid->getStraps()) {
582+
PadDirectConnectionStraps* straps
583+
= dynamic_cast<PadDirectConnectionStraps*>(comp.get());
584+
if (straps) {
585+
straps->setTargetType(odb::dbWireShapeType::RING);
586+
}
587+
}
577588
}
578589
}
579590

src/pdn/src/PdnGen.i

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,8 @@ void make_core_grid(pdn::VoltageDomain* domain,
8181
const std::vector<odb::dbTechLayer*>& generate_obstructions,
8282
pdn::PowerCell* powercell,
8383
odb::dbNet* powercontrol,
84-
const char* powercontrolnetwork)
84+
const char* powercontrolnetwork,
85+
const std::vector<odb::dbTechLayer*>& pad_pin_layers)
8586
{
8687
PdnGen* pdngen = ord::getPdnGen();
8788
StartsWith starts_with = POWER;
@@ -95,7 +96,8 @@ void make_core_grid(pdn::VoltageDomain* domain,
9596
generate_obstructions,
9697
powercell,
9798
powercontrol,
98-
powercontrolnetwork);
99+
powercontrolnetwork,
100+
pad_pin_layers);
99101
}
100102

101103
void make_instance_grid(pdn::VoltageDomain* domain,

src/pdn/src/grid.cpp

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -121,15 +121,21 @@ void Grid::makeShapes(const Shape::ShapeTreeMap& global_shapes,
121121

122122
Shape::ShapeTreeMap local_shapes = global_shapes;
123123
// make shapes
124+
std::vector<GridComponent*> deferred;
124125
for (auto* component : getGridComponents()) {
125-
// make initial shapes
126-
component->makeShapes(local_shapes);
127-
// cut shapes to avoid obstructions
128-
component->cutShapes(local_obstructions);
129-
// add shapes and obstructions to they are accounted for in future
130-
// components
131-
component->getObstructions(local_obstructions);
132-
component->getShapes(local_shapes);
126+
if (!component->make(local_shapes, local_obstructions)) {
127+
debugPrint(logger,
128+
utl::PDN,
129+
"Make",
130+
2,
131+
"Deferring shape creation for component in \"{}\".",
132+
getName());
133+
deferred.push_back(component);
134+
}
135+
}
136+
// make deferred components
137+
for (auto* component : deferred) {
138+
component->make(local_shapes, local_obstructions);
133139
}
134140

135141
// refine shapes

src/pdn/src/grid.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ class Straps;
2727
class Connect;
2828
class GridComponent;
2929
class GridSwitchedPower;
30+
class PadDirectConnectionStraps;
3031

3132
class PdnGen;
3233

src/pdn/src/grid_component.cpp

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,23 @@ std::string GridComponent::typeToString(Type type)
6262
return "Unknown";
6363
}
6464

65+
bool GridComponent::make(Shape::ShapeTreeMap& shapes,
66+
Shape::ObstructionTreeMap& obstructions)
67+
{
68+
const int shape_count = getShapeCount();
69+
70+
// make initial shapes
71+
makeShapes(shapes);
72+
// cut shapes to avoid obstructions
73+
cutShapes(obstructions);
74+
// add shapes and obstructions to they are accounted for in future
75+
// components
76+
getObstructions(obstructions);
77+
getShapes(shapes);
78+
79+
return shape_count != getShapeCount();
80+
}
81+
6582
ShapePtr GridComponent::addShape(std::unique_ptr<Shape> shape)
6683
{
6784
debugPrint(getLogger(),

src/pdn/src/grid_component.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,9 @@ class GridComponent
4646
Grid* getGrid() const { return grid_; }
4747
VoltageDomain* getDomain() const;
4848

49+
bool make(Shape::ShapeTreeMap& shapes,
50+
Shape::ObstructionTreeMap& obstructions);
51+
4952
virtual void makeShapes(const Shape::ShapeTreeMap& other_shapes) = 0;
5053
virtual bool refineShapes(Shape::ShapeTreeMap& all_shapes,
5154
Shape::ObstructionTreeMap& all_obstructions)

src/pdn/src/pdn.tcl

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -169,7 +169,9 @@ sta::define_cmd_args "define_pdn_grid" {[-name <name>] \
169169
[-obstructions <list_of_layers>] \
170170
[-power_switch_cell <name>] \
171171
[-power_control <signal_name>] \
172-
[-power_control_network (STAR|DAISY)]
172+
[-power_control_network (STAR|DAISY)] \
173+
[-connect_to_pads] \
174+
[-connect_to_pad_layers layers]
173175
} ;#checker off
174176

175177
proc define_pdn_grid { args } {
@@ -502,7 +504,7 @@ proc add_pdn_ring { args } {
502504
if { [info exists flags(-connect_to_pads)] } {
503505
if { ![info exists keys(-connect_to_pad_layers)] } {
504506
foreach layer [[ord::get_db_tech] getLayers] {
505-
if { [$layer getType] == "ROUTING" } {
507+
if { [$layer getRoutingLevel] > 0 } {
506508
lappend connect_to_pad_layers $layer
507509
}
508510
}
@@ -840,8 +842,8 @@ proc deprecated { args_var key { use "." } } {
840842
proc define_pdn_grid { args } {
841843
sta::parse_key_args "define_pdn_grid" args \
842844
keys {-name -voltage_domains -pins -starts_with -obstructions -power_switch_cell \
843-
-power_control -power_control_network} \
844-
flags {} ;# checker off
845+
-power_control -power_control_network -connect_to_pad_layers} \
846+
flags {-connect_to_pads} ;# checker off
845847

846848
sta::check_argc_eq0 "define_pdn_grid" $args
847849
pdn::check_design_state "define_pdn_grid"
@@ -900,6 +902,21 @@ proc define_pdn_grid { args } {
900902
set power_control_network $keys(-power_control_network)
901903
}
902904

905+
set connect_to_pad_layers {}
906+
if { [info exists flags(-connect_to_pads)] } {
907+
if { ![info exists keys(-connect_to_pad_layers)] } {
908+
foreach layer [[ord::get_db_tech] getLayers] {
909+
if { [$layer getRoutingLevel] > 0 } {
910+
lappend connect_to_pad_layers $layer
911+
}
912+
}
913+
} else {
914+
foreach layer $keys(-connect_to_pad_layers) {
915+
lappend connect_to_pad_layers [get_layer $layer]
916+
}
917+
}
918+
}
919+
903920
foreach domain $domains {
904921
pdn::make_core_grid \
905922
$domain \
@@ -909,7 +926,8 @@ proc define_pdn_grid { args } {
909926
$obstructions \
910927
$power_cell \
911928
$power_control \
912-
$power_control_network
929+
$power_control_network \
930+
$connect_to_pad_layers
913931
}
914932
}
915933

src/pdn/src/straps.cpp

Lines changed: 28 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -955,8 +955,7 @@ ShapePtr PadDirectConnectionStraps::getClosestShape(
955955
for (auto it = search_shapes.qbegin(bgi::intersects(search_rect)
956956
&& bgi::satisfies([&](const auto& other) {
957957
return other->getNet() == net
958-
&& other->getType()
959-
== target_shapes_type_;
958+
&& isTargetShape(other.get());
960959
}));
961960
it != search_shapes.qend();
962961
it++) {
@@ -1019,7 +1018,7 @@ void PadDirectConnectionStraps::makeShapesFacingCore(
10191018
std::map<odb::dbTechLayer*, std::set<odb::dbTechLayer*>> connectable_layers;
10201019
for (const auto& [layer, shapes] : other_shapes) {
10211020
for (const auto& shape : shapes) {
1022-
if (shape->getType() == target_shapes_type_) {
1021+
if (isTargetShape(shape.get())) {
10231022
const auto layers = getGrid()->connectableLayers(layer);
10241023
pin_layers.insert(layers.begin(), layers.end());
10251024
for (auto* clayer : layers) {
@@ -1574,6 +1573,32 @@ bool PadDirectConnectionStraps::refineShape(
15741573
return false;
15751574
}
15761575

1576+
bool PadDirectConnectionStraps::isTargetShape(const Shape* shape) const
1577+
{
1578+
if (target_shapes_type_) {
1579+
return shape->getType() == target_shapes_type_.value();
1580+
}
1581+
1582+
switch (shape->getType().getValue()) {
1583+
case odb::dbWireShapeType::STRIPE:
1584+
case odb::dbWireShapeType::RING:
1585+
return true;
1586+
case odb::dbWireShapeType::NONE:
1587+
case odb::dbWireShapeType::PADRING:
1588+
case odb::dbWireShapeType::BLOCKRING:
1589+
case odb::dbWireShapeType::FOLLOWPIN:
1590+
case odb::dbWireShapeType::IOWIRE:
1591+
case odb::dbWireShapeType::COREWIRE:
1592+
case odb::dbWireShapeType::BLOCKWIRE:
1593+
case odb::dbWireShapeType::BLOCKAGEWIRE:
1594+
case odb::dbWireShapeType::FILLWIRE:
1595+
case odb::dbWireShapeType::DRCFILL:
1596+
return false;
1597+
}
1598+
1599+
return false;
1600+
}
1601+
15771602
////////
15781603

15791604
RepairChannelStraps::RepairChannelStraps(

0 commit comments

Comments
 (0)