Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

AArch64 issues #2473

Merged
merged 9 commits into from
Sep 24, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 7 additions & 7 deletions arch/AArch64/AArch64GenCSMappingInsn.inc
Original file line number Diff line number Diff line change
Expand Up @@ -13190,47 +13190,47 @@
/* bl $addr */
AArch64_BL /* 1828 */, AARCH64_INS_BL,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_GRP_BRANCH_RELATIVE, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_GRP_BRANCH_RELATIVE, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
{
/* blr $Rn */
AArch64_BLR /* 1829 */, AARCH64_INS_BLR,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
{
/* blraa $Rn, $Rm */
AArch64_BLRAA /* 1830 */, AARCH64_INS_BLRAA,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
{
/* blraaz $Rn */
AArch64_BLRAAZ /* 1831 */, AARCH64_INS_BLRAAZ,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
{
/* blrab $Rn, $Rm */
AArch64_BLRAB /* 1832 */, AARCH64_INS_BLRAB,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
{
/* blrabz $Rn */
AArch64_BLRABZ /* 1833 */, AARCH64_INS_BLRABZ,
#ifndef CAPSTONE_DIET
{ AARCH64_REG_SP, 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { AARCH64_REG_LR, 0 }, { AARCH64_GRP_CALL, AARCH64_FEATURE_HASPAUTH, 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
Expand Down Expand Up @@ -37390,7 +37390,7 @@
/* mrs $Rt, $systemreg */
AArch64_MRS /* 4853 */, AARCH64_INS_MRS,
#ifndef CAPSTONE_DIET
{ 0 }, { AARCH64_REG_NZCV, 0 }, { 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}
{ 0 }, { 0 }, { 0 }, 0, 0, { .aarch64 = { .mem_acc = CS_AC_INVALID }}

#endif
},
Expand Down
2,064 changes: 1,038 additions & 1,026 deletions arch/AArch64/AArch64GenDisassemblerTables.inc

Large diffs are not rendered by default.

1,333 changes: 667 additions & 666 deletions arch/AArch64/AArch64GenInstrInfo.inc

Large diffs are not rendered by default.

82 changes: 66 additions & 16 deletions arch/AArch64/AArch64Mapping.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,24 @@
#include "AArch64Linkage.h"
#include "AArch64Mapping.h"

#define CHAR(c) #c[0]

static float aarch64_exact_fp_to_fp(aarch64_exactfpimm exact) {
switch (exact) {
default:
CS_ASSERT(0 && "Not handled.");
return 999.0;
case AARCH64_EXACTFPIMM_HALF:
return 0.5;
case AARCH64_EXACTFPIMM_ONE:
return 1.0;
case AARCH64_EXACTFPIMM_TWO:
return 2.0;
case AARCH64_EXACTFPIMM_ZERO:
return 0.0;
}
}

#ifndef CAPSTONE_DIET
static const aarch64_reg aarch64_flag_regs[] = {
AARCH64_REG_NZCV,
Expand Down Expand Up @@ -1747,28 +1765,53 @@ static void add_cs_detail_template_1(MCInst *MI, aarch64_op_group op_group,
// Shift is handled in printShifter()
break;
}

#define SCALE_SET(T) \
do { \
T Val; \
if (CHAR(T) == 'i') /* Signed */ \
Val = (int8_t)UnscaledVal * \
(1 << AArch64_AM_getShiftValue(Shift)); \
else \
Val = (uint8_t)UnscaledVal * \
(1 << AArch64_AM_getShiftValue(Shift)); \
AArch64_set_detail_op_imm(MI, OpNum, AARCH64_OP_IMM, Val); \
} while (0)

switch (op_group) {
default:
assert(0 &&
"Operand group for Imm8OptLsl not handled.");
case AArch64_OP_GROUP_Imm8OptLsl_int16_t:
case AArch64_OP_GROUP_Imm8OptLsl_int32_t:
case AArch64_OP_GROUP_Imm8OptLsl_int64_t:
case AArch64_OP_GROUP_Imm8OptLsl_int16_t: {
SCALE_SET(int16_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_int32_t: {
SCALE_SET(int32_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_int64_t: {
SCALE_SET(int64_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_int8_t: {
int8_t Val = (int8_t)UnscaledVal *
(1 << AArch64_AM_getShiftValue(Shift));
AArch64_set_detail_op_imm(MI, OpNum, AARCH64_OP_IMM,
Val);
SCALE_SET(int8_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_uint16_t: {
SCALE_SET(uint16_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_uint32_t: {
SCALE_SET(uint32_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_uint64_t: {
SCALE_SET(uint64_t);
break;
}
case AArch64_OP_GROUP_Imm8OptLsl_uint16_t:
case AArch64_OP_GROUP_Imm8OptLsl_uint32_t:
case AArch64_OP_GROUP_Imm8OptLsl_uint64_t:
case AArch64_OP_GROUP_Imm8OptLsl_uint8_t: {
uint8_t Val = (uint8_t)UnscaledVal *
(1 << AArch64_AM_getShiftValue(Shift));
AArch64_set_detail_op_imm(MI, OpNum, AARCH64_OP_IMM,
Val);
SCALE_SET(uint8_t);
break;
}
}
Expand Down Expand Up @@ -1875,7 +1918,7 @@ static void add_cs_detail_template_1(MCInst *MI, aarch64_op_group op_group,
unsigned EltSize = temp_arg_0;
AArch64_get_detail_op(MI, 0)->vas = EltSize;
AArch64_set_detail_op_reg(
MI, OpNum, MCInst_getOpVal(MI, OpNum) - AArch64_PN0);
MI, OpNum, MCInst_getOpVal(MI, OpNum));
break;
}
case AArch64_OP_GROUP_PrefetchOp_0:
Expand Down Expand Up @@ -2483,7 +2526,8 @@ void AArch64_set_detail_op_reg(MCInst *MI, unsigned OpNum, aarch64_reg Reg)
AArch64_set_detail_op_sme(MI, OpNum, AARCH64_SME_MATRIX_TILE,
sme_reg_to_vas(Reg));
return;
} else if ((Reg >= AARCH64_REG_P0) && (Reg <= AARCH64_REG_P15)) {
} else if (((Reg >= AARCH64_REG_P0) && (Reg <= AARCH64_REG_P15)) ||
((Reg >= AARCH64_REG_PN0) && (Reg <= AARCH64_REG_PN15))) {
// SME/SVE predicate register.
AArch64_set_detail_op_pred(MI, OpNum);
return;
Expand Down Expand Up @@ -2695,6 +2739,9 @@ void AArch64_set_detail_op_sys(MCInst *MI, unsigned OpNum, aarch64_sysop sys_op,

AArch64_get_detail_op(MI, 0)->type = type;
AArch64_get_detail_op(MI, 0)->sysop = sys_op;
if (sys_op.sub_type == AARCH64_OP_EXACTFPIMM) {
AArch64_get_detail_op(MI, 0)->fp = aarch64_exact_fp_to_fp(sys_op.imm.exactfpimm);
}
AArch64_inc_op_count(MI);
}

Expand Down Expand Up @@ -2891,6 +2938,9 @@ void AArch64_insert_detail_op_sys(MCInst *MI, unsigned index, aarch64_sysop sys_
AArch64_setup_op(&op);
op.type = type;
op.sysop = sys_op;
if (op.sysop.sub_type == AARCH64_OP_EXACTFPIMM) {
op.fp = aarch64_exact_fp_to_fp(op.sysop.imm.exactfpimm);
}
insert_op(MI, index, op);
}

Expand Down
4 changes: 2 additions & 2 deletions bindings/python/capstone/aarch64.py
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,6 @@ class AArch64OpValue(ctypes.Union):
('imm_range', AArch64ImmRange),
('fp', ctypes.c_double),
('mem', AArch64OpMem),
('sysop', AArch64SysOp),
('sme', AArch64OpSme),
('pred', AArch64OpPred),
)
Expand All @@ -110,6 +109,7 @@ class AArch64Op(ctypes.Structure):
('type', ctypes.c_uint),
('is_vreg', ctypes.c_bool),
('value', AArch64OpValue),
('sysop', AArch64SysOp),
('access', ctypes.c_uint8),
('is_list_member', ctypes.c_bool),
)
Expand All @@ -136,7 +136,7 @@ def imm_range(self):

@property
def sysop(self):
return self.value.sysop
return self.sysop

@property
def sme(self):
Expand Down
17 changes: 11 additions & 6 deletions bindings/python/cstest_py/src/cstest_py/details.py
Original file line number Diff line number Diff line change
Expand Up @@ -752,29 +752,34 @@ def test_expected_aarch64(actual: CsInsn, expected: dict) -> bool:
return False
elif aop.type == AARCH64_OP_SYSREG:
if not compare_enum(
aop.value.sysop.sub_type, eop.get("sub_type"), "sub_type"
aop.sysop.sub_type, eop.get("sub_type"), "sub_type"
):
return False
if not compare_uint64(
aop.value.sysop.reg.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
aop.sysop.reg.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
):
return False
elif aop.type == AARCH64_OP_SYSIMM:
if not compare_enum(
aop.value.sysop.sub_type, eop.get("sub_type"), "sub_type"
aop.sysop.sub_type, eop.get("sub_type"), "sub_type"
):
return False
if not compare_uint64(
aop.value.sysop.imm.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
aop.sysop.imm.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
):
return False
# EXACTFPIMM operands
if not compare_fp(
aop.fp, eop.get("fp"), "fp"
):
return False
elif aop.type == AARCH64_OP_SYSALIAS:
if not compare_enum(
aop.value.sysop.sub_type, eop.get("sub_type"), "sub_type"
aop.sysop.sub_type, eop.get("sub_type"), "sub_type"
):
return False
if not compare_uint64(
aop.value.sysop.alias.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
aop.sysop.alias.raw_val, eop.get("sys_raw_val"), "sys_raw_val"
):
return False
elif aop.type == AARCH64_OP_PRED:
Expand Down
1 change: 1 addition & 0 deletions cstool/cstool_aarch64.c
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,7 @@ void print_insn_detail_aarch64(csh handle, cs_insn *ins)
break;
case AARCH64_OP_EXACTFPIMM:
printf("\t\toperands[%u].subtype EXACTFPIMM = %d\n", i, op->sysop.imm.exactfpimm);
printf("\t\toperands[%u].fp = %.1f\n", i, op->fp);
break;
case AARCH64_OP_DBNXS:
printf("\t\toperands[%u].subtype DBNXS = %d\n", i, op->sysop.imm.dbnxs);
Expand Down
3 changes: 2 additions & 1 deletion docs/cs_v6_release_guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,8 +109,9 @@ Nonetheless, we hope this additional information is useful to you.
**AArch64**

- Updated to LLVM-18
- Adding new instructions of SME, SVE2 extensions. With it the `sme` and `pred` operands are added.
- Adding new instructions of SME, SVE2 extensions. With it the new `sme` and `pred` operands are added.
- System operands are provided with way more detail in separated operand.
- The `EXACTFPIMM` operand also sets the `fp` field.

**PPC**

Expand Down
2 changes: 1 addition & 1 deletion include/capstone/aarch64.h
Original file line number Diff line number Diff line change
Expand Up @@ -2836,10 +2836,10 @@ typedef struct cs_aarch64_op {
aarch64_imm_range imm_range; ///< An immediate range
double fp; ///< floating point value for FP operand
aarch64_op_mem mem; ///< base/index/scale/disp value for MEM operand
aarch64_sysop sysop; ///< System operand
aarch64_op_sme sme; ///< SME matrix operand
aarch64_op_pred pred; ///< Predicate register
};
aarch64_sysop sysop; ///< System operand

/// How is this operand accessed? (READ, WRITE or READ|WRITE)
/// This field is combined of cs_ac_type.
Expand Down
2 changes: 1 addition & 1 deletion suite/cstest/include/test_case.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ static const cyaml_schema_field_t test_insn_data_mapping_schema[] = {
CYAML_FIELD_STRING_PTR(
"op_str", CYAML_FLAG_POINTER_NULL_STR | CYAML_FLAG_OPTIONAL,
TestInsnData, op_str, 0, CYAML_UNLIMITED),
CYAML_FIELD_UINT("is_alias", CYAML_FLAG_OPTIONAL, TestInsnData,
CYAML_FIELD_INT("is_alias", CYAML_FLAG_OPTIONAL, TestInsnData,
is_alias),
CYAML_FIELD_INT("alias_id",
CYAML_FLAG_SCALAR_PLAIN | CYAML_FLAG_OPTIONAL,
Expand Down
2 changes: 2 additions & 0 deletions suite/cstest/include/test_detail_aarch64.h
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ typedef struct {
int8_t imm_range_first;
int8_t imm_range_offset;
double fp;
bool fp_set; /// Only relevant for SysOps with EXACTFPIMM
uint64_t sys_raw_val;

TestDetailAArch64SME *sme;
Expand Down Expand Up @@ -103,6 +104,7 @@ static const cyaml_schema_field_t test_detail_aarch64_op_mapping_schema[] = {
CYAML_FIELD_INT("imm_range_offset", CYAML_FLAG_OPTIONAL,
TestDetailAArch64Op, imm_range_offset),
CYAML_FIELD_FLOAT("fp", CYAML_FLAG_OPTIONAL, TestDetailAArch64Op, fp),
CYAML_FIELD_BOOL("fp_set", CYAML_FLAG_OPTIONAL, TestDetailAArch64Op, fp_set),
CYAML_FIELD_UINT("sys_raw_val", CYAML_FLAG_OPTIONAL,
TestDetailAArch64Op, sys_raw_val),
CYAML_FIELD_MAPPING_PTR("sme", CYAML_FLAG_OPTIONAL, TestDetailAArch64Op,
Expand Down
4 changes: 4 additions & 0 deletions suite/cstest/src/test_detail_aarch64.c
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ TestDetailAArch64Op *test_detail_aarch64_op_clone(TestDetailAArch64Op *op)
clone->imm_range_first = op->imm_range_first;
clone->imm_range_offset = op->imm_range_offset;
clone->fp = op->fp;
clone->fp_set = op->fp_set;
clone->sys_raw_val = op->sys_raw_val;
clone->shift_value = op->shift_value;
clone->is_vreg = op->is_vreg;
Expand Down Expand Up @@ -187,6 +188,9 @@ bool test_expected_aarch64(csh *handle, cs_aarch64 *actual,
false);
compare_uint64_ret(op->sysop.imm.raw_val,
eop->sys_raw_val, false);
if (eop->fp_set) {
compare_fp_ret(op->fp, eop->fp, false);
}
break;
case AARCH64_OP_SYSALIAS:
compare_enum_ret(op->sysop.sub_type, eop->sub_type,
Expand Down
3 changes: 1 addition & 2 deletions tests/details/aarch64.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,7 @@ test_cases:
sub_type: AARCH64_OP_REG_MRS
sys_raw_val: 0xc000
cc: AArch64CC_Invalid
update_flags: 1
regs_write: [ nzcv, x9 ]
regs_write: [ x9 ]

-
asm_text: "msr SPSel, #0"
Expand Down
2 changes: 1 addition & 1 deletion tests/details/cs_common_details.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -309,7 +309,7 @@ test_cases:
mnemonic: "mrs"
op_str: "x9, MIDR_EL1"
details:
regs_impl_write: []
regs_impl_write: [ ]
groups: [ privilege ]
-
asm_text: "msr SPSel, #0"
Expand Down
Loading
Loading