siliconcompiler 0.32.3__py3-none-any.whl → 0.33.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.
- siliconcompiler/__init__.py +19 -2
- siliconcompiler/_metadata.py +1 -1
- siliconcompiler/apps/sc.py +2 -2
- siliconcompiler/apps/sc_install.py +3 -3
- siliconcompiler/apps/sc_issue.py +1 -1
- siliconcompiler/apps/sc_remote.py +4 -4
- siliconcompiler/apps/sc_show.py +2 -2
- siliconcompiler/apps/utils/replay.py +5 -3
- siliconcompiler/asic.py +120 -0
- siliconcompiler/checklist.py +150 -0
- siliconcompiler/core.py +267 -289
- siliconcompiler/flowgraph.py +803 -515
- siliconcompiler/fpga.py +84 -0
- siliconcompiler/metric.py +420 -0
- siliconcompiler/optimizer/vizier.py +2 -3
- siliconcompiler/package/__init__.py +29 -6
- siliconcompiler/pdk.py +415 -0
- siliconcompiler/record.py +449 -0
- siliconcompiler/remote/client.py +6 -3
- siliconcompiler/remote/schema.py +116 -112
- siliconcompiler/remote/server.py +3 -5
- siliconcompiler/report/dashboard/cli/__init__.py +13 -722
- siliconcompiler/report/dashboard/cli/board.py +895 -0
- siliconcompiler/report/dashboard/web/__init__.py +10 -10
- siliconcompiler/report/dashboard/web/components/__init__.py +5 -4
- siliconcompiler/report/dashboard/web/components/flowgraph.py +3 -3
- siliconcompiler/report/dashboard/web/components/graph.py +6 -3
- siliconcompiler/report/dashboard/web/state.py +1 -1
- siliconcompiler/report/dashboard/web/utils/__init__.py +4 -3
- siliconcompiler/report/html_report.py +2 -3
- siliconcompiler/report/report.py +13 -7
- siliconcompiler/report/summary_image.py +1 -1
- siliconcompiler/report/summary_table.py +3 -3
- siliconcompiler/report/utils.py +11 -10
- siliconcompiler/scheduler/__init__.py +145 -280
- siliconcompiler/scheduler/run_node.py +2 -1
- siliconcompiler/scheduler/send_messages.py +4 -4
- siliconcompiler/scheduler/slurm.py +2 -2
- siliconcompiler/schema/__init__.py +19 -2
- siliconcompiler/schema/baseschema.py +493 -0
- siliconcompiler/schema/cmdlineschema.py +250 -0
- siliconcompiler/{sphinx_ext → schema/docs}/__init__.py +3 -1
- siliconcompiler/{sphinx_ext → schema/docs}/dynamicgen.py +63 -81
- siliconcompiler/{sphinx_ext → schema/docs}/schemagen.py +73 -85
- siliconcompiler/{sphinx_ext → schema/docs}/utils.py +12 -13
- siliconcompiler/schema/editableschema.py +136 -0
- siliconcompiler/schema/journalingschema.py +238 -0
- siliconcompiler/schema/namedschema.py +41 -0
- siliconcompiler/schema/packageschema.py +101 -0
- siliconcompiler/schema/parameter.py +791 -0
- siliconcompiler/schema/parametertype.py +323 -0
- siliconcompiler/schema/parametervalue.py +736 -0
- siliconcompiler/schema/safeschema.py +37 -0
- siliconcompiler/schema/schema_cfg.py +109 -1789
- siliconcompiler/schema/utils.py +5 -68
- siliconcompiler/schema_obj.py +119 -0
- siliconcompiler/tool.py +1308 -0
- siliconcompiler/tools/_common/__init__.py +6 -10
- siliconcompiler/tools/_common/sdc/sc_constraints.sdc +1 -1
- siliconcompiler/tools/bluespec/convert.py +7 -7
- siliconcompiler/tools/builtin/_common.py +1 -1
- siliconcompiler/tools/builtin/concatenate.py +2 -2
- siliconcompiler/tools/builtin/minimum.py +1 -1
- siliconcompiler/tools/builtin/mux.py +2 -1
- siliconcompiler/tools/builtin/nop.py +1 -1
- siliconcompiler/tools/builtin/verify.py +6 -4
- siliconcompiler/tools/chisel/convert.py +4 -4
- siliconcompiler/tools/genfasm/bitstream.py +3 -3
- siliconcompiler/tools/ghdl/convert.py +1 -1
- siliconcompiler/tools/icarus/compile.py +4 -4
- siliconcompiler/tools/icepack/bitstream.py +6 -1
- siliconcompiler/tools/klayout/convert_drc_db.py +5 -0
- siliconcompiler/tools/klayout/klayout_export.py +0 -1
- siliconcompiler/tools/klayout/klayout_utils.py +3 -10
- siliconcompiler/tools/nextpnr/apr.py +6 -1
- siliconcompiler/tools/nextpnr/nextpnr.py +4 -4
- siliconcompiler/tools/openroad/_apr.py +13 -0
- siliconcompiler/tools/openroad/rdlroute.py +3 -3
- siliconcompiler/tools/openroad/scripts/apr/postamble.tcl +1 -1
- siliconcompiler/tools/openroad/scripts/apr/preamble.tcl +5 -5
- siliconcompiler/tools/openroad/scripts/apr/sc_antenna_repair.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_clock_tree_synthesis.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_detailed_placement.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_detailed_route.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_endcap_tapcell_insertion.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_fillercell_insertion.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_fillmetal_insertion.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_global_placement.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_global_route.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_init_floorplan.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_macro_placement.tcl +3 -3
- siliconcompiler/tools/openroad/scripts/apr/sc_metrics.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_pin_placement.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_power_grid.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_repair_design.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_repair_timing.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/apr/sc_write_data.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/common/procs.tcl +57 -1
- siliconcompiler/tools/openroad/scripts/common/screenshot.tcl +2 -2
- siliconcompiler/tools/openroad/scripts/common/write_images.tcl +28 -3
- siliconcompiler/tools/openroad/scripts/sc_rcx.tcl +1 -1
- siliconcompiler/tools/openroad/scripts/sc_rdlroute.tcl +3 -3
- siliconcompiler/tools/openroad/scripts/sc_show.tcl +6 -6
- siliconcompiler/tools/slang/__init__.py +10 -10
- siliconcompiler/tools/surelog/parse.py +4 -4
- siliconcompiler/tools/sv2v/convert.py +20 -3
- siliconcompiler/tools/verilator/compile.py +2 -2
- siliconcompiler/tools/verilator/verilator.py +3 -3
- siliconcompiler/tools/vpr/place.py +1 -1
- siliconcompiler/tools/vpr/route.py +4 -4
- siliconcompiler/tools/vpr/screenshot.py +1 -1
- siliconcompiler/tools/vpr/show.py +5 -5
- siliconcompiler/tools/vpr/vpr.py +24 -24
- siliconcompiler/tools/xdm/convert.py +2 -2
- siliconcompiler/tools/xyce/simulate.py +1 -1
- siliconcompiler/tools/yosys/sc_synth_asic.tcl +74 -68
- siliconcompiler/tools/yosys/syn_asic.py +2 -2
- siliconcompiler/toolscripts/_tools.json +7 -7
- siliconcompiler/toolscripts/ubuntu22/install-vpr.sh +0 -2
- siliconcompiler/toolscripts/ubuntu24/install-vpr.sh +0 -2
- siliconcompiler/utils/__init__.py +8 -112
- siliconcompiler/utils/flowgraph.py +339 -0
- siliconcompiler/{issue.py → utils/issue.py} +4 -3
- siliconcompiler/utils/logging.py +1 -2
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/METADATA +9 -8
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/RECORD +151 -134
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/WHEEL +1 -1
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/entry_points.txt +8 -8
- siliconcompiler/schema/schema_obj.py +0 -1936
- siliconcompiler/toolscripts/ubuntu20/install-vpr.sh +0 -29
- siliconcompiler/toolscripts/ubuntu20/install-yosys-parmys.sh +0 -61
- /siliconcompiler/{templates → data/templates}/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/email/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/email/general.j2 +0 -0
- /siliconcompiler/{templates → data/templates}/email/summary.j2 +0 -0
- /siliconcompiler/{templates → data/templates}/issue/README.txt +0 -0
- /siliconcompiler/{templates → data/templates}/issue/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/issue/run.sh +0 -0
- /siliconcompiler/{templates → data/templates}/replay/replay.py.j2 +0 -0
- /siliconcompiler/{templates → data/templates}/replay/replay.sh.j2 +0 -0
- /siliconcompiler/{templates → data/templates}/replay/requirements.txt +0 -0
- /siliconcompiler/{templates → data/templates}/replay/setup.sh +0 -0
- /siliconcompiler/{templates → data/templates}/report/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/report/bootstrap.min.css +0 -0
- /siliconcompiler/{templates → data/templates}/report/bootstrap.min.js +0 -0
- /siliconcompiler/{templates → data/templates}/report/bootstrap_LICENSE.md +0 -0
- /siliconcompiler/{templates → data/templates}/report/sc_report.j2 +0 -0
- /siliconcompiler/{templates → data/templates}/slurm/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/slurm/run.sh +0 -0
- /siliconcompiler/{templates → data/templates}/tcl/__init__.py +0 -0
- /siliconcompiler/{templates → data/templates}/tcl/manifest.tcl.j2 +0 -0
- /siliconcompiler/{units.py → utils/units.py} +0 -0
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/licenses/LICENSE +0 -0
- {siliconcompiler-0.32.3.dist-info → siliconcompiler-0.33.0.dist-info}/top_level.txt +0 -0
|
@@ -1,12 +1,8 @@
|
|
|
1
1
|
import contextlib
|
|
2
|
-
import distro
|
|
3
|
-
import getpass
|
|
4
2
|
import multiprocessing
|
|
5
3
|
import logging
|
|
6
4
|
import os
|
|
7
|
-
import platform
|
|
8
5
|
import psutil
|
|
9
|
-
import socket
|
|
10
6
|
import re
|
|
11
7
|
import shlex
|
|
12
8
|
import shutil
|
|
@@ -17,25 +13,25 @@ import packaging.version
|
|
|
17
13
|
import packaging.specifiers
|
|
18
14
|
from io import StringIO
|
|
19
15
|
import traceback
|
|
20
|
-
from datetime import datetime
|
|
21
16
|
from logging.handlers import QueueHandler, QueueListener
|
|
22
17
|
from siliconcompiler import sc_open
|
|
23
18
|
from siliconcompiler import utils
|
|
24
|
-
from siliconcompiler import _metadata
|
|
25
19
|
from siliconcompiler.remote import Client
|
|
26
|
-
from siliconcompiler
|
|
20
|
+
from siliconcompiler import Schema
|
|
21
|
+
from siliconcompiler.schema import JournalingSchema
|
|
22
|
+
from siliconcompiler.record import RecordTime, RecordTool
|
|
27
23
|
from siliconcompiler.scheduler import slurm
|
|
28
24
|
from siliconcompiler.scheduler import docker_runner
|
|
29
25
|
from siliconcompiler import NodeStatus, SiliconCompilerError
|
|
30
|
-
from siliconcompiler.flowgraph import
|
|
31
|
-
_get_pruned_node_inputs,
|
|
32
|
-
_unreachable_steps_to_execute, _nodes_to_execute, \
|
|
26
|
+
from siliconcompiler.utils.flowgraph import _get_flowgraph_execution_order, \
|
|
27
|
+
_get_pruned_node_inputs, \
|
|
33
28
|
get_nodes_from, nodes_to_execute, _check_flowgraph
|
|
34
29
|
from siliconcompiler.utils.logging import SCBlankLoggerFormatter
|
|
35
30
|
from siliconcompiler.tools._common import input_file_node_name
|
|
36
31
|
import lambdapdk
|
|
37
32
|
from siliconcompiler.tools._common import get_tool_task, record_metric
|
|
38
33
|
from siliconcompiler.scheduler import send_messages
|
|
34
|
+
from siliconcompiler.flowgraph import RuntimeFlowgraph
|
|
39
35
|
|
|
40
36
|
try:
|
|
41
37
|
import resource
|
|
@@ -61,6 +57,14 @@ def _get_callback(hook):
|
|
|
61
57
|
_failed_log_lines = 20
|
|
62
58
|
|
|
63
59
|
|
|
60
|
+
#######################################
|
|
61
|
+
def _do_record_access():
|
|
62
|
+
'''
|
|
63
|
+
Determine if Schema should record calls to .get
|
|
64
|
+
'''
|
|
65
|
+
return False
|
|
66
|
+
|
|
67
|
+
|
|
64
68
|
###############################################################################
|
|
65
69
|
class SiliconCompilerTimeout(Exception):
|
|
66
70
|
''' Minimal Exception wrapper used to raise sc timeout errors.
|
|
@@ -101,7 +105,7 @@ def run(chip):
|
|
|
101
105
|
copy_old_run_dir(chip, org_jobname)
|
|
102
106
|
clean_build_dir(chip)
|
|
103
107
|
_reset_flow_nodes(chip, flow, nodes_to_execute(chip, flow))
|
|
104
|
-
|
|
108
|
+
chip.schema.get("record", field='schema').record_python_packages()
|
|
105
109
|
|
|
106
110
|
if chip.get('option', 'remote'):
|
|
107
111
|
client = Client(chip)
|
|
@@ -175,18 +179,17 @@ def _local_process(chip, flow):
|
|
|
175
179
|
extra_setup_nodes = {}
|
|
176
180
|
|
|
177
181
|
if chip.get('option', 'clean') or not chip.get('option', 'from'):
|
|
178
|
-
load_nodes =
|
|
182
|
+
load_nodes = list(chip.schema.get("flowgraph", flow, field="schema").get_nodes())
|
|
179
183
|
else:
|
|
180
184
|
for step in chip.get('option', 'from'):
|
|
181
185
|
from_nodes.extend(
|
|
182
186
|
[(step, index) for index in chip.getkeys('flowgraph', flow, step)])
|
|
183
187
|
|
|
184
|
-
|
|
185
|
-
chip,
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
chip.get('option', 'prune'))
|
|
188
|
+
runtime = RuntimeFlowgraph(
|
|
189
|
+
chip.schema.get("flowgraph", flow, field="schema"),
|
|
190
|
+
to_steps=chip.get('option', 'from'),
|
|
191
|
+
prune_nodes=chip.get('option', 'prune'))
|
|
192
|
+
load_nodes = list(runtime.get_nodes())
|
|
190
193
|
|
|
191
194
|
for node_level in _get_flowgraph_execution_order(chip, flow):
|
|
192
195
|
for step, index in node_level:
|
|
@@ -201,12 +204,14 @@ def _local_process(chip, flow):
|
|
|
201
204
|
if os.path.exists(manifest):
|
|
202
205
|
# ensure we setup these nodes again
|
|
203
206
|
try:
|
|
204
|
-
|
|
207
|
+
journal = JournalingSchema(Schema())
|
|
208
|
+
journal.read_manifest(manifest)
|
|
209
|
+
extra_setup_nodes[(step, index)] = journal
|
|
205
210
|
except Exception:
|
|
206
211
|
pass
|
|
207
212
|
|
|
208
213
|
# Setup tools for all nodes to run.
|
|
209
|
-
nodes = nodes_to_execute(chip, flow)
|
|
214
|
+
nodes = list(nodes_to_execute(chip, flow))
|
|
210
215
|
all_setup_nodes = nodes + load_nodes + list(extra_setup_nodes.keys())
|
|
211
216
|
for layer_nodes in _get_flowgraph_execution_order(chip, flow):
|
|
212
217
|
for step, index in layer_nodes:
|
|
@@ -222,19 +227,28 @@ def _local_process(chip, flow):
|
|
|
222
227
|
except: # noqa E722
|
|
223
228
|
pass
|
|
224
229
|
if node_status:
|
|
225
|
-
chip.
|
|
230
|
+
chip.schema.get("record", field='schema').set('status', node_status,
|
|
231
|
+
step=step, index=index)
|
|
226
232
|
|
|
227
233
|
def mark_pending(step, index):
|
|
228
|
-
chip.
|
|
234
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.PENDING,
|
|
235
|
+
step=step, index=index)
|
|
229
236
|
for next_step, next_index in get_nodes_from(chip, flow, [(step, index)]):
|
|
230
237
|
if chip.get('record', 'status', step=next_step, index=next_index) == \
|
|
231
238
|
NodeStatus.SKIPPED:
|
|
232
239
|
continue
|
|
233
240
|
|
|
234
241
|
# Mark following steps as pending
|
|
235
|
-
chip.
|
|
242
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.PENDING,
|
|
243
|
+
step=next_step, index=next_index)
|
|
236
244
|
|
|
237
245
|
# Check if nodes have been modified from previous data
|
|
246
|
+
runtimeflow = RuntimeFlowgraph(
|
|
247
|
+
chip.schema.get("flowgraph", flow, field="schema"),
|
|
248
|
+
from_steps=chip.get('option', 'from'),
|
|
249
|
+
to_steps=chip.get('option', 'to'),
|
|
250
|
+
prune_nodes=chip.get('option', 'prune'))
|
|
251
|
+
|
|
238
252
|
for layer_nodes in _get_flowgraph_execution_order(chip, flow):
|
|
239
253
|
for step, index in layer_nodes:
|
|
240
254
|
# Only look at successful nodes
|
|
@@ -242,12 +256,14 @@ def _local_process(chip, flow):
|
|
|
242
256
|
(NodeStatus.SUCCESS, NodeStatus.SKIPPED):
|
|
243
257
|
continue
|
|
244
258
|
|
|
245
|
-
if
|
|
259
|
+
if (step, index) in runtimeflow.get_nodes() and \
|
|
260
|
+
not check_node_inputs(chip, step, index):
|
|
246
261
|
# change failing nodes to pending
|
|
247
262
|
mark_pending(step, index)
|
|
248
263
|
elif (step, index) in extra_setup_nodes:
|
|
249
264
|
# import old information
|
|
250
|
-
chip.schema.
|
|
265
|
+
JournalingSchema(chip.schema).import_journal(
|
|
266
|
+
schema=extra_setup_nodes[(step, index)])
|
|
251
267
|
|
|
252
268
|
# Ensure pending nodes cause following nodes to be run
|
|
253
269
|
for step, index in nodes:
|
|
@@ -344,7 +360,8 @@ def _setup_node(chip, step, index, flow=None):
|
|
|
344
360
|
|
|
345
361
|
if setup_ret is not None:
|
|
346
362
|
chip.logger.warning(f'Removing {step}{index} due to {setup_ret}')
|
|
347
|
-
chip.
|
|
363
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.SKIPPED,
|
|
364
|
+
step=step, index=index)
|
|
348
365
|
|
|
349
366
|
return False
|
|
350
367
|
|
|
@@ -457,17 +474,17 @@ def _runtask(chip, flow, step, index, exec_func, pipe=None, queue=None, replay=F
|
|
|
457
474
|
chip.set('arg', 'step', step, clobber=True)
|
|
458
475
|
chip.set('arg', 'index', index, clobber=True)
|
|
459
476
|
|
|
460
|
-
chip.schema.
|
|
477
|
+
chip.schema = JournalingSchema(chip.schema)
|
|
478
|
+
chip.schema.start_journal()
|
|
461
479
|
|
|
462
480
|
# Make record of sc version and machine
|
|
463
|
-
|
|
481
|
+
chip.schema.get("record", field='schema').record_version(step, index)
|
|
464
482
|
# Record user information if enabled
|
|
465
483
|
if chip.get('option', 'track', step=step, index=index):
|
|
466
|
-
|
|
484
|
+
chip.schema.get("record", field='schema').record_userinformation(step, index)
|
|
467
485
|
|
|
468
486
|
# Start wall timer
|
|
469
|
-
|
|
470
|
-
__record_time(chip, step, index, wall_start, 'start')
|
|
487
|
+
chip.schema.get("record", field='schema').record_time(step, index, RecordTime.START)
|
|
471
488
|
|
|
472
489
|
workdir = _setup_workdir(chip, step, index, replay)
|
|
473
490
|
cwd = os.getcwd()
|
|
@@ -485,7 +502,8 @@ def _runtask(chip, flow, step, index, exec_func, pipe=None, queue=None, replay=F
|
|
|
485
502
|
|
|
486
503
|
# return to original directory
|
|
487
504
|
os.chdir(cwd)
|
|
488
|
-
chip.schema.
|
|
505
|
+
chip.schema.stop_journal()
|
|
506
|
+
chip.schema = chip.schema.get_base_schema()
|
|
489
507
|
|
|
490
508
|
if pipe:
|
|
491
509
|
pipe.send(chip._packages)
|
|
@@ -493,7 +511,8 @@ def _runtask(chip, flow, step, index, exec_func, pipe=None, queue=None, replay=F
|
|
|
493
511
|
|
|
494
512
|
###########################################################################
|
|
495
513
|
def _haltstep(chip, flow, step, index, log=True):
|
|
496
|
-
chip.
|
|
514
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.ERROR,
|
|
515
|
+
step=step, index=index)
|
|
497
516
|
chip.write_manifest(os.path.join("outputs", f"{chip.get('design')}.pkg.json"))
|
|
498
517
|
|
|
499
518
|
if log:
|
|
@@ -566,12 +585,14 @@ def _select_inputs(chip, step, index, trial=False):
|
|
|
566
585
|
else:
|
|
567
586
|
sel_inputs = _get_pruned_node_inputs(chip, flow, (step, index))
|
|
568
587
|
|
|
569
|
-
if (step, index) not in
|
|
588
|
+
if (step, index) not in chip.schema.get("flowgraph", flow, field="schema").get_entry_nodes() \
|
|
589
|
+
and not sel_inputs:
|
|
570
590
|
chip.logger.error(f'No inputs selected after running {tool}')
|
|
571
591
|
_haltstep(chip, flow, step, index)
|
|
572
592
|
|
|
573
593
|
if not trial:
|
|
574
|
-
chip.
|
|
594
|
+
chip.schema.get("record", field='schema').set('inputnode', sel_inputs,
|
|
595
|
+
step=step, index=index)
|
|
575
596
|
|
|
576
597
|
return sel_inputs
|
|
577
598
|
|
|
@@ -661,15 +682,15 @@ def __read_std_streams(chip, quiet,
|
|
|
661
682
|
# Chip helper Functions
|
|
662
683
|
############################################################################
|
|
663
684
|
def _getexe(chip, tool, step, index):
|
|
664
|
-
path = chip.get('tool', tool, 'path', step=step, index=index)
|
|
665
685
|
exe = chip.get('tool', tool, 'exe')
|
|
666
686
|
if exe is None:
|
|
667
687
|
return None
|
|
688
|
+
path = chip.find_files('tool', tool, 'path', step=step, index=index)
|
|
668
689
|
|
|
669
690
|
syspath = os.getenv('PATH', os.defpath)
|
|
670
691
|
if path:
|
|
671
692
|
# Prepend 'path' schema var to system path
|
|
672
|
-
syspath =
|
|
693
|
+
syspath = path + os.pathsep + syspath
|
|
673
694
|
|
|
674
695
|
fullexe = shutil.which(exe, path=syspath)
|
|
675
696
|
|
|
@@ -714,20 +735,12 @@ def _makecmd(chip, tool, task, step, index, script_name='replay.sh', include_pat
|
|
|
714
735
|
|
|
715
736
|
fullexe = _getexe(chip, tool, step, index)
|
|
716
737
|
|
|
717
|
-
is_posix = __is_posix()
|
|
718
|
-
|
|
719
738
|
def parse_options(options):
|
|
720
739
|
if not options:
|
|
721
740
|
return []
|
|
722
741
|
shlex_opts = []
|
|
723
742
|
for option in options:
|
|
724
|
-
option
|
|
725
|
-
if (option.startswith("\"") and option.endswith("\"")) or \
|
|
726
|
-
(option.startswith("'") and option.endswith("'")):
|
|
727
|
-
# Make sure strings are quoted in double quotes
|
|
728
|
-
shlex_opts.append(f'"{option[1:-1]}"')
|
|
729
|
-
else:
|
|
730
|
-
shlex_opts.extend(shlex.split(option, posix=is_posix))
|
|
743
|
+
shlex_opts.append(str(option).strip())
|
|
731
744
|
return shlex_opts
|
|
732
745
|
|
|
733
746
|
# Add scripts files
|
|
@@ -743,9 +756,10 @@ def _makecmd(chip, tool, task, step, index, script_name='replay.sh', include_pat
|
|
|
743
756
|
runtime_options = getattr(chip._get_tool_module(step, index), 'runtime_options', None)
|
|
744
757
|
if runtime_options:
|
|
745
758
|
try:
|
|
746
|
-
|
|
759
|
+
if _do_record_access():
|
|
760
|
+
chip.schema.add_journaling_type("get")
|
|
747
761
|
cmdlist.extend(parse_options(runtime_options(chip)))
|
|
748
|
-
chip.schema.
|
|
762
|
+
chip.schema.remove_journaling_type("get")
|
|
749
763
|
except Exception as e:
|
|
750
764
|
chip.logger.error(f'Failed to get runtime options for {tool}/{task}')
|
|
751
765
|
raise e
|
|
@@ -753,14 +767,7 @@ def _makecmd(chip, tool, task, step, index, script_name='replay.sh', include_pat
|
|
|
753
767
|
# Separate variables to be able to display nice name of executable
|
|
754
768
|
cmd = os.path.basename(cmdlist[0])
|
|
755
769
|
cmd_args = cmdlist[1:]
|
|
756
|
-
print_cmd =
|
|
757
|
-
cmdlist = [cmdlist[0]]
|
|
758
|
-
for arg in cmd_args:
|
|
759
|
-
if arg.startswith("\"") and arg.endswith("\""):
|
|
760
|
-
# Remove quoting since subprocess will handle that for us
|
|
761
|
-
cmdlist.append(arg[1:-1])
|
|
762
|
-
else:
|
|
763
|
-
cmdlist.append(arg)
|
|
770
|
+
print_cmd = shlex.join([cmd, *cmd_args])
|
|
764
771
|
|
|
765
772
|
# create replay file
|
|
766
773
|
with open(script_name, 'w') as f:
|
|
@@ -793,9 +800,9 @@ def _makecmd(chip, tool, task, step, index, script_name='replay.sh', include_pat
|
|
|
793
800
|
add_new_line = True
|
|
794
801
|
|
|
795
802
|
if add_new_line:
|
|
796
|
-
format_cmd.append(cmdarg)
|
|
803
|
+
format_cmd.append(shlex.quote(cmdarg))
|
|
797
804
|
else:
|
|
798
|
-
format_cmd[-1] += f' {cmdarg}'
|
|
805
|
+
format_cmd[-1] += f' {shlex.quote(cmdarg)}'
|
|
799
806
|
|
|
800
807
|
replay_opts["cmds"] = format_cmd
|
|
801
808
|
|
|
@@ -915,9 +922,8 @@ def _run_executable_or_builtin(chip, step, index, version, toolpath, workdir, ru
|
|
|
915
922
|
##################
|
|
916
923
|
# Make record of tool options
|
|
917
924
|
if cmd_args is not None:
|
|
918
|
-
chip.
|
|
919
|
-
|
|
920
|
-
step=step, index=index)
|
|
925
|
+
chip.schema.get("record", field='schema').record_tool(
|
|
926
|
+
step, index, cmd_args, RecordTool.ARGS)
|
|
921
927
|
|
|
922
928
|
chip.logger.info('%s', printable_cmd)
|
|
923
929
|
timeout = chip.get('option', 'timeout', step=step, index=index)
|
|
@@ -962,7 +968,6 @@ def _run_executable_or_builtin(chip, step, index, version, toolpath, workdir, ru
|
|
|
962
968
|
if nice:
|
|
963
969
|
preexec_fn = set_nice
|
|
964
970
|
|
|
965
|
-
cmd_start_time = time.time()
|
|
966
971
|
proc = subprocess.Popen(cmdlist,
|
|
967
972
|
stdin=subprocess.DEVNULL,
|
|
968
973
|
stdout=stdout_writer,
|
|
@@ -1004,7 +1009,7 @@ def _run_executable_or_builtin(chip, step, index, version, toolpath, workdir, ru
|
|
|
1004
1009
|
is_stdout_log, stdout_reader, stdout_print,
|
|
1005
1010
|
is_stderr_log, stderr_reader, stderr_print)
|
|
1006
1011
|
|
|
1007
|
-
if timeout is not None and time.time() -
|
|
1012
|
+
if timeout is not None and time.time() - cpu_start > timeout:
|
|
1008
1013
|
chip.logger.error(f'Step timed out after {timeout} seconds')
|
|
1009
1014
|
utils.terminate_process(proc.pid)
|
|
1010
1015
|
raise SiliconCompilerTimeout(f'{step}{index} timeout')
|
|
@@ -1024,7 +1029,7 @@ def _run_executable_or_builtin(chip, step, index, version, toolpath, workdir, ru
|
|
|
1024
1029
|
is_stderr_log, stderr_reader, stderr_print)
|
|
1025
1030
|
retcode = proc.returncode
|
|
1026
1031
|
|
|
1027
|
-
chip.
|
|
1032
|
+
chip.schema.get("record", field='schema').record_tool(step, index, retcode, RecordTool.EXITCODE)
|
|
1028
1033
|
if retcode != 0:
|
|
1029
1034
|
msg = f'Command failed with code {retcode}.'
|
|
1030
1035
|
if logfile:
|
|
@@ -1056,9 +1061,10 @@ def _post_process(chip, step, index):
|
|
|
1056
1061
|
func = getattr(chip._get_task_module(step, index, flow=flow), 'post_process', None)
|
|
1057
1062
|
if func:
|
|
1058
1063
|
try:
|
|
1059
|
-
|
|
1064
|
+
if _do_record_access():
|
|
1065
|
+
chip.schema.add_journaling_type("get")
|
|
1060
1066
|
func(chip)
|
|
1061
|
-
chip.schema.
|
|
1067
|
+
chip.schema.remove_journaling_type("get")
|
|
1062
1068
|
except Exception as e:
|
|
1063
1069
|
chip.logger.error(f'Failed to run post-process for {tool}/{task}.')
|
|
1064
1070
|
print_traceback(chip, e)
|
|
@@ -1123,10 +1129,12 @@ def _executenode(chip, step, index, replay):
|
|
|
1123
1129
|
toolpath, version = _check_tool_version(chip, step, index, run_func)
|
|
1124
1130
|
|
|
1125
1131
|
if version:
|
|
1126
|
-
chip.
|
|
1132
|
+
chip.schema.get("record", field='schema').record_tool(
|
|
1133
|
+
step, index, version, RecordTool.VERSION)
|
|
1127
1134
|
|
|
1128
1135
|
if toolpath:
|
|
1129
|
-
chip.
|
|
1136
|
+
chip.schema.get("record", field='schema').record_tool(
|
|
1137
|
+
step, index, toolpath, RecordTool.PATH)
|
|
1130
1138
|
|
|
1131
1139
|
# Write manifest (tool interface) (Don't move this!)
|
|
1132
1140
|
_write_task_manifest(chip, tool)
|
|
@@ -1151,9 +1159,10 @@ def _pre_process(chip, step, index):
|
|
|
1151
1159
|
func = getattr(chip._get_task_module(step, index, flow=flow), 'pre_process', None)
|
|
1152
1160
|
if func:
|
|
1153
1161
|
try:
|
|
1154
|
-
|
|
1162
|
+
if _do_record_access():
|
|
1163
|
+
chip.schema.add_journaling_type("get")
|
|
1155
1164
|
func(chip)
|
|
1156
|
-
chip.schema.
|
|
1165
|
+
chip.schema.remove_journaling_type("get")
|
|
1157
1166
|
except Exception as e:
|
|
1158
1167
|
chip.logger.error(f"Pre-processing failed for '{tool}/{task}'.")
|
|
1159
1168
|
raise e
|
|
@@ -1167,11 +1176,10 @@ def _set_env_vars(chip, step, index):
|
|
|
1167
1176
|
|
|
1168
1177
|
tool, task = get_tool_task(chip, step, index)
|
|
1169
1178
|
|
|
1170
|
-
|
|
1171
|
-
|
|
1179
|
+
if _do_record_access():
|
|
1180
|
+
chip.schema.add_journaling_type("get")
|
|
1172
1181
|
os.environ.update(_get_run_env_vars(chip, tool, task, step, index, include_path=True))
|
|
1173
|
-
|
|
1174
|
-
chip.schema._stop_record_access()
|
|
1182
|
+
chip.schema.remove_journaling_type("get")
|
|
1175
1183
|
|
|
1176
1184
|
return org_env
|
|
1177
1185
|
|
|
@@ -1265,7 +1273,8 @@ def _hash_files(chip, step, index, setup=False):
|
|
|
1265
1273
|
|
|
1266
1274
|
|
|
1267
1275
|
def _finalizenode(chip, step, index, replay):
|
|
1268
|
-
if chip.schema.
|
|
1276
|
+
if chip.schema.is_journaling() and any(
|
|
1277
|
+
[record["type"] == "get" for record in chip.schema.get_journal()]):
|
|
1269
1278
|
assert_required_accesses(chip, step, index)
|
|
1270
1279
|
|
|
1271
1280
|
flow = chip.get('option', 'flow')
|
|
@@ -1290,12 +1299,11 @@ def _finalizenode(chip, step, index, replay):
|
|
|
1290
1299
|
_hash_files(chip, step, index)
|
|
1291
1300
|
|
|
1292
1301
|
# Capture wall runtime and cpu cores
|
|
1293
|
-
|
|
1294
|
-
__record_time(chip, step, index, wall_end, 'end')
|
|
1302
|
+
end_time = chip.schema.get("record", field='schema').record_time(step, index, RecordTime.END)
|
|
1295
1303
|
|
|
1296
1304
|
# calculate total time
|
|
1297
1305
|
total_times = []
|
|
1298
|
-
for check_step, check_index in
|
|
1306
|
+
for check_step, check_index in chip.schema.get("flowgraph", flow, field="schema").get_nodes():
|
|
1299
1307
|
total_time = chip.get('metric', 'totaltime', step=check_step, index=check_index)
|
|
1300
1308
|
if total_time is not None:
|
|
1301
1309
|
total_times.append(total_time)
|
|
@@ -1304,7 +1312,8 @@ def _finalizenode(chip, step, index, replay):
|
|
|
1304
1312
|
else:
|
|
1305
1313
|
total_time = 0.0
|
|
1306
1314
|
|
|
1307
|
-
walltime =
|
|
1315
|
+
walltime = end_time - chip.schema.get("record", field='schema').get_recorded_time(
|
|
1316
|
+
step, index, RecordTime.START)
|
|
1308
1317
|
record_metric(chip, step, index, 'tasktime', walltime,
|
|
1309
1318
|
source=None, source_unit='s')
|
|
1310
1319
|
record_metric(chip, step, index, 'totaltime', total_time + walltime,
|
|
@@ -1313,7 +1322,9 @@ def _finalizenode(chip, step, index, replay):
|
|
|
1313
1322
|
|
|
1314
1323
|
# Save a successful manifest
|
|
1315
1324
|
if not is_skipped:
|
|
1316
|
-
chip.
|
|
1325
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.SUCCESS,
|
|
1326
|
+
step=step, index=index)
|
|
1327
|
+
|
|
1317
1328
|
chip.write_manifest(os.path.join("outputs", f"{chip.get('design')}.pkg.json"))
|
|
1318
1329
|
|
|
1319
1330
|
if chip._error and not replay:
|
|
@@ -1335,7 +1346,7 @@ def _finalizenode(chip, step, index, replay):
|
|
|
1335
1346
|
|
|
1336
1347
|
def _make_testcase(chip, step, index):
|
|
1337
1348
|
# Import here to avoid circular import
|
|
1338
|
-
from siliconcompiler.issue import generate_testcase
|
|
1349
|
+
from siliconcompiler.utils.issue import generate_testcase
|
|
1339
1350
|
|
|
1340
1351
|
generate_testcase(
|
|
1341
1352
|
chip,
|
|
@@ -1378,7 +1389,8 @@ def assert_required_accesses(chip, step, index):
|
|
|
1378
1389
|
if tool == 'builtin':
|
|
1379
1390
|
return
|
|
1380
1391
|
|
|
1381
|
-
gets = chip.schema.
|
|
1392
|
+
gets = set([tuple(record["key"]) for record in chip.schema.get_journal()
|
|
1393
|
+
if record["type"] == "get"])
|
|
1382
1394
|
logfile = os.path.join(
|
|
1383
1395
|
chip.getworkdir(jobname=jobname, step=step, index=index),
|
|
1384
1396
|
f'{step}.log')
|
|
@@ -1457,20 +1469,20 @@ def _reset_flow_nodes(chip, flow, nodes_to_execute):
|
|
|
1457
1469
|
|
|
1458
1470
|
def clear_node(step, index):
|
|
1459
1471
|
# Reset metrics and records
|
|
1472
|
+
chip.schema.get("metric", field='schema').clear(step, index)
|
|
1460
1473
|
for metric in chip.getkeys('metric'):
|
|
1461
1474
|
_clear_metric(chip, step, index, metric)
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
'status',
|
|
1466
|
-
'pythonpackage'])
|
|
1475
|
+
|
|
1476
|
+
chip.schema.get("record", field='schema').clear(
|
|
1477
|
+
step, index, keep=['remoteid', 'status', 'pythonpackage'])
|
|
1467
1478
|
|
|
1468
1479
|
# Mark all nodes as pending
|
|
1469
|
-
for step, index in
|
|
1470
|
-
chip.
|
|
1480
|
+
for step, index in chip.schema.get("flowgraph", flow, field="schema").get_nodes():
|
|
1481
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.PENDING,
|
|
1482
|
+
step=step, index=index)
|
|
1471
1483
|
|
|
1472
1484
|
should_resume = not chip.get('option', 'clean')
|
|
1473
|
-
for step, index in
|
|
1485
|
+
for step, index in chip.schema.get("flowgraph", flow, field="schema").get_nodes():
|
|
1474
1486
|
stepdir = chip.getworkdir(step=step, index=index)
|
|
1475
1487
|
cfg = f"{stepdir}/outputs/{chip.get('design')}.pkg.json"
|
|
1476
1488
|
|
|
@@ -1484,12 +1496,14 @@ def _reset_flow_nodes(chip, flow, nodes_to_execute):
|
|
|
1484
1496
|
try:
|
|
1485
1497
|
old_status = Schema(manifest=cfg).get('record', 'status', step=step, index=index)
|
|
1486
1498
|
if old_status:
|
|
1487
|
-
chip.
|
|
1499
|
+
chip.schema.get("record", field='schema').set('status', old_status,
|
|
1500
|
+
step=step, index=index)
|
|
1488
1501
|
except Exception:
|
|
1489
1502
|
# unable to load so leave it default
|
|
1490
1503
|
pass
|
|
1491
1504
|
else:
|
|
1492
|
-
chip.
|
|
1505
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.ERROR,
|
|
1506
|
+
step=step, index=index)
|
|
1493
1507
|
|
|
1494
1508
|
for step in chip.getkeys('flowgraph', flow):
|
|
1495
1509
|
all_indices_failed = True
|
|
@@ -1577,13 +1591,15 @@ def _check_node_dependencies(chip, node, deps, deps_was_successful):
|
|
|
1577
1591
|
# Fail if any dependency failed for non-builtin task
|
|
1578
1592
|
if tool != 'builtin':
|
|
1579
1593
|
deps.clear()
|
|
1580
|
-
chip.
|
|
1594
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.ERROR,
|
|
1595
|
+
step=step, index=index)
|
|
1581
1596
|
return
|
|
1582
1597
|
|
|
1583
1598
|
# Fail if no dependency successfully finished for builtin task
|
|
1584
1599
|
if had_deps and len(deps) == 0 \
|
|
1585
1600
|
and tool == 'builtin' and not deps_was_successful.get(node):
|
|
1586
|
-
chip.
|
|
1601
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.ERROR,
|
|
1602
|
+
step=step, index=index)
|
|
1587
1603
|
|
|
1588
1604
|
|
|
1589
1605
|
def _launch_nodes(chip, nodes_to_run, processes, local_processes):
|
|
@@ -1653,7 +1669,8 @@ def _launch_nodes(chip, nodes_to_run, processes, local_processes):
|
|
|
1653
1669
|
if _get_callback('pre_node'):
|
|
1654
1670
|
_get_callback('pre_node')(chip, *node)
|
|
1655
1671
|
|
|
1656
|
-
chip.
|
|
1672
|
+
chip.schema.get("record", field='schema').set('status', NodeStatus.RUNNING,
|
|
1673
|
+
step=node[0], index=node[1])
|
|
1657
1674
|
start_times[node] = time.time()
|
|
1658
1675
|
changed = True
|
|
1659
1676
|
|
|
@@ -1693,7 +1710,7 @@ def _process_completed_nodes(chip, processes, running_nodes):
|
|
|
1693
1710
|
f'{chip.design}.pkg.json')
|
|
1694
1711
|
chip.logger.debug(f'{step}{index} is complete merging: {manifest}')
|
|
1695
1712
|
if os.path.exists(manifest):
|
|
1696
|
-
chip.schema.read_journal(manifest)
|
|
1713
|
+
JournalingSchema(chip.schema).read_journal(manifest)
|
|
1697
1714
|
|
|
1698
1715
|
if processes[node]["parent_pipe"] and processes[node]["parent_pipe"].poll(1):
|
|
1699
1716
|
try:
|
|
@@ -1711,7 +1728,7 @@ def _process_completed_nodes(chip, processes, running_nodes):
|
|
|
1711
1728
|
if not status or status == NodeStatus.PENDING:
|
|
1712
1729
|
status = NodeStatus.ERROR
|
|
1713
1730
|
|
|
1714
|
-
chip.
|
|
1731
|
+
chip.schema.get("record", field='schema').set('status', status, step=step, index=index)
|
|
1715
1732
|
|
|
1716
1733
|
changed = True
|
|
1717
1734
|
|
|
@@ -1722,156 +1739,27 @@ def _process_completed_nodes(chip, processes, running_nodes):
|
|
|
1722
1739
|
|
|
1723
1740
|
|
|
1724
1741
|
def _check_nodes_status(chip, flow):
|
|
1725
|
-
|
|
1726
|
-
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1742
|
+
flowgraph = chip.schema.get("flowgraph", flow, field="schema")
|
|
1743
|
+
runtime = RuntimeFlowgraph(
|
|
1744
|
+
flowgraph,
|
|
1745
|
+
from_steps=chip.get('option', 'from'),
|
|
1746
|
+
to_steps=chip.get('option', 'to'),
|
|
1747
|
+
prune_nodes=chip.get('option', 'prune'))
|
|
1748
|
+
runtime_no_prune = RuntimeFlowgraph(
|
|
1749
|
+
flowgraph,
|
|
1750
|
+
from_steps=chip.get('option', 'from'),
|
|
1751
|
+
to_steps=chip.get('option', 'to'))
|
|
1752
|
+
|
|
1753
|
+
all_steps = [step for step, index in runtime_no_prune.get_exit_nodes()
|
|
1754
|
+
if (step, index) not in chip.get('option', 'prune')]
|
|
1755
|
+
complete_steps = [step for step, _ in runtime.get_completed_nodes(
|
|
1756
|
+
record=chip.schema.get("record", field='schema'))]
|
|
1757
|
+
|
|
1758
|
+
unreached = set(all_steps).difference(complete_steps)
|
|
1759
|
+
|
|
1760
|
+
if unreached:
|
|
1731
1761
|
raise SiliconCompilerError(
|
|
1732
|
-
f'These final steps could not be reached: {
|
|
1733
|
-
|
|
1734
|
-
|
|
1735
|
-
#######################################
|
|
1736
|
-
def __record_version(chip, step, index):
|
|
1737
|
-
chip.set('record', 'scversion', _metadata.version, step=step, index=index)
|
|
1738
|
-
chip.set('record', 'pythonversion', platform.python_version(), step=step, index=index)
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
#######################################
|
|
1742
|
-
def __record_packages(chip):
|
|
1743
|
-
try:
|
|
1744
|
-
from pip._internal.operations.freeze import freeze
|
|
1745
|
-
except: # noqa E722
|
|
1746
|
-
freeze = None
|
|
1747
|
-
|
|
1748
|
-
if freeze:
|
|
1749
|
-
# clear record
|
|
1750
|
-
chip.set('record', 'pythonpackage', [])
|
|
1751
|
-
|
|
1752
|
-
for pkg in freeze():
|
|
1753
|
-
chip.add('record', 'pythonpackage', pkg)
|
|
1754
|
-
|
|
1755
|
-
|
|
1756
|
-
#######################################
|
|
1757
|
-
def __record_time(chip, step, index, record_time, timetype):
|
|
1758
|
-
formatted_time = datetime.fromtimestamp(record_time).strftime('%Y-%m-%d %H:%M:%S')
|
|
1759
|
-
|
|
1760
|
-
if timetype == 'start':
|
|
1761
|
-
key = 'starttime'
|
|
1762
|
-
elif timetype == 'end':
|
|
1763
|
-
key = 'endtime'
|
|
1764
|
-
else:
|
|
1765
|
-
raise ValueError(f'{timetype} is not a valid time record')
|
|
1766
|
-
|
|
1767
|
-
chip.set('record', key, formatted_time, step=step, index=index)
|
|
1768
|
-
|
|
1769
|
-
|
|
1770
|
-
def get_record_time(chip, step, index, timetype):
|
|
1771
|
-
return datetime.strptime(
|
|
1772
|
-
chip.get('record', timetype, step=step, index=index),
|
|
1773
|
-
'%Y-%m-%d %H:%M:%S').timestamp()
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
#######################################
|
|
1777
|
-
def _get_cloud_region():
|
|
1778
|
-
# TODO: add logic to figure out if we're running on a remote cluster and
|
|
1779
|
-
# extract the region in a provider-specific way.
|
|
1780
|
-
return 'local'
|
|
1781
|
-
|
|
1782
|
-
|
|
1783
|
-
#######################################
|
|
1784
|
-
def __record_usermachine(chip, step, index):
|
|
1785
|
-
machine_info = _get_machine_info()
|
|
1786
|
-
chip.set('record', 'platform', machine_info['system'], step=step, index=index)
|
|
1787
|
-
|
|
1788
|
-
if machine_info['distro']:
|
|
1789
|
-
chip.set('record', 'distro', machine_info['distro'], step=step, index=index)
|
|
1790
|
-
|
|
1791
|
-
chip.set('record', 'osversion', machine_info['osversion'], step=step, index=index)
|
|
1792
|
-
|
|
1793
|
-
if machine_info['kernelversion']:
|
|
1794
|
-
chip.set('record', 'kernelversion', machine_info['kernelversion'], step=step, index=index)
|
|
1795
|
-
|
|
1796
|
-
chip.set('record', 'arch', machine_info['arch'], step=step, index=index)
|
|
1797
|
-
|
|
1798
|
-
chip.set('record', 'userid', getpass.getuser(), step=step, index=index)
|
|
1799
|
-
|
|
1800
|
-
chip.set('record', 'machine', platform.node(), step=step, index=index)
|
|
1801
|
-
|
|
1802
|
-
chip.set('record', 'region', _get_cloud_region(), step=step, index=index)
|
|
1803
|
-
|
|
1804
|
-
try:
|
|
1805
|
-
for interface, addrs in psutil.net_if_addrs().items():
|
|
1806
|
-
if interface == 'lo':
|
|
1807
|
-
# don't consider loopback device
|
|
1808
|
-
continue
|
|
1809
|
-
|
|
1810
|
-
if not addrs:
|
|
1811
|
-
# skip missing addrs
|
|
1812
|
-
continue
|
|
1813
|
-
|
|
1814
|
-
use_addr = False
|
|
1815
|
-
for addr in addrs:
|
|
1816
|
-
if addr.family == socket.AF_INET:
|
|
1817
|
-
if not addr.address.startswith('127.'):
|
|
1818
|
-
use_addr = True
|
|
1819
|
-
break
|
|
1820
|
-
|
|
1821
|
-
if use_addr:
|
|
1822
|
-
ipaddr = None
|
|
1823
|
-
macaddr = None
|
|
1824
|
-
for addr in addrs:
|
|
1825
|
-
if not ipaddr and addr.family == socket.AF_INET:
|
|
1826
|
-
ipaddr = addr.address
|
|
1827
|
-
if not ipaddr and addr.family == socket.AF_INET6:
|
|
1828
|
-
ipaddr = addr.address
|
|
1829
|
-
if not macaddr and addr.family == psutil.AF_LINK:
|
|
1830
|
-
macaddr = addr.address
|
|
1831
|
-
|
|
1832
|
-
chip.set('record', 'ipaddr', ipaddr, step=step, index=index)
|
|
1833
|
-
chip.set('record', 'macaddr', macaddr, step=step, index=index)
|
|
1834
|
-
break
|
|
1835
|
-
except: # noqa E722
|
|
1836
|
-
chip.logger.warning('Could not find default network interface info')
|
|
1837
|
-
|
|
1838
|
-
|
|
1839
|
-
#######################################
|
|
1840
|
-
def _get_machine_info():
|
|
1841
|
-
system = platform.system()
|
|
1842
|
-
if system == 'Darwin':
|
|
1843
|
-
lower_sys_name = 'macos'
|
|
1844
|
-
else:
|
|
1845
|
-
lower_sys_name = system.lower()
|
|
1846
|
-
|
|
1847
|
-
if system == 'Linux':
|
|
1848
|
-
distro_name = distro.id()
|
|
1849
|
-
else:
|
|
1850
|
-
distro_name = None
|
|
1851
|
-
|
|
1852
|
-
if system == 'Darwin':
|
|
1853
|
-
osversion, _, _ = platform.mac_ver()
|
|
1854
|
-
elif system == 'Linux':
|
|
1855
|
-
osversion = distro.version()
|
|
1856
|
-
else:
|
|
1857
|
-
osversion = platform.release()
|
|
1858
|
-
|
|
1859
|
-
if system == 'Linux':
|
|
1860
|
-
kernelversion = platform.release()
|
|
1861
|
-
elif system == 'Windows':
|
|
1862
|
-
kernelversion = platform.version()
|
|
1863
|
-
elif system == 'Darwin':
|
|
1864
|
-
kernelversion = platform.release()
|
|
1865
|
-
else:
|
|
1866
|
-
kernelversion = None
|
|
1867
|
-
|
|
1868
|
-
arch = platform.machine()
|
|
1869
|
-
|
|
1870
|
-
return {'system': lower_sys_name,
|
|
1871
|
-
'distro': distro_name,
|
|
1872
|
-
'osversion': osversion,
|
|
1873
|
-
'kernelversion': kernelversion,
|
|
1874
|
-
'arch': arch}
|
|
1762
|
+
f'These final steps could not be reached: {",".join(sorted(unreached))}', chip=chip)
|
|
1875
1763
|
|
|
1876
1764
|
|
|
1877
1765
|
def print_traceback(chip, exception):
|
|
@@ -2146,12 +2034,11 @@ def copy_old_run_dir(chip, org_jobname):
|
|
|
2146
2034
|
return
|
|
2147
2035
|
|
|
2148
2036
|
# Copy nodes forward
|
|
2149
|
-
|
|
2150
|
-
chip,
|
|
2151
|
-
|
|
2152
|
-
|
|
2153
|
-
|
|
2154
|
-
chip.get('option', 'prune')))
|
|
2037
|
+
runtime = RuntimeFlowgraph(
|
|
2038
|
+
chip.schema.get("flowgraph", flow, field="schema"),
|
|
2039
|
+
to_steps=chip.get('option', 'from'),
|
|
2040
|
+
prune_nodes=chip.get('option', 'prune'))
|
|
2041
|
+
org_nodes = set(runtime.get_nodes())
|
|
2155
2042
|
|
|
2156
2043
|
copy_nodes = org_nodes.difference(from_nodes)
|
|
2157
2044
|
|
|
@@ -2197,8 +2084,7 @@ def copy_old_run_dir(chip, org_jobname):
|
|
|
2197
2084
|
# delete file as it might be a hard link
|
|
2198
2085
|
os.remove(manifest)
|
|
2199
2086
|
schema.set('option', 'jobname', chip.get('option', 'jobname'))
|
|
2200
|
-
|
|
2201
|
-
schema.write_json(f)
|
|
2087
|
+
schema.write_manifest(manifest)
|
|
2202
2088
|
|
|
2203
2089
|
|
|
2204
2090
|
def clean_node_dir(chip, step, index):
|
|
@@ -2228,7 +2114,8 @@ def clean_build_dir(chip):
|
|
|
2228
2114
|
for step, index in nodes_to_execute(chip):
|
|
2229
2115
|
clean_node_dir(chip, step, index)
|
|
2230
2116
|
|
|
2231
|
-
all_nodes = set(
|
|
2117
|
+
all_nodes = set(chip.schema.get("flowgraph", chip.get('option', 'flow'),
|
|
2118
|
+
field="schema").get_nodes())
|
|
2232
2119
|
old_nodes = __collect_nodes_in_workdir(chip)
|
|
2233
2120
|
node_mismatch = old_nodes.difference(all_nodes)
|
|
2234
2121
|
if node_mismatch:
|
|
@@ -2291,7 +2178,8 @@ def _check_manifest_dynamic(chip, step, index):
|
|
|
2291
2178
|
paramtype = chip.get(*keypath, field='type')
|
|
2292
2179
|
is_perstep = not chip.get(*keypath, field='pernode').is_never()
|
|
2293
2180
|
if ('file' in paramtype) or ('dir' in paramtype):
|
|
2294
|
-
for val, check_step, check_index in chip.schema.
|
|
2181
|
+
for val, check_step, check_index in chip.schema.get(*keypath,
|
|
2182
|
+
field=None).getvalues():
|
|
2295
2183
|
if is_perstep:
|
|
2296
2184
|
if check_step is None:
|
|
2297
2185
|
check_step = Schema.GLOBAL_KEY
|
|
@@ -2315,35 +2203,12 @@ def _check_manifest_dynamic(chip, step, index):
|
|
|
2315
2203
|
|
|
2316
2204
|
|
|
2317
2205
|
#######################################
|
|
2318
|
-
def _clear_metric(chip, step, index, metric
|
|
2206
|
+
def _clear_metric(chip, step, index, metric):
|
|
2319
2207
|
'''
|
|
2320
2208
|
Helper function to clear metrics records
|
|
2321
2209
|
'''
|
|
2322
2210
|
|
|
2323
|
-
# This function is often called in a loop; don't clear
|
|
2324
|
-
# metrics which the caller wants to preserve.
|
|
2325
|
-
if preserve and metric in preserve:
|
|
2326
|
-
return
|
|
2327
|
-
|
|
2328
2211
|
flow = chip.get('option', 'flow')
|
|
2329
2212
|
tool, task = get_tool_task(chip, step, index, flow=flow)
|
|
2330
2213
|
|
|
2331
|
-
chip.unset('metric', metric, step=step, index=index)
|
|
2332
2214
|
chip.unset('tool', tool, 'task', task, 'report', metric, step=step, index=index)
|
|
2333
|
-
|
|
2334
|
-
|
|
2335
|
-
#######################################
|
|
2336
|
-
def _clear_record(chip, step, index, record, preserve=None):
|
|
2337
|
-
'''
|
|
2338
|
-
Helper function to clear record parameters
|
|
2339
|
-
'''
|
|
2340
|
-
|
|
2341
|
-
# This function is often called in a loop; don't clear
|
|
2342
|
-
# records which the caller wants to preserve.
|
|
2343
|
-
if preserve and record in preserve:
|
|
2344
|
-
return
|
|
2345
|
-
|
|
2346
|
-
if chip.get('record', record, field='pernode').is_never():
|
|
2347
|
-
chip.unset('record', record)
|
|
2348
|
-
else:
|
|
2349
|
-
chip.unset('record', record, step=step, index=index)
|