pyedb 0.53.0__py3-none-any.whl → 0.55.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of pyedb might be problematic. Click here for more details.
- pyedb/__init__.py +1 -8
- pyedb/configuration/cfg_boundaries.py +69 -151
- pyedb/configuration/cfg_components.py +201 -460
- pyedb/configuration/cfg_data.py +4 -2
- pyedb/configuration/cfg_general.py +13 -36
- pyedb/configuration/cfg_modeler.py +2 -1
- pyedb/configuration/cfg_nets.py +21 -35
- pyedb/configuration/cfg_operations.py +22 -151
- pyedb/configuration/cfg_package_definition.py +56 -112
- pyedb/configuration/cfg_padstacks.py +292 -688
- pyedb/configuration/cfg_pin_groups.py +32 -79
- pyedb/configuration/cfg_ports_sources.py +20 -9
- pyedb/configuration/cfg_s_parameter_models.py +67 -172
- pyedb/configuration/cfg_setup.py +102 -295
- pyedb/configuration/configuration.py +66 -6
- pyedb/dotnet/database/cell/connectable.py +38 -9
- pyedb/dotnet/database/cell/hierarchy/component.py +28 -28
- pyedb/dotnet/database/cell/hierarchy/model.py +1 -1
- pyedb/dotnet/database/cell/layout.py +64 -3
- pyedb/dotnet/database/cell/layout_obj.py +3 -3
- pyedb/dotnet/database/cell/primitive/path.py +6 -8
- pyedb/dotnet/database/cell/primitive/primitive.py +10 -31
- pyedb/dotnet/database/cell/terminal/edge_terminal.py +2 -2
- pyedb/dotnet/database/cell/terminal/padstack_instance_terminal.py +1 -1
- pyedb/dotnet/database/cell/terminal/pingroup_terminal.py +1 -1
- pyedb/dotnet/database/cell/terminal/point_terminal.py +1 -1
- pyedb/dotnet/database/cell/terminal/terminal.py +26 -28
- pyedb/dotnet/database/cell/voltage_regulator.py +0 -21
- pyedb/dotnet/database/components.py +99 -91
- pyedb/dotnet/database/definition/component_def.py +4 -4
- pyedb/dotnet/database/definition/component_model.py +1 -1
- pyedb/dotnet/database/definition/package_def.py +2 -3
- pyedb/dotnet/database/dotnet/database.py +27 -218
- pyedb/dotnet/database/dotnet/primitive.py +16 -16
- pyedb/dotnet/database/edb_data/control_file.py +5 -5
- pyedb/dotnet/database/edb_data/hfss_extent_info.py +6 -6
- pyedb/dotnet/database/edb_data/layer_data.py +35 -35
- pyedb/dotnet/database/edb_data/padstacks_data.py +65 -90
- pyedb/dotnet/database/edb_data/primitives_data.py +5 -5
- pyedb/dotnet/database/edb_data/sources.py +6 -6
- pyedb/dotnet/database/edb_data/variables.py +8 -4
- pyedb/dotnet/database/geometry/point_data.py +14 -10
- pyedb/dotnet/database/geometry/polygon_data.py +3 -5
- pyedb/dotnet/database/hfss.py +50 -52
- pyedb/dotnet/database/layout_validation.py +14 -11
- pyedb/dotnet/database/materials.py +10 -11
- pyedb/dotnet/database/modeler.py +104 -101
- pyedb/dotnet/database/nets.py +20 -23
- pyedb/dotnet/database/padstack.py +156 -84
- pyedb/dotnet/database/sim_setup_data/data/settings.py +24 -0
- pyedb/dotnet/database/sim_setup_data/io/siwave.py +26 -1
- pyedb/dotnet/database/siwave.py +47 -47
- pyedb/dotnet/database/stackup.py +152 -87
- pyedb/dotnet/database/utilities/heatsink.py +4 -4
- pyedb/dotnet/database/utilities/obj_base.py +3 -3
- pyedb/dotnet/database/utilities/simulation_setup.py +2 -2
- pyedb/dotnet/database/utilities/value.py +116 -0
- pyedb/dotnet/edb.py +248 -170
- pyedb/edb_logger.py +12 -27
- pyedb/extensions/via_design_backend.py +6 -3
- pyedb/generic/design_types.py +68 -21
- pyedb/generic/general_methods.py +0 -120
- pyedb/generic/process.py +44 -108
- pyedb/generic/settings.py +75 -19
- pyedb/grpc/__init__.py +0 -0
- pyedb/grpc/database/components.py +55 -17
- pyedb/grpc/database/control_file.py +5 -5
- pyedb/grpc/database/definition/materials.py +24 -31
- pyedb/grpc/database/definition/package_def.py +18 -18
- pyedb/grpc/database/definition/padstack_def.py +104 -51
- pyedb/grpc/database/geometry/arc_data.py +7 -5
- pyedb/grpc/database/geometry/point_3d_data.py +8 -7
- pyedb/grpc/database/geometry/polygon_data.py +4 -3
- pyedb/grpc/database/hierarchy/component.py +43 -38
- pyedb/grpc/database/hierarchy/pin_pair_model.py +15 -14
- pyedb/grpc/database/hierarchy/pingroup.py +9 -9
- pyedb/grpc/database/layers/stackup_layer.py +45 -44
- pyedb/grpc/database/layout/layout.py +17 -13
- pyedb/grpc/database/layout/voltage_regulator.py +7 -7
- pyedb/grpc/database/layout_validation.py +16 -15
- pyedb/grpc/database/modeler.py +60 -58
- pyedb/grpc/database/net/net.py +15 -14
- pyedb/grpc/database/nets.py +112 -31
- pyedb/grpc/database/padstacks.py +303 -190
- pyedb/grpc/database/ports/ports.py +5 -6
- pyedb/grpc/database/primitive/bondwire.py +8 -7
- pyedb/grpc/database/primitive/circle.py +4 -4
- pyedb/grpc/database/primitive/padstack_instance.py +191 -23
- pyedb/grpc/database/primitive/path.py +7 -7
- pyedb/grpc/database/primitive/polygon.py +3 -3
- pyedb/grpc/database/primitive/primitive.py +13 -17
- pyedb/grpc/database/primitive/rectangle.py +13 -13
- pyedb/grpc/database/simulation_setup/hfss_general_settings.py +1 -1
- pyedb/grpc/database/simulation_setup/hfss_simulation_setup.py +10 -0
- pyedb/grpc/database/simulation_setup/siwave_simulation_setup.py +17 -1
- pyedb/grpc/database/siwave.py +31 -25
- pyedb/grpc/database/source_excitations.py +335 -233
- pyedb/grpc/database/stackup.py +165 -148
- pyedb/grpc/database/terminal/bundle_terminal.py +18 -8
- pyedb/grpc/database/terminal/edge_terminal.py +10 -0
- pyedb/grpc/database/terminal/padstack_instance_terminal.py +16 -5
- pyedb/grpc/database/terminal/pingroup_terminal.py +12 -11
- pyedb/grpc/database/terminal/point_terminal.py +4 -3
- pyedb/grpc/database/terminal/terminal.py +9 -9
- pyedb/grpc/database/utility/value.py +109 -0
- pyedb/grpc/database/utility/xml_control_file.py +5 -5
- pyedb/grpc/edb.py +130 -63
- pyedb/grpc/edb_init.py +3 -10
- pyedb/grpc/rpc_session.py +10 -10
- pyedb/libraries/common.py +366 -0
- pyedb/libraries/rf_libraries/base_functions.py +1358 -0
- pyedb/libraries/rf_libraries/planar_antennas.py +628 -0
- pyedb/misc/decorators.py +61 -0
- pyedb/misc/misc.py +0 -13
- pyedb/siwave.py +2 -2
- {pyedb-0.53.0.dist-info → pyedb-0.55.0.dist-info}/METADATA +2 -3
- {pyedb-0.53.0.dist-info → pyedb-0.55.0.dist-info}/RECORD +119 -112
- {pyedb-0.53.0.dist-info → pyedb-0.55.0.dist-info}/WHEEL +0 -0
- {pyedb-0.53.0.dist-info → pyedb-0.55.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -23,7 +23,9 @@
|
|
|
23
23
|
"""
|
|
24
24
|
This module contains the `EdbPadstacks` class.
|
|
25
25
|
"""
|
|
26
|
+
from collections import defaultdict
|
|
26
27
|
import math
|
|
28
|
+
from typing import Dict, List
|
|
27
29
|
import warnings
|
|
28
30
|
|
|
29
31
|
import numpy as np
|
|
@@ -82,7 +84,7 @@ class EdbPadstacks(object):
|
|
|
82
84
|
@property
|
|
83
85
|
def _edb(self):
|
|
84
86
|
""" """
|
|
85
|
-
return self._pedb.
|
|
87
|
+
return self._pedb.core
|
|
86
88
|
|
|
87
89
|
def _get_edb_value(self, value):
|
|
88
90
|
return self._pedb.edb_value(value)
|
|
@@ -126,15 +128,15 @@ class EdbPadstacks(object):
|
|
|
126
128
|
"""
|
|
127
129
|
|
|
128
130
|
if val == 0:
|
|
129
|
-
return self._edb.
|
|
131
|
+
return self._edb.Definition.PadType.RegularPad
|
|
130
132
|
elif val == 1:
|
|
131
|
-
return self._edb.
|
|
133
|
+
return self._edb.Definition.PadType.AntiPad
|
|
132
134
|
elif val == 2:
|
|
133
|
-
return self._edb.
|
|
135
|
+
return self._edb.Definition.PadType.ThermalPad
|
|
134
136
|
elif val == 3:
|
|
135
|
-
return self._edb.
|
|
137
|
+
return self._edb.Definition.PadType.Hole
|
|
136
138
|
elif val == 4:
|
|
137
|
-
return self._edb.
|
|
139
|
+
return self._edb.Definition.PadType.UnknownGeomType
|
|
138
140
|
else:
|
|
139
141
|
return val
|
|
140
142
|
|
|
@@ -151,29 +153,29 @@ class EdbPadstacks(object):
|
|
|
151
153
|
EDB.PadGeometryType enumerator value.
|
|
152
154
|
"""
|
|
153
155
|
if val == 0:
|
|
154
|
-
return self._edb.
|
|
156
|
+
return self._edb.Definition.PadGeometryType.NoGeometry
|
|
155
157
|
elif val == 1:
|
|
156
|
-
return self._edb.
|
|
158
|
+
return self._edb.Definition.PadGeometryType.Circle
|
|
157
159
|
elif val == 2:
|
|
158
|
-
return self._edb.
|
|
160
|
+
return self._edb.Definition.PadGeometryType.Square
|
|
159
161
|
elif val == 3:
|
|
160
|
-
return self._edb.
|
|
162
|
+
return self._edb.Definition.PadGeometryType.Rectangle
|
|
161
163
|
elif val == 4:
|
|
162
|
-
return self._edb.
|
|
164
|
+
return self._edb.Definition.PadGeometryType.Oval
|
|
163
165
|
elif val == 5:
|
|
164
|
-
return self._edb.
|
|
166
|
+
return self._edb.Definition.PadGeometryType.Bullet
|
|
165
167
|
elif val == 6:
|
|
166
|
-
return self._edb.
|
|
168
|
+
return self._edb.Definition.PadGeometryType.NSidedPolygon
|
|
167
169
|
elif val == 7:
|
|
168
|
-
return self._edb.
|
|
170
|
+
return self._edb.Definition.PadGeometryType.Polygon
|
|
169
171
|
elif val == 8:
|
|
170
|
-
return self._edb.
|
|
172
|
+
return self._edb.Definition.PadGeometryType.Round45
|
|
171
173
|
elif val == 9:
|
|
172
|
-
return self._edb.
|
|
174
|
+
return self._edb.Definition.PadGeometryType.Round90
|
|
173
175
|
elif val == 10:
|
|
174
|
-
return self._edb.
|
|
176
|
+
return self._edb.Definition.PadGeometryType.Square45
|
|
175
177
|
elif val == 11:
|
|
176
|
-
return self._edb.
|
|
178
|
+
return self._edb.Definition.PadGeometryType.Square90
|
|
177
179
|
else:
|
|
178
180
|
return val
|
|
179
181
|
|
|
@@ -187,10 +189,10 @@ class EdbPadstacks(object):
|
|
|
187
189
|
List of definitions via padstack definitions.
|
|
188
190
|
|
|
189
191
|
"""
|
|
190
|
-
if len(self._definitions) == len(self._pedb.
|
|
192
|
+
if len(self._definitions) == len(list(self._pedb._db.PadstackDefs)):
|
|
191
193
|
return self._definitions
|
|
192
194
|
self._definitions = {}
|
|
193
|
-
for padstackdef in self._pedb.
|
|
195
|
+
for padstackdef in list(self._pedb._db.PadstackDefs):
|
|
194
196
|
PadStackData = padstackdef.GetData()
|
|
195
197
|
if len(PadStackData.GetLayerNames()) >= 1:
|
|
196
198
|
self._definitions[padstackdef.GetName()] = EDBPadstack(padstackdef, self)
|
|
@@ -329,11 +331,11 @@ class EdbPadstacks(object):
|
|
|
329
331
|
|
|
330
332
|
class PadType:
|
|
331
333
|
(RegularPad, AntiPad, ThermalPad, Hole, UnknownGeomType) = (
|
|
332
|
-
self._edb.
|
|
333
|
-
self._edb.
|
|
334
|
-
self._edb.
|
|
335
|
-
self._edb.
|
|
336
|
-
self._edb.
|
|
334
|
+
self._edb.Definition.PadType.RegularPad,
|
|
335
|
+
self._edb.Definition.PadType.AntiPad,
|
|
336
|
+
self._edb.Definition.PadType.ThermalPad,
|
|
337
|
+
self._edb.Definition.PadType.Hole,
|
|
338
|
+
self._edb.Definition.PadType.UnknownGeomType,
|
|
337
339
|
)
|
|
338
340
|
|
|
339
341
|
return PadType
|
|
@@ -372,32 +374,32 @@ class EdbPadstacks(object):
|
|
|
372
374
|
Name of the padstack if the operation is successful.
|
|
373
375
|
"""
|
|
374
376
|
|
|
375
|
-
PadStack = self._edb.
|
|
376
|
-
new_PadStackData = self._edb.
|
|
377
|
+
PadStack = self._edb.Definition.PadstackDef.Create(self._layout.cell.GetDatabase(), padstackname)
|
|
378
|
+
new_PadStackData = self._edb.Definition.PadstackDefData.Create()
|
|
377
379
|
list_values = convert_py_list_to_net_list(
|
|
378
380
|
[self._get_edb_value(holediam), self._get_edb_value(paddiam), self._get_edb_value(antipaddiam)]
|
|
379
381
|
)
|
|
380
382
|
value0 = self._get_edb_value(0.0)
|
|
381
383
|
new_PadStackData.SetHoleParameters(
|
|
382
|
-
self._edb.
|
|
384
|
+
self._edb.Definition.PadGeometryType.Circle,
|
|
383
385
|
list_values,
|
|
384
386
|
value0,
|
|
385
387
|
value0,
|
|
386
388
|
value0,
|
|
387
389
|
)
|
|
388
|
-
new_PadStackData.SetHoleRange(self._edb.
|
|
390
|
+
new_PadStackData.SetHoleRange(self._edb.Definition.PadstackHoleRange.UpperPadToLowerPad)
|
|
389
391
|
layers = list(self._pedb.stackup.signal_layers.keys())
|
|
390
392
|
if not startlayer:
|
|
391
393
|
startlayer = layers[0]
|
|
392
394
|
if not endlayer:
|
|
393
395
|
endlayer = layers[len(layers) - 1]
|
|
394
396
|
|
|
395
|
-
antipad_shape = self._edb.
|
|
397
|
+
antipad_shape = self._edb.Definition.PadGeometryType.Circle
|
|
396
398
|
started = False
|
|
397
399
|
new_PadStackData.SetPadParameters(
|
|
398
400
|
"Default",
|
|
399
|
-
self._edb.
|
|
400
|
-
self._edb.
|
|
401
|
+
self._edb.Definition.PadType.RegularPad,
|
|
402
|
+
self._edb.Definition.PadGeometryType.Circle,
|
|
401
403
|
convert_py_list_to_net_list([self._get_edb_value(paddiam)]),
|
|
402
404
|
value0,
|
|
403
405
|
value0,
|
|
@@ -406,7 +408,7 @@ class EdbPadstacks(object):
|
|
|
406
408
|
|
|
407
409
|
new_PadStackData.SetPadParameters(
|
|
408
410
|
"Default",
|
|
409
|
-
self._edb.
|
|
411
|
+
self._edb.Definition.PadType.AntiPad,
|
|
410
412
|
antipad_shape,
|
|
411
413
|
convert_py_list_to_net_list([self._get_edb_value(antipaddiam)]),
|
|
412
414
|
value0,
|
|
@@ -421,8 +423,8 @@ class EdbPadstacks(object):
|
|
|
421
423
|
if started:
|
|
422
424
|
new_PadStackData.SetPadParameters(
|
|
423
425
|
layer,
|
|
424
|
-
self._edb.
|
|
425
|
-
self._edb.
|
|
426
|
+
self._edb.Definition.PadType.RegularPad,
|
|
427
|
+
self._edb.Definition.PadGeometryType.Circle,
|
|
426
428
|
convert_py_list_to_net_list([self._get_edb_value(paddiam)]),
|
|
427
429
|
value0,
|
|
428
430
|
value0,
|
|
@@ -430,7 +432,7 @@ class EdbPadstacks(object):
|
|
|
430
432
|
)
|
|
431
433
|
new_PadStackData.SetPadParameters(
|
|
432
434
|
layer,
|
|
433
|
-
self._edb.
|
|
435
|
+
self._edb.Definition.PadType.AntiPad,
|
|
434
436
|
antipad_shape,
|
|
435
437
|
convert_py_list_to_net_list([self._get_edb_value(antipaddiam)]),
|
|
436
438
|
value0,
|
|
@@ -491,13 +493,13 @@ class EdbPadstacks(object):
|
|
|
491
493
|
|
|
492
494
|
else:
|
|
493
495
|
psdef = padstackInst._edb_object.GetPadstackDef()
|
|
494
|
-
newdefdata = self._edb.
|
|
495
|
-
newdefdata.SetSolderBallShape(self._edb.
|
|
496
|
+
newdefdata = self._edb.Definition.PadstackDefData(psdef.GetData())
|
|
497
|
+
newdefdata.SetSolderBallShape(self._edb.Definition.SolderballShape.Cylinder)
|
|
496
498
|
newdefdata.SetSolderBallParameter(self._get_edb_value(ballDiam), self._get_edb_value(ballDiam))
|
|
497
499
|
sball_placement = (
|
|
498
|
-
self._edb.
|
|
500
|
+
self._edb.Definition.SolderballPlacement.AbovePadstack
|
|
499
501
|
if isTopPlaced
|
|
500
|
-
else self._edb.
|
|
502
|
+
else self._edb.Definition.SolderballPlacement.BelowPadstack
|
|
501
503
|
)
|
|
502
504
|
newdefdata.SetSolderBallPlacement(sball_placement)
|
|
503
505
|
psdef.SetData(newdefdata)
|
|
@@ -558,7 +560,7 @@ class EdbPadstacks(object):
|
|
|
558
560
|
if self._port_exist(port_name):
|
|
559
561
|
port_name = generate_unique_name(port_name, n=2)
|
|
560
562
|
self._logger.info("An existing port already has this same name. Renaming to {}.".format(port_name))
|
|
561
|
-
self._edb.
|
|
563
|
+
self._edb.Cell.Terminal.PadstackInstanceTerminal.Create(
|
|
562
564
|
self._active_layout,
|
|
563
565
|
padstackinstance.GetNet(),
|
|
564
566
|
port_name,
|
|
@@ -631,7 +633,7 @@ class EdbPadstacks(object):
|
|
|
631
633
|
else:
|
|
632
634
|
if not isinstance(pin, EDBPadstackInstance):
|
|
633
635
|
pin = EDBPadstackInstance(pin, self._pedb)
|
|
634
|
-
padparams = self._edb.
|
|
636
|
+
padparams = self._edb.Definition.PadstackDefData(
|
|
635
637
|
pin._edb_object.GetPadstackDef().GetData()
|
|
636
638
|
).GetPadParametersValue(layername, self.int_to_pad_type(pad_type))
|
|
637
639
|
if padparams[2]:
|
|
@@ -642,12 +644,12 @@ class EdbPadstacks(object):
|
|
|
642
644
|
rotation = padparams[5].ToDouble()
|
|
643
645
|
return geometry_type, parameters, offset_x, offset_y, rotation
|
|
644
646
|
else:
|
|
645
|
-
if isinstance(pin, self._edb.
|
|
646
|
-
padparams = self._edb.
|
|
647
|
+
if isinstance(pin, self._edb.Definition.PadstackDef):
|
|
648
|
+
padparams = self._edb.Definition.PadstackDefData(pin.GetData()).GetPolygonalPadParameters(
|
|
647
649
|
layername, self.int_to_pad_type(pad_type)
|
|
648
650
|
)
|
|
649
651
|
else:
|
|
650
|
-
padparams = self._edb.
|
|
652
|
+
padparams = self._edb.Definition.PadstackDefData(
|
|
651
653
|
pin._edb_object.GetPadstackDef().GetData()
|
|
652
654
|
).GetPolygonalPadParameters(layername, self.int_to_pad_type(pad_type))
|
|
653
655
|
|
|
@@ -680,7 +682,7 @@ class EdbPadstacks(object):
|
|
|
680
682
|
"""
|
|
681
683
|
if self.definitions:
|
|
682
684
|
for padstack in list(self.definitions.values()):
|
|
683
|
-
cloned_padstack_data = self._edb.
|
|
685
|
+
cloned_padstack_data = self._edb.Definition.PadstackDefData(padstack.edb_padstack.GetData())
|
|
684
686
|
layers_name = cloned_padstack_data.GetLayerNames()
|
|
685
687
|
all_succeed = True
|
|
686
688
|
for layer in layers_name:
|
|
@@ -691,11 +693,11 @@ class EdbPadstacks(object):
|
|
|
691
693
|
params = convert_py_list_to_net_list(
|
|
692
694
|
[self._pedb.edb_value(value)] * len(parameters)
|
|
693
695
|
) # pragma no cover
|
|
694
|
-
geom = self._edb.
|
|
696
|
+
geom = self._edb.Definition.PadGeometryType.Circle
|
|
695
697
|
offset_x = self._pedb.edb_value(offset_x)
|
|
696
698
|
offset_y = self._pedb.edb_value(offset_y)
|
|
697
699
|
rot = self._pedb.edb_value(rot)
|
|
698
|
-
antipad = self._edb.
|
|
700
|
+
antipad = self._edb.Definition.PadType.AntiPad
|
|
699
701
|
if cloned_padstack_data.SetPadParameters(
|
|
700
702
|
layer, antipad, geom, params, offset_x, offset_y, rot
|
|
701
703
|
): # pragma no cover
|
|
@@ -943,9 +945,9 @@ class EdbPadstacks(object):
|
|
|
943
945
|
if not padstackname:
|
|
944
946
|
padstackname = generate_unique_name("VIA")
|
|
945
947
|
# assert not self.isreadonly, "Write Functions are not available within AEDT"
|
|
946
|
-
padstackData = self._edb.
|
|
948
|
+
padstackData = self._edb.Definition.PadstackDefData.Create()
|
|
947
949
|
if has_hole and not polygon_hole:
|
|
948
|
-
ptype = self._edb.
|
|
950
|
+
ptype = self._edb.Definition.PadGeometryType.Circle
|
|
949
951
|
hole_param = Array[type(holediam)]([holediam])
|
|
950
952
|
padstackData.SetHoleParameters(ptype, hole_param, value0, value0, value0)
|
|
951
953
|
padstackData.SetHolePlatingPercentage(self._get_edb_value(20.0))
|
|
@@ -964,7 +966,7 @@ class EdbPadstacks(object):
|
|
|
964
966
|
padstackData.SetPolygonalHoleParameters(hole_param, value0, value0, value0)
|
|
965
967
|
padstackData.SetHolePlatingPercentage(self._get_edb_value(20.0))
|
|
966
968
|
else:
|
|
967
|
-
ptype = self._edb.
|
|
969
|
+
ptype = self._edb.Definition.PadGeometryType.NoGeometry
|
|
968
970
|
|
|
969
971
|
x_size = self._get_edb_value(x_size)
|
|
970
972
|
y_size = self._get_edb_value(y_size)
|
|
@@ -980,13 +982,13 @@ class EdbPadstacks(object):
|
|
|
980
982
|
anti_pad_y_size = self._get_edb_value(anti_pad_y_size)
|
|
981
983
|
|
|
982
984
|
if hole_range == "through": # pragma no cover
|
|
983
|
-
padstackData.SetHoleRange(self._edb.
|
|
985
|
+
padstackData.SetHoleRange(self._edb.Definition.PadstackHoleRange.Through)
|
|
984
986
|
elif hole_range == "begin_on_upper_pad": # pragma no cover
|
|
985
|
-
padstackData.SetHoleRange(self._edb.
|
|
987
|
+
padstackData.SetHoleRange(self._edb.Definition.PadstackHoleRange.BeginOnUpperPad)
|
|
986
988
|
elif hole_range == "end_on_lower_pad": # pragma no cover
|
|
987
|
-
padstackData.SetHoleRange(self._edb.
|
|
989
|
+
padstackData.SetHoleRange(self._edb.Definition.PadstackHoleRange.EndOnLowerPad)
|
|
988
990
|
elif hole_range == "upper_pad_to_lower_pad": # pragma no cover
|
|
989
|
-
padstackData.SetHoleRange(self._edb.
|
|
991
|
+
padstackData.SetHoleRange(self._edb.Definition.PadstackHoleRange.UpperPadToLowerPad)
|
|
990
992
|
else: # pragma no cover
|
|
991
993
|
self._logger.error("Unknown padstack hole range")
|
|
992
994
|
padstackData.SetMaterial("copper")
|
|
@@ -997,10 +999,10 @@ class EdbPadstacks(object):
|
|
|
997
999
|
layers = layers[: layers.index(stop_layer) + 1]
|
|
998
1000
|
pad_array = Array[type(paddiam)]([paddiam])
|
|
999
1001
|
if pad_shape == "Circle": # pragma no cover
|
|
1000
|
-
pad_shape = self._edb.
|
|
1002
|
+
pad_shape = self._edb.Definition.PadGeometryType.Circle
|
|
1001
1003
|
elif pad_shape == "Rectangle": # pragma no cover
|
|
1002
1004
|
pad_array = Array[type(x_size)]([x_size, y_size])
|
|
1003
|
-
pad_shape = self._edb.
|
|
1005
|
+
pad_shape = self._edb.Definition.PadGeometryType.Rectangle
|
|
1004
1006
|
elif pad_shape == "Polygon":
|
|
1005
1007
|
if isinstance(pad_polygon, list):
|
|
1006
1008
|
_poly = self._pedb.modeler.create_polygon(pad_polygon, layers[0], net_name="dummy")
|
|
@@ -1013,10 +1015,10 @@ class EdbPadstacks(object):
|
|
|
1013
1015
|
pad_array = pad_polygon
|
|
1014
1016
|
if antipad_shape == "Bullet": # pragma no cover
|
|
1015
1017
|
antipad_array = Array[type(x_size)]([x_size, y_size, corner_radius])
|
|
1016
|
-
antipad_shape = self._edb.
|
|
1018
|
+
antipad_shape = self._edb.Definition.PadGeometryType.Bullet
|
|
1017
1019
|
elif antipad_shape == "Rectangle": # pragma no cover
|
|
1018
1020
|
antipad_array = Array[type(anti_pad_x_size)]([anti_pad_x_size, anti_pad_y_size])
|
|
1019
|
-
antipad_shape = self._edb.
|
|
1021
|
+
antipad_shape = self._edb.Definition.PadGeometryType.Rectangle
|
|
1020
1022
|
elif antipad_shape == "Polygon":
|
|
1021
1023
|
if isinstance(antipad_polygon, list):
|
|
1022
1024
|
_poly = self._pedb.modeler.create_polygon(antipad_polygon, layers[0], net_name="dummy")
|
|
@@ -1029,14 +1031,14 @@ class EdbPadstacks(object):
|
|
|
1029
1031
|
antipad_array = antipad_polygon
|
|
1030
1032
|
else: # pragma no cover
|
|
1031
1033
|
antipad_array = Array[type(antipaddiam)]([antipaddiam])
|
|
1032
|
-
antipad_shape = self._edb.
|
|
1034
|
+
antipad_shape = self._edb.Definition.PadGeometryType.Circle
|
|
1033
1035
|
if add_default_layer: # pragma no cover
|
|
1034
1036
|
layers = layers + ["Default"]
|
|
1035
1037
|
if antipad_shape == "Polygon" and pad_shape == "Polygon":
|
|
1036
1038
|
for layer in layers:
|
|
1037
1039
|
padstackData.SetPolygonalPadParameters(
|
|
1038
1040
|
layer,
|
|
1039
|
-
self._edb.
|
|
1041
|
+
self._edb.Definition.PadType.RegularPad,
|
|
1040
1042
|
pad_array._edb_object,
|
|
1041
1043
|
pad_offset_x,
|
|
1042
1044
|
pad_offset_y,
|
|
@@ -1044,7 +1046,7 @@ class EdbPadstacks(object):
|
|
|
1044
1046
|
)
|
|
1045
1047
|
padstackData.SetPolygonalPadParameters(
|
|
1046
1048
|
layer,
|
|
1047
|
-
self._edb.
|
|
1049
|
+
self._edb.Definition.PadType.AntiPad,
|
|
1048
1050
|
antipad_array._edb_object,
|
|
1049
1051
|
pad_offset_x,
|
|
1050
1052
|
pad_offset_y,
|
|
@@ -1054,7 +1056,7 @@ class EdbPadstacks(object):
|
|
|
1054
1056
|
for layer in layers:
|
|
1055
1057
|
padstackData.SetPadParameters(
|
|
1056
1058
|
layer,
|
|
1057
|
-
self._edb.
|
|
1059
|
+
self._edb.Definition.PadType.RegularPad,
|
|
1058
1060
|
pad_shape,
|
|
1059
1061
|
pad_array,
|
|
1060
1062
|
pad_offset_x,
|
|
@@ -1064,7 +1066,7 @@ class EdbPadstacks(object):
|
|
|
1064
1066
|
|
|
1065
1067
|
padstackData.SetPadParameters(
|
|
1066
1068
|
layer,
|
|
1067
|
-
self._edb.
|
|
1069
|
+
self._edb.Definition.PadType.AntiPad,
|
|
1068
1070
|
antipad_shape,
|
|
1069
1071
|
antipad_array,
|
|
1070
1072
|
offset_x,
|
|
@@ -1072,7 +1074,7 @@ class EdbPadstacks(object):
|
|
|
1072
1074
|
rotation,
|
|
1073
1075
|
)
|
|
1074
1076
|
|
|
1075
|
-
padstackDefinition = self._edb.
|
|
1077
|
+
padstackDefinition = self._edb.Definition.PadstackDef.Create(self.db, padstackname)
|
|
1076
1078
|
padstackDefinition.SetData(padstackData)
|
|
1077
1079
|
self._logger.info("Padstack %s create correctly", padstackname)
|
|
1078
1080
|
return padstackname
|
|
@@ -1121,12 +1123,12 @@ class EdbPadstacks(object):
|
|
|
1121
1123
|
Name of the new padstack.
|
|
1122
1124
|
"""
|
|
1123
1125
|
p1 = self.definitions[target_padstack_name].edb_padstack.GetData()
|
|
1124
|
-
new_padstack_definition_data = self._edb.
|
|
1126
|
+
new_padstack_definition_data = self._edb.Definition.PadstackDefData(p1)
|
|
1125
1127
|
|
|
1126
1128
|
if not new_padstack_name:
|
|
1127
1129
|
new_padstack_name = generate_unique_name(target_padstack_name)
|
|
1128
1130
|
|
|
1129
|
-
padstack_definition = self._edb.
|
|
1131
|
+
padstack_definition = self._edb.Definition.PadstackDef.Create(self.db, new_padstack_name)
|
|
1130
1132
|
padstack_definition.SetData(new_padstack_definition_data)
|
|
1131
1133
|
|
|
1132
1134
|
return new_padstack_name
|
|
@@ -1175,7 +1177,8 @@ class EdbPadstacks(object):
|
|
|
1175
1177
|
for pad in list(self.definitions.keys()):
|
|
1176
1178
|
if pad == definition_name:
|
|
1177
1179
|
padstack = self.definitions[pad].edb_padstack
|
|
1178
|
-
position = self._edb.
|
|
1180
|
+
# position = self._edb.Geometry.PointData(position[0], position[1])
|
|
1181
|
+
position = self._pedb.pedb_class.database.geometry.point_data.PointData.create_from_xy(self._pedb, *position)
|
|
1179
1182
|
net = self._pedb.nets.find_or_create_net(net_name)
|
|
1180
1183
|
rotation = (
|
|
1181
1184
|
self._get_edb_value(rotation * math.pi / 180)
|
|
@@ -1202,20 +1205,20 @@ class EdbPadstacks(object):
|
|
|
1202
1205
|
if solderlayer:
|
|
1203
1206
|
solderlayer = sign_layers_values[solderlayer]._edb_layer
|
|
1204
1207
|
if padstack:
|
|
1205
|
-
padstack_instance = self._edb.
|
|
1208
|
+
padstack_instance = self._edb.Cell.Primitive.PadstackInstance.Create(
|
|
1206
1209
|
self._active_layout,
|
|
1207
|
-
net,
|
|
1210
|
+
net._edb_object,
|
|
1208
1211
|
via_name,
|
|
1209
1212
|
padstack,
|
|
1210
|
-
position,
|
|
1213
|
+
position._edb_object,
|
|
1211
1214
|
rotation,
|
|
1212
1215
|
fromlayer,
|
|
1213
1216
|
tolayer,
|
|
1214
1217
|
solderlayer,
|
|
1215
1218
|
None,
|
|
1216
1219
|
)
|
|
1217
|
-
padstack_instance.
|
|
1218
|
-
py_padstack_instance = EDBPadstackInstance(padstack_instance
|
|
1220
|
+
padstack_instance.SetIsLayoutPin(is_pin)
|
|
1221
|
+
py_padstack_instance = EDBPadstackInstance(padstack_instance, self._pedb)
|
|
1219
1222
|
|
|
1220
1223
|
return py_padstack_instance
|
|
1221
1224
|
else:
|
|
@@ -1290,12 +1293,12 @@ class EdbPadstacks(object):
|
|
|
1290
1293
|
bool
|
|
1291
1294
|
``True`` if successful.
|
|
1292
1295
|
"""
|
|
1293
|
-
pad_type = self._edb.
|
|
1294
|
-
pad_geo = self._edb.
|
|
1296
|
+
pad_type = self._edb.Definition.PadType.RegularPad
|
|
1297
|
+
pad_geo = self._edb.Definition.PadGeometryType.Circle
|
|
1295
1298
|
vals = self._get_edb_value(0)
|
|
1296
1299
|
params = convert_py_list_to_net_list([self._get_edb_value(0)])
|
|
1297
1300
|
p1 = self.definitions[padstack_name].edb_padstack.GetData()
|
|
1298
|
-
newPadstackDefinitionData = self._edb.
|
|
1301
|
+
newPadstackDefinitionData = self._edb.Definition.PadstackDefData(p1)
|
|
1299
1302
|
|
|
1300
1303
|
if not layer_name:
|
|
1301
1304
|
layer_name = list(self._pedb.stackup.signal_layers.keys())
|
|
@@ -1358,11 +1361,11 @@ class EdbPadstacks(object):
|
|
|
1358
1361
|
``True`` if successful.
|
|
1359
1362
|
"""
|
|
1360
1363
|
shape_dict = {
|
|
1361
|
-
"Circle": self._edb.
|
|
1362
|
-
"Square": self._edb.
|
|
1363
|
-
"Rectangle": self._edb.
|
|
1364
|
-
"Oval": self._edb.
|
|
1365
|
-
"Bullet": self._edb.
|
|
1364
|
+
"Circle": self._edb.Definition.PadGeometryType.Circle,
|
|
1365
|
+
"Square": self._edb.Definition.PadGeometryType.Square,
|
|
1366
|
+
"Rectangle": self._edb.Definition.PadGeometryType.Rectangle,
|
|
1367
|
+
"Oval": self._edb.Definition.PadGeometryType.Oval,
|
|
1368
|
+
"Bullet": self._edb.Definition.PadGeometryType.Bullet,
|
|
1366
1369
|
}
|
|
1367
1370
|
pad_shape = shape_dict[pad_shape]
|
|
1368
1371
|
if not isinstance(pad_params, list):
|
|
@@ -1381,7 +1384,7 @@ class EdbPadstacks(object):
|
|
|
1381
1384
|
antipad_rotation = self._get_edb_value(antipad_rotation)
|
|
1382
1385
|
|
|
1383
1386
|
p1 = self.definitions[padstack_name].edb_padstack.GetData()
|
|
1384
|
-
new_padstack_def = self._edb.
|
|
1387
|
+
new_padstack_def = self._edb.Definition.PadstackDefData(p1)
|
|
1385
1388
|
if not layer_name:
|
|
1386
1389
|
layer_name = list(self._pedb.stackup.signal_layers.keys())
|
|
1387
1390
|
elif isinstance(layer_name, str):
|
|
@@ -1389,7 +1392,7 @@ class EdbPadstacks(object):
|
|
|
1389
1392
|
for layer in layer_name:
|
|
1390
1393
|
new_padstack_def.SetPadParameters(
|
|
1391
1394
|
layer,
|
|
1392
|
-
self._edb.
|
|
1395
|
+
self._edb.Definition.PadType.RegularPad,
|
|
1393
1396
|
pad_shape,
|
|
1394
1397
|
pad_params,
|
|
1395
1398
|
pad_x_offset,
|
|
@@ -1398,7 +1401,7 @@ class EdbPadstacks(object):
|
|
|
1398
1401
|
)
|
|
1399
1402
|
new_padstack_def.SetPadParameters(
|
|
1400
1403
|
layer,
|
|
1401
|
-
self._edb.
|
|
1404
|
+
self._edb.Definition.PadType.AntiPad,
|
|
1402
1405
|
antipad_shape,
|
|
1403
1406
|
antipad_params,
|
|
1404
1407
|
antipad_x_offset,
|
|
@@ -1871,3 +1874,72 @@ class EdbPadstacks(object):
|
|
|
1871
1874
|
all_instances[item].delete()
|
|
1872
1875
|
|
|
1873
1876
|
return True
|
|
1877
|
+
|
|
1878
|
+
@staticmethod
|
|
1879
|
+
def dbscan(
|
|
1880
|
+
padstack: Dict[int, List[float]], max_distance: float = 1e-3, min_samples: int = 5
|
|
1881
|
+
) -> Dict[int, List[str]]:
|
|
1882
|
+
"""
|
|
1883
|
+
density based spatial clustering for padstack instances
|
|
1884
|
+
|
|
1885
|
+
Parameters
|
|
1886
|
+
----------
|
|
1887
|
+
padstack : dict.
|
|
1888
|
+
padstack id: [x, y]
|
|
1889
|
+
|
|
1890
|
+
max_distance: float
|
|
1891
|
+
maximum distance between two points to be included in one cluster
|
|
1892
|
+
|
|
1893
|
+
min_samples: int
|
|
1894
|
+
minimum number of points that a cluster must have
|
|
1895
|
+
|
|
1896
|
+
Returns
|
|
1897
|
+
-------
|
|
1898
|
+
dict
|
|
1899
|
+
clusters {cluster label: [padstack ids]} <
|
|
1900
|
+
"""
|
|
1901
|
+
|
|
1902
|
+
padstack_ids = list(padstack.keys())
|
|
1903
|
+
xy_array = np.array([padstack[pid] for pid in padstack_ids])
|
|
1904
|
+
n = len(padstack_ids)
|
|
1905
|
+
|
|
1906
|
+
labels = -1 * np.ones(n, dtype=int)
|
|
1907
|
+
visited = np.zeros(n, dtype=bool)
|
|
1908
|
+
cluster_id = 0
|
|
1909
|
+
|
|
1910
|
+
def region_query(point_idx):
|
|
1911
|
+
distances = np.linalg.norm(xy_array - xy_array[point_idx], axis=1)
|
|
1912
|
+
return np.where(distances <= max_distance)[0]
|
|
1913
|
+
|
|
1914
|
+
def expand_cluster(point_idx, neighbors):
|
|
1915
|
+
nonlocal cluster_id
|
|
1916
|
+
labels[point_idx] = cluster_id
|
|
1917
|
+
i = 0
|
|
1918
|
+
while i < len(neighbors):
|
|
1919
|
+
neighbor_idx = neighbors[i]
|
|
1920
|
+
if not visited[neighbor_idx]:
|
|
1921
|
+
visited[neighbor_idx] = True
|
|
1922
|
+
neighbor_neighbors = region_query(neighbor_idx)
|
|
1923
|
+
if len(neighbor_neighbors) >= min_samples:
|
|
1924
|
+
neighbors = np.concatenate((neighbors, neighbor_neighbors))
|
|
1925
|
+
if labels[neighbor_idx] == -1:
|
|
1926
|
+
labels[neighbor_idx] = cluster_id
|
|
1927
|
+
i += 1
|
|
1928
|
+
|
|
1929
|
+
for point_idx in range(n):
|
|
1930
|
+
if visited[point_idx]:
|
|
1931
|
+
continue
|
|
1932
|
+
visited[point_idx] = True
|
|
1933
|
+
neighbors = region_query(point_idx)
|
|
1934
|
+
if len(neighbors) < min_samples:
|
|
1935
|
+
labels[point_idx] = -1
|
|
1936
|
+
else:
|
|
1937
|
+
expand_cluster(point_idx, neighbors)
|
|
1938
|
+
cluster_id += 1
|
|
1939
|
+
|
|
1940
|
+
# group point IDs by label
|
|
1941
|
+
clusters = defaultdict(list)
|
|
1942
|
+
for i, label in enumerate(labels):
|
|
1943
|
+
clusters[int(label)].append(padstack_ids[i])
|
|
1944
|
+
|
|
1945
|
+
return dict(clusters)
|
|
@@ -19,6 +19,7 @@
|
|
|
19
19
|
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
20
|
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
21
|
# SOFTWARE.
|
|
22
|
+
import warnings
|
|
22
23
|
|
|
23
24
|
from pyedb.dotnet.database.sim_setup_data.data.adaptive_frequency_data import (
|
|
24
25
|
AdaptiveFrequencyData,
|
|
@@ -901,6 +902,24 @@ class HfssSolverSettings(object):
|
|
|
901
902
|
def enhanced_low_freq_accuracy(self):
|
|
902
903
|
"""Whether to enable legacy low-frequency sampling.
|
|
903
904
|
|
|
905
|
+
.. deprecated:: pyedb 0.54.0
|
|
906
|
+
Use :func:`enhanced_low_frequency_accuracy` instead.
|
|
907
|
+
|
|
908
|
+
Returns
|
|
909
|
+
-------
|
|
910
|
+
bool
|
|
911
|
+
``True`` if low frequency accuracy is used, ``False`` otherwise.
|
|
912
|
+
"""
|
|
913
|
+
warnings.warn(
|
|
914
|
+
"`enhanced_low_freq_accuracy` is deprecated, use `enhanced_low_frequency_accuracy` instead.",
|
|
915
|
+
DeprecationWarning,
|
|
916
|
+
)
|
|
917
|
+
return self._hfss_solver_settings.EnhancedLowFreqAccuracy
|
|
918
|
+
|
|
919
|
+
@property
|
|
920
|
+
def enhanced_low_frequency_accuracy(self):
|
|
921
|
+
"""Whether to enable legacy low-frequency sampling.
|
|
922
|
+
|
|
904
923
|
Returns
|
|
905
924
|
-------
|
|
906
925
|
bool
|
|
@@ -913,6 +932,11 @@ class HfssSolverSettings(object):
|
|
|
913
932
|
self._hfss_solver_settings.EnhancedLowFreqAccuracy = value
|
|
914
933
|
self._parent._update_setup()
|
|
915
934
|
|
|
935
|
+
@enhanced_low_frequency_accuracy.setter
|
|
936
|
+
def enhanced_low_frequency_accuracy(self, value):
|
|
937
|
+
self._hfss_solver_settings.EnhancedLowFreqAccuracy = value
|
|
938
|
+
self._parent._update_setup()
|
|
939
|
+
|
|
916
940
|
@property
|
|
917
941
|
def order_basis(self):
|
|
918
942
|
"""Order of the basic functions for HFSS.
|
|
@@ -19,6 +19,7 @@
|
|
|
19
19
|
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
20
|
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
21
|
# SOFTWARE.
|
|
22
|
+
import warnings
|
|
22
23
|
|
|
23
24
|
|
|
24
25
|
def _parse_value(v):
|
|
@@ -92,7 +93,7 @@ class AdvancedSettings(SettingsBase):
|
|
|
92
93
|
def __init__(self, parent):
|
|
93
94
|
super().__init__(parent)
|
|
94
95
|
self.defaults = {
|
|
95
|
-
"
|
|
96
|
+
"mesh_automatic": True,
|
|
96
97
|
"ignore_non_functional_pads": True,
|
|
97
98
|
"include_coplane_coupling": True,
|
|
98
99
|
"include_fringe_coupling": True,
|
|
@@ -339,6 +340,26 @@ class AdvancedSettings(SettingsBase):
|
|
|
339
340
|
depending on drawing size, number of modes, and/or maximum sweep
|
|
340
341
|
frequency.
|
|
341
342
|
|
|
343
|
+
.. deprecated:: 0.54.0
|
|
344
|
+
Use :func:`automatic_mesh` instead.
|
|
345
|
+
|
|
346
|
+
Returns
|
|
347
|
+
-------
|
|
348
|
+
bool
|
|
349
|
+
``True`` if automatic mesh is used, ``False`` otherwise.
|
|
350
|
+
"""
|
|
351
|
+
warnings.warn(
|
|
352
|
+
"`automatic_mesh` is deprecated." "Use `mesh_automatic` instead.",
|
|
353
|
+
DeprecationWarning,
|
|
354
|
+
)
|
|
355
|
+
return self.sim_setup_info.simulation_settings.AdvancedSettings.MeshAutoMatic
|
|
356
|
+
|
|
357
|
+
@property
|
|
358
|
+
def mesh_automatic(self):
|
|
359
|
+
"""Whether to automatically pick a suitable mesh refinement frequency,
|
|
360
|
+
depending on drawing size, number of modes, and/or maximum sweep
|
|
361
|
+
frequency.
|
|
362
|
+
|
|
342
363
|
Returns
|
|
343
364
|
-------
|
|
344
365
|
bool
|
|
@@ -492,6 +513,10 @@ class AdvancedSettings(SettingsBase):
|
|
|
492
513
|
|
|
493
514
|
@automatic_mesh.setter
|
|
494
515
|
def automatic_mesh(self, value):
|
|
516
|
+
self.mesh_automatic = value
|
|
517
|
+
|
|
518
|
+
@mesh_automatic.setter
|
|
519
|
+
def mesh_automatic(self, value):
|
|
495
520
|
edb_setup_info = self.sim_setup_info
|
|
496
521
|
|
|
497
522
|
edb_setup_info.simulation_settings.AdvancedSettings.MeshAutoMatic = value
|