lattice/icestorm: add ignoreloops/seed support (similar to trellis) and icestorm_args.
authorFlorent Kermarrec <florent@enjoy-digital.fr>
Mon, 11 May 2020 07:33:26 +0000 (09:33 +0200)
committerFlorent Kermarrec <florent@enjoy-digital.fr>
Mon, 11 May 2020 07:33:26 +0000 (09:33 +0200)
litex/build/lattice/icestorm.py
litex/build/lattice/trellis.py

index 2822a9b539a276650f0cbaf24f9168072ec80ad8..059363c04041fd3f5582aaa3ff9727598c842056 100644 (file)
@@ -93,32 +93,35 @@ def parse_device(device):
 _build_template = [
     "yosys -l {build_name}.rpt {build_name}.ys",
     "nextpnr-ice40 --json {build_name}.json --pcf {build_name}.pcf --asc {build_name}.txt \
-    --pre-pack {build_name}_pre_pack.py --{architecture} --package {package} {timefailarg}",
+    --pre-pack {build_name}_pre_pack.py --{architecture} --package {package} {timefailarg} {ignoreloops} --seed {seed}",
     "icepack -s {build_name}.txt {build_name}.bin"
 ]
 
-def _build_script(build_template, build_name, architecture, package, timingstrict):
+def _build_script(build_template, build_name, architecture, package, timingstrict, ignoreloops, seed):
     if sys.platform in ("win32", "cygwin"):
         script_ext = ".bat"
-        build_script_contents = "@echo off\nrem Autogenerated by LiteX / git: " + tools.get_litex_git_revision() + "\n\n"
+        script_contents = "@echo off\nrem Autogenerated by LiteX / git: " + tools.get_litex_git_revision() + "\n\n"
         fail_stmt = " || exit /b"
     else:
         script_ext = ".sh"
-        build_script_contents = "# Autogenerated by LiteX / git: " + tools.get_litex_git_revision() + "\nset -e\n"
+        script_contents = "# Autogenerated by LiteX / git: " + tools.get_litex_git_revision() + "\nset -e\n"
         fail_stmt = ""
 
     for s in build_template:
         s_fail = s + "{fail_stmt}\n"  # Required so Windows scripts fail early.
-        build_script_contents += s_fail.format(
+        script_contents += s_fail.format(
             build_name   = build_name,
             architecture = architecture,
             package      = package,
             timefailarg  = "--timing-allow-fail" if not timingstrict else "",
-            fail_stmt    = fail_stmt)
+            ignoreloops  = "--ignore-loops" if ignoreloops else "",
+            fail_stmt    = fail_stmt,
+            seed         = seed)
 
-    build_script_file = "build_" + build_name + script_ext
-    tools.write_to_file(build_script_file, build_script_contents,force_unix=False)
-    return build_script_file
+    script_file = "build_" + build_name + script_ext
+    tools.write_to_file(script_file, script_contents, force_unix=False)
+
+    return script_file
 
 def _run_script(script):
     if sys.platform in ("win32", "cygwin"):
@@ -158,6 +161,8 @@ class LatticeIceStormToolchain:
         synth_opts     = "",
         run            = True,
         timingstrict   = False,
+        ignoreloops    = False,
+        seed           = 1,
         **kwargs):
 
         # Create build directory
@@ -190,7 +195,7 @@ class LatticeIceStormToolchain:
         (family, architecture, package) = parse_device(platform.device)
 
         # Generate build script
-        script = _build_script(self.build_template, build_name, architecture, package, timingstrict)
+        script = _build_script(self.build_template, build_name, architecture, package, timingstrict, ignoreloops, seed)
 
         # Run
         if run:
@@ -207,3 +212,18 @@ class LatticeIceStormToolchain:
                 raise ValueError("Clock already constrained to {:.2f}ns, new constraint to {:.2f}ns"
                     .format(self.clocks[clk], period))
         self.clocks[clk] = period
+
+def icestorm_args(parser):
+    parser.add_argument("--nextpnr-timingstrict", action="store_true",
+                        help="fail if timing not met, i.e., do NOT pass '--timing-allow-fail' to nextpnr")
+    parser.add_argument("--nextpnr-ignoreloops", action="store_true",
+                        help="ignore combinational loops in timing analysis, i.e. pass '--ignore-loops' to nextpnr")
+    parser.add_argument("--nextpnr-seed", default=1, type=int,
+                        help="seed to pass to nextpnr")
+
+def icestorm_argdict(args):
+    return {
+        "timingstrict": args.nextpnr_timingstrict,
+        "ignoreloops":  args.nextpnr_ignoreloops,
+        "seed":         args.nextpnr_seed,
+    }
\ No newline at end of file
index 36b5cbc3e50f72d54907cd79a88ff37f6770011f..38e4cdaeb37fd101abbda3abcd05fcb34c5c1356 100644 (file)
@@ -134,14 +134,14 @@ def _build_script(source, build_template, build_name, architecture, package, spe
     for s in build_template:
         s_fail = s + "{fail_stmt}\n"  # Required so Windows scripts fail early.
         script_contents += s_fail.format(
-            build_name      = build_name,
-            architecture    = architecture,
-            package         = package,
-            speed_grade     = speed_grade,
-            timefailarg     = "--timing-allow-fail" if not timingstrict else "",
-            ignoreloops     = "--ignore-loops" if ignoreloops else "",
-            fail_stmt       = fail_stmt,
-            seed            = seed)
+            build_name   = build_name,
+            architecture = architecture,
+            package      = package,
+            speed_grade  = speed_grade,
+            timefailarg  = "--timing-allow-fail" if not timingstrict else "",
+            ignoreloops  = "--ignore-loops" if ignoreloops else "",
+            fail_stmt    = fail_stmt,
+            seed         = seed)
 
     script_file = "build_" + build_name + script_ext
     tools.write_to_file(script_file, script_contents, force_unix=False)