mirror of
https://github.com/radareorg/radare2.git
synced 2025-02-20 06:12:55 +00:00
Migrate s390.cs and fix the abidiff suppression rules ##arch
This commit is contained in:
parent
721f818364
commit
db1d06da6b
10
.github/workflows/build.yml
vendored
10
.github/workflows/build.yml
vendored
@ -594,9 +594,13 @@ jobs:
|
||||
tar -xvf r2-static-latest.tar.xz -C r2-static-latest --strip-components=1
|
||||
- name: ABI compatibility check
|
||||
run: |
|
||||
echo '[suppress_type]' > abidiff.supressions.conf
|
||||
echo 'name_regexp = ^cs_' >> abidiff.supressions.conf
|
||||
for lib in r2-static-latest/usr/lib/libr_*.so; do abidiff --suppr abidiff.supressions.conf ${lib} r2-static/usr/lib/$(basename ${lib}); done
|
||||
echo '[suppress_function]' > abidiff.conf
|
||||
echo 'name_not_regexp = ^r_.*' >> abidiff.conf
|
||||
echo '[suppress_variable]' >> abidiff.conf
|
||||
echo 'name_not_regexp = ^r_.*' >> abidiff.conf
|
||||
for lib in r2-static-latest/usr/lib/libr_*.so; do
|
||||
echo $lib ; abidiff --suppr abidiff.conf ${lib} r2-static/usr/lib/$(basename ${lib});
|
||||
done
|
||||
|
||||
|
||||
# Release creation
|
||||
|
2
dist/plugins-cfg/plugins.def.cfg
vendored
2
dist/plugins-cfg/plugins.def.cfg
vendored
@ -46,7 +46,7 @@ arch.ppc_gnu
|
||||
arch.propeller
|
||||
arch.pyc
|
||||
arch.riscv_cs
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
arch.s390_gnu
|
||||
arch.snes
|
||||
anal.sparc_cs
|
||||
|
2
dist/plugins-cfg/plugins.mingw.cfg
vendored
2
dist/plugins-cfg/plugins.mingw.cfg
vendored
@ -35,7 +35,7 @@ arch.ppc_gnu
|
||||
arch.sh
|
||||
anal.sparc_cs
|
||||
arch.sparc_gnu
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
arch.s390_gnu
|
||||
anal.tms320
|
||||
arch.tricore
|
||||
|
2
dist/plugins-cfg/plugins.nogpl.cfg
vendored
2
dist/plugins-cfg/plugins.nogpl.cfg
vendored
@ -16,7 +16,7 @@ arch.msp430
|
||||
anal.null
|
||||
anal.ppc_cs
|
||||
anal.sparc_cs
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
anal.tms320
|
||||
arch.v850
|
||||
arch.ws
|
||||
|
2
dist/plugins-cfg/plugins.static.cfg
vendored
2
dist/plugins-cfg/plugins.static.cfg
vendored
@ -24,7 +24,7 @@ anal.ppc_cs
|
||||
arch.ppc_gnu
|
||||
anal.sparc_cs
|
||||
arch.sparc_gnu
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
arch.s390_gnu
|
||||
anal.m680x_cs
|
||||
arch.sh
|
||||
|
2
dist/plugins-cfg/plugins.static.nogpl.cfg
vendored
2
dist/plugins-cfg/plugins.static.nogpl.cfg
vendored
@ -15,7 +15,7 @@ arch.mcs96
|
||||
anal.null
|
||||
arch.sh
|
||||
anal.sparc_cs
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
arch.ws
|
||||
arch.xap
|
||||
anal.x86_cs
|
||||
|
2
dist/plugins-cfg/plugins.termux.cfg
vendored
2
dist/plugins-cfg/plugins.termux.cfg
vendored
@ -15,7 +15,7 @@ anal.ppc_cs
|
||||
arch.mcs96
|
||||
arch.ppc_gnu
|
||||
arch.s390_gnu
|
||||
anal.s390_cs
|
||||
arch.s390_cs
|
||||
anal.sparc_cs
|
||||
arch.sparc_gnu
|
||||
arch.v850
|
||||
|
@ -70,7 +70,6 @@ r_anal_sources = [
|
||||
'p/anal_loongarch_gnu.c',
|
||||
'p/anal_null.c',
|
||||
'p/anal_ppc_cs.c',
|
||||
'p/anal_s390_cs.c',
|
||||
'p/anal_sparc_cs.c',
|
||||
'p/anal_tms320.c',
|
||||
# join_paths('arch/whitespace/wsdis.c'),
|
||||
|
@ -12,7 +12,7 @@ all: ${ALL_TARGETS}
|
||||
|
||||
ALL_TARGETS=
|
||||
# TODO: rename to enabled plugins
|
||||
ANAL_PLUGINS=null.mk arc.mk ppc_gnu.mk ppc_cs.mk arm_gnu.mk avr.mk xap.mk bpf.mk dalvik.mk sh.mk ebc.mk gb.mk lh5801.mk ws.mk h8300.mk cr16.mk v850.mk msp430.mk sparc_gnu.mk sparc_cs.mk x86_cs.mk cris.mk 6502.mk snes.mk riscv.mk vax.mk xtensa.mk rsp.mk tricore.mk s390_cs.mk pickle.mk
|
||||
ANAL_PLUGINS=null.mk arc.mk ppc_cs.mk arm_gnu.mk avr.mk xap.mk bpf.mk dalvik.mk sh.mk ebc.mk gb.mk lh5801.mk ws.mk h8300.mk cr16.mk v850.mk msp430.mk sparc_gnu.mk sparc_cs.mk x86_cs.mk cris.mk 6502.mk snes.mk riscv.mk vax.mk xtensa.mk rsp.mk tricore.mk s390_cs.mk pickle.mk
|
||||
include $(ANAL_PLUGINS)
|
||||
|
||||
clean:
|
||||
|
@ -1,273 +0,0 @@
|
||||
/* radare2 - LGPL - Copyright 2014-2022 - pancake */
|
||||
|
||||
#include <r_anal.h>
|
||||
#include <r_lib.h>
|
||||
#include <capstone/capstone.h>
|
||||
#include <capstone/systemz.h>
|
||||
// instruction set: http://www.tachyonsoft.com/inst390m.htm
|
||||
|
||||
#if CS_API_MAJOR < 2
|
||||
#error Old Capstone not supported
|
||||
#endif
|
||||
|
||||
#define INSOP(n) insn->detail->sysz.operands[n]
|
||||
|
||||
static void opex(RStrBuf *buf, csh handle, cs_insn *insn) {
|
||||
int i;
|
||||
PJ *pj = pj_new ();
|
||||
if (!pj) {
|
||||
return;
|
||||
}
|
||||
pj_o (pj);
|
||||
pj_ka (pj, "operands");
|
||||
cs_sysz *x = &insn->detail->sysz;
|
||||
for (i = 0; i < x->op_count; i++) {
|
||||
cs_sysz_op *op = x->operands + i;
|
||||
pj_o (pj);
|
||||
switch (op->type) {
|
||||
case SYSZ_OP_REG:
|
||||
pj_ks (pj, "type", "reg");
|
||||
pj_ks (pj, "value", cs_reg_name (handle, op->reg));
|
||||
break;
|
||||
case SYSZ_OP_IMM:
|
||||
pj_ks (pj, "type", "imm");
|
||||
pj_kN (pj, "value", op->imm);
|
||||
break;
|
||||
case SYSZ_OP_MEM:
|
||||
pj_ks (pj, "type", "mem");
|
||||
if (op->mem.base != SYSZ_REG_INVALID) {
|
||||
pj_ks (pj, "base", cs_reg_name (handle, op->mem.base));
|
||||
}
|
||||
pj_kN (pj, "disp", op->mem.disp);
|
||||
break;
|
||||
default:
|
||||
pj_ks (pj, "type", "invalid");
|
||||
break;
|
||||
}
|
||||
pj_end (pj); /* o operand */
|
||||
}
|
||||
pj_end (pj); /* a operands */
|
||||
pj_end (pj);
|
||||
|
||||
r_strbuf_init (buf);
|
||||
r_strbuf_append (buf, pj_string (pj));
|
||||
pj_free (pj);
|
||||
}
|
||||
|
||||
#define CSINC SYSZ
|
||||
#define CSINC_MODE CS_MODE_BIG_ENDIAN
|
||||
#include "capstone.inc"
|
||||
|
||||
static int analop(RAnal *a, RAnalOp *op, ut64 addr, const ut8 *buf, int len, RAnalOpMask mask) {
|
||||
csh handle = init_capstone (a);
|
||||
if (handle == 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
cs_insn *insn = NULL;
|
||||
op->addr = addr;
|
||||
op->size = 2;
|
||||
|
||||
// capstone-next
|
||||
int n = cs_disasm (handle, (const ut8*)buf, len, addr, 1, &insn);
|
||||
if (n < 1) {
|
||||
if (mask & R_ARCH_OP_MASK_DISASM) {
|
||||
op->mnemonic = strdup ("invalid");
|
||||
}
|
||||
op->type = R_ANAL_OP_TYPE_ILL;
|
||||
return -1;
|
||||
}
|
||||
if (mask & R_ARCH_OP_MASK_OPEX) {
|
||||
opex (&op->opex, handle, insn);
|
||||
}
|
||||
if (mask & R_ARCH_OP_MASK_DISASM) {
|
||||
op->mnemonic = r_str_newf ("%s%s%s",
|
||||
insn->mnemonic, insn->op_str[0]? " ": "",
|
||||
insn->op_str);
|
||||
// if syntax is not AT&T
|
||||
if (a->config->syntax != R_ARCH_SYNTAX_ATT) {
|
||||
op->mnemonic = r_str_replace (op->mnemonic, "%", "", -1);
|
||||
}
|
||||
}
|
||||
op->size = insn->size;
|
||||
switch (insn->id) {
|
||||
#if CS_API_MAJOR >= 5
|
||||
case SYSZ_INS_SVC:
|
||||
op->type = R_ANAL_OP_TYPE_SWI;
|
||||
break;
|
||||
case SYSZ_INS_STM:
|
||||
op->type = R_ANAL_OP_TYPE_PUSH;
|
||||
break;
|
||||
case SYSZ_INS_BASR:
|
||||
op->type = R_ANAL_OP_TYPE_CALL;
|
||||
break;
|
||||
case SYSZ_INS_BALR:
|
||||
op->type = R_ANAL_OP_TYPE_RCALL;
|
||||
//op->jump = INSOP (0).imm;
|
||||
op->fail = addr + op->size;
|
||||
break;
|
||||
case SYSZ_INS_B:
|
||||
op->type = R_ANAL_OP_TYPE_JMP;
|
||||
op->jump = addr + r_num_get (NULL, insn->op_str);
|
||||
break;
|
||||
#endif
|
||||
case SYSZ_INS_BRCL:
|
||||
case SYSZ_INS_BRASL:
|
||||
op->type = R_ANAL_OP_TYPE_CALL;
|
||||
break;
|
||||
case SYSZ_INS_LDR:
|
||||
op->type = R_ANAL_OP_TYPE_LOAD;
|
||||
break;
|
||||
case SYSZ_INS_L:
|
||||
case SYSZ_INS_LR:
|
||||
case SYSZ_INS_LA:
|
||||
op->type = R_ANAL_OP_TYPE_MOV;
|
||||
break;
|
||||
case SYSZ_INS_ST:
|
||||
op->type = R_ANAL_OP_TYPE_STORE;
|
||||
break;
|
||||
case SYSZ_INS_BR:
|
||||
op->type = R_ANAL_OP_TYPE_RJMP;
|
||||
break;
|
||||
case SYSZ_INS_BRC:
|
||||
case SYSZ_INS_BER:
|
||||
case SYSZ_INS_BHR:
|
||||
case SYSZ_INS_BHER:
|
||||
case SYSZ_INS_BLR:
|
||||
case SYSZ_INS_BLER:
|
||||
case SYSZ_INS_BLHR:
|
||||
case SYSZ_INS_BNER:
|
||||
case SYSZ_INS_BNHR:
|
||||
case SYSZ_INS_BNHER:
|
||||
case SYSZ_INS_BNLR:
|
||||
case SYSZ_INS_BNLER:
|
||||
case SYSZ_INS_BNLHR:
|
||||
case SYSZ_INS_BNOR:
|
||||
case SYSZ_INS_BOR:
|
||||
case SYSZ_INS_BRAS:
|
||||
case SYSZ_INS_BRCT:
|
||||
case SYSZ_INS_BRCTG:
|
||||
op->type = R_ANAL_OP_TYPE_CJMP;
|
||||
break;
|
||||
case SYSZ_INS_JE:
|
||||
case SYSZ_INS_JGE:
|
||||
case SYSZ_INS_JHE:
|
||||
case SYSZ_INS_JGHE:
|
||||
case SYSZ_INS_JH:
|
||||
case SYSZ_INS_JGH:
|
||||
case SYSZ_INS_JLE:
|
||||
case SYSZ_INS_JGLE:
|
||||
case SYSZ_INS_JLH:
|
||||
case SYSZ_INS_JGLH:
|
||||
case SYSZ_INS_JL:
|
||||
case SYSZ_INS_JGL:
|
||||
case SYSZ_INS_JNE:
|
||||
case SYSZ_INS_JGNE:
|
||||
case SYSZ_INS_JNHE:
|
||||
case SYSZ_INS_JGNHE:
|
||||
case SYSZ_INS_JNH:
|
||||
case SYSZ_INS_JGNH:
|
||||
case SYSZ_INS_JNLE:
|
||||
case SYSZ_INS_JGNLE:
|
||||
case SYSZ_INS_JNLH:
|
||||
case SYSZ_INS_JGNLH:
|
||||
case SYSZ_INS_JNL:
|
||||
case SYSZ_INS_JGNL:
|
||||
case SYSZ_INS_JNO:
|
||||
case SYSZ_INS_JGNO:
|
||||
case SYSZ_INS_JO:
|
||||
case SYSZ_INS_JGO:
|
||||
case SYSZ_INS_JG:
|
||||
op->type = R_ANAL_OP_TYPE_CJMP;
|
||||
op->jump = INSOP (0).imm;
|
||||
op->fail = addr+op->size;
|
||||
break;
|
||||
case SYSZ_INS_XI:
|
||||
op->type = R_ANAL_OP_TYPE_XOR;
|
||||
break;
|
||||
case SYSZ_INS_OI:
|
||||
op->type = R_ANAL_OP_TYPE_OR;
|
||||
break;
|
||||
case SYSZ_INS_J:
|
||||
op->type = R_ANAL_OP_TYPE_JMP;
|
||||
op->jump = INSOP (0).imm;
|
||||
op->fail = UT64_MAX;
|
||||
break;
|
||||
}
|
||||
cs_free (insn, n);
|
||||
return op->size;
|
||||
}
|
||||
|
||||
static bool set_reg_profile(RAnal *anal) {
|
||||
const char *p =
|
||||
"=PC r15\n"
|
||||
"=LR r14\n"
|
||||
"=SP r13\n"
|
||||
"=BP r12\n"
|
||||
"=A0 r0\n"
|
||||
"=A1 r1\n"
|
||||
"=A2 r2\n"
|
||||
"=A3 r3\n"
|
||||
"=SN r0\n"
|
||||
"gpr sb .32 36 0\n" // r9
|
||||
"gpr sl .32 40 0\n" // rl0
|
||||
"gpr fp .32 44 0\n" // r11
|
||||
"gpr ip .32 48 0\n" // r12
|
||||
"gpr sp .32 52 0\n" // r13
|
||||
"gpr lr .32 56 0\n" // r14
|
||||
"gpr pc .32 60 0\n" // r15
|
||||
|
||||
"gpr r0 .32 0 0\n"
|
||||
"gpr r1 .32 4 0\n"
|
||||
"gpr r2 .32 8 0\n"
|
||||
"gpr r3 .32 12 0\n"
|
||||
"gpr r4 .32 16 0\n"
|
||||
"gpr r5 .32 20 0\n"
|
||||
"gpr r6 .32 24 0\n"
|
||||
"gpr r7 .32 28 0\n"
|
||||
"gpr r8 .32 32 0\n"
|
||||
"gpr r9 .32 36 0\n"
|
||||
"gpr r10 .32 40 0\n"
|
||||
"gpr r11 .32 44 0\n"
|
||||
"gpr r12 .32 48 0\n"
|
||||
"gpr r13 .32 52 0\n"
|
||||
"gpr r14 .32 56 0\n"
|
||||
"gpr r15 .32 60 0\n"
|
||||
;
|
||||
return r_reg_set_profile_string (anal->reg, p);
|
||||
}
|
||||
|
||||
static int archinfo(RAnal *anal, int q) {
|
||||
switch (q) {
|
||||
case R_ANAL_ARCHINFO_DATA_ALIGN:
|
||||
case R_ANAL_ARCHINFO_ALIGN:
|
||||
return 1;
|
||||
case R_ANAL_ARCHINFO_MAX_OP_SIZE:
|
||||
return 6;
|
||||
case R_ANAL_ARCHINFO_MIN_OP_SIZE:
|
||||
return 2;
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
|
||||
RAnalPlugin r_anal_plugin_s390_cs = {
|
||||
.name = "s390",
|
||||
.desc = "Capstone SystemZ microanalysis",
|
||||
.author = "pancake",
|
||||
.esil = false,
|
||||
.license = "BSD",
|
||||
.arch = "s390",
|
||||
.bits = 32 | 64, // it's actually 31
|
||||
.op = &analop,
|
||||
.archinfo = archinfo,
|
||||
.set_reg_profile = &set_reg_profile,
|
||||
.mnemonics = cs_mnemonics,
|
||||
};
|
||||
|
||||
#ifndef R2_PLUGIN_INCORE
|
||||
R_API RLibStruct radare_plugin = {
|
||||
.type = R_LIB_TYPE_ANAL,
|
||||
.data = &r_anal_plugin_s390_cs,
|
||||
.version = R2_VERSION
|
||||
};
|
||||
#endif
|
@ -1,13 +0,0 @@
|
||||
OBJ_ANAL_S390CS_CS=anal_s390_cs.o
|
||||
|
||||
include p/capstone.mk
|
||||
|
||||
STATIC_OBJ+=${OBJ_ANAL_S390CS_CS}
|
||||
|
||||
TARGET_ANAL_S390CS_CS=anal_s390_cs.${EXT_SO}
|
||||
|
||||
ALL_TARGETS+=${TARGET_ANAL_S390CS_CS}
|
||||
|
||||
${TARGET_ANAL_S390CS_CS}: ${OBJ_SYSTEMZ_CS}
|
||||
${CC} ${CFLAGS} $(call libname,anal_s390_cs) $(CS_LDFLAGS) \
|
||||
-o anal_s390_cs.${EXT_SO} ${OBJ_ANAL_S390CS_CS}
|
@ -21,6 +21,7 @@ r_arch_sources = [
|
||||
'p/ppc/gnu/ppc-opc.c',
|
||||
'p/null/plugin.c',
|
||||
'p/lm32/plugin.c',
|
||||
'p/s390/plugin.c',
|
||||
'p/mcs96/plugin.c',
|
||||
'p/xtensa/plugin.c',
|
||||
'p/lanai/plugin.c',
|
||||
|
303
libr/arch/p/s390/plugin.c
Normal file
303
libr/arch/p/s390/plugin.c
Normal file
@ -0,0 +1,303 @@
|
||||
/* radare2 - LGPL - Copyright 2014-2023 - pancake */
|
||||
|
||||
#include <r_arch.h>
|
||||
#include <r_lib.h>
|
||||
#include <capstone/capstone.h>
|
||||
#include <capstone/systemz.h>
|
||||
// instruction set: http://www.tachyonsoft.com/inst390m.htm
|
||||
|
||||
#if CS_API_MAJOR < 2
|
||||
#error Old Capstone not supported
|
||||
#endif
|
||||
|
||||
#define INSOP(n) insn->detail->sysz.operands[n]
|
||||
|
||||
static void opex(RStrBuf *buf, csh handle, cs_insn *insn) {
|
||||
int i;
|
||||
PJ *pj = pj_new ();
|
||||
if (!pj) {
|
||||
return;
|
||||
}
|
||||
pj_o (pj);
|
||||
pj_ka (pj, "operands");
|
||||
cs_sysz *x = &insn->detail->sysz;
|
||||
for (i = 0; i < x->op_count; i++) {
|
||||
cs_sysz_op *op = x->operands + i;
|
||||
pj_o (pj);
|
||||
switch (op->type) {
|
||||
case SYSZ_OP_REG:
|
||||
pj_ks (pj, "type", "reg");
|
||||
pj_ks (pj, "value", cs_reg_name (handle, op->reg));
|
||||
break;
|
||||
case SYSZ_OP_IMM:
|
||||
pj_ks (pj, "type", "imm");
|
||||
pj_kN (pj, "value", op->imm);
|
||||
break;
|
||||
case SYSZ_OP_MEM:
|
||||
pj_ks (pj, "type", "mem");
|
||||
if (op->mem.base != SYSZ_REG_INVALID) {
|
||||
pj_ks (pj, "base", cs_reg_name (handle, op->mem.base));
|
||||
}
|
||||
pj_kN (pj, "disp", op->mem.disp);
|
||||
break;
|
||||
default:
|
||||
pj_ks (pj, "type", "invalid");
|
||||
break;
|
||||
}
|
||||
pj_end (pj); /* o operand */
|
||||
}
|
||||
pj_end (pj); /* a operands */
|
||||
pj_end (pj);
|
||||
|
||||
r_strbuf_init (buf);
|
||||
r_strbuf_append (buf, pj_string (pj));
|
||||
pj_free (pj);
|
||||
}
|
||||
|
||||
#define CSINC SYSZ
|
||||
#define CSINC_MODE CS_MODE_BIG_ENDIAN
|
||||
#include "../capstone.inc"
|
||||
|
||||
static char *mnemonics(RArchSession *s, int id, bool json) {
|
||||
CapstonePluginData *cpd = (CapstonePluginData*)s->data;
|
||||
return r_arch_cs_mnemonics (s, cpd->cs_handle, id, json);
|
||||
}
|
||||
|
||||
static bool init(RArchSession *s) {
|
||||
r_return_val_if_fail (s, false);
|
||||
if (s->data) {
|
||||
R_LOG_WARN ("Already initialized");
|
||||
return false;
|
||||
}
|
||||
s->data = R_NEW0 (CapstonePluginData);
|
||||
CapstonePluginData *cpd = (CapstonePluginData*)s->data;
|
||||
if (!r_arch_cs_init (s, &cpd->cs_handle)) {
|
||||
R_LOG_ERROR ("Cannot initialize capstone");
|
||||
R_FREE (s->data);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool decode(RArchSession *a, RAnalOp *op, RArchDecodeMask mask) {
|
||||
CapstonePluginData *cpd = (CapstonePluginData*)a->data;
|
||||
// static int analop(RAnal *a, RAnalOp *op, ut64 addr, const ut8 *buf, int len, RAnalOpMask mask) {
|
||||
const ut8 *buf = op->bytes;
|
||||
size_t len = op->size;
|
||||
ut64 addr = op->addr;
|
||||
|
||||
cs_insn *insn = NULL;
|
||||
op->addr = addr;
|
||||
|
||||
int n = cs_disasm (cpd->cs_handle, (const ut8*)buf, len, addr, 1, &insn);
|
||||
if (n < 1) {
|
||||
if (mask & R_ARCH_OP_MASK_DISASM) {
|
||||
op->mnemonic = strdup ("invalid");
|
||||
}
|
||||
op->size = 1;
|
||||
op->type = R_ANAL_OP_TYPE_ILL;
|
||||
return false;
|
||||
}
|
||||
if (mask & R_ARCH_OP_MASK_OPEX) {
|
||||
opex (&op->opex, cpd->cs_handle, insn);
|
||||
}
|
||||
if (mask & R_ARCH_OP_MASK_DISASM) {
|
||||
op->mnemonic = r_str_newf ("%s%s%s",
|
||||
insn->mnemonic, insn->op_str[0]? " ": "",
|
||||
insn->op_str);
|
||||
// if syntax is not AT&T
|
||||
if (a->config->syntax != R_ARCH_SYNTAX_ATT) {
|
||||
op->mnemonic = r_str_replace (op->mnemonic, "%", "", -1);
|
||||
}
|
||||
}
|
||||
op->size = insn->size;
|
||||
switch (insn->id) {
|
||||
#if CS_API_MAJOR >= 5
|
||||
case SYSZ_INS_SVC:
|
||||
op->type = R_ANAL_OP_TYPE_SWI;
|
||||
break;
|
||||
case SYSZ_INS_STM:
|
||||
op->type = R_ANAL_OP_TYPE_PUSH;
|
||||
break;
|
||||
case SYSZ_INS_BASR:
|
||||
op->type = R_ANAL_OP_TYPE_CALL;
|
||||
break;
|
||||
case SYSZ_INS_BALR:
|
||||
op->type = R_ANAL_OP_TYPE_RCALL;
|
||||
//op->jump = INSOP (0).imm;
|
||||
op->fail = addr + op->size;
|
||||
break;
|
||||
case SYSZ_INS_B:
|
||||
op->type = R_ANAL_OP_TYPE_JMP;
|
||||
op->jump = addr + r_num_get (NULL, insn->op_str);
|
||||
break;
|
||||
#endif
|
||||
case SYSZ_INS_BRCL:
|
||||
case SYSZ_INS_BRASL:
|
||||
op->type = R_ANAL_OP_TYPE_CALL;
|
||||
break;
|
||||
case SYSZ_INS_LDR:
|
||||
op->type = R_ANAL_OP_TYPE_LOAD;
|
||||
break;
|
||||
case SYSZ_INS_L:
|
||||
case SYSZ_INS_LR:
|
||||
case SYSZ_INS_LA:
|
||||
op->type = R_ANAL_OP_TYPE_MOV;
|
||||
break;
|
||||
case SYSZ_INS_ST:
|
||||
op->type = R_ANAL_OP_TYPE_STORE;
|
||||
break;
|
||||
case SYSZ_INS_BR:
|
||||
op->type = R_ANAL_OP_TYPE_RJMP;
|
||||
break;
|
||||
case SYSZ_INS_BRC:
|
||||
case SYSZ_INS_BER:
|
||||
case SYSZ_INS_BHR:
|
||||
case SYSZ_INS_BHER:
|
||||
case SYSZ_INS_BLR:
|
||||
case SYSZ_INS_BLER:
|
||||
case SYSZ_INS_BLHR:
|
||||
case SYSZ_INS_BNER:
|
||||
case SYSZ_INS_BNHR:
|
||||
case SYSZ_INS_BNHER:
|
||||
case SYSZ_INS_BNLR:
|
||||
case SYSZ_INS_BNLER:
|
||||
case SYSZ_INS_BNLHR:
|
||||
case SYSZ_INS_BNOR:
|
||||
case SYSZ_INS_BOR:
|
||||
case SYSZ_INS_BRAS:
|
||||
case SYSZ_INS_BRCT:
|
||||
case SYSZ_INS_BRCTG:
|
||||
op->type = R_ANAL_OP_TYPE_CJMP;
|
||||
break;
|
||||
case SYSZ_INS_JE:
|
||||
case SYSZ_INS_JGE:
|
||||
case SYSZ_INS_JHE:
|
||||
case SYSZ_INS_JGHE:
|
||||
case SYSZ_INS_JH:
|
||||
case SYSZ_INS_JGH:
|
||||
case SYSZ_INS_JLE:
|
||||
case SYSZ_INS_JGLE:
|
||||
case SYSZ_INS_JLH:
|
||||
case SYSZ_INS_JGLH:
|
||||
case SYSZ_INS_JL:
|
||||
case SYSZ_INS_JGL:
|
||||
case SYSZ_INS_JNE:
|
||||
case SYSZ_INS_JGNE:
|
||||
case SYSZ_INS_JNHE:
|
||||
case SYSZ_INS_JGNHE:
|
||||
case SYSZ_INS_JNH:
|
||||
case SYSZ_INS_JGNH:
|
||||
case SYSZ_INS_JNLE:
|
||||
case SYSZ_INS_JGNLE:
|
||||
case SYSZ_INS_JNLH:
|
||||
case SYSZ_INS_JGNLH:
|
||||
case SYSZ_INS_JNL:
|
||||
case SYSZ_INS_JGNL:
|
||||
case SYSZ_INS_JNO:
|
||||
case SYSZ_INS_JGNO:
|
||||
case SYSZ_INS_JO:
|
||||
case SYSZ_INS_JGO:
|
||||
case SYSZ_INS_JG:
|
||||
op->type = R_ANAL_OP_TYPE_CJMP;
|
||||
op->jump = INSOP (0).imm;
|
||||
op->fail = addr + op->size;
|
||||
break;
|
||||
case SYSZ_INS_XI:
|
||||
op->type = R_ANAL_OP_TYPE_XOR;
|
||||
break;
|
||||
case SYSZ_INS_OI:
|
||||
op->type = R_ANAL_OP_TYPE_OR;
|
||||
break;
|
||||
case SYSZ_INS_J:
|
||||
op->type = R_ANAL_OP_TYPE_JMP;
|
||||
op->jump = INSOP (0).imm;
|
||||
op->fail = UT64_MAX;
|
||||
break;
|
||||
}
|
||||
cs_free (insn, n);
|
||||
return op->size > 1;
|
||||
}
|
||||
|
||||
static char *regs(RArchSession *as) {
|
||||
const char p[] =
|
||||
"=PC r15\n"
|
||||
"=LR r14\n"
|
||||
"=SP r13\n"
|
||||
"=BP r12\n"
|
||||
"=A0 r0\n"
|
||||
"=A1 r1\n"
|
||||
"=A2 r2\n"
|
||||
"=A3 r3\n"
|
||||
"=SN r0\n"
|
||||
"gpr sb .32 36 0\n" // r9
|
||||
"gpr sl .32 40 0\n" // rl0
|
||||
"gpr fp .32 44 0\n" // r11
|
||||
"gpr ip .32 48 0\n" // r12
|
||||
"gpr sp .32 52 0\n" // r13
|
||||
"gpr lr .32 56 0\n" // r14
|
||||
"gpr pc .32 60 0\n" // r15
|
||||
|
||||
"gpr r0 .32 0 0\n"
|
||||
"gpr r1 .32 4 0\n"
|
||||
"gpr r2 .32 8 0\n"
|
||||
"gpr r3 .32 12 0\n"
|
||||
"gpr r4 .32 16 0\n"
|
||||
"gpr r5 .32 20 0\n"
|
||||
"gpr r6 .32 24 0\n"
|
||||
"gpr r7 .32 28 0\n"
|
||||
"gpr r8 .32 32 0\n"
|
||||
"gpr r9 .32 36 0\n"
|
||||
"gpr r10 .32 40 0\n"
|
||||
"gpr r11 .32 44 0\n"
|
||||
"gpr r12 .32 48 0\n"
|
||||
"gpr r13 .32 52 0\n"
|
||||
"gpr r14 .32 56 0\n"
|
||||
"gpr r15 .32 60 0\n"
|
||||
;
|
||||
return strdup (p);
|
||||
}
|
||||
|
||||
static int archinfo(RArchSession *as, ut32 q) {
|
||||
switch (q) {
|
||||
case R_ANAL_ARCHINFO_DATA_ALIGN:
|
||||
case R_ANAL_ARCHINFO_ALIGN:
|
||||
return 1;
|
||||
case R_ANAL_ARCHINFO_MAX_OP_SIZE:
|
||||
return 6;
|
||||
case R_ANAL_ARCHINFO_MIN_OP_SIZE:
|
||||
return 2;
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
|
||||
static bool fini(RArchSession *s) {
|
||||
r_return_val_if_fail (s, false);
|
||||
CapstonePluginData *cpd = (CapstonePluginData*)s->data;
|
||||
cs_close (&cpd->cs_handle);
|
||||
R_FREE (s->data);
|
||||
return true;
|
||||
}
|
||||
|
||||
RArchPlugin r_arch_plugin_s390_cs = {
|
||||
.name = "s390",
|
||||
.desc = "Capstone SystemZ microanalysis",
|
||||
.author = "pancake",
|
||||
.license = "BSD",
|
||||
.arch = "s390",
|
||||
.bits = R_SYS_BITS_PACK2 (32, 64), // it's actually 31
|
||||
.decode = &decode,
|
||||
.info = archinfo,
|
||||
.regs = ®s,
|
||||
.mnemonics = mnemonics,
|
||||
.init = init,
|
||||
.fini = fini
|
||||
};
|
||||
|
||||
#ifndef R2_PLUGIN_INCORE
|
||||
R_API RLibStruct radare_plugin = {
|
||||
.type = R_LIB_TYPE_ARCH,
|
||||
.data = &r_arch_plugin_s390_cs,
|
||||
.version = R2_VERSION
|
||||
};
|
||||
#endif
|
13
libr/arch/p/s390_cs.mk
Normal file
13
libr/arch/p/s390_cs.mk
Normal file
@ -0,0 +1,13 @@
|
||||
OBJ_ARCH_S390CS_CS=p/s390/plugin.o
|
||||
|
||||
include p/capstone.mk
|
||||
|
||||
STATIC_OBJ+=${OBJ_ARCH_S390CS_CS}
|
||||
|
||||
TARGET_ARCH_S390CS_CS=arch_s390_cs.${EXT_SO}
|
||||
|
||||
ALL_TARGETS+=${TARGET_ARCH_S390CS_CS}
|
||||
|
||||
${TARGET_ARCH_S390CS_CS}: ${OBJ_SYSTEMZ_CS}
|
||||
${CC} ${CFLAGS} $(call libname,arch_s390_cs) $(CS_LDFLAGS) \
|
||||
-o arch_s390_cs.${EXT_SO} ${OBJ_ARCH_S390CS_CS}
|
@ -1582,7 +1582,6 @@ extern RAnalPlugin r_anal_plugin_jdh8;
|
||||
extern RAnalPlugin r_anal_plugin_ppc_cs;
|
||||
extern RAnalPlugin r_anal_plugin_sh;
|
||||
extern RAnalPlugin r_anal_plugin_sparc_cs;
|
||||
extern RAnalPlugin r_anal_plugin_s390_cs;
|
||||
extern RAnalPlugin r_anal_plugin_tms320;
|
||||
extern RAnalPlugin r_anal_plugin_x86;
|
||||
extern RAnalPlugin r_anal_plugin_x86_cs;
|
||||
|
@ -330,6 +330,7 @@ extern RArchPlugin r_arch_plugin_h8300;
|
||||
extern RArchPlugin r_arch_plugin_bf;
|
||||
extern RArchPlugin r_arch_plugin_sparc_gnu;
|
||||
extern RArchPlugin r_arch_plugin_hppa_gnu;
|
||||
extern RArchPlugin r_arch_plugin_s390_cs;
|
||||
extern RArchPlugin r_arch_plugin_s390_gnu;
|
||||
extern RArchPlugin r_arch_plugin_m68k_gnu;
|
||||
extern RArchPlugin r_arch_plugin_ppc_gnu;
|
||||
|
@ -171,14 +171,13 @@ anal_plugins += [
|
||||
'mips_cs',
|
||||
'ppc_cs',
|
||||
'sparc_cs',
|
||||
's390_cs',
|
||||
'tms320',
|
||||
'x86_cs',
|
||||
'xcore_cs'
|
||||
]
|
||||
|
||||
arch_plugins += [
|
||||
'm68k_gnu',
|
||||
's390_cs',
|
||||
]
|
||||
|
||||
if no_user_plugins
|
||||
@ -192,6 +191,7 @@ if no_user_plugins
|
||||
'z80',
|
||||
'pdp11',
|
||||
'ppc_gnu',
|
||||
'm68k_gnu',
|
||||
# 'hppa_gnu',
|
||||
'sparc_gnu',
|
||||
'lanai',
|
||||
|
@ -67,11 +67,11 @@ EXPECT=<<EOF
|
||||
| 0x0000192e c5c5000000a0 bprp 0xc, 0x232e, 0x1a6e
|
||||
| 0x00001934 0000 invalid
|
||||
| 0x00001936 0090 invalid
|
||||
| 0x00001938 47f0f001 b 1(r15)
|
||||
,==< 0x00001938 47f0f001 b 1(r15)
|
||||
| 0x0000193c 58f0c31c l r15, 0x31c(r12)
|
||||
| 0x00001940 184e lr r4, r14
|
||||
| 0x00001942 05ef balr r14, r15
|
||||
| 0x00001944 00 invalid
|
||||
| 0x00001944 0000 invalid
|
||||
;-- entry0:
|
||||
;-- hit0_0:
|
||||
0x00001928 47f0f024 b 36(%r15)
|
||||
|
@ -221,10 +221,12 @@ FILE=-
|
||||
CMDS=<<EOF
|
||||
e asm.arch=s390
|
||||
e cfg.bigendian=true
|
||||
wx 051e
|
||||
aom
|
||||
aoml~?
|
||||
EOF
|
||||
EXPECT=<<EOF
|
||||
balr
|
||||
2345
|
||||
EOF
|
||||
RUN
|
||||
|
Loading…
x
Reference in New Issue
Block a user