siliconcompiler 0.32.3__py3-none-any.whl → 0.33.1__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.
Files changed (280) hide show
  1. siliconcompiler/__init__.py +19 -2
  2. siliconcompiler/_common.py +5 -0
  3. siliconcompiler/_metadata.py +1 -1
  4. siliconcompiler/apps/sc.py +2 -2
  5. siliconcompiler/apps/sc_install.py +10 -3
  6. siliconcompiler/apps/sc_issue.py +1 -1
  7. siliconcompiler/apps/sc_remote.py +10 -5
  8. siliconcompiler/apps/sc_show.py +2 -2
  9. siliconcompiler/apps/utils/replay.py +5 -3
  10. siliconcompiler/asic.py +120 -0
  11. siliconcompiler/checklist.py +150 -0
  12. siliconcompiler/core.py +299 -299
  13. siliconcompiler/flowgraph.py +803 -515
  14. siliconcompiler/fpga.py +84 -0
  15. siliconcompiler/metric.py +479 -0
  16. siliconcompiler/optimizer/vizier.py +2 -3
  17. siliconcompiler/package/__init__.py +29 -6
  18. siliconcompiler/pdk.py +415 -0
  19. siliconcompiler/record.py +453 -0
  20. siliconcompiler/remote/client.py +15 -5
  21. siliconcompiler/remote/schema.py +116 -112
  22. siliconcompiler/remote/server.py +9 -6
  23. siliconcompiler/report/dashboard/cli/__init__.py +14 -721
  24. siliconcompiler/report/dashboard/cli/board.py +899 -0
  25. siliconcompiler/report/dashboard/web/__init__.py +10 -10
  26. siliconcompiler/report/dashboard/web/components/__init__.py +5 -4
  27. siliconcompiler/report/dashboard/web/components/flowgraph.py +3 -3
  28. siliconcompiler/report/dashboard/web/components/graph.py +6 -3
  29. siliconcompiler/report/dashboard/web/state.py +1 -1
  30. siliconcompiler/report/dashboard/web/utils/__init__.py +4 -3
  31. siliconcompiler/report/html_report.py +2 -3
  32. siliconcompiler/report/report.py +22 -11
  33. siliconcompiler/report/summary_image.py +1 -1
  34. siliconcompiler/report/summary_table.py +3 -3
  35. siliconcompiler/report/utils.py +21 -14
  36. siliconcompiler/scheduler/__init__.py +234 -1206
  37. siliconcompiler/scheduler/run_node.py +2 -1
  38. siliconcompiler/scheduler/send_messages.py +11 -5
  39. siliconcompiler/scheduler/slurm.py +11 -44
  40. siliconcompiler/scheduler/taskscheduler.py +320 -0
  41. siliconcompiler/schema/__init__.py +19 -2
  42. siliconcompiler/schema/baseschema.py +493 -0
  43. siliconcompiler/schema/cmdlineschema.py +250 -0
  44. siliconcompiler/{sphinx_ext → schema/docs}/__init__.py +3 -1
  45. siliconcompiler/{sphinx_ext → schema/docs}/dynamicgen.py +63 -81
  46. siliconcompiler/{sphinx_ext → schema/docs}/schemagen.py +73 -85
  47. siliconcompiler/{sphinx_ext → schema/docs}/utils.py +12 -13
  48. siliconcompiler/schema/editableschema.py +136 -0
  49. siliconcompiler/schema/journalingschema.py +238 -0
  50. siliconcompiler/schema/namedschema.py +41 -0
  51. siliconcompiler/schema/packageschema.py +101 -0
  52. siliconcompiler/schema/parameter.py +791 -0
  53. siliconcompiler/schema/parametertype.py +323 -0
  54. siliconcompiler/schema/parametervalue.py +736 -0
  55. siliconcompiler/schema/safeschema.py +37 -0
  56. siliconcompiler/schema/schema_cfg.py +109 -1789
  57. siliconcompiler/schema/utils.py +5 -68
  58. siliconcompiler/schema_obj.py +119 -0
  59. siliconcompiler/tool.py +1416 -0
  60. siliconcompiler/tools/_common/__init__.py +6 -10
  61. siliconcompiler/tools/_common/asic.py +5 -5
  62. siliconcompiler/tools/_common/sdc/sc_constraints.sdc +1 -1
  63. siliconcompiler/tools/bluespec/convert.py +9 -8
  64. siliconcompiler/tools/builtin/_common.py +9 -2
  65. siliconcompiler/tools/builtin/concatenate.py +7 -3
  66. siliconcompiler/tools/builtin/minimum.py +7 -2
  67. siliconcompiler/tools/builtin/mux.py +8 -2
  68. siliconcompiler/tools/builtin/nop.py +7 -2
  69. siliconcompiler/tools/builtin/verify.py +11 -5
  70. siliconcompiler/tools/chisel/convert.py +10 -10
  71. siliconcompiler/tools/genfasm/bitstream.py +3 -3
  72. siliconcompiler/tools/ghdl/convert.py +1 -1
  73. siliconcompiler/tools/icarus/compile.py +4 -4
  74. siliconcompiler/tools/icepack/bitstream.py +6 -1
  75. siliconcompiler/tools/klayout/convert_drc_db.py +5 -0
  76. siliconcompiler/tools/klayout/drc.py +2 -2
  77. siliconcompiler/tools/klayout/klayout_export.py +0 -1
  78. siliconcompiler/tools/klayout/klayout_show.py +6 -6
  79. siliconcompiler/tools/klayout/klayout_utils.py +15 -22
  80. siliconcompiler/tools/netgen/count_lvs.py +2 -2
  81. siliconcompiler/tools/netgen/lvs.py +1 -1
  82. siliconcompiler/tools/nextpnr/apr.py +6 -1
  83. siliconcompiler/tools/nextpnr/nextpnr.py +4 -4
  84. siliconcompiler/tools/openroad/_apr.py +15 -2
  85. siliconcompiler/tools/openroad/rdlroute.py +3 -3
  86. siliconcompiler/tools/openroad/scripts/apr/postamble.tcl +1 -1
  87. siliconcompiler/tools/openroad/scripts/apr/preamble.tcl +5 -5
  88. siliconcompiler/tools/openroad/scripts/apr/sc_antenna_repair.tcl +2 -2
  89. siliconcompiler/tools/openroad/scripts/apr/sc_clock_tree_synthesis.tcl +2 -2
  90. siliconcompiler/tools/openroad/scripts/apr/sc_detailed_placement.tcl +2 -2
  91. siliconcompiler/tools/openroad/scripts/apr/sc_detailed_route.tcl +2 -2
  92. siliconcompiler/tools/openroad/scripts/apr/sc_endcap_tapcell_insertion.tcl +2 -2
  93. siliconcompiler/tools/openroad/scripts/apr/sc_fillercell_insertion.tcl +2 -2
  94. siliconcompiler/tools/openroad/scripts/apr/sc_fillmetal_insertion.tcl +2 -2
  95. siliconcompiler/tools/openroad/scripts/apr/sc_global_placement.tcl +2 -2
  96. siliconcompiler/tools/openroad/scripts/apr/sc_global_route.tcl +2 -2
  97. siliconcompiler/tools/openroad/scripts/apr/sc_init_floorplan.tcl +3 -9
  98. siliconcompiler/tools/openroad/scripts/apr/sc_macro_placement.tcl +3 -3
  99. siliconcompiler/tools/openroad/scripts/apr/sc_metrics.tcl +2 -2
  100. siliconcompiler/tools/openroad/scripts/apr/sc_pin_placement.tcl +2 -2
  101. siliconcompiler/tools/openroad/scripts/apr/sc_power_grid.tcl +2 -2
  102. siliconcompiler/tools/openroad/scripts/apr/sc_repair_design.tcl +2 -2
  103. siliconcompiler/tools/openroad/scripts/apr/sc_repair_timing.tcl +2 -2
  104. siliconcompiler/tools/openroad/scripts/apr/sc_write_data.tcl +2 -2
  105. siliconcompiler/tools/openroad/scripts/common/procs.tcl +75 -1
  106. siliconcompiler/tools/openroad/scripts/common/read_input_files.tcl +1 -7
  107. siliconcompiler/tools/openroad/scripts/common/screenshot.tcl +2 -2
  108. siliconcompiler/tools/openroad/scripts/common/write_images.tcl +28 -3
  109. siliconcompiler/tools/openroad/scripts/sc_rcx.tcl +1 -1
  110. siliconcompiler/tools/openroad/scripts/sc_rdlroute.tcl +3 -3
  111. siliconcompiler/tools/openroad/scripts/sc_show.tcl +6 -6
  112. siliconcompiler/tools/opensta/scripts/sc_timing.tcl +10 -0
  113. siliconcompiler/tools/opensta/timing.py +11 -0
  114. siliconcompiler/tools/slang/__init__.py +13 -13
  115. siliconcompiler/tools/slang/elaborate.py +6 -6
  116. siliconcompiler/tools/slang/lint.py +1 -3
  117. siliconcompiler/tools/surelog/parse.py +4 -4
  118. siliconcompiler/tools/sv2v/convert.py +20 -3
  119. siliconcompiler/tools/verilator/compile.py +2 -2
  120. siliconcompiler/tools/verilator/verilator.py +3 -3
  121. siliconcompiler/tools/vpr/_xml_constraint.py +8 -8
  122. siliconcompiler/tools/vpr/place.py +1 -1
  123. siliconcompiler/tools/vpr/route.py +4 -4
  124. siliconcompiler/tools/vpr/screenshot.py +1 -1
  125. siliconcompiler/tools/vpr/show.py +5 -5
  126. siliconcompiler/tools/vpr/vpr.py +24 -24
  127. siliconcompiler/tools/xdm/convert.py +2 -2
  128. siliconcompiler/tools/xyce/simulate.py +1 -1
  129. siliconcompiler/tools/yosys/prepareLib.py +2 -2
  130. siliconcompiler/tools/yosys/sc_synth_asic.tcl +111 -63
  131. siliconcompiler/tools/yosys/screenshot.py +1 -1
  132. siliconcompiler/tools/yosys/syn_asic.py +7 -7
  133. siliconcompiler/toolscripts/_tools.json +12 -10
  134. siliconcompiler/toolscripts/rhel8/install-chisel.sh +9 -2
  135. siliconcompiler/toolscripts/rhel8/install-icarus.sh +10 -3
  136. siliconcompiler/toolscripts/rhel8/install-klayout.sh +8 -1
  137. siliconcompiler/toolscripts/rhel8/install-magic.sh +9 -2
  138. siliconcompiler/toolscripts/rhel8/install-montage.sh +1 -1
  139. siliconcompiler/toolscripts/rhel8/install-netgen.sh +9 -2
  140. siliconcompiler/toolscripts/rhel8/install-slang.sh +11 -4
  141. siliconcompiler/toolscripts/rhel8/install-surelog.sh +9 -2
  142. siliconcompiler/toolscripts/rhel8/install-sv2v.sh +11 -4
  143. siliconcompiler/toolscripts/rhel8/install-verible.sh +11 -3
  144. siliconcompiler/toolscripts/rhel8/install-verilator.sh +10 -3
  145. siliconcompiler/toolscripts/rhel8/install-xyce.sh +15 -10
  146. siliconcompiler/toolscripts/rhel9/install-chisel.sh +9 -2
  147. siliconcompiler/toolscripts/rhel9/install-ghdl.sh +9 -2
  148. siliconcompiler/toolscripts/rhel9/install-gtkwave.sh +10 -3
  149. siliconcompiler/toolscripts/rhel9/install-icarus.sh +10 -3
  150. siliconcompiler/toolscripts/rhel9/install-klayout.sh +8 -1
  151. siliconcompiler/toolscripts/rhel9/install-magic.sh +9 -2
  152. siliconcompiler/toolscripts/rhel9/install-montage.sh +1 -1
  153. siliconcompiler/toolscripts/rhel9/install-netgen.sh +9 -2
  154. siliconcompiler/toolscripts/rhel9/install-openroad.sh +16 -3
  155. siliconcompiler/toolscripts/rhel9/install-opensta.sh +17 -5
  156. siliconcompiler/toolscripts/rhel9/install-slang.sh +11 -4
  157. siliconcompiler/toolscripts/rhel9/install-surelog.sh +9 -2
  158. siliconcompiler/toolscripts/rhel9/install-sv2v.sh +11 -4
  159. siliconcompiler/toolscripts/rhel9/install-verible.sh +11 -3
  160. siliconcompiler/toolscripts/rhel9/install-verilator.sh +10 -3
  161. siliconcompiler/toolscripts/rhel9/install-vpr.sh +9 -2
  162. siliconcompiler/toolscripts/rhel9/install-xdm.sh +10 -2
  163. siliconcompiler/toolscripts/rhel9/install-xyce.sh +15 -10
  164. siliconcompiler/toolscripts/rhel9/install-yosys-moosic.sh +9 -2
  165. siliconcompiler/toolscripts/rhel9/install-yosys-parmys.sh +10 -3
  166. siliconcompiler/toolscripts/rhel9/install-yosys-slang.sh +10 -2
  167. siliconcompiler/toolscripts/rhel9/install-yosys.sh +9 -2
  168. siliconcompiler/toolscripts/ubuntu20/install-bambu.sh +10 -2
  169. siliconcompiler/toolscripts/ubuntu20/install-bluespec.sh +10 -3
  170. siliconcompiler/toolscripts/ubuntu20/install-chisel.sh +9 -2
  171. siliconcompiler/toolscripts/ubuntu20/install-ghdl.sh +9 -2
  172. siliconcompiler/toolscripts/ubuntu20/install-gtkwave.sh +9 -2
  173. siliconcompiler/toolscripts/ubuntu20/install-icarus.sh +9 -2
  174. siliconcompiler/toolscripts/ubuntu20/install-icepack.sh +9 -2
  175. siliconcompiler/toolscripts/ubuntu20/install-klayout.sh +8 -1
  176. siliconcompiler/toolscripts/ubuntu20/install-magic.sh +9 -2
  177. siliconcompiler/toolscripts/ubuntu20/install-montage.sh +1 -1
  178. siliconcompiler/toolscripts/ubuntu20/install-netgen.sh +9 -2
  179. siliconcompiler/toolscripts/ubuntu20/install-nextpnr.sh +9 -2
  180. siliconcompiler/toolscripts/ubuntu20/install-openroad.sh +16 -3
  181. siliconcompiler/toolscripts/ubuntu20/install-opensta.sh +16 -5
  182. siliconcompiler/toolscripts/ubuntu20/install-slang.sh +11 -4
  183. siliconcompiler/toolscripts/ubuntu20/install-slurm.sh +9 -2
  184. siliconcompiler/toolscripts/ubuntu20/install-surelog.sh +10 -2
  185. siliconcompiler/toolscripts/ubuntu20/install-sv2v.sh +11 -4
  186. siliconcompiler/toolscripts/ubuntu20/install-verible.sh +11 -3
  187. siliconcompiler/toolscripts/ubuntu20/install-verilator.sh +9 -2
  188. siliconcompiler/toolscripts/ubuntu20/install-xdm.sh +10 -2
  189. siliconcompiler/toolscripts/ubuntu20/install-xyce.sh +13 -8
  190. siliconcompiler/toolscripts/ubuntu20/install-yosys-moosic.sh +9 -2
  191. siliconcompiler/toolscripts/ubuntu20/install-yosys.sh +9 -2
  192. siliconcompiler/toolscripts/ubuntu22/install-bambu.sh +10 -2
  193. siliconcompiler/toolscripts/ubuntu22/install-bluespec.sh +10 -3
  194. siliconcompiler/toolscripts/ubuntu22/install-chisel.sh +9 -2
  195. siliconcompiler/toolscripts/ubuntu22/install-ghdl.sh +9 -2
  196. siliconcompiler/toolscripts/ubuntu22/install-gtkwave.sh +9 -2
  197. siliconcompiler/toolscripts/ubuntu22/install-icarus.sh +9 -2
  198. siliconcompiler/toolscripts/ubuntu22/install-icepack.sh +9 -2
  199. siliconcompiler/toolscripts/ubuntu22/install-klayout.sh +8 -1
  200. siliconcompiler/toolscripts/ubuntu22/install-magic.sh +9 -2
  201. siliconcompiler/toolscripts/ubuntu22/install-montage.sh +1 -1
  202. siliconcompiler/toolscripts/ubuntu22/install-netgen.sh +9 -2
  203. siliconcompiler/toolscripts/ubuntu22/install-nextpnr.sh +9 -2
  204. siliconcompiler/toolscripts/ubuntu22/install-openroad.sh +16 -3
  205. siliconcompiler/toolscripts/ubuntu22/install-opensta.sh +17 -5
  206. siliconcompiler/toolscripts/ubuntu22/install-slang.sh +11 -4
  207. siliconcompiler/toolscripts/ubuntu22/install-slurm.sh +9 -2
  208. siliconcompiler/toolscripts/ubuntu22/install-surelog.sh +10 -2
  209. siliconcompiler/toolscripts/ubuntu22/install-sv2v.sh +11 -4
  210. siliconcompiler/toolscripts/ubuntu22/install-verible.sh +11 -3
  211. siliconcompiler/toolscripts/ubuntu22/install-verilator.sh +9 -2
  212. siliconcompiler/toolscripts/ubuntu22/install-vpr.sh +9 -4
  213. siliconcompiler/toolscripts/ubuntu22/install-xdm.sh +10 -2
  214. siliconcompiler/toolscripts/ubuntu22/install-xyce.sh +13 -8
  215. siliconcompiler/toolscripts/ubuntu22/install-yosys-moosic.sh +9 -2
  216. siliconcompiler/toolscripts/ubuntu22/install-yosys-parmys.sh +10 -3
  217. siliconcompiler/toolscripts/ubuntu22/install-yosys-slang.sh +10 -2
  218. siliconcompiler/toolscripts/ubuntu22/install-yosys.sh +9 -2
  219. siliconcompiler/toolscripts/ubuntu24/install-bambu.sh +12 -4
  220. siliconcompiler/toolscripts/ubuntu24/install-bluespec.sh +10 -3
  221. siliconcompiler/toolscripts/ubuntu24/install-chisel.sh +9 -2
  222. siliconcompiler/toolscripts/ubuntu24/install-ghdl.sh +9 -2
  223. siliconcompiler/toolscripts/ubuntu24/install-gtkwave.sh +9 -2
  224. siliconcompiler/toolscripts/ubuntu24/install-icarus.sh +9 -2
  225. siliconcompiler/toolscripts/ubuntu24/install-icepack.sh +9 -2
  226. siliconcompiler/toolscripts/ubuntu24/install-klayout.sh +8 -1
  227. siliconcompiler/toolscripts/ubuntu24/install-magic.sh +9 -2
  228. siliconcompiler/toolscripts/ubuntu24/install-montage.sh +1 -1
  229. siliconcompiler/toolscripts/ubuntu24/install-netgen.sh +9 -2
  230. siliconcompiler/toolscripts/ubuntu24/install-nextpnr.sh +9 -2
  231. siliconcompiler/toolscripts/ubuntu24/install-openroad.sh +16 -3
  232. siliconcompiler/toolscripts/ubuntu24/install-opensta.sh +17 -5
  233. siliconcompiler/toolscripts/ubuntu24/install-slang.sh +11 -4
  234. siliconcompiler/toolscripts/ubuntu24/install-slurm.sh +9 -2
  235. siliconcompiler/toolscripts/ubuntu24/install-surelog.sh +10 -2
  236. siliconcompiler/toolscripts/ubuntu24/install-sv2v.sh +11 -4
  237. siliconcompiler/toolscripts/ubuntu24/install-verible.sh +11 -3
  238. siliconcompiler/toolscripts/ubuntu24/install-verilator.sh +9 -2
  239. siliconcompiler/toolscripts/ubuntu24/install-vpr.sh +9 -4
  240. siliconcompiler/toolscripts/ubuntu24/install-xdm.sh +10 -2
  241. siliconcompiler/toolscripts/ubuntu24/install-xyce.sh +13 -8
  242. siliconcompiler/toolscripts/ubuntu24/install-yosys-moosic.sh +9 -2
  243. siliconcompiler/toolscripts/ubuntu24/install-yosys-parmys.sh +10 -3
  244. siliconcompiler/toolscripts/ubuntu24/install-yosys-slang.sh +10 -2
  245. siliconcompiler/toolscripts/ubuntu24/install-yosys.sh +9 -2
  246. siliconcompiler/utils/__init__.py +19 -112
  247. siliconcompiler/utils/flowgraph.py +244 -0
  248. siliconcompiler/{issue.py → utils/issue.py} +18 -25
  249. siliconcompiler/utils/logging.py +3 -4
  250. {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.1.dist-info}/METADATA +9 -8
  251. siliconcompiler-0.33.1.dist-info/RECORD +488 -0
  252. {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.1.dist-info}/WHEEL +1 -1
  253. {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.1.dist-info}/entry_points.txt +8 -8
  254. siliconcompiler/schema/schema_obj.py +0 -1936
  255. siliconcompiler/toolscripts/ubuntu20/install-vpr.sh +0 -29
  256. siliconcompiler/toolscripts/ubuntu20/install-yosys-parmys.sh +0 -61
  257. siliconcompiler-0.32.3.dist-info/RECORD +0 -470
  258. /siliconcompiler/{templates → data/templates}/__init__.py +0 -0
  259. /siliconcompiler/{templates → data/templates}/email/__init__.py +0 -0
  260. /siliconcompiler/{templates → data/templates}/email/general.j2 +0 -0
  261. /siliconcompiler/{templates → data/templates}/email/summary.j2 +0 -0
  262. /siliconcompiler/{templates → data/templates}/issue/README.txt +0 -0
  263. /siliconcompiler/{templates → data/templates}/issue/__init__.py +0 -0
  264. /siliconcompiler/{templates → data/templates}/issue/run.sh +0 -0
  265. /siliconcompiler/{templates → data/templates}/replay/replay.py.j2 +0 -0
  266. /siliconcompiler/{templates → data/templates}/replay/replay.sh.j2 +0 -0
  267. /siliconcompiler/{templates → data/templates}/replay/requirements.txt +0 -0
  268. /siliconcompiler/{templates → data/templates}/replay/setup.sh +0 -0
  269. /siliconcompiler/{templates → data/templates}/report/__init__.py +0 -0
  270. /siliconcompiler/{templates → data/templates}/report/bootstrap.min.css +0 -0
  271. /siliconcompiler/{templates → data/templates}/report/bootstrap.min.js +0 -0
  272. /siliconcompiler/{templates → data/templates}/report/bootstrap_LICENSE.md +0 -0
  273. /siliconcompiler/{templates → data/templates}/report/sc_report.j2 +0 -0
  274. /siliconcompiler/{templates → data/templates}/slurm/__init__.py +0 -0
  275. /siliconcompiler/{templates → data/templates}/slurm/run.sh +0 -0
  276. /siliconcompiler/{templates → data/templates}/tcl/__init__.py +0 -0
  277. /siliconcompiler/{templates → data/templates}/tcl/manifest.tcl.j2 +0 -0
  278. /siliconcompiler/{units.py → utils/units.py} +0 -0
  279. {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.1.dist-info}/licenses/LICENSE +0 -0
  280. {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.1.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,84 @@
1
+ from siliconcompiler.schema import BaseSchema
2
+ from siliconcompiler.schema import EditableSchema, Parameter, Scope
3
+ from siliconcompiler.schema.utils import trim
4
+
5
+
6
+ class FPGASchema(BaseSchema):
7
+ def __init__(self):
8
+ super().__init__()
9
+
10
+ schema_fpga(self)
11
+
12
+
13
+ ###############################################################################
14
+ # FPGA
15
+ ###############################################################################
16
+ def schema_fpga(schema):
17
+ schema = EditableSchema(schema)
18
+
19
+ partname = 'default'
20
+ key = 'default'
21
+
22
+ schema.insert(
23
+ 'partname',
24
+ Parameter(
25
+ 'str',
26
+ scope=Scope.GLOBAL,
27
+ shorthelp="FPGA: part name",
28
+ switch="-fpga_partname <str>",
29
+ example=["cli: -fpga_partname fpga64k",
30
+ "api: chip.set('fpga', 'partname', 'fpga64k')"],
31
+ help=trim("""
32
+ Complete part name used as a device target by the FPGA compilation
33
+ tool. The part name must be an exact string match to the partname
34
+ hard coded within the FPGA EDA tool.""")))
35
+
36
+ schema.insert(
37
+ partname, 'vendor',
38
+ Parameter(
39
+ 'str',
40
+ scope=Scope.GLOBAL,
41
+ shorthelp="FPGA: vendor name",
42
+ switch="-fpga_vendor 'partname <str>'",
43
+ example=["cli: -fpga_vendor 'fpga64k acme'",
44
+ "api: chip.set('fpga', 'fpga64k', 'vendor', 'acme')"],
45
+ help=trim("""
46
+ Name of the FPGA vendor for the FPGA partname.""")))
47
+
48
+ schema.insert(
49
+ partname, 'lutsize',
50
+ Parameter(
51
+ 'int',
52
+ scope=Scope.GLOBAL,
53
+ shorthelp="FPGA: lutsize",
54
+ switch="-fpga_lutsize 'partname <int>'",
55
+ example=["cli: -fpga_lutsize 'fpga64k 4'",
56
+ "api: chip.set('fpga', 'fpga64k', 'lutsize', '4')"],
57
+ help=trim("""
58
+ Specify the number of inputs in each lookup table (LUT) for the
59
+ FPGA partname. For architectures with fracturable LUTs, this is
60
+ the number of inputs of the unfractured LUT.""")))
61
+
62
+ schema.insert(
63
+ partname, 'file', key,
64
+ Parameter(
65
+ '[file]',
66
+ scope=Scope.GLOBAL,
67
+ shorthelp="FPGA: file",
68
+ switch="-fpga_file 'partname key <file>'",
69
+ example=["cli: -fpga_file 'fpga64k archfile my_arch.xml'",
70
+ "api: chip.set('fpga', 'fpga64k', 'file', 'archfile', 'my_arch.xml')"],
71
+ help=trim("""
72
+ Specify a file for the FPGA partname.""")))
73
+
74
+ schema.insert(
75
+ partname, 'var', key,
76
+ Parameter(
77
+ '[str]',
78
+ scope=Scope.GLOBAL,
79
+ shorthelp="FPGA: var",
80
+ switch="-fpga_var 'partname key <str>'",
81
+ example=["cli: -fpga_var 'fpga64k channelwidth 100'",
82
+ "api: chip.set('fpga', 'fpga64k', 'var', 'channelwidth', '100')"],
83
+ help=trim("""
84
+ Specify a variable value for the FPGA partname.""")))
@@ -0,0 +1,479 @@
1
+ from siliconcompiler.schema import BaseSchema
2
+ from siliconcompiler.schema import EditableSchema, Parameter, PerNode, Scope
3
+ from siliconcompiler.schema.utils import trim
4
+
5
+ from siliconcompiler.utils.units import convert
6
+ from siliconcompiler.record import RecordTime
7
+
8
+
9
+ class MetricSchema(BaseSchema):
10
+ def __init__(self):
11
+ super().__init__()
12
+
13
+ schema_metric(self)
14
+
15
+ def clear(self, step, index):
16
+ '''
17
+ Clear all saved metrics for a given step and index
18
+
19
+ Args:
20
+ step (str): Step name to clear.
21
+ index (str/int): Index name to clear.
22
+ '''
23
+ for metric in self.getkeys():
24
+ self.unset(metric, step=step, index=str(index))
25
+
26
+ def record(self, step, index, metric, value, unit=None):
27
+ """
28
+ Record a metric
29
+
30
+ Args:
31
+ step (str): step to record
32
+ index (str/int): index to record
33
+ metric (str): name of metric
34
+ value (int/float): value to record
35
+ unit (str): unit associated with value
36
+ """
37
+ metric_unit = self.get(metric, field='unit')
38
+
39
+ if not metric_unit and unit:
40
+ raise ValueError(f"{metric} does not have a unit, but {unit} was supplied")
41
+
42
+ if metric_unit:
43
+ value = convert(value, from_unit=unit, to_unit=metric_unit)
44
+
45
+ return self.set(metric, value, step=step, index=str(index))
46
+
47
+ def record_totaltime(self, step, index, flow, record):
48
+ """
49
+ Record the total time for this node
50
+
51
+ Args:
52
+ step (str): step to record
53
+ index (str/int): index to record
54
+ flow (:class:`FlowgraphSchema`): flowgraph to lookup nodes in
55
+ record (:class:`RecordSchema`): record to lookup data in
56
+ """
57
+ all_nodes = flow.get_nodes()
58
+ node_times = [
59
+ (record.get_recorded_time(*node, RecordTime.START),
60
+ record.get_recorded_time(*node, RecordTime.END)) for node in all_nodes
61
+ ]
62
+
63
+ # Remove incomplete records
64
+ node_times = [times for times in node_times if times[0] is not None]
65
+
66
+ if len(node_times) == 0:
67
+ return False
68
+
69
+ node_end = record.get_recorded_time(step, index, RecordTime.END)
70
+ if node_end is None:
71
+ return False
72
+
73
+ node_times = sorted(node_times)
74
+ if len(node_times) > 1:
75
+ new_times = []
76
+ for n in range(len(node_times)):
77
+ if not new_times:
78
+ new_times.append(node_times[n])
79
+ continue
80
+ prev_start_time, prev_end_time = new_times[-1]
81
+ start_time, end_time = node_times[n]
82
+
83
+ new_start = min(prev_start_time, start_time)
84
+
85
+ if prev_end_time is None:
86
+ new_times[-1] = (new_start, end_time)
87
+ elif prev_end_time >= start_time:
88
+ if end_time is not None:
89
+ new_end = max(prev_end_time, end_time)
90
+ else:
91
+ new_end = prev_end_time
92
+ new_times[-1] = (new_start, new_end)
93
+ else:
94
+ new_times.append(node_times[n])
95
+ node_times = new_times
96
+
97
+ total_time = 0
98
+ for start_time, end_time in node_times:
99
+ if start_time > node_end:
100
+ continue
101
+ total_time += min(end_time, node_end) - start_time
102
+
103
+ return self.record(step, index, "totaltime", total_time, unit="s")
104
+
105
+
106
+ ###########################################################################
107
+ # Metrics to Track
108
+ ###########################################################################
109
+ def schema_metric(schema):
110
+ schema = EditableSchema(schema)
111
+
112
+ metrics = {'errors': 'errors',
113
+ 'warnings': 'warnings',
114
+ 'drvs': 'design rule violations',
115
+ 'drcs': 'physical design rule violations',
116
+ 'unconstrained': 'unconstrained timing paths'}
117
+
118
+ for item, description in metrics.items():
119
+ schema.insert(
120
+ item,
121
+ Parameter(
122
+ 'int',
123
+ scope=Scope.JOB,
124
+ shorthelp=f"Metric: total {item}",
125
+ switch=f"-metric_{item} 'step index <int>'",
126
+ example=[
127
+ f"cli: -metric_{item} 'dfm 0 0'",
128
+ f"api: chip.set('metric', '{item}', 0, step='dfm', index=0)"],
129
+ pernode=PerNode.REQUIRED,
130
+ help=trim(f"""Metric tracking the total number of {description} on a
131
+ per step and index basis.""")))
132
+
133
+ schema.insert(
134
+ 'coverage',
135
+ Parameter(
136
+ 'float',
137
+ unit='%',
138
+ scope=Scope.JOB,
139
+ shorthelp="Metric: coverage",
140
+ switch="-metric_coverage 'step index <float>'",
141
+ example=[
142
+ "cli: -metric_coverage 'place 0 99.9'",
143
+ "api: chip.set('metric', 'coverage', 99.9, step='place', index=0)"],
144
+ pernode=PerNode.REQUIRED,
145
+ help=trim("""
146
+ Metric tracking the test coverage in the design expressed as a percentage
147
+ with 100 meaning full coverage. The meaning of the metric depends on the
148
+ task being executed. It can refer to code coverage, feature coverage,
149
+ stuck at fault coverage.""")))
150
+
151
+ schema.insert(
152
+ 'security',
153
+ Parameter(
154
+ 'float',
155
+ unit='%',
156
+ scope=Scope.JOB,
157
+ shorthelp="Metric: security",
158
+ switch="-metric_security 'step index <float>'",
159
+ example=[
160
+ "cli: -metric_security 'place 0 100'",
161
+ "api: chip.set('metric', 'security', 100, step='place', index=0)"],
162
+ pernode=PerNode.REQUIRED,
163
+ help=trim("""
164
+ Metric tracking the level of security (1/vulnerability) of the design.
165
+ A completely secure design would have a score of 100. There is no
166
+ absolute scale for the security metrics (like with power, area, etc)
167
+ so the metric will be task and tool dependent.""")))
168
+
169
+ metrics = {'luts': 'FPGA LUTs used',
170
+ 'dsps': 'FPGA DSP slices used',
171
+ 'brams': 'FPGA BRAM tiles used'}
172
+
173
+ for item, description in metrics.items():
174
+ schema.insert(
175
+ item,
176
+ Parameter(
177
+ 'int',
178
+ scope=Scope.JOB,
179
+ shorthelp=f"Metric: {description}",
180
+ switch=f"-metric_{item} 'step index <int>'",
181
+ example=[
182
+ f"cli: -metric_{item} 'place 0 100'",
183
+ f"api: chip.set('metric', '{item}', 100, step='place', index=0)"],
184
+ pernode=PerNode.REQUIRED,
185
+ help=trim(f"""
186
+ Metric tracking the total {description} used by the design as reported
187
+ by the implementation tool. There is no standardized definition
188
+ for this metric across vendors, so metric comparisons can
189
+ generally only be done between runs on identical tools and
190
+ device families.""")))
191
+
192
+ metrics = {'cellarea': 'cell area (ignoring fillers)',
193
+ 'totalarea': 'physical die area',
194
+ 'macroarea': 'macro cell area',
195
+ 'padcellarea': 'io pad cell area',
196
+ 'stdcellarea': 'standard cell area'}
197
+
198
+ for item, description in metrics.items():
199
+ schema.insert(
200
+ item,
201
+ Parameter(
202
+ 'float',
203
+ unit='um^2',
204
+ scope=Scope.JOB,
205
+ shorthelp=f"Metric: {item}",
206
+ switch=f"-metric_{item} 'step index <float>'",
207
+ example=[
208
+ f"cli: -metric_{item} 'place 0 100.00'",
209
+ f"api: chip.set('metric', '{item}', 100.00, step='place', index=0)"],
210
+ pernode=PerNode.REQUIRED,
211
+ help=trim(f"""
212
+ Metric tracking the total {description} occupied by the design.""")))
213
+
214
+ schema.insert(
215
+ 'utilization',
216
+ Parameter(
217
+ 'float',
218
+ unit='%',
219
+ scope=Scope.JOB,
220
+ shorthelp="Metric: area utilization",
221
+ switch="-metric_utilization 'step index <float>'",
222
+ example=[
223
+ "cli: -metric_utilization 'place 0 50.00'",
224
+ "api: chip.set('metric', 'utilization', 50.00, step='place', index=0)"],
225
+ pernode=PerNode.REQUIRED,
226
+ help=trim("""
227
+ Metric tracking the area utilization of the design calculated as
228
+ 100 * (cellarea/totalarea).""")))
229
+
230
+ schema.insert(
231
+ 'logicdepth',
232
+ Parameter(
233
+ 'int',
234
+ scope=Scope.JOB,
235
+ shorthelp="Metric: logic depth",
236
+ switch="-metric_logicdepth 'step index <int>'",
237
+ example=[
238
+ "cli: -metric_logicdepth 'place 0 8'",
239
+ "api: chip.set('metric', 'logicdepth', 8, step='place', index=0)"],
240
+ pernode=PerNode.REQUIRED,
241
+ help=trim("""
242
+ Metric tracking the logic depth of the design. This is determined
243
+ by the number of logic gates between the start of the critital timing
244
+ path to the end of the path.""")))
245
+
246
+ metrics = {'peakpower': 'worst case total peak power',
247
+ 'averagepower': 'average workload power',
248
+ 'leakagepower': 'leakage power with rails active but without any dynamic '
249
+ 'switching activity'}
250
+
251
+ for item, description in metrics.items():
252
+ schema.insert(
253
+ item,
254
+ Parameter(
255
+ 'float',
256
+ unit='mw',
257
+ scope=Scope.JOB,
258
+ shorthelp=f"Metric: {item}",
259
+ switch=f"-metric_{item} 'step index <float>'",
260
+ example=[
261
+ f"cli: -metric_{item} 'place 0 0.01'",
262
+ f"api: chip.set('metric', '{item}', 0.01, step='place', index=0)"],
263
+ pernode=PerNode.REQUIRED,
264
+ help=trim(f"""
265
+ Metric tracking the {description} of the design specified on a per step
266
+ and index basis. Power metric depend heavily on the method
267
+ being used for extraction: dynamic vs static, workload
268
+ specification (vcd vs saif), power models, process/voltage/temperature.
269
+ The power {item} metric tries to capture the data that would
270
+ usually be reflected inside a datasheet given the appropriate
271
+ footnote conditions.""")))
272
+
273
+ schema.insert(
274
+ 'irdrop',
275
+ Parameter(
276
+ 'float',
277
+ unit='mv',
278
+ scope=Scope.JOB,
279
+ shorthelp="Metric: peak IR drop",
280
+ switch="-metric_irdrop 'step index <float>'",
281
+ example=[
282
+ "cli: -metric_irdrop 'place 0 0.05'",
283
+ "api: chip.set('metric', 'irdrop', 0.05, step='place', index=0)"],
284
+ pernode=PerNode.REQUIRED,
285
+ help=trim("""
286
+ Metric tracking the peak IR drop in the design based on extracted
287
+ power and ground rail parasitics, library power models, and
288
+ switching activity. The switching activity calculated on a per
289
+ node basis is taken from one of three possible sources, in order
290
+ of priority: VCD file, SAIF file, 'activityfactor' parameter.""")))
291
+
292
+ metrics = {'holdpaths': 'hold',
293
+ 'setuppaths': 'setup'}
294
+
295
+ for item, description in metrics.items():
296
+ schema.insert(
297
+ item,
298
+ Parameter(
299
+ 'int',
300
+ scope=Scope.JOB,
301
+ shorthelp=f"Metric: {item}",
302
+ switch=f"-metric_{item} 'step index <int>'",
303
+ example=[
304
+ f"cli: -metric_{item} 'place 0 10'",
305
+ f"api: chip.set('metric', '{item}', 10, step='place', index=0)"],
306
+ pernode=PerNode.REQUIRED,
307
+ help=trim(f"""
308
+ Metric tracking the total number of timing paths violating {description}
309
+ constraints.""")))
310
+
311
+ metrics = {'holdslack': 'worst hold slack (positive or negative)',
312
+ 'holdwns': 'worst negative hold slack (positive values truncated to zero)',
313
+ 'holdtns': 'total negative hold slack (TNS)',
314
+ 'holdskew': 'hold clock skew',
315
+ 'setupslack': 'worst setup slack (positive or negative)',
316
+ 'setupwns': 'worst negative setup slack (positive values truncated to zero)',
317
+ 'setuptns': 'total negative setup slack (TNS)',
318
+ 'setupskew': 'setup clock skew'}
319
+
320
+ for item, description in metrics.items():
321
+ schema.insert(
322
+ item,
323
+ Parameter(
324
+ 'float',
325
+ unit='ns',
326
+ scope=Scope.JOB,
327
+ shorthelp=f"Metric: {item}",
328
+ switch=f"-metric_{item} 'step index <float>'",
329
+ example=[
330
+ f"cli: -metric_{item} 'place 0 0.01'",
331
+ f"api: chip.set('metric', '{item}', 0.01, step='place', index=0)"],
332
+ pernode=PerNode.REQUIRED,
333
+ help=trim(f"""
334
+ Metric tracking the {description} on a per step and index basis.""")))
335
+
336
+ metrics = {'fmax': 'maximum clock frequency'}
337
+
338
+ for item, description in metrics.items():
339
+ schema.insert(
340
+ item,
341
+ Parameter(
342
+ 'float',
343
+ unit='Hz',
344
+ scope=Scope.JOB,
345
+ shorthelp=f"Metric: {item}",
346
+ switch=f"-metric_{item} 'step index <float>'",
347
+ example=[
348
+ f"cli: -metric_{item} 'place 0 100e6'",
349
+ f"api: chip.set('metric', '{item}', 100e6, step='place', index=0)"],
350
+ pernode=PerNode.REQUIRED,
351
+ help=trim(f"""
352
+ Metric tracking the {description} on a per step and index basis.""")))
353
+
354
+ metrics = {'macros': 'macros',
355
+ 'cells': 'cell instances',
356
+ 'registers': 'register instances',
357
+ 'buffers': 'buffer instances',
358
+ 'inverters': 'inverter instances',
359
+ 'transistors': 'transistors',
360
+ 'pins': 'pins',
361
+ 'nets': 'nets',
362
+ 'vias': 'vias'}
363
+
364
+ for item, description in metrics.items():
365
+ schema.insert(
366
+ item,
367
+ Parameter(
368
+ 'int',
369
+ scope=Scope.JOB,
370
+ shorthelp=f"Metric: {item}",
371
+ switch=f"-metric_{item} 'step index <int>'",
372
+ example=[
373
+ f"cli: -metric_{item} 'place 0 100'",
374
+ f"api: chip.set('metric', '{item}', 50, step='place', index=0)"],
375
+ pernode=PerNode.REQUIRED,
376
+ help=trim(f"""
377
+ Metric tracking the total number of {description} in the design
378
+ on a per step and index basis.""")))
379
+
380
+ schema.insert(
381
+ 'wirelength',
382
+ Parameter(
383
+ 'float',
384
+ unit='um',
385
+ scope=Scope.JOB,
386
+ shorthelp="Metric: wirelength",
387
+ switch="-metric_wirelength 'step index <float>'",
388
+ example=[
389
+ "cli: -metric_wirelength 'place 0 100.0'",
390
+ "api: chip.set('metric', 'wirelength', 50.0, step='place', index=0)"],
391
+ pernode=PerNode.REQUIRED,
392
+ help=trim("""
393
+ Metric tracking the total wirelength of the design on a per step
394
+ and index basis.""")))
395
+
396
+ schema.insert(
397
+ 'overflow',
398
+ Parameter(
399
+ 'int',
400
+ scope=Scope.JOB,
401
+ shorthelp="Metric: overflow",
402
+ switch="-metric_overflow 'step index <int>'",
403
+ example=[
404
+ "cli: -metric_overflow 'place 0 0'",
405
+ "api: chip.set('metric', 'overflow', 50, step='place', index=0)"],
406
+ pernode=PerNode.REQUIRED,
407
+ help=trim("""
408
+ Metric tracking the total number of overflow tracks for the routing
409
+ on per step and index basis. Any non-zero number suggests an over
410
+ congested design. To analyze where the congestion is occurring
411
+ inspect the router log files for detailed per metal overflow
412
+ reporting and open up the design to find routing hotspots.""")))
413
+
414
+ schema.insert(
415
+ 'memory',
416
+ Parameter(
417
+ 'float',
418
+ unit='B',
419
+ scope=Scope.JOB,
420
+ shorthelp="Metric: memory",
421
+ switch="-metric_memory 'step index <float>'",
422
+ example=[
423
+ "cli: -metric_memory 'dfm 0 10e9'",
424
+ "api: chip.set('metric', 'memory', 10e9, step='dfm', index=0)"],
425
+ pernode=PerNode.REQUIRED,
426
+ help=trim("""
427
+ Metric tracking total peak program memory footprint on a per
428
+ step and index basis.""")))
429
+
430
+ schema.insert(
431
+ 'exetime',
432
+ Parameter(
433
+ 'float',
434
+ unit='s',
435
+ scope=Scope.JOB,
436
+ shorthelp="Metric: exetime",
437
+ switch="-metric_exetime 'step index <float>'",
438
+ example=[
439
+ "cli: -metric_exetime 'dfm 0 10.0'",
440
+ "api: chip.set('metric', 'exetime', 10.0, step='dfm', index=0)"],
441
+ pernode=PerNode.REQUIRED,
442
+ help=trim("""
443
+ Metric tracking time spent by the EDA executable :keypath:`tool,<tool>,exe` on a
444
+ per step and index basis. It does not include the SiliconCompiler
445
+ runtime overhead or time waiting for I/O operations and
446
+ inter-processor communication to complete.""")))
447
+
448
+ schema.insert(
449
+ 'tasktime',
450
+ Parameter(
451
+ 'float',
452
+ unit='s',
453
+ scope=Scope.JOB,
454
+ shorthelp="Metric: tasktime",
455
+ switch="-metric_tasktime 'step index <float>'",
456
+ example=[
457
+ "cli: -metric_tasktime 'dfm 0 10.0'",
458
+ "api: chip.set('metric', 'tasktime', 10.0, step='dfm', index=0)"],
459
+ pernode=PerNode.REQUIRED,
460
+ help=trim("""
461
+ Metric tracking the total amount of time spent on a task from
462
+ beginning to end, including data transfers and pre/post
463
+ processing.""")))
464
+
465
+ schema.insert(
466
+ 'totaltime',
467
+ Parameter(
468
+ 'float',
469
+ unit='s',
470
+ scope=Scope.JOB,
471
+ shorthelp="Metric: totaltime",
472
+ switch="-metric_totaltime 'step index <float>'",
473
+ example=[
474
+ "cli: -metric_totaltime 'dfm 0 10.0'",
475
+ "api: chip.set('metric', 'totaltime', 10.0, step='dfm', index=0)"],
476
+ pernode=PerNode.REQUIRED,
477
+ help=trim("""
478
+ Metric tracking the total amount of time spent from the beginning
479
+ of the run up to and including the current step and index.""")))
@@ -3,7 +3,6 @@ import uuid
3
3
  import math
4
4
  from siliconcompiler import Chip
5
5
  from siliconcompiler.optimizer import Optimizer
6
- from siliconcompiler.flowgraph import _get_flowgraph_nodes
7
6
 
8
7
  try:
9
8
  from vizier.service import clients as vz_clients
@@ -158,7 +157,7 @@ class VizierOptimizier(Optimizer):
158
157
  chip.graph(flow, org_flow, name=graph_name)
159
158
 
160
159
  # Complete nodes
161
- nodes = _get_flowgraph_nodes(chip, org_flow)
160
+ nodes = chip.schema.get("flowgraph", org_flow, field="schema").get_nodes()
162
161
  for step, _ in list(nodes):
163
162
  nodes.append((step, None))
164
163
  nodes = set(nodes)
@@ -168,7 +167,7 @@ class VizierOptimizier(Optimizer):
168
167
  if key[0] == 'history':
169
168
  continue
170
169
 
171
- for value, step, index in chip.schema._getvals(*key):
170
+ for value, step, index in chip.schema.get(*key, field=None).getvalues():
172
171
  node = (step, index)
173
172
 
174
173
  if node in nodes:
@@ -3,14 +3,15 @@ from urllib.parse import urlparse
3
3
  import importlib
4
4
  import re
5
5
  from siliconcompiler import SiliconCompilerError
6
- from siliconcompiler.utils import default_cache_dir, _resolve_env_vars
6
+ from siliconcompiler.utils import default_cache_dir
7
7
  import json
8
8
  from importlib.metadata import distributions, distribution
9
9
  import functools
10
10
  import time
11
11
  from pathlib import Path
12
12
 
13
- from siliconcompiler.utils import get_plugins
13
+ from siliconcompiler.utils import get_plugins, get_env_vars
14
+ from siliconcompiler.schema.parametervalue import PathNodeValue
14
15
 
15
16
 
16
17
  def get_cache_path(chip):
@@ -46,6 +47,18 @@ def _python_path_resolver(chip, package, path, ref, url, fetch):
46
47
  return path_from_python(chip, url.netloc)
47
48
 
48
49
 
50
+ def _key_path_resolver(chip, package, path, ref, url, fetch):
51
+ key = url.netloc.split(',')
52
+ if chip.get(*key, field='pernode').is_never():
53
+ paths = chip.find_files(*key)
54
+ else:
55
+ paths = chip.find_files(*key, step=chip.get('arg', 'step'), index=chip.get('arg', 'index'))
56
+
57
+ if isinstance(paths, list):
58
+ return paths[0]
59
+ return paths
60
+
61
+
49
62
  def _get_path_resolver(path):
50
63
  url = urlparse(path)
51
64
 
@@ -54,6 +67,9 @@ def _get_path_resolver(path):
54
67
  if func:
55
68
  return func, url
56
69
 
70
+ if url.scheme == "key":
71
+ return _key_path_resolver, url
72
+
57
73
  if url.scheme == "file":
58
74
  return _file_path_resolver, url
59
75
 
@@ -69,11 +85,15 @@ def _path(chip, package, fetch):
69
85
  data['path'] = chip.get('package', 'source', package, 'path')
70
86
  data['ref'] = chip.get('package', 'source', package, 'ref')
71
87
  if not data['path']:
72
- raise SiliconCompilerError(
73
- f'Could not find package source for {package} in schema. '
74
- 'You can use register_source() to add it.', chip=chip)
88
+ if package.startswith("key://"):
89
+ data['path'] = package
90
+ else:
91
+ raise SiliconCompilerError(
92
+ f'Could not find package source for {package} in schema. '
93
+ 'You can use register_source() to add it.', chip=chip)
75
94
 
76
- data['path'] = _resolve_env_vars(chip, data['path'], None, None)
95
+ env_vars = get_env_vars(chip, None, None)
96
+ data['path'] = PathNodeValue.resolve_env_vars(data['path'], envvars=env_vars)
77
97
 
78
98
  if os.path.exists(data['path']):
79
99
  # Path is already a path
@@ -102,6 +122,9 @@ def path(chip, package, fetch=True):
102
122
  if isinstance(data_path, tuple) and len(data_path) == 2:
103
123
  data_path, changed = data_path
104
124
 
125
+ if package.startswith("key://"):
126
+ return data_path
127
+
105
128
  if os.path.exists(data_path):
106
129
  if package not in chip._packages and changed:
107
130
  chip.logger.info(f'Saved {package} data to {data_path}')