hdl.dsl: raise SyntaxError for mis-nested If/Elif/Else statements
authorThomas Watson <twatson52@icloud.com>
Tue, 11 May 2021 01:59:34 +0000 (20:59 -0500)
committerwhitequark <whitequark@whitequark.org>
Tue, 11 May 2021 02:41:32 +0000 (02:41 +0000)
nmigen/hdl/dsl.py
tests/test_hdl_dsl.py

index fd207741d15745879e20b15f79927f001c738e1c..829cd2f8ad491cb67cdb121b500eb8794c3ece41 100644 (file)
@@ -226,6 +226,7 @@ class Module(_ModuleBuilderRoot, Elaboratable):
         cond = self._check_signed_cond(cond)
         src_loc = tracer.get_src_loc(src_loc_at=1)
         if_data = self._set_ctrl("If", {
+            "depth":    self.domain._depth,
             "tests":    [],
             "bodies":   [],
             "src_loc":  src_loc,
@@ -249,7 +250,7 @@ class Module(_ModuleBuilderRoot, Elaboratable):
         cond = self._check_signed_cond(cond)
         src_loc = tracer.get_src_loc(src_loc_at=1)
         if_data = self._get_ctrl("If")
-        if if_data is None or len(if_data["tests"]) == 0:
+        if if_data is None or if_data["depth"] != self.domain._depth:
             raise SyntaxError("Elif without preceding If")
         try:
             _outer_case, self._statements = self._statements, []
@@ -268,7 +269,7 @@ class Module(_ModuleBuilderRoot, Elaboratable):
         self._check_context("Else", context=None)
         src_loc = tracer.get_src_loc(src_loc_at=1)
         if_data = self._get_ctrl("If")
-        if if_data is None:
+        if if_data is None or if_data["depth"] != self.domain._depth:
             raise SyntaxError("Else without preceding If/Elif")
         try:
             _outer_case, self._statements = self._statements, []
index 6c5f1178f87b06089ff7be38e30f6f08cafda422..a2d0c96f7e679dddb34144c12a61b8dd14baa6f9 100644 (file)
@@ -281,6 +281,34 @@ class DSLTestCase(FHDLTestCase):
             with m.Else():
                 pass
 
+    def test_Else_wrong_nested(self):
+        m = Module()
+        with m.If(self.s1):
+            with self.assertRaisesRegex(SyntaxError,
+                    r"^Else without preceding If/Elif$"):
+                with m.Else():
+                    pass
+
+    def test_Elif_Elif_wrong_nested(self):
+        m = Module()
+        with m.If(self.s1):
+            pass
+        with m.Elif(self.s2):
+            with self.assertRaisesRegex(SyntaxError,
+                    r"^Elif without preceding If$"):
+                with m.Elif(self.s3):
+                    pass
+
+    def test_Else_Else_wrong_nested(self):
+        m = Module()
+        with m.If(self.s1):
+            pass
+        with m.Else():
+            with self.assertRaisesRegex(SyntaxError,
+                    r"^Else without preceding If/Elif$"):
+                with m.Else():
+                    pass
+
     def test_If_wide(self):
         m = Module()
         with m.If(self.w1):