1 /* udis86 - libudis86/syn.c
3 * Copyright (c) 2002-2013 Vivek Thampi
6 * Redistribution and use in source and binary forms, with or without modification,
7 * are permitted provided that the following conditions are met:
9 * * Redistributions of source code must retain the above copyright notice,
10 * this list of conditions and the following disclaimer.
11 * * Redistributions in binary form must reproduce the above copyright notice,
12 * this list of conditions and the following disclaimer in the documentation
13 * and/or other materials provided with the distribution.
15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
19 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
22 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 /* -----------------------------------------------------------------------------
32 * Intel Register Table - Order Matters (types.h)!
33 * -----------------------------------------------------------------------------
35 const char* ud_reg_tab
[] =
37 "al", "cl", "dl", "bl",
38 "ah", "ch", "dh", "bh",
39 "spl", "bpl", "sil", "dil",
40 "r8b", "r9b", "r10b", "r11b",
41 "r12b", "r13b", "r14b", "r15b",
43 "ax", "cx", "dx", "bx",
44 "sp", "bp", "si", "di",
45 "r8w", "r9w", "r10w", "r11w",
46 "r12w", "r13w" , "r14w", "r15w",
48 "eax", "ecx", "edx", "ebx",
49 "esp", "ebp", "esi", "edi",
50 "r8d", "r9d", "r10d", "r11d",
51 "r12d", "r13d", "r14d", "r15d",
53 "rax", "rcx", "rdx", "rbx",
54 "rsp", "rbp", "rsi", "rdi",
55 "r8", "r9", "r10", "r11",
56 "r12", "r13", "r14", "r15",
58 "es", "cs", "ss", "ds",
61 "cr0", "cr1", "cr2", "cr3",
62 "cr4", "cr5", "cr6", "cr7",
63 "cr8", "cr9", "cr10", "cr11",
64 "cr12", "cr13", "cr14", "cr15",
66 "dr0", "dr1", "dr2", "dr3",
67 "dr4", "dr5", "dr6", "dr7",
68 "dr8", "dr9", "dr10", "dr11",
69 "dr12", "dr13", "dr14", "dr15",
71 "mm0", "mm1", "mm2", "mm3",
72 "mm4", "mm5", "mm6", "mm7",
74 "st0", "st1", "st2", "st3",
75 "st4", "st5", "st6", "st7",
77 "xmm0", "xmm1", "xmm2", "xmm3",
78 "xmm4", "xmm5", "xmm6", "xmm7",
79 "xmm8", "xmm9", "xmm10", "xmm11",
80 "xmm12", "xmm13", "xmm14", "xmm15",
87 ud_syn_rel_target(struct ud
*u
, struct ud_operand
*opr
)
89 const uint64_t trunc_mask
= 0xffffffffffffffffull
>> (64 - u
->opr_mode
);
91 case 8 : return (u
->pc
+ opr
->lval
.sbyte
) & trunc_mask
;
92 case 16: return (u
->pc
+ opr
->lval
.sword
) & trunc_mask
;
93 case 32: return (u
->pc
+ opr
->lval
.sdword
) & trunc_mask
;
94 default: UD_ASSERT(!"invalid relative offset size.");
102 * Printf style function for printing translated assembly
103 * output. Returns the number of characters written and
104 * moves the buffer pointer forward. On an overflow,
105 * returns a negative number and truncates the output.
108 ud_asmprintf(struct ud
*u
, const char *fmt
, ...)
114 avail
= u
->asm_buf_size
- u
->asm_buf_fill
- 1 /* nullchar */;
115 ret
= vsnprintf((char*) u
->asm_buf
+ u
->asm_buf_fill
, avail
, fmt
, ap
);
116 if (ret
< 0 || ret
> avail
) {
117 u
->asm_buf_fill
= u
->asm_buf_size
- 1;
119 u
->asm_buf_fill
+= ret
;
127 ud_syn_print_addr(struct ud
*u
, uint64_t addr
)
129 const char *name
= NULL
;
130 if (u
->sym_resolver
) {
132 name
= u
->sym_resolver(u
, addr
, &offset
);
135 ud_asmprintf(u
, "%s%+" FMT64
"d", name
, offset
);
137 ud_asmprintf(u
, "%s", name
);
142 ud_asmprintf(u
, "0x%" FMT64
"x", addr
);
147 ud_syn_print_imm(struct ud
* u
, const struct ud_operand
*op
)
150 if (op
->_oprcode
== OP_sI
&& op
->size
!= u
->opr_mode
) {
152 v
= (int64_t)op
->lval
.sbyte
;
154 UD_ASSERT(op
->size
== 32);
155 v
= (int64_t)op
->lval
.sdword
;
157 if (u
->opr_mode
< 64) {
158 v
= v
& ((1ull << u
->opr_mode
) - 1ull);
162 case 8 : v
= op
->lval
.ubyte
; break;
163 case 16: v
= op
->lval
.uword
; break;
164 case 32: v
= op
->lval
.udword
; break;
165 case 64: v
= op
->lval
.uqword
; break;
166 default: UD_ASSERT(!"invalid offset"); v
= 0; /* keep cc happy */
169 ud_asmprintf(u
, "0x%" FMT64
"x", v
);
174 ud_syn_print_mem_disp(struct ud
* u
, const struct ud_operand
*op
, int sign
)
176 UD_ASSERT(op
->offset
!= 0);
177 if (op
->base
== UD_NONE
&& op
->index
== UD_NONE
) {
179 UD_ASSERT(op
->scale
== UD_NONE
&& op
->offset
!= 8);
180 /* unsigned mem-offset */
181 switch (op
->offset
) {
182 case 16: v
= op
->lval
.uword
; break;
183 case 32: v
= op
->lval
.udword
; break;
184 case 64: v
= op
->lval
.uqword
; break;
185 default: UD_ASSERT(!"invalid offset"); v
= 0; /* keep cc happy */
187 ud_asmprintf(u
, "0x%" FMT64
"x", v
);
190 UD_ASSERT(op
->offset
!= 64);
191 switch (op
->offset
) {
192 case 8 : v
= op
->lval
.sbyte
; break;
193 case 16: v
= op
->lval
.sword
; break;
194 case 32: v
= op
->lval
.sdword
; break;
195 default: UD_ASSERT(!"invalid offset"); v
= 0; /* keep cc happy */
198 ud_asmprintf(u
, "-0x%" FMT64
"x", -v
);
200 ud_asmprintf(u
, "%s0x%" FMT64
"x", sign
? "+" : "", v
);
206 vim: set ts=2 sw=2 expandtab