add means to subscript two levels deep
authorLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Sat, 4 Apr 2020 19:24:08 +0000 (20:24 +0100)
committerLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Sat, 4 Apr 2020 19:24:08 +0000 (20:24 +0100)
libreriscv
src/soc/decoder/power_pseudo.py
src/soc/decoder/pseudo/parser.py

index 6ad52e429bfcc8f815de14109833eb9288bc9c86..d38dcfdcc6923a03b8b3ac0ff8d03781dc6e7e80 160000 (submodule)
@@ -1 +1 @@
-Subproject commit 6ad52e429bfcc8f815de14109833eb9288bc9c86
+Subproject commit d38dcfdcc6923a03b8b3ac0ff8d03781dc6e7e80
index c4f962a28c7f1fea10e38c9eb4ff45ae33d32604..37aa56fc4dc601b25e55e8cff82916207a00eaa6 100644 (file)
@@ -126,11 +126,18 @@ MEM(EA, 1) <- (RS)[56:63]
 RB <- RA
 RA <- EA
 """
+
+testgprslice = """
+MEM(EA, 4) <- GPR(r)[32:63]
+#x <- x[0][32:63]
+"""
+
 #code = testmul
 #code = testgetzero
 #code = testcat
 #code = testgpr
-code = testmem
+#code = testmem
+code = testgprslice
 #code = testreg
 #code = cnttzd
 #code = cmpi
@@ -178,6 +185,9 @@ class GPR(dict):
         for i in range(32):
             self[i] = SelectableInt(regfile[i], 64)
 
+    def __call__(self, ridx):
+        return self[ridx]
+
     def set_form(self, form):
         self.form = form
 
index 9384ca213d5c23a47edf63e5ed58990e8a59909e..6abe1913a204d3bf7b6683e28fda08ae94fc4840 100644 (file)
@@ -151,6 +151,27 @@ def identify_sint_mul_pattern(p):
     elt = l[0]
     return isinstance(elt, ast.Constant)
 
+def apply_trailer(atom, trailer):
+    if trailer[0] == "TLIST":
+        # assume depth of one
+        atom = apply_trailer(atom, trailer[1])
+        trailer = trailer[2]
+    if trailer[0] == "CALL":
+        #p[0] = ast.Expr(ast.Call(p[1], p[2][1], []))
+        return ast.Call(atom, trailer[1], [])
+        # if p[1].id == 'print':
+        #    p[0] = ast.Printnl(ast.Tuple(p[2][1]), None, None)
+        # else:
+        #    p[0] = ast.CallFunc(p[1], p[2][1], None, None)
+    else:
+        print("subscript atom", trailer[1])
+        #raise AssertionError("not implemented %s" % p[2][0])
+        subs = trailer[1]
+        if len(subs) == 1:
+            idx = subs[0]
+        else:
+            idx = ast.Slice(subs[0], subs[1], None)
+        return ast.Subscript(atom, idx, ast.Load())
 
 ##########   Parser (tokens -> AST) ######
 
@@ -451,30 +472,18 @@ class PowerParser:
 
     # power: atom trailer* ['**' factor]
     # trailers enables function calls (and subscripts).
-    # I only allow one level of calls
-    # so this is 'trailer'
+    # so this is 'trailerlist'
     def p_power(self, p):
         """power : atom
-                 | atom trailer"""
+                 | atom trailerlist"""
         if len(p) == 2:
             p[0] = p[1]
         else:
-            if p[2][0] == "CALL":
-                #p[0] = ast.Expr(ast.Call(p[1], p[2][1], []))
-                p[0] = ast.Call(p[1], p[2][1], [])
-                # if p[1].id == 'print':
-                #    p[0] = ast.Printnl(ast.Tuple(p[2][1]), None, None)
-                # else:
-                #    p[0] = ast.CallFunc(p[1], p[2][1], None, None)
-            else:
-                print("subscript atom", p[2][1])
-                #raise AssertionError("not implemented %s" % p[2][0])
-                subs = p[2][1]
-                if len(subs) == 1:
-                    idx = subs[0]
-                else:
-                    idx = ast.Slice(subs[0], subs[1], None)
-                p[0] = ast.Subscript(p[1], idx, ast.Load())
+            print("power dump atom")
+            print(astor.dump_tree(p[1]))
+            print("power dump trailerlist")
+            print(astor.dump_tree(p[2]))
+            p[0] = apply_trailer(p[1], p[2])
 
     def p_atom_name(self, p):
         """atom : NAME"""
@@ -533,6 +542,15 @@ class PowerParser:
         else:
             p[0] = p[2]
 
+    def p_trailerlist(self, p):
+        """trailerlist : trailer trailerlist
+                       | trailer
+        """
+        if len(p) == 2:
+            p[0] = p[1]
+        else:
+            p[0] = ("TLIST", p[1], p[2])
+
     # trailer: '(' [arglist] ')' | '[' subscriptlist ']' | '.' NAME
     def p_trailer(self, p):
         """trailer : trailer_arglist