7 #define USHORT uint16_t
10 ULONG isdata
[1000000]; /* each bit defines one byte as: code=0, data=1 */
12 extern void dis_asm(ULONG off
, ULONG val
, char *stg
);
14 int static inline le2int(unsigned char* buf
)
16 int32_t res
= (buf
[3] << 24) | (buf
[2] << 16) | (buf
[1] << 8) | buf
[0];
21 int main(int argc
, char **argv
)
26 ULONG pos
, sz
, val
, loop
;
30 if(argc
== 1 || strcmp(argv
[1], "--help") == 0)
31 { printf("Usage: arm_disass [input file]\n");
32 printf(" disassembles input file to 'disasm.txt'\n");
36 in
= fopen(argv
[1], "rb");
38 { printf("Cannot open %s", argv
[1]);
42 out
= fopen("disasm.txt", "w");
43 if(out
== NULL
) exit(-1);
45 fseek(in
, 0, SEEK_END
);
48 /* first loop only sets data/code tags */
49 for(loop
=0; loop
<2; loop
++)
51 for(pos
=0; pos
<sz
; pos
+=4)
53 /* clear disassembler string start */
55 /* read next code dword */
56 fseek(in
, pos
, SEEK_SET
);
61 /* check for data tag set: if 1 byte out of 4 is marked => assume data */
62 if((isdata
[pos
>>5] & (0xf << (pos
& 31))) || (val
& 0xffff0000) == 0)
64 sprintf(stg
, "%6x: %08x", pos
, val
);
68 dis_asm(pos
, val
, stg
);
70 /* check for instant mov operation */
71 if(memcmp(stg
+17, "mov ", 4) == 0 && (ptr
=strstr(stg
, "0x")) != NULL
)
73 regid
= *(USHORT
*)(stg
+22);
75 sscanf(ptr
+2, "%x", &offset
);
80 /* check for add/sub operation */
81 if((ptr
=strstr(stg
, "0x")) != NULL
82 && (memcmp(stg
+17, "add ", 4) == 0 || memcmp(stg
+17, "sub ", 4) == 0))
84 if(regid
== *(USHORT
*)(stg
+22) && regid
== *(USHORT
*)(stg
+26))
86 sscanf(ptr
+2, "%x", &offset1
);
90 if(memcmp(stg
+17, "add ", 4) == 0) offset
+= offset1
;
91 else offset
-= offset1
;
93 /* add result to disassembler string */
94 sprintf(stg
+strlen(stg
), " <- 0x%x", offset
);
102 /* check for const data */
103 if(memcmp(stg
+26, "[pc, ", 5) == 0 && (ptr
=strstr(stg
, "0x")) != NULL
)
105 sscanf(ptr
+2, "%x", &offset
);
110 isdata
[(pos
+offset
+8)>>5] |= 1 << ((pos
+offset
+8) & 31);
112 /* add const data to disassembler string */
113 fseek(in
, pos
+offset
+8, SEEK_SET
);
114 fread(&buf
, 1, 4, in
);
115 offset
= le2int(buf
);
117 sprintf(stg
+strlen(stg
), " <- 0x%x", offset
);
121 /* remove trailing spaces */
122 while(stg
[strlen(stg
)-1] == 32)
123 stg
[strlen(stg
)-1] = 0;
126 fprintf(out
, "%s\n", stg
);