add byte reverse instructions from PowerISA v3.1B
authorJacob Lifshay <programmerjake@gmail.com>
Thu, 20 Jul 2023 01:00:58 +0000 (18:00 -0700)
committerJacob Lifshay <programmerjake@gmail.com>
Thu, 20 Jul 2023 01:00:58 +0000 (18:00 -0700)
openpower/isa/byterev.mdwn [new file with mode: 0644]
openpower/isatables/RM-2P-1S1D.csv
openpower/isatables/minor_31.csv
src/openpower/decoder/isa/.gitignore
src/openpower/decoder/isa/caller.py
src/openpower/decoder/power_enums.py
src/openpower/test/bitmanip/bitmanip_cases.py

diff --git a/openpower/isa/byterev.mdwn b/openpower/isa/byterev.mdwn
new file mode 100644 (file)
index 0000000..41da2d8
--- /dev/null
@@ -0,0 +1,54 @@
+<!-- This defines instructions described in PowerISA Version 3.1B Book I -->
+<!-- Section 3.3.16 Byte-Reverse Instructions page 119 (145) -->
+
+# Byte-Reverse Halfword
+
+X-Form
+
+* brh RA,RS
+
+Pseudo-code:
+
+    RA <- ((RS)[8:15]  || (RS)[0:7]   ||
+           (RS)[24:31] || (RS)[16:23] ||
+           (RS)[40:47] || (RS)[32:39] ||
+           (RS)[56:63] || (RS)[48:55])
+
+Special Registers Altered:
+
+    None
+
+# Byte-Reverse Word
+
+X-Form
+
+* brw RA,RS
+
+Pseudo-code:
+
+    RA <- ((RS)[24:31] || (RS)[16:23] ||
+           (RS)[8:15]  || (RS)[0:7]   ||
+           (RS)[56:63] || (RS)[48:55] ||
+           (RS)[40:47] || (RS)[32:39])
+
+Special Registers Altered:
+
+    None
+
+# Byte-Reverse Doubleword
+
+X-Form
+
+* brd RA,RS
+
+Pseudo-code:
+
+    RA <- ((RS)[56:63] || (RS)[48:55] ||
+           (RS)[40:47] || (RS)[32:39] ||
+           (RS)[24:31] || (RS)[16:23] ||
+           (RS)[8:15]  || (RS)[0:7])
+
+Special Registers Altered:
+
+    None
+
index a251c8ea9f8c654fa8c3d621ea7e9653270d46c6..32df21be0e6619788e8d79f2dfb5a1059d00ce84 100644 (file)
@@ -8,7 +8,10 @@ cmpli,CROP,,2P,EXTRA3,EN,d:BF,s:RA,0,0,RA,0,0,0,0,BF,0
 cmpi,CROP,,2P,EXTRA3,EN,d:BF,s:RA,0,0,RA,0,0,0,0,BF,0
 popcntb,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
 prtyw,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
+brw,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
 prtyd,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
+brd,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
+brh,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
 cdtbcd,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
 cbcdtd,NORMAL,,2P,EXTRA3,EN,d:RA,s:RS,0,0,RS,0,0,RA,0,0,0
 mfspr,NORMAL,,2P,EXTRA3,EN,d:RS,s:SPR,0,0,SPR,0,0,RT,0,0,0
index 0c977dbedc7e6b76e1503f920137b4d389e1bc54..9579c7d4f5326508057cd63462c07b710c9f5722 100644 (file)
@@ -15,6 +15,9 @@ opcode,unit,internal op,in1,in2,in3,out,CR in,CR out,inv A,inv out,cry in,cry ou
 0b0001001010,ALU,OP_ADDG6S,RA,RB,NONE,RT,NONE,CR0,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,addg6s,XO,,,
 0b0000011100,LOGICAL,OP_AND,RS,RB,NONE,RA,NONE,CR0,0,0,ZERO,0,NONE,0,0,0,0,0,0,RC,0,0,and,X,,,
 0b0000111100,LOGICAL,OP_AND,RS,RB,NONE,RA,NONE,CR0,1,0,ZERO,0,NONE,0,0,0,0,0,0,RC,0,0,andc,X,,,
+0b0011011011,LOGICAL,OP_BYTEREV,RS,NONE,NONE,RA,NONE,NONE,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,brh,X,,0,
+0b0010011011,LOGICAL,OP_BYTEREV,RS,NONE,NONE,RA,NONE,NONE,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,brw,X,,0,
+0b0010111011,LOGICAL,OP_BYTEREV,RS,NONE,NONE,RA,NONE,NONE,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,brd,X,,0,
 0b0100111010,ALU,OP_CBCDTD,RS,NONE,NONE,RA,NONE,NONE,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,cbcdtd,X,,,
 0b0100011010,ALU,OP_CDTBCD,RS,NONE,NONE,RA,NONE,NONE,1,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,cdtbcd,X,,,
 0b0011111100,LOGICAL,OP_BPERM,RS,RB,NONE,RA,NONE,NONE,0,0,ZERO,0,NONE,0,0,0,0,0,0,NONE,0,0,bpermd,X,,,
index 555dab2cdfc6a853b73e574be13862cfe0315ef5..c72caceb5159f71d5596389c09995314cb4f2f22 100644 (file)
@@ -4,6 +4,7 @@
 /bitmanip.py
 /branch.py
 /butterfly.py
+/byterev.py
 /comparefixed.py
 /condition.py
 /fixedarith.py
index 363fe8b20a7bb66f70e4136dd0850579e58f14fa..30f2e5211639c8f4391167e050f41003037320e8 100644 (file)
@@ -1956,6 +1956,7 @@ class ISACaller(ISACallerHelper, ISAFPHelpers, StepLoop):
                        *LDST_UPDATE_INSNS,
                        'ffmadds', 'fdmadds', 'ffadds',
                        'minmax',
+                       "brh", "brw", "brd",
                        'setvl', 'svindex', 'svremap', 'svstep',
                        'svshape', 'svshape2',
                        'grev', 'ternlogi', 'bmask', 'cprop',
index 20e28ffa31754deb50e0f0832f3f83b99688aed2..aa49b23b85861f235f511a6f144ed847af9e9c0e 100644 (file)
@@ -736,6 +736,7 @@ _insns = [
     "absdacs", "absdacu",                     # AV bitmanip
     "avgadd",                                 # AV bitmanip
     "b", "bc", "bcctr", "bclr", "bctar",
+    "brh", "brw", "brd",
     "bmask",                                  # AV bitmanip
     "bpermd",
     "cbcdtd",
@@ -953,6 +954,7 @@ class MicrOp(Enum):
     OP_SHADD = 103
     OP_MADDSUBRS = 104
     OP_MADDRS = 105
+    OP_BYTEREV = 106
 
 
 class SelType(Enum):
index c89d3f81fb0c9e5514c07c177923625654cdf33d..73877a571453eab8bbb590403752e5d27e19680e 100644 (file)
@@ -4,6 +4,7 @@ from openpower.endian import bigendian
 from openpower.simulator.program import Program
 from openpower.test.state import ExpectedState
 from nmutil.sim_util import hash_256
+import struct
 
 
 class BitManipTestCase(TestAccumulatorBase):
@@ -116,3 +117,20 @@ class BitManipTestCase(TestAccumulatorBase):
     @skip_case("invalid, replaced by grevlut")
     def case_grevi_3(self):
         self.do_case_grev(True, True, 0xFFFF_FFFF_0000_0000, 6)
+
+    def case_byterev(self):
+        """ brh/brw/brd """
+        for pack_str, mnemonic in ("HHHH", "brh"), ("LL", "brw"), ("Q", "brd"):
+            prog = Program(list(SVP64Asm([f"{mnemonic} 3,4"])), bigendian)
+            for RS in 0x0123456789ABCDEF, 0xFEDCBA9876543210:
+                chunks = struct.unpack("<" + pack_str, struct.pack("<Q", RS))
+                expected = struct.unpack(
+                    "<Q", struct.pack(">" + pack_str, *chunks))[0]
+                with self.subTest(
+                    mnemonic=mnemonic, RS=hex(RS), expected=hex(expected),
+                ):
+                    gprs = [0] * 32
+                    gprs[4] = RS
+                    e = ExpectedState(pc=4, int_regs=gprs)
+                    e.intregs[3] = expected
+                    self.add_case(prog, gprs, expected=e)