Skip to content

Instantly share code, notes, and snippets.

@vnd
Created June 18, 2016 17:01
Show Gist options
  • Save vnd/9b1b358c83959b229d6c8a66cfb7709d to your computer and use it in GitHub Desktop.
Save vnd/9b1b358c83959b229d6c8a66cfb7709d to your computer and use it in GitHub Desktop.
/* Taken from http://www.capstone-engine.org/lang_c.html */
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <inttypes.h>
#include <byteswap.h>
#include <capstone/capstone.h>
// http://stackoverflow.com/a/6933094/708549
static uint8_t* hex_decode(const char *in, size_t len, uint8_t *out)
{
unsigned int i, t, hn, ln;
for (t = 0,i = 0; i < len; i+=2,++t) {
hn = in[i] > '9' ? in[i] - 'A' + 10 : in[i] - '0';
ln = in[i+1] > '9' ? in[i+1] - 'A' + 10 : in[i+1] - '0';
out[t] = (hn << 4 ) | ln;
}
return out;
}
int main(int argc, char **argv)
{
csh handle;
cs_insn *insn;
size_t count, j;
uint32_t op;
int n;
if (argc != 2) {
printf("./decode <4 bytes hex string> \n");
return -1;
}
char *ascii = argv[1];
if (!strncmp(ascii, "0x", 2)) {
ascii += 2;
}
if (strlen(ascii) != 8) {
printf("wrong instruction length\n");
return -2;
}
for (n = 0; n < 8; n++) {
if (!isxdigit(ascii[n])) {
printf("not hex string (pos %d)\n", n);
return -3;
}
}
printf("%s\n", ascii);
hex_decode(ascii, 8, (char*)&op);
op = bswap_32(op);
if (cs_open(CS_ARCH_ARM, CS_MODE_ARM, &handle)) {
printf("ERROR: Failed to initialize engine!\n");
return -1;
}
cs_option(handle, CS_OPT_DETAIL, CS_OPT_ON);
count = cs_disasm(handle, (char*)&op, 4, 0, 0, &insn);
if (count <= 0) {
printf("ERROR: Failed to disassemble given code!\n");
goto Exit;
}
for (j = 0; j < count; j++) {
cs_insn *i = &(insn[j]);
printf("0x%"PRIx64":\t%s %s\n", i->address, i->mnemonic, i->op_str);
cs_detail *detail = i->detail;
printf("subtracted for op 0: %d\n", detail->arm.operands[0].subtracted);
printf("subtracted for op 1: %d\n", detail->arm.operands[1].subtracted);
if (detail->arm.operands[1].type == ARM_OP_MEM) {
printf("base for op 1: %d\n", detail->arm.operands[1].mem.base);
printf("index for op 1: %d\n", detail->arm.operands[1].mem.index);
printf("scale for op 1: %d\n", detail->arm.operands[1].mem.scale);
printf("disp for op 1: %d\n", detail->arm.operands[1].mem.disp);
}
//cs_arm *arm = &(detail->arm);
if (detail->regs_read_count > 0) {
printf("\tImplicit registers read: ");
for (n = 0; n < detail->regs_read_count; n++) {
printf("%s ", cs_reg_name(handle, detail->regs_read[n]));
}
printf("\n");
}
if (detail->groups_count > 0) {
printf("\tThis instruction belongs to groups: ");
for (n = 0; n < detail->groups_count; n++) {
printf("%u ", detail->groups[n]);
}
printf("\n");
}
}
cs_free(insn, count);
Exit:
cs_close(&handle);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment