about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorFabrice Desclaux <fabrice.desclaux@cea.fr>2021-02-14 18:41:05 +0100
committerFabrice Desclaux <fabrice.desclaux@cea.fr>2021-02-14 18:41:05 +0100
commitbe9a1aaab320a17d1d07b04ddd7b84b39cf20147 (patch)
tree1e813ca30c9c918422f0d6a7215a146baccd2679
parent75f6a44d3918106c35e2837dda47d3725c3a9f09 (diff)
downloadmiasm-be9a1aaab320a17d1d07b04ddd7b84b39cf20147.tar.gz
miasm-be9a1aaab320a17d1d07b04ddd7b84b39cf20147.zip
Fix ADD/SUB; Add CMN
-rw-r--r--miasm/arch/aarch64/arch.py37
-rw-r--r--miasm/arch/aarch64/regs.py6
-rw-r--r--test/arch/aarch64/arch.py4
3 files changed, 45 insertions, 2 deletions
diff --git a/miasm/arch/aarch64/arch.py b/miasm/arch/aarch64/arch.py
index 25bf5c12..fc52fe11 100644
--- a/miasm/arch/aarch64/arch.py
+++ b/miasm/arch/aarch64/arch.py
@@ -156,6 +156,9 @@ reg_ext_off = (gpregz32_extend | gpregz64_extend)
 gpregs_32_64 = (gpregs32_info.parser | gpregs64_info.parser)
 gpregsz_32_64 = (gpregsz32_info.parser | gpregsz64_info.parser | base_expr)
 
+gpregs_32_64_nosp = (gpregs32_nosp_info.parser | gpregs64_nosp_info.parser)
+
+
 simdregs = (simd08_info.parser | simd16_info.parser | simd32_info.parser | simd64_info.parser)
 simdregs_h = (simd32_info.parser | simd64_info.parser | simd128_info.parser)
 
@@ -168,6 +171,11 @@ gpregsz_info = {32: gpregsz32_info,
                 64: gpregsz64_info}
 
 
+gpregs_nosp_info = {
+    32: gpregs32_nosp_info,
+    64: gpregs64_nosp_info
+}
+
 simds_info = {8: simd08_info,
               16: simd16_info,
               32: simd32_info,
@@ -539,6 +547,29 @@ class aarch64_gpreg_noarg(reg_noarg):
         self.value = self.gpregs_info[self.expr.size].expr.index(self.expr)
         return True
 
+class aarch64_gpreg_noarg_nosp(aarch64_gpreg_noarg):
+    parser = gpregs_32_64_nosp
+    gpregs_info = gpregs_nosp_info
+
+    def decode(self, v):
+        size = 64 if self.parent.sf.value else 32
+        if v >= len(self.gpregs_info[size].expr):
+            return False
+        self.expr = self.gpregs_info[size].expr[v]
+        return True
+
+    def encode(self):
+        if not test_set_sf(self.parent, self.expr.size):
+            return False
+        if not self.expr.size in self.gpregs_info:
+            return False
+        if not self.expr in self.gpregs_info[self.expr.size].expr:
+            return False
+        if self.expr not in self.gpregs_info[self.expr.size].expr:
+            return False
+        self.value = self.gpregs_info[self.expr.size].expr.index(self.expr)
+        return True
+
 
 class aarch64_simdreg(reg_noarg, aarch64_arg):
     parser = simdregs
@@ -1666,6 +1697,8 @@ rmz = bs(l=5, cls=(aarch64_gpregz,), fname="rm")
 rnz = bs(l=5, cls=(aarch64_gpregz,), fname="rn")
 rdz = bs(l=5, cls=(aarch64_gpregz,), fname="rd")
 
+rd_nosp = bs(l=5, cls=(aarch64_gpreg_noarg_nosp, aarch64_arg), fname="rd")
+
 
 rn_n1 = bs(l=5, cls=(aarch64_gpreg_n1,), fname="rn")
 rm_n1 = bs(l=5, cls=(aarch64_gpreg_n1,), fname="rm")
@@ -1835,7 +1868,9 @@ aarch64op("adrp", [bs('1'), immlo, bs('10000'), immhip, rd64], [rd64, immhip])
 aarch64op("adr",  [bs('0'), immlo, bs('10000'), immhi, rd64], [rd64, immhi])
 
 # add/sub (reg shift)
-aarch64op("addsub", [sf, bs_adsu_name, modf, bs('01011'), shift, bs('0'), rm_sft, imm6, rn, rd], [rd, rn, rm_sft])
+aarch64op("addsub", [sf, bs_adsu_name, modf, bs('01011'), shift, bs('0'), rm_sft, imm6, rn, rd_nosp], [rd_nosp, rn, rm_sft])
+aarch64op("CMN", [sf, bs('0'), bs('1'), bs('01011'), shift, bs('0'), rm_sft, imm6, rn, bs('11111')], [rn, rm_sft])
+
 aarch64op("cmp", [sf, bs('1'), bs('1'), bs('01011'), shift, bs('0'), rm_sft, imm6, rn, bs('11111')], [rn, rm_sft], alias=True)
 # add/sub (reg ext)
 aarch64op("addsub", [sf, bs_adsu_name, modf, bs('01011'), bs('00'), bs('1'), rm_ext, option, imm3, rn, rd], [rd, rn, rm_ext])
diff --git a/miasm/arch/aarch64/regs.py b/miasm/arch/aarch64/regs.py
index 7d19b113..9dee726b 100644
--- a/miasm/arch/aarch64/regs.py
+++ b/miasm/arch/aarch64/regs.py
@@ -2,7 +2,7 @@
 
 from builtins import range
 from miasm.expression.expression import ExprId
-from miasm.core.cpu import gen_reg, gen_regs
+from miasm.core.cpu import gen_reg, gen_regs, reg_info
 
 exception_flags = ExprId('exception_flags', 32)
 interrupt_num = ExprId('interrupt_num', 32)
@@ -25,6 +25,10 @@ gpregsz64_str = ["X%d" % i for i in range(0x1e)] + ["LR", "XZR"]
 gpregsz64_expr, gpregsz64_init, gpregsz64_info = gen_regs(
     gpregsz64_str, globals(), 64)
 
+gpregs32_nosp, _, gpregs32_nosp_info = gen_regs(gpregs32_str[:-1], globals(), 32)
+gpregs64_nosp, _, gpregs64_nosp_info = gen_regs(gpregs64_str[:-1], globals(), 64)
+
+
 cr_str = ["c%d" % i for i in range(0x10)]
 cr_expr, cr_init, cr_info = gen_regs(cr_str, globals(), 32)
 
diff --git a/test/arch/aarch64/arch.py b/test/arch/aarch64/arch.py
index dc505bdd..9be0c6c5 100644
--- a/test/arch/aarch64/arch.py
+++ b/test/arch/aarch64/arch.py
@@ -73,6 +73,10 @@ reg_tests_aarch64 = [
     ("004029D0    CMP        X0, 0x3F",
      "1FFC00F1"),
 
+    ("XXXXXXXX    CMN        W12, W9",
+     "9F01092B"),
+    ("XXXXXXXX    CMN        W0, 0x1",
+     "1F040031"),
 
     ("0007FA38    AND        W0, W0, 0x7000000",
      "00080812"),