siliconcompiler 0.28.9__py3-none-any.whl → 0.29.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 (164) hide show
  1. siliconcompiler/_metadata.py +1 -1
  2. siliconcompiler/apps/__init__.py +26 -0
  3. siliconcompiler/apps/sc_remote.py +15 -14
  4. siliconcompiler/apps/sc_show.py +5 -5
  5. siliconcompiler/apps/utils/replay.py +194 -0
  6. siliconcompiler/checklists/__init__.py +12 -0
  7. siliconcompiler/core.py +89 -22
  8. siliconcompiler/flows/__init__.py +34 -0
  9. siliconcompiler/flows/_common.py +11 -13
  10. siliconcompiler/flows/asicflow.py +83 -42
  11. siliconcompiler/flows/showflow.py +1 -1
  12. siliconcompiler/libs/__init__.py +5 -0
  13. siliconcompiler/optimizer/__init__.py +199 -0
  14. siliconcompiler/optimizer/vizier.py +259 -0
  15. siliconcompiler/pdks/__init__.py +5 -0
  16. siliconcompiler/remote/__init__.py +11 -0
  17. siliconcompiler/remote/client.py +753 -815
  18. siliconcompiler/report/report.py +2 -0
  19. siliconcompiler/report/summary_table.py +1 -1
  20. siliconcompiler/scheduler/__init__.py +118 -58
  21. siliconcompiler/scheduler/send_messages.py +1 -1
  22. siliconcompiler/schema/schema_cfg.py +16 -4
  23. siliconcompiler/schema/schema_obj.py +29 -10
  24. siliconcompiler/schema/utils.py +2 -0
  25. siliconcompiler/sphinx_ext/__init__.py +85 -0
  26. siliconcompiler/sphinx_ext/dynamicgen.py +19 -34
  27. siliconcompiler/sphinx_ext/schemagen.py +3 -2
  28. siliconcompiler/targets/__init__.py +26 -0
  29. siliconcompiler/targets/gf180_demo.py +3 -3
  30. siliconcompiler/templates/replay/replay.py.j2 +62 -0
  31. siliconcompiler/templates/replay/requirements.txt +7 -0
  32. siliconcompiler/templates/replay/setup.sh +130 -0
  33. siliconcompiler/tools/__init__.py +60 -0
  34. siliconcompiler/tools/_common/__init__.py +15 -1
  35. siliconcompiler/tools/_common/asic.py +17 -9
  36. siliconcompiler/tools/builtin/concatenate.py +1 -1
  37. siliconcompiler/tools/ghdl/ghdl.py +1 -2
  38. siliconcompiler/tools/klayout/convert_drc_db.py +1 -1
  39. siliconcompiler/tools/klayout/drc.py +1 -1
  40. siliconcompiler/tools/klayout/export.py +8 -1
  41. siliconcompiler/tools/klayout/klayout.py +2 -2
  42. siliconcompiler/tools/klayout/klayout_convert_drc_db.py +2 -2
  43. siliconcompiler/tools/klayout/klayout_export.py +7 -5
  44. siliconcompiler/tools/klayout/klayout_operations.py +4 -3
  45. siliconcompiler/tools/klayout/klayout_show.py +3 -2
  46. siliconcompiler/tools/klayout/klayout_utils.py +1 -1
  47. siliconcompiler/tools/klayout/operations.py +8 -0
  48. siliconcompiler/tools/klayout/screenshot.py +6 -1
  49. siliconcompiler/tools/klayout/show.py +8 -1
  50. siliconcompiler/tools/magic/magic.py +1 -1
  51. siliconcompiler/tools/openroad/__init__.py +103 -0
  52. siliconcompiler/tools/openroad/{openroad.py → _apr.py} +415 -423
  53. siliconcompiler/tools/openroad/antenna_repair.py +78 -0
  54. siliconcompiler/tools/openroad/clock_tree_synthesis.py +64 -0
  55. siliconcompiler/tools/openroad/detailed_placement.py +59 -0
  56. siliconcompiler/tools/openroad/detailed_route.py +62 -0
  57. siliconcompiler/tools/openroad/endcap_tapcell_insertion.py +52 -0
  58. siliconcompiler/tools/openroad/fillercell_insertion.py +58 -0
  59. siliconcompiler/tools/openroad/{dfm.py → fillmetal_insertion.py} +35 -19
  60. siliconcompiler/tools/openroad/global_placement.py +58 -0
  61. siliconcompiler/tools/openroad/global_route.py +63 -0
  62. siliconcompiler/tools/openroad/init_floorplan.py +103 -0
  63. siliconcompiler/tools/openroad/macro_placement.py +65 -0
  64. siliconcompiler/tools/openroad/metrics.py +23 -8
  65. siliconcompiler/tools/openroad/pin_placement.py +56 -0
  66. siliconcompiler/tools/openroad/power_grid.py +65 -0
  67. siliconcompiler/tools/openroad/rcx_bench.py +7 -4
  68. siliconcompiler/tools/openroad/rcx_extract.py +2 -1
  69. siliconcompiler/tools/openroad/rdlroute.py +4 -4
  70. siliconcompiler/tools/openroad/repair_design.py +59 -0
  71. siliconcompiler/tools/openroad/repair_timing.py +63 -0
  72. siliconcompiler/tools/openroad/screenshot.py +9 -20
  73. siliconcompiler/tools/openroad/scripts/apr/postamble.tcl +44 -0
  74. siliconcompiler/tools/openroad/scripts/apr/preamble.tcl +95 -0
  75. siliconcompiler/tools/openroad/scripts/apr/sc_antenna_repair.tcl +51 -0
  76. siliconcompiler/tools/openroad/scripts/apr/sc_clock_tree_synthesis.tcl +66 -0
  77. siliconcompiler/tools/openroad/scripts/apr/sc_detailed_placement.tcl +41 -0
  78. siliconcompiler/tools/openroad/scripts/apr/sc_detailed_route.tcl +71 -0
  79. siliconcompiler/tools/openroad/scripts/apr/sc_endcap_tapcell_insertion.tcl +55 -0
  80. siliconcompiler/tools/openroad/scripts/apr/sc_fillercell_insertion.tcl +27 -0
  81. siliconcompiler/tools/openroad/scripts/apr/sc_fillmetal_insertion.tcl +36 -0
  82. siliconcompiler/tools/openroad/scripts/apr/sc_global_placement.tcl +26 -0
  83. siliconcompiler/tools/openroad/scripts/apr/sc_global_route.tcl +61 -0
  84. siliconcompiler/tools/openroad/scripts/apr/sc_init_floorplan.tcl +333 -0
  85. siliconcompiler/tools/openroad/scripts/apr/sc_macro_placement.tcl +123 -0
  86. siliconcompiler/tools/openroad/scripts/apr/sc_metrics.tcl +22 -0
  87. siliconcompiler/tools/openroad/scripts/apr/sc_pin_placement.tcl +41 -0
  88. siliconcompiler/tools/openroad/scripts/apr/sc_power_grid.tcl +60 -0
  89. siliconcompiler/tools/openroad/scripts/apr/sc_repair_design.tcl +68 -0
  90. siliconcompiler/tools/openroad/scripts/apr/sc_repair_timing.tcl +83 -0
  91. siliconcompiler/tools/openroad/scripts/apr/sc_write_data.tcl +125 -0
  92. siliconcompiler/tools/openroad/scripts/common/debugging.tcl +28 -0
  93. siliconcompiler/tools/openroad/scripts/common/procs.tcl +727 -0
  94. siliconcompiler/tools/openroad/scripts/common/read_input_files.tcl +59 -0
  95. siliconcompiler/tools/openroad/scripts/common/read_liberty.tcl +20 -0
  96. siliconcompiler/tools/openroad/scripts/common/read_timing_constraints.tcl +16 -0
  97. siliconcompiler/tools/openroad/scripts/common/reports.tcl +180 -0
  98. siliconcompiler/tools/openroad/scripts/common/screenshot.tcl +18 -0
  99. siliconcompiler/tools/openroad/scripts/common/write_images.tcl +395 -0
  100. siliconcompiler/tools/openroad/scripts/{sc_rcx_bench.tcl → rcx/sc_rcx_bench.tcl} +5 -5
  101. siliconcompiler/tools/openroad/scripts/{sc_rcx_extract.tcl → rcx/sc_rcx_extract.tcl} +0 -0
  102. siliconcompiler/tools/openroad/scripts/sc_rcx.tcl +5 -16
  103. siliconcompiler/tools/openroad/scripts/sc_rdlroute.tcl +51 -51
  104. siliconcompiler/tools/openroad/scripts/sc_show.tcl +110 -0
  105. siliconcompiler/tools/openroad/show.py +28 -23
  106. siliconcompiler/tools/openroad/{export.py → write_data.py} +31 -26
  107. siliconcompiler/tools/opensta/__init__.py +2 -2
  108. siliconcompiler/tools/opensta/check_library.py +27 -0
  109. siliconcompiler/tools/opensta/scripts/sc_check_library.tcl +255 -0
  110. siliconcompiler/tools/opensta/scripts/sc_timing.tcl +1 -1
  111. siliconcompiler/tools/sv2v/sv2v.py +1 -2
  112. siliconcompiler/tools/verilator/verilator.py +6 -7
  113. siliconcompiler/tools/vivado/vivado.py +1 -1
  114. siliconcompiler/tools/yosys/__init__.py +149 -0
  115. siliconcompiler/tools/yosys/lec.py +22 -9
  116. siliconcompiler/tools/yosys/sc_lec.tcl +94 -49
  117. siliconcompiler/tools/yosys/sc_syn.tcl +1 -0
  118. siliconcompiler/tools/yosys/screenshot.py +2 -2
  119. siliconcompiler/tools/yosys/syn_asic.py +105 -74
  120. siliconcompiler/tools/yosys/syn_asic.tcl +58 -12
  121. siliconcompiler/tools/yosys/syn_fpga.py +2 -3
  122. siliconcompiler/tools/yosys/syn_fpga.tcl +26 -19
  123. siliconcompiler/toolscripts/_tools.json +5 -5
  124. siliconcompiler/utils/__init__.py +7 -3
  125. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/METADATA +22 -17
  126. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/RECORD +131 -114
  127. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/WHEEL +1 -1
  128. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/entry_points.txt +13 -0
  129. siliconcompiler/libs/asap7sc7p5t.py +0 -8
  130. siliconcompiler/libs/gf180mcu.py +0 -8
  131. siliconcompiler/libs/interposer.py +0 -8
  132. siliconcompiler/libs/nangate45.py +0 -8
  133. siliconcompiler/libs/sg13g2_stdcell.py +0 -8
  134. siliconcompiler/libs/sky130hd.py +0 -8
  135. siliconcompiler/libs/sky130io.py +0 -8
  136. siliconcompiler/pdks/asap7.py +0 -8
  137. siliconcompiler/pdks/freepdk45.py +0 -8
  138. siliconcompiler/pdks/gf180.py +0 -8
  139. siliconcompiler/pdks/ihp130.py +0 -8
  140. siliconcompiler/pdks/interposer.py +0 -8
  141. siliconcompiler/pdks/skywater130.py +0 -8
  142. siliconcompiler/tools/openroad/cts.py +0 -45
  143. siliconcompiler/tools/openroad/floorplan.py +0 -75
  144. siliconcompiler/tools/openroad/physyn.py +0 -27
  145. siliconcompiler/tools/openroad/place.py +0 -41
  146. siliconcompiler/tools/openroad/route.py +0 -45
  147. siliconcompiler/tools/openroad/scripts/__init__.py +0 -0
  148. siliconcompiler/tools/openroad/scripts/sc_apr.tcl +0 -514
  149. siliconcompiler/tools/openroad/scripts/sc_cts.tcl +0 -68
  150. siliconcompiler/tools/openroad/scripts/sc_dfm.tcl +0 -22
  151. siliconcompiler/tools/openroad/scripts/sc_export.tcl +0 -100
  152. siliconcompiler/tools/openroad/scripts/sc_floorplan.tcl +0 -456
  153. siliconcompiler/tools/openroad/scripts/sc_metrics.tcl +0 -1
  154. siliconcompiler/tools/openroad/scripts/sc_physyn.tcl +0 -6
  155. siliconcompiler/tools/openroad/scripts/sc_place.tcl +0 -84
  156. siliconcompiler/tools/openroad/scripts/sc_procs.tcl +0 -494
  157. siliconcompiler/tools/openroad/scripts/sc_report.tcl +0 -189
  158. siliconcompiler/tools/openroad/scripts/sc_route.tcl +0 -143
  159. siliconcompiler/tools/openroad/scripts/sc_screenshot.tcl +0 -18
  160. siliconcompiler/tools/openroad/scripts/sc_write_images.tcl +0 -393
  161. siliconcompiler/tools/yosys/yosys.py +0 -148
  162. /siliconcompiler/tools/openroad/scripts/{sc_write.tcl → common/write_data.tcl} +0 -0
  163. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/LICENSE +0 -0
  164. {siliconcompiler-0.28.9.dist-info → siliconcompiler-0.29.1.dist-info}/top_level.txt +0 -0
@@ -150,9 +150,9 @@ def convert_drc(view, path):
150
150
 
151
151
  def main():
152
152
  # SC_ROOT provided by CLI
153
- sys.path.append(SC_ROOT) # noqa: F821
153
+ sys.path.append(SC_KLAYOUT_ROOT) # noqa: F821
154
154
 
155
- from tools.klayout.klayout_utils import get_schema
155
+ from klayout_utils import get_schema
156
156
 
157
157
  schema = get_schema(manifest='sc_manifest.json')
158
158
 
@@ -42,7 +42,7 @@ import fnmatch
42
42
  def gds_export(design_name, in_def, in_files, out_file, tech, allow_missing, config_file='',
43
43
  seal_file='',
44
44
  timestamps=True):
45
- from tools.klayout.klayout_utils import get_write_options # noqa E402
45
+ from klayout_utils import get_write_options # noqa E402
46
46
 
47
47
  # Load def file
48
48
  main_layout = pya.Layout()
@@ -119,16 +119,18 @@ def gds_export(design_name, in_def, in_files, out_file, tech, allow_missing, con
119
119
 
120
120
  def main():
121
121
  # SC_ROOT provided by CLI
122
- sys.path.append(SC_ROOT) # noqa: F821
122
+ sys.path.append(SC_KLAYOUT_ROOT) # noqa: F821
123
+ sys.path.append(SC_TOOLS_ROOT) # noqa: F821
124
+ print(sys.path)
123
125
 
124
- from tools.klayout.klayout_utils import (
126
+ from klayout_utils import (
125
127
  technology,
126
128
  get_streams,
127
129
  save_technology,
128
130
  get_schema
129
131
  )
130
- from tools.klayout.klayout_show import show
131
- from tools._common.asic import get_libraries
132
+ from klayout_show import show
133
+ from _common.asic import get_libraries
132
134
 
133
135
  schema = get_schema(manifest='sc_manifest.json')
134
136
 
@@ -148,7 +148,7 @@ def rename_cell(base_layout, old_name, new_name):
148
148
 
149
149
 
150
150
  def write_stream(layout, outfile, timestamps):
151
- from tools.klayout.klayout_utils import get_write_options
151
+ from klayout_utils import get_write_options
152
152
 
153
153
  print(f"[INFO] Writing layout: '{outfile}'")
154
154
 
@@ -324,9 +324,10 @@ def parse_operations(schema, base_layout, steps):
324
324
 
325
325
  if __name__ == "__main__":
326
326
  # SC_ROOT provided by CLI
327
- sys.path.append(SC_ROOT) # noqa: F821
327
+ sys.path.append(SC_KLAYOUT_ROOT) # noqa: F821
328
+ sys.path.append(SC_TOOLS_ROOT) # noqa: F821
328
329
 
329
- from tools.klayout.klayout_utils import (
330
+ from klayout_utils import (
330
331
  technology,
331
332
  get_streams,
332
333
  get_schema
@@ -205,9 +205,10 @@ def __screenshot_montage(schema, view, xbins, ybins):
205
205
 
206
206
  def main():
207
207
  # SC_ROOT provided by CLI, and is only accessible when this is main module
208
- sys.path.append(SC_ROOT) # noqa: F821
208
+ sys.path.append(SC_KLAYOUT_ROOT) # noqa: F821
209
+ sys.path.append(SC_TOOLS_ROOT) # noqa: F821
209
210
 
210
- from tools.klayout.klayout_utils import (
211
+ from klayout_utils import (
211
212
  technology,
212
213
  get_schema
213
214
  )
@@ -21,7 +21,7 @@ def get_streams(schema):
21
21
 
22
22
 
23
23
  def technology(design, schema):
24
- from tools._common.asic import get_libraries
24
+ from _common.asic import get_libraries
25
25
 
26
26
  sc_step = schema.get('arg', 'step')
27
27
  sc_index = schema.get('arg', 'index')
@@ -1,5 +1,7 @@
1
+ import os
1
2
  from siliconcompiler import SiliconCompilerError
2
3
  from siliconcompiler.tools.klayout.klayout import setup as setup_tool
4
+ from siliconcompiler.tools.klayout.klayout import runtime_options as runtime_options_tool
3
5
  from siliconcompiler.tools._common import input_provides, get_tool_task
4
6
 
5
7
 
@@ -194,3 +196,9 @@ def setup(chip):
194
196
  raise SiliconCompilerError('write requires a filename to save to', chip=chip)
195
197
  chip.add('tool', tool, 'task', task, 'output', args,
196
198
  step=step, index=index)
199
+
200
+
201
+ def runtime_options(chip):
202
+ return runtime_options_tool(chip) + [
203
+ '-rd', f'SC_TOOLS_ROOT={os.path.dirname(os.path.dirname(__file__))}'
204
+ ]
@@ -1,11 +1,12 @@
1
- from siliconcompiler.tools.klayout import klayout
2
1
  from siliconcompiler.tools.klayout.klayout import setup as setup_tool
3
2
  from siliconcompiler.tools.klayout.show import general_gui_setup
4
3
  from siliconcompiler.tools.klayout.show import pre_process as show_pre_process
4
+ from siliconcompiler.tools.klayout.show import runtime_options as show_runtime_options
5
5
  from siliconcompiler.tools._common import get_tool_task
6
6
 
7
7
 
8
8
  def make_docs(chip):
9
+ from siliconcompiler.tools.klayout import klayout
9
10
  klayout.make_docs(chip)
10
11
  chip.set('tool', 'klayout', 'task', 'screenshot', 'var', 'show_filepath', '<path>')
11
12
 
@@ -98,3 +99,7 @@ def setup_gui_screenshot(chip, require_input=True):
98
99
  for y in range(ybins):
99
100
  chip.add('tool', tool, 'task', task, 'output', f'{design}_X{x}_Y{y}.png',
100
101
  step=step, index=index)
102
+
103
+
104
+ def runtime_options(chip):
105
+ return show_runtime_options(chip)
@@ -1,12 +1,13 @@
1
1
  import os
2
2
  import shutil
3
3
 
4
- from siliconcompiler.tools.klayout import klayout
5
4
  from siliconcompiler.tools.klayout.klayout import setup as setup_tool
5
+ from siliconcompiler.tools.klayout.klayout import runtime_options as runtime_options_tool
6
6
  from siliconcompiler.tools._common import find_incoming_ext, get_tool_task
7
7
 
8
8
 
9
9
  def make_docs(chip):
10
+ from siliconcompiler.tools.klayout import klayout
10
11
  klayout.make_docs(chip)
11
12
  chip.set('tool', 'klayout', 'task', 'show', 'var', 'show_filepath', '<path>')
12
13
 
@@ -99,3 +100,9 @@ def pre_process(chip):
99
100
  ext_file = os.path.join(rel_path, f'{chip.top()}.{ext}')
100
101
  if ext_file and os.path.exists(ext_file):
101
102
  shutil.copy2(ext_file, f"inputs/{chip.top()}.{ext}")
103
+
104
+
105
+ def runtime_options(chip):
106
+ return runtime_options_tool(chip) + [
107
+ '-rd', f'SC_TOOLS_ROOT={os.path.dirname(os.path.dirname(__file__))}'
108
+ ]
@@ -13,7 +13,6 @@ import gzip
13
13
  import shutil
14
14
  import os
15
15
  from siliconcompiler.tools._common import input_provides, get_tool_task
16
- from siliconcompiler.targets import freepdk45_demo
17
16
  from siliconcompiler import utils
18
17
 
19
18
 
@@ -21,6 +20,7 @@ from siliconcompiler import utils
21
20
  # Make Docs
22
21
  ####################################################################
23
22
  def make_docs(chip):
23
+ from siliconcompiler.targets import freepdk45_demo
24
24
  chip.use(freepdk45_demo)
25
25
 
26
26
 
@@ -0,0 +1,103 @@
1
+ '''
2
+ OpenROAD is an automated physical design platform for
3
+ integrated circuit design with a complete set of features
4
+ needed to translate a synthesized netlist to a tapeout ready
5
+ GDSII.
6
+
7
+ Documentation: https://openroad.readthedocs.io/
8
+
9
+ Sources: https://github.com/The-OpenROAD-Project/OpenROAD
10
+
11
+ Installation: https://github.com/The-OpenROAD-Project/OpenROAD
12
+ '''
13
+ from siliconcompiler.tools._common import get_tool_task
14
+
15
+
16
+ ####################################################################
17
+ # Make Docs
18
+ ####################################################################
19
+ def make_docs(chip):
20
+ from siliconcompiler.targets import asap7_demo
21
+ chip.use(asap7_demo)
22
+
23
+
24
+ ################################
25
+ # Setup Tool (pre executable)
26
+ ################################
27
+ def setup(chip, exit=True, clobber=False):
28
+ step = chip.get('arg', 'step')
29
+ index = chip.get('arg', 'index')
30
+ tool, task = get_tool_task(chip, step, index)
31
+
32
+ chip.set('tool', tool, 'exe', 'openroad')
33
+ chip.set('tool', tool, 'vswitch', '-version')
34
+ chip.set('tool', tool, 'version', '>=v2.0-17598', clobber=clobber)
35
+ chip.set('tool', tool, 'format', 'tcl', clobber=clobber)
36
+
37
+ option = [
38
+ "-no_init",
39
+ "-metrics", "reports/metrics.json"
40
+ ]
41
+
42
+ # exit automatically in batch mode and not breakpoint
43
+ if exit and \
44
+ not chip.get('option', 'breakpoint', step=step, index=index):
45
+ option.append("-exit")
46
+
47
+ chip.set('tool', tool, 'task', task, 'option', option,
48
+ step=step, index=index, clobber=clobber)
49
+
50
+ chip.set('tool', tool, 'task', task, 'refdir',
51
+ 'tools/openroad/scripts',
52
+ step=step, index=index, package='siliconcompiler')
53
+
54
+ # basic warning and error grep check on logfile
55
+ chip.set('tool', tool, 'task', task, 'regex', 'warnings',
56
+ r'^\[WARNING|Warning',
57
+ step=step, index=index, clobber=clobber)
58
+ chip.set('tool', tool, 'task', task, 'regex', 'errors',
59
+ r'^\[ERROR',
60
+ step=step, index=index, clobber=clobber)
61
+
62
+ chip.set('tool', tool, 'task', task, 'var', 'debug_level',
63
+ 'list of "tool key level" to enable debugging of OpenROAD',
64
+ field='help')
65
+
66
+ if chip.get('option', 'nodisplay'):
67
+ # Tells QT to use the offscreen platform if nodisplay is used
68
+ chip.set('tool', tool, 'task', task, 'env',
69
+ 'QT_QPA_PLATFORM', 'offscreen',
70
+ step=step, index=index)
71
+
72
+
73
+ ################################
74
+ # Version Check
75
+ ################################
76
+ def parse_version(stdout):
77
+ # stdout will be in one of the following forms:
78
+ # - 1 08de3b46c71e329a10aa4e753dcfeba2ddf54ddd
79
+ # - 1 v2.0-880-gd1c7001ad
80
+ # - v2.0-1862-g0d785bd84
81
+
82
+ # strip off the "1" prefix if it's there
83
+ version = stdout.split()[-1]
84
+
85
+ pieces = version.split('-')
86
+ if len(pieces) > 1:
87
+ # strip off the hash in the new version style
88
+ return '-'.join(pieces[:-1])
89
+ else:
90
+ return pieces[0]
91
+
92
+
93
+ def normalize_version(version):
94
+ if '.' in version:
95
+ return version.lstrip('v')
96
+ else:
97
+ return '0'
98
+
99
+
100
+ ##################################################
101
+ if __name__ == "__main__":
102
+ chip = make_docs()
103
+ chip.write_manifest("openroad.json")