mirror of
https://github.com/openharmony/third_party_elfutils.git
synced 2026-07-19 19:43:34 -04:00
Add x86-64 disassembler support.
This commit is contained in:
@@ -1,3 +1,13 @@
|
||||
2008-01-08 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* Makefile.am: Add x86-64 disassembler.
|
||||
* x86_64_init.c (x86_64_init): Hook up disassembler.
|
||||
|
||||
2007-12-28 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* Makefile.am: Add x86 disassembler.
|
||||
* i386_init.c (i386_init): Hook up disassembler.
|
||||
|
||||
2007-12-15 Roland McGrath <roland@redhat.com>
|
||||
|
||||
* ppc_regs.c (ppc_register_info): Return "spefscr", not "spr512".
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
## Process this file with automake to create Makefile.in
|
||||
##
|
||||
## Copyright (C) 2000-2006, 2007 Red Hat, Inc.
|
||||
## Copyright (C) 2000-2006, 2007, 2008 Red Hat, Inc.
|
||||
## This file is part of Red Hat elfutils.
|
||||
##
|
||||
## Red Hat elfutils is free software; you can redistribute it and/or modify
|
||||
@@ -72,8 +72,7 @@ am_libebl_sh_pic_a_OBJECTS = $(sh_SRCS:.c=.os)
|
||||
|
||||
x86_64_SRCS = x86_64_init.c x86_64_symbol.c x86_64_corenote.c \
|
||||
x86_64_retval.c x86_64_regs.c i386_auxv.c
|
||||
# XXX Not yet
|
||||
# cpu_x86_64 = ../libcpu/libcpu_x86_64.a
|
||||
cpu_x86_64 = ../libcpu/libcpu_x86_64.a
|
||||
libebl_x86_64_pic_a_SOURCES = $(x86_64_SRCS)
|
||||
am_libebl_x86_64_pic_a_OBJECTS = $(x86_64_SRCS:.c=.os)
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/* Initialization of x86-64 specific backend library.
|
||||
Copyright (C) 2002, 2005, 2006, 2007 Red Hat, Inc.
|
||||
Copyright (C) 2002, 2005, 2006, 2007, 2008 Red Hat, Inc.
|
||||
This file is part of Red Hat elfutils.
|
||||
Written by Ulrich Drepper <drepper@redhat.com>, 2002.
|
||||
|
||||
@@ -54,8 +54,7 @@ x86_64_init (elf, machine, eh, ehlen)
|
||||
HOOK (eh, return_value_location);
|
||||
HOOK (eh, register_info);
|
||||
HOOK (eh, auxv_info);
|
||||
// XXX Not yet.
|
||||
// HOOK (eh, disasm);
|
||||
HOOK (eh, disasm);
|
||||
|
||||
return MODVERSION;
|
||||
}
|
||||
|
||||
@@ -1,3 +1,12 @@
|
||||
2008-01-08 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* Makefile.am: Enable x86-64 again.
|
||||
* defs/i386: Lots of changes for x86-64.
|
||||
* i386_data.h: Add support for use in x86-64 disassembler.
|
||||
* i386_disasm.c: Likewise.
|
||||
* i386_parse.y: Likewise.
|
||||
* defs/x86_64: Removed.
|
||||
|
||||
2008-01-04 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* defs/i386: Cleanups, remove masks which are not needed.
|
||||
|
||||
+7
-9
@@ -1,6 +1,6 @@
|
||||
## Process this file with automake to create Makefile.in
|
||||
##
|
||||
## Copyright (C) 2002, 2004, 2005, 2007 Red Hat, Inc.
|
||||
## Copyright (C) 2002, 2004, 2005, 2007, 2008 Red Hat, Inc.
|
||||
## This file is part of Red Hat elfutils.
|
||||
##
|
||||
## Red Hat elfutils is free software; you can redistribute it and/or modify
|
||||
@@ -43,13 +43,11 @@ if MUDFLAP
|
||||
libmudflap = -lmudflap
|
||||
endif
|
||||
|
||||
# XXX x86-64 uncommented for now.
|
||||
noinst_LIBRARIES = libcpu_i386.a# libcpu_x86_64.a
|
||||
noinst_LIBRARIES = libcpu_i386.a libcpu_x86_64.a
|
||||
noinst_PROGRAMS = i386_gendis
|
||||
|
||||
libcpu_i386_a_SOURCES = i386_disasm.c
|
||||
# XXX Unused for now.
|
||||
#libcpu_x86_64_a_SOURCES = x86_64_disasm.c
|
||||
libcpu_x86_64_a_SOURCES = x86_64_disasm.c
|
||||
|
||||
i386_gendis_SOURCES = i386_gendis.c i386_lex.l i386_parse.y
|
||||
|
||||
@@ -58,11 +56,11 @@ x86_64_disasm.o: x86_64.mnemonics x86_64_dis.h i386_disasm.c
|
||||
|
||||
i386_dis.h: i386_gendis $(srcdir)/defs/i386
|
||||
m4 -Di386 -DDISASSEMBLER $(srcdir)/defs/i386 | ./i386_gendis - > $@
|
||||
x86_64_dis.h: i386_gendis $(srcdir)/defs/x86_64
|
||||
m4 -Dx86_64 -DDISASSEMBLER $(srcdir)/defs/x86_64 | ./i386_gendis - > $@
|
||||
x86_64_dis.h: i386_gendis $(srcdir)/defs/i386
|
||||
m4 -Dx86_64 -DDISASSEMBLER $(srcdir)/defs/i386 | ./i386_gendis - > $@
|
||||
|
||||
i386.mnemonics x86_64.mnemonics: %.mnemonics: $(srcdir)/defs/%
|
||||
m4 -D$(<F) -DDISASSEMBLER $^ \
|
||||
i386.mnemonics x86_64.mnemonics: %.mnemonics: $(srcdir)/defs/i386
|
||||
m4 -D$(@:.mnemonics=) -DDISASSEMBLER $^ \
|
||||
| sed '1,/^%%/d;/^#/d;/^[[:space:]]*$$/d;s/[^:]*:\([^[:space:]]*\).*/MNE(\1)/;s/{[^}]*}//g;/INVALID/d' \
|
||||
| sort -u > $@
|
||||
|
||||
|
||||
+100
-47
@@ -1,6 +1,8 @@
|
||||
%mask {s} 1
|
||||
%mask {w} 1
|
||||
%mask {w1} 1
|
||||
%mask {W1} 1
|
||||
%mask {W2} 1
|
||||
dnl floating point reg suffix
|
||||
%mask {D} 1
|
||||
%mask {imm8} 8
|
||||
@@ -8,6 +10,7 @@ dnl floating point reg suffix
|
||||
%mask {imm16} 16
|
||||
%mask {reg} 3
|
||||
%mask {reg16} 3
|
||||
%mask {reg64} 3
|
||||
%mask {tttn} 4
|
||||
%mask {mod} 2
|
||||
%mask {moda} 2
|
||||
@@ -17,6 +20,8 @@ dnl like {r_m} but referencing byte register
|
||||
%mask {8r_m} 3
|
||||
dnl like {r_m} but referencing 16-bit register
|
||||
%mask {16r_m} 3
|
||||
dnl like {r_m} but referencing 32- or 64-bit register
|
||||
%mask {64r_m} 3
|
||||
%mask {disp8} 8
|
||||
dnl imm really is 8/16/32 bit depending on the situation.
|
||||
%mask {imm} 8
|
||||
@@ -62,18 +67,18 @@ ifdef(`i386',
|
||||
0001010{w},{imm}:adc {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}010{r_m},{imm}:adc{w} {imm}{w},{mod}{r_m}{w}
|
||||
1000001{w},{mod}010{r_m},{imms8}:adc{w} {imms8},{mod}{r_m}
|
||||
0001000{w},{mod}{reg}{r_m}:adc {reg}{w},{mod}{r_m}
|
||||
0001001{w},{mod}{reg}{r_m}:adc {mod}{r_m},{reg}{w}
|
||||
0001000{w},{mod}{reg}{r_m}:adc {reg}{w},{mod}{r_m}{w}
|
||||
0001001{w},{mod}{reg}{r_m}:adc {mod}{r_m}{w},{reg}{w}
|
||||
0000010{w},{imm}:add {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}000{r_m},{imm}:add{w} {imm}{w},{mod}{r_m}{w}
|
||||
10000011,{mod}000{r_m},{imms8}:add{w0} {imms8},{mod}{r_m}
|
||||
0000000{w},{mod}{reg}{r_m}:add {reg}{w},{mod}{r_m}
|
||||
0000001{w},{mod}{reg}{r_m}:add {mod}{r_m},{reg}{w}
|
||||
0000000{w},{mod}{reg}{r_m}:add {reg}{w},{mod}{r_m}{w}
|
||||
0000001{w},{mod}{reg}{r_m}:add {mod}{r_m}{w},{reg}{w}
|
||||
01100110,00001111,11010000,{Mod}{xmmreg}{R_m}:addsubpd {Mod}{R_m},{xmmreg}
|
||||
11110010,00001111,11010000,{Mod}{xmmreg}{R_m}:addsubps {Mod}{R_m},{xmmreg}
|
||||
0010010{w},{imm}:and {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}100{r_m},{imm}:and{w} {imm}{w},{mod}{r_m}{w}
|
||||
1000001{w},{mod}100{r_m},{imms}:and{w} {imms},{mod}{r_m}
|
||||
1000001{w},{mod}100{r_m},{imms8}:and{w} {imms8},{mod}{r_m}
|
||||
0010000{w},{mod}{reg}{r_m}:and {reg}{w},{mod}{r_m}{w}
|
||||
0010001{w},{mod}{reg}{r_m}:and {mod}{r_m}{w},{reg}{w}
|
||||
01100110,00001111,01010100,{Mod}{xmmreg}{R_m}:andpd {Mod}{R_m},{xmmreg}
|
||||
@@ -83,6 +88,8 @@ ifdef(`i386',
|
||||
ifdef(`i386',
|
||||
`01100011,{mod}{reg16}{r_m}:arpl {reg16},{mod}{r_m}
|
||||
01100010,{moda}{reg}{r_m}:bound {reg},{moda}{r_m}
|
||||
',
|
||||
`01100011,{mod}{reg64}{r_m}:movslq {mod}{r_m},{reg64}
|
||||
')dnl
|
||||
00001111,10111100,{mod}{reg}{r_m}:bsf {mod}{r_m},{reg}
|
||||
00001111,10111101,{mod}{reg}{r_m}:bsr {mod}{r_m},{reg}
|
||||
@@ -95,12 +102,12 @@ ifdef(`i386',
|
||||
00001111,10111010,{mod}110{r_m},{imm8}:btr{w} {imm8},{mod}{r_m}
|
||||
00001111,10101011,{mod}{reg}{r_m}:bts {reg},{mod}{r_m}
|
||||
00001111,10111010,{mod}101{r_m},{imm8}:bts{w} {imm8},{mod}{r_m}
|
||||
11101000,{rel}:call {rel}
|
||||
11111111,{mod}010{r_m}:call *{mod}{r_m}
|
||||
11101000,{rel}:call{W} {rel}
|
||||
11111111,{mod}010{64r_m}:call{W} *{mod}{64r_m}
|
||||
ifdef(`i386',
|
||||
`10011010,{absval},{sel}:lcall {sel},{absval}
|
||||
')dnl
|
||||
11111111,{mod}011{r_m}:lcall *{mod}{r_m}
|
||||
11111111,{mod}011{64r_m}:lcall{W} *{mod}{64r_m}
|
||||
# SPECIAL 10011000:[{rex.w}?cltq:{dpfx}?cbtw:cwtl]
|
||||
10011000:INVALID
|
||||
# SPECIAL 10011001:[{rew.w}?cqto:{dpfx}?cltd:cwtd]
|
||||
@@ -120,10 +127,17 @@ ifdef(`i386',
|
||||
10000011,{mod}111{r_m},{imms8}:cmp{w0} {imms8},{mod}{r_m}
|
||||
0011100{w},{mod}{reg}{r_m}:cmp {reg}{w},{mod}{r_m}{w}
|
||||
0011101{w},{mod}{reg}{r_m}:cmp {mod}{r_m}{w},{reg}{w}
|
||||
11110010,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:cmpsd {imm8},{Mod}{R_m},{xmmreg}
|
||||
ifdef(`ASSEMBLER',
|
||||
`11110010,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:cmpsd {imm8},{Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:cmpss {imm8},{Mod}{R_m},{xmmreg}
|
||||
01100110,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:cmppd {imm8},{Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:cmpps {imm8},{Mod}{R_m},{xmmreg}
|
||||
',
|
||||
`11110010,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:INVALID {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:INVALID {Mod}{R_m},{xmmreg}
|
||||
01100110,00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:INVALID {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},{imm8}:INVALID {Mod}{R_m},{xmmreg}
|
||||
')dnl
|
||||
1010011{w}:{RE}cmps{w} {es_di},{ds_si}
|
||||
00001111,1011000{w},{mod}{reg}{r_m}:cmpxchg {reg}{w},{mod}{r_m}{w}
|
||||
ifdef(`i386',
|
||||
@@ -146,7 +160,7 @@ ifdef(`i386',
|
||||
')dnl
|
||||
1111011{w},{mod}110{r_m}:div{w} {mod}{r_m}{w}
|
||||
00001111,01110111:emms
|
||||
11001000,{imm16},{imm8}:enter {imm16},{imm8}
|
||||
11001000,{imm16},{imm8}:enter{W} {imm16},{imm8}
|
||||
11011001,11010000:fnop
|
||||
11011001,11100000:fchs
|
||||
11011001,11100001:fabs
|
||||
@@ -342,33 +356,44 @@ ifdef(`ASSEMBLER',
|
||||
0110110{w}:{R}ins{w} {dx},{es_di}
|
||||
11001101,{imm8}:int {imm8}
|
||||
11001100:int3
|
||||
11001110:into
|
||||
ifdef(`i386',
|
||||
`11001110:into
|
||||
')dnl
|
||||
00001111,00001000:invd
|
||||
# ORDER
|
||||
00001111,00000001,11111000:swapgs
|
||||
00001111,00000001,{mod}111{r_m}:invlpg {mod}{r_m}
|
||||
# ORDER END
|
||||
11001111:iret{W}
|
||||
11001111:iret{W1}
|
||||
0111{tttn},{disp8}:j{tttn} {disp8}
|
||||
00001111,1000{tttn},{rel}:j{tttn} {rel}
|
||||
00001111,1001{tttn},{mod}000{8r_m}:set{tttn} {mod}{8r_m}
|
||||
# SPECIAL 11100011,{disp8}:[{dpfx}?jcxz:jecxz] {disp8}
|
||||
11100011,{disp8}:INVALID {disp8}
|
||||
11101011,{disp8}:jmp {disp8}
|
||||
11101001,{rel}:jmp {rel}
|
||||
11111111,{mod}100{r_m}:jmp *{mod}{r_m}
|
||||
11101001,{rel}:jmp{W} {rel}
|
||||
11111111,{mod}100{64r_m}:jmp{W} *{mod}{64r_m}
|
||||
11101010,{absval},{sel}:ljmp {sel},{absval}
|
||||
11111111,{mod}101{r_m}:ljmp *{mod}{r_m}
|
||||
11111111,{mod}101{64r_m}:ljmp{W} *{mod}{64r_m}
|
||||
10011111:lahf
|
||||
00001111,00000010,{mod}{reg}{16r_m}:lar {mod}{16r_m},{reg}
|
||||
11000101,{mod}{reg}{r_m}:lds {mod}{r_m},{reg}
|
||||
ifdef(`i386',
|
||||
`11000101,{mod}{reg}{r_m}:lds {mod}{r_m},{reg}
|
||||
')dnl
|
||||
10001101,{mod}{reg}{r_m}:lea {mod}{r_m},{reg}
|
||||
11001001:leave
|
||||
11000100,{mod}{reg}{r_m}:les {mod}{r_m},{reg}
|
||||
11001001:leave{W}
|
||||
ifdef(`i386',
|
||||
`11000100,{mod}{reg}{r_m}:les {mod}{r_m},{reg}
|
||||
')dnl
|
||||
00001111,10110100,{mod}{reg}{r_m}:lfs {mod}{r_m},{reg}
|
||||
00001111,00000001,{mod}010{r_m}:lgdt{w0} {mod}{r_m}
|
||||
00001111,10110101,{mod}{reg}{r_m}:lgs {mod}{r_m},{reg}
|
||||
ifdef(`i386',
|
||||
`00001111,00000001,{mod}010{r_m}:lgdt{w0} {mod}{r_m}
|
||||
00001111,00000001,{mod}011{r_m}:lidt{w0} {mod}{r_m}
|
||||
',
|
||||
`00001111,00000001,{mod}010{r_m}:lgdt {mod}{r_m}
|
||||
00001111,00000001,{mod}011{r_m}:lidt {mod}{r_m}
|
||||
')dnl
|
||||
00001111,00000000,{mod}010{16r_m}:lldt {mod}{16r_m}
|
||||
00001111,00000001,{mod}110{16r_m}:lmsw {mod}{16r_m}
|
||||
11110000:lock
|
||||
@@ -385,10 +410,10 @@ ifdef(`ASSEMBLER',
|
||||
1011{w}{reg},{imm}:mov {imm}{w},{reg}{w}
|
||||
1010000{w},{abs}:mov {abs},{ax}{w}
|
||||
1010001{w},{abs}:mov {ax}{w},{abs}
|
||||
00001111,00100000,11{ccc}{reg}:mov {ccc},{reg}
|
||||
00001111,00100010,11{ccc}{reg}:mov {reg},{ccc}
|
||||
00001111,00100001,11{ddd}{reg}:mov {ddd},{reg}
|
||||
00001111,00100011,11{ddd}{reg}:mov {reg},{ddd}
|
||||
00001111,00100000,11{ccc}{reg64}:mov {ccc},{reg64}
|
||||
00001111,00100010,11{ccc}{reg64}:mov {reg64},{ccc}
|
||||
00001111,00100001,11{ddd}{reg64}:mov {ddd},{reg64}
|
||||
00001111,00100011,11{ddd}{reg64}:mov {reg64},{ddd}
|
||||
10001100,{mod}{sreg3}{r_m}:mov {sreg3},{mod}{r_m}
|
||||
10001110,{mod}{sreg3}{r_m}:mov {mod}{r_m},{sreg3}
|
||||
1010010{w}:{R}movs{w} {ds_si},{es_di}
|
||||
@@ -398,12 +423,8 @@ ifdef(`ASSEMBLER',
|
||||
00001111,10110111,{mod}{reg}{16r_m}:movzwl {mod}{16r_m},{reg}
|
||||
1111011{w},{mod}100{r_m}:mul{w} {mod}{r_m}{w}
|
||||
1111011{w},{mod}011{r_m}:neg{w} {mod}{r_m}{w}
|
||||
ifdef(`ASSEMBLER',
|
||||
`10010000:nop
|
||||
11110011,10010000:pause
|
||||
',
|
||||
`10010000:{R}INVALID
|
||||
')dnl
|
||||
10010000:nop
|
||||
1111011{w},{mod}010{r_m}:not{w} {mod}{r_m}{w}
|
||||
0000100{w},{mod}{reg}{r_m}:or {reg}{w},{mod}{r_m}{w}
|
||||
0000101{w},{mod}{reg}{r_m}:or {mod}{r_m}{w},{reg}{w}
|
||||
@@ -413,17 +434,36 @@ ifdef(`ASSEMBLER',
|
||||
1110011{w},{imm8}:out {ax}{w},{imm8}
|
||||
1110111{w}:out {ax}{w},{dx}
|
||||
0110111{w}:{R}outs{w} {ds_si},{dx}
|
||||
10001111,{mod}000{r_m}:pop{w} {mod}{r_m}
|
||||
01011{reg}:pop {reg}
|
||||
00001111,10{sreg3}001:pop {sreg3}
|
||||
01100001:popa{W}
|
||||
ifdef(`i386',
|
||||
`10001111,{mod}000{r_m}:pop{w} {mod}{r_m}
|
||||
',
|
||||
# XXX This is not the cleanest way...
|
||||
`10001111,11000{reg64}:pop {reg64}
|
||||
10001111,{mod}000{r_m}:pop{W} {mod}{r_m}
|
||||
')dnl
|
||||
00001111,10{sreg3}001:pop{W} {sreg3}
|
||||
10011101:popf{W}
|
||||
11111111,{mod}110{r_m}:push{w} {mod}{r_m}
|
||||
01010{reg}:push {reg}
|
||||
011010{s}0,{imm}:push {imm}{s}
|
||||
# XXX This is not the cleanest way...
|
||||
ifdef(`i386',
|
||||
`11111111,{mod}110{r_m}:push{w} {mod}{r_m}
|
||||
',
|
||||
`11111111,11110{reg64}:push {reg64}
|
||||
11111111,{mod}110{r_m}:pushq {mod}{r_m}
|
||||
')dnl
|
||||
ifdef(`i386',
|
||||
`01010{reg}:push {reg}
|
||||
01011{reg}:pop {reg}
|
||||
',
|
||||
`01010{reg64}:push {reg64}
|
||||
01011{reg64}:pop {reg64}
|
||||
')dnl
|
||||
011010{s}0,{imm}:push{W} {imm}{s}
|
||||
000{sreg2}110:push {sreg2}
|
||||
00001111,10{sreg3}000:push {sreg3}
|
||||
01100000:pusha{W}
|
||||
00001111,10{sreg3}000:push{W} {sreg3}
|
||||
ifdef(`i386',
|
||||
`01100000:pusha{W}
|
||||
01100001:popa{W}
|
||||
')dnl
|
||||
10011100:pushf{W}
|
||||
1101000{w},{mod}010{r_m}:rcl{w} {mod}{r_m}{w}
|
||||
1101001{w},{mod}010{r_m}:rcl{w} %cl,{mod}{r_m}{w}
|
||||
@@ -434,8 +474,8 @@ ifdef(`ASSEMBLER',
|
||||
00001111,00110010:rdmsr
|
||||
00001111,00110011:rdpmc
|
||||
00001111,00110001:rdtsc
|
||||
11000011:ret
|
||||
11000010,{imm16}:ret {imm16}
|
||||
11000011:ret{W}
|
||||
11000010,{imm16}:ret{W} {imm16}
|
||||
11001011:lret
|
||||
11001010,{imm16}:lret {imm16}
|
||||
1101000{w},{mod}000{r_m}:rol{w} {mod}{r_m}{w}
|
||||
@@ -453,7 +493,7 @@ ifdef(`ASSEMBLER',
|
||||
0001101{w},{mod}{reg}{r_m}:sbb {mod}{r_m}{w},{reg}{w}
|
||||
0001110{w},{imm}:sbb {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}011{r_m},{imm}:sbb{w} {imm}{w},{mod}{r_m}{w}
|
||||
1000001{w},{mod}011{r_m},{imms}:sbb{w} {imms},{mod}{r_m}
|
||||
1000001{w},{mod}011{r_m},{imms8}:sbb{w} {imms8},{mod}{r_m}
|
||||
1010111{w}:{RE}scas {es_di},{ax}{w}
|
||||
00001111,1001{tttn},{mod}000{r_m}:set{tttn} {mod}{r_m}
|
||||
1101000{w},{mod}100{r_m}:shl{w} {mod}{r_m}{w}
|
||||
@@ -471,14 +511,27 @@ ifdef(`ASSEMBLER',
|
||||
00001111,00000001,11000010:vmlaunch
|
||||
00001111,00000001,11000011:vmresume
|
||||
00001111,00000001,11000100:vmxoff
|
||||
00001111,01111000,{mod}{reg}{r_m}:vmread {reg},{mod}{r_m}
|
||||
00001111,01111001,{mod}{reg}{r_m}:vmwrite {mod}{r_m},{reg}
|
||||
00001111,00000001,{mod}000{r_m}:sgdtl {mod}{r_m}
|
||||
00001111,01111000,{mod}{reg64}{64r_m}:vmread {reg64},{mod}{64r_m}
|
||||
00001111,01111001,{mod}{reg64}{64r_m}:vmwrite {mod}{64r_m},{reg64}
|
||||
ifdef(`i386',
|
||||
`00001111,00000001,{mod}000{r_m}:sgdtl {mod}{r_m}
|
||||
',
|
||||
`00001111,00000001,{mod}000{r_m}:sgdt {mod}{r_m}
|
||||
')dnl
|
||||
# ORDER END
|
||||
# ORDER
|
||||
00001111,00000001,11001000:monitor %eax,%ecx,%edx
|
||||
ifdef(`i386',
|
||||
`00001111,00000001,11001000:monitor %eax,%ecx,%edx
|
||||
00001111,00000001,11001001:mwait %eax,%ecx
|
||||
00001111,00000001,{mod}001{r_m}:sidtl {mod}{r_m}
|
||||
',
|
||||
`00001111,00000001,11001000:monitor %rax,%rcx,%rdx
|
||||
00001111,00000001,11001001:mwait %rax,%rcx
|
||||
')dnl
|
||||
ifdef(`i386',
|
||||
`00001111,00000001,{mod}001{r_m}:sidtl {mod}{r_m}
|
||||
',
|
||||
`00001111,00000001,{mod}001{r_m}:sidt {mod}{r_m}
|
||||
')dnl
|
||||
# ORDER END
|
||||
00001111,00000000,{mod}000{r_m}:sldt {mod}{r_m}
|
||||
00001111,00000001,{mod}100{r_m}:smsw {mod}{r_m}
|
||||
@@ -491,7 +544,7 @@ ifdef(`ASSEMBLER',
|
||||
0010101{w},{mod}{reg}{r_m}:sub {mod}{r_m}{w},{reg}{w}
|
||||
0010110{w},{imm}:sub {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}101{r_m},{imm}:sub{w} {imm}{w},{mod}{r_m}{w}
|
||||
1000001{w},{mod}101{r_m},{imms}:sub{w} {imms},{mod}{r_m}
|
||||
1000001{w},{mod}101{r_m},{imms8}:sub{w} {imms8},{mod}{r_m}
|
||||
1000010{w},{mod}{reg}{r_m}:test {reg}{w},{mod}{r_m}{w}
|
||||
1010100{w},{imm}:test {imm}{w},{ax}{w}
|
||||
1111011{w},{mod}000{r_m},{imm}:test{w} {imm}{w},{mod}{r_m}{w}
|
||||
@@ -515,7 +568,7 @@ ifdef(`ASSEMBLER',
|
||||
0011001{w},{mod}{reg}{r_m}:xor {mod}{r_m}{w},{reg}{w}
|
||||
0011010{w},{imm}:xor {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}110{r_m},{imm}:xor{w} {imm}{w},{mod}{r_m}{w}
|
||||
1000001{w},{mod}110{r_m},{imms}:xor{w} {imms},{mod}{r_m}
|
||||
1000001{w},{mod}110{r_m},{imms8}:xor{w} {imms8},{mod}{r_m}
|
||||
00001111,01110111:emms
|
||||
01100110,00001111,11011011,{Mod}{xmmreg}{R_m}:pand {Mod}{R_m},{xmmreg}
|
||||
00001111,11011011,{MOD}{mmxreg}{R_M}:pand {MOD}{R_M},{mmxreg}
|
||||
|
||||
@@ -1,341 +0,0 @@
|
||||
%mask {s} 1
|
||||
%mask {w} 1
|
||||
%mask {D} 1
|
||||
%mask {imm8} 8
|
||||
%mask {imm16} 16
|
||||
%mask {reg} 3
|
||||
%mask {tttn} 4
|
||||
%mask {gg} 2
|
||||
%mask {mod} 2
|
||||
%mask {MOD} 2
|
||||
%mask {r_m} 3
|
||||
%mask {disp8} 8
|
||||
# imm really is 8/16/32 bit depending on the situation.
|
||||
%mask {imm} 8
|
||||
%mask {abs} 32
|
||||
%mask {sel} 16
|
||||
%mask {imm32} 32
|
||||
%mask {dispA} 32
|
||||
%mask {ccc} 3
|
||||
%mask {ddd} 3
|
||||
%mask {sreg3} 3
|
||||
%mask {sreg2} 2
|
||||
%mask {mmxreg} 3
|
||||
%mask {R_M} 3
|
||||
%mask {0g} 2
|
||||
%mask {GG} 2
|
||||
%mask {gG} 2
|
||||
%mask {Mod} 2
|
||||
%mask {xmmreg} 3
|
||||
%mask {R_m} 3
|
||||
%mask {xmmreg1} 3
|
||||
%mask {xmmreg2} 3
|
||||
%mask {mmreg} 3
|
||||
%prefix {R}
|
||||
%prefix {RE}
|
||||
%suffix {W}
|
||||
%suffix {WW}
|
||||
%synonym {xmmreg1} {xmmreg}
|
||||
%synonym {xmmreg2} {xmmreg}
|
||||
|
||||
%%
|
||||
0001010{w},{imm}:adc {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}010{r_m},{imm}:adc{w} {imm},{mod}{r_m}
|
||||
1000001{w},{mod}010{r_m},{imm8}:adc{w} {imm8},{mod}{r_m}
|
||||
0001000{w},{mod}{reg}{r_m}:adc{w} {reg},{mod}{r_m}
|
||||
0001001{w},{mod}{reg}{r_m}:adc{w} {mod}{r_m},{reg}
|
||||
0000010{w},{imm}:add {imm}{w},{ax}{w}
|
||||
1000000{w},{mod}000{r_m},{imm}:add{w} {imm},{mod}{r_m}
|
||||
1000001{w},{mod}000{r_m},{imm8}:add{w} {imm8},{mod}{r_m}
|
||||
0000000{w},{mod}{reg}{r_m}:add {reg}{w},{mod}{r_m}
|
||||
0000001{w},{mod}{reg}{r_m}:add {mod}{r_m},{reg}{w}
|
||||
01100110,00001111,01011000,{Mod}{xmmreg}{R_m}:addpd {Mod}{R_m},{xmmreg}
|
||||
00001111,01011000,{Mod}{xmmreg}{R_m}:addps {Mod}{R_m},{xmmreg}
|
||||
11110010,00001111,01011000,{Mod}{xmmreg}{R_m}:addsd {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,01011000,{Mod}{xmmreg}{R_m}:addss {Mod}{R_m},{xmmreg}
|
||||
01100110,00001111,11010000,{Mod}{xmmreg}{R_m}:addsubpd {Mod}{R_m},{xmmreg}
|
||||
11110010,00001111,11010000,{Mod}{xmmreg}{R_m}:addsubps {Mod}{R_m},{xmmreg}
|
||||
#
|
||||
#
|
||||
#
|
||||
0010000{w},{mod}{reg}{r_m}:and{w} {reg},{mod}{r_m}
|
||||
0010001{w},{mod}{reg}{r_m}:and{w} {mod}{r_m},{reg}
|
||||
0010010{w},{imm}:and {imm}{w},{ax}{w}
|
||||
100000{s}{w},{mod}100{r_m},{imm}:and{w} {imm}{s},{mod}{r_m}
|
||||
01100011,{mod}{reg}{r_m}:arpl {reg},{mod}{r_m}
|
||||
01100010,{mod}{reg}{r_m}:bound {reg},{mod}{r_m}
|
||||
00001111,10111100,{mod}{reg}{r_m}:bsf {reg},{mod}{r_m}
|
||||
00001111,10111101,{mod}{reg}{r_m}:bsr {reg},{mod}{r_m}
|
||||
00001111,11001{reg}:bswap {reg}
|
||||
00001111,10111010,{mod}100{r_m},{imm8}:bt {imm8},{mod}{r_m}
|
||||
00001111,10100011,{mod}{reg}{r_m}:bt {reg},{mod}{r_m}
|
||||
00001111,10111010,{mod}111{r_m},{imm8}:btc {imm8},{mod}{r_m}
|
||||
00001111,10111011,{mod}{reg}{r_m}:btc {reg},{mod}{r_m}
|
||||
00001111,10111010,{mod}110{r_m},{imm8}:btr {imm8},{mod}{r_m}
|
||||
00001111,10110011,{mod}{reg}{r_m}:btr {reg},{mod}{r_m}
|
||||
00001111,10111010,{mod}101{r_m},{imm8}:bts {imm8},{mod}{r_m}
|
||||
00001111,10101011,{mod}{reg}{r_m}:bts {reg},{mod}{r_m}
|
||||
11101000,{abs}:call {abs}
|
||||
11111111,{mod}010{r_m}:call *{mod}{r_m}
|
||||
10011010,{abs},{sel}:lcall {sel},{abs}
|
||||
11111111,{mod}011{r_m}:lcall {mod}{r_m}
|
||||
10011000:cbt{WW}
|
||||
#SPECIAL 10011001:[{dpfx}?cltd:cwtd]
|
||||
11111000:clc
|
||||
11111100:cld
|
||||
11111010:cli
|
||||
00001111,00000110:clts
|
||||
11110101:cmc
|
||||
00001111,0100{tttn},{mod}{reg}{r_m}:cmov{tttn} {mod}{r_m},{reg}
|
||||
0011100{w},{mod}{reg}{r_m}:cmp{w} {reg},{mod}{r_m}
|
||||
0011101{w},{mod}{reg}{r_m}:cmp{w} {mod}{r_m},{reg}
|
||||
0011110{w},{imm}:cmp {imm}{w},{ax}{w}
|
||||
100000{s}{w},{mod}111{r_m},{imm}:cmp{w} {imm}{s},{mod}{r_m}
|
||||
1010011{w}:{RE}cmps{w}
|
||||
00001111,1011000{w},{mod}{reg}{r_m}:cmpxchg{w} {reg},{mod}{r_m}
|
||||
00001111,11000111,{mod}{reg}{r_m}:cmpxchg8b {reg},{mod}{r_m}
|
||||
00001111,10100010:cpuid
|
||||
00100111:daa
|
||||
00101111:das
|
||||
1111111{w},{mod}001{r_m}:dec{w} {mod}{r_m}
|
||||
01001{reg}:dec {reg}
|
||||
1111011{w},{mod}110{r_m}:div{w} {mod}{r_m}
|
||||
11001000,{imm16},{imm8}:enter {imm16},{imm8}
|
||||
11110100:hlt
|
||||
1111011{w},{mod}111{r_m}:idiv{w} {mod}{r_m}
|
||||
1111011{w},{mod}101{r_m}:imul{w} {mod}{r_m}
|
||||
00001111,10101111,{mod}{reg}{r_m}:imul {reg},{mod}{r_m}
|
||||
011010{s}1,{mod}{reg}{r_m},{imm}:imul {imm}{s},{mod}{r_m},{reg}
|
||||
1110010{w},{imm8}:in {imm8},{ax}{w}
|
||||
1110110{w}:in {dx},{ax}{w}
|
||||
1111111{w},{mod}000{r_m}:inc{w} {mod}{r_m}
|
||||
01000{reg}:inc {reg}
|
||||
0110110{w}:{R}ins{w} {dx},{es_di}
|
||||
11001101,{imm8}:int {imm8}
|
||||
11001100:int 3
|
||||
11001110:into
|
||||
00001111,00001000:invd
|
||||
00001111,00000001,{mod}111{r_m}:invlpg {mod}{r_m}
|
||||
11001111:iret{W}
|
||||
0111{tttn},{disp8}:j{tttn} {disp8}
|
||||
00001111,1000{tttn},{dispA}:j{tttn} {dispA}
|
||||
#SPECIAL 11100011,{disp8}:[{dpfx}?jcxz:jecxz] {disp8}
|
||||
11101011,{disp8}:jmp {disp8}
|
||||
11101001,{dispA}:jmp {dispA}
|
||||
11111111,{mod}100{r_m}:jmp *{mod}{r_m}
|
||||
11101010,{abs},{sel}:ljmp {sel},{abs}
|
||||
11111111,{mod}101{r_m}:ljmp {mod}{r_m}
|
||||
10011111:lahf
|
||||
00001111,00000010,{mod}{reg}{r_m}:lar {mod}{r_m},{reg}
|
||||
11000101,{mod}{reg}{r_m}:lds {mod}{r_m},{reg}
|
||||
10001101,{mod}{reg}{r_m}:lea {mod}{r_m},{reg}
|
||||
11001001:leave
|
||||
11000100,{mod}{reg}{r_m}:les {mod}{r_m},{reg}
|
||||
00001111,10110100,{mod}{reg}{r_m}:lfs {mod}{r_m},{reg}
|
||||
00001111,00000001,{mod}010{r_m}:lgdt{WW} {mod}{r_m}
|
||||
00001111,10110101,{mod}{reg}{r_m}:lgs {mod}{r_m},{reg}
|
||||
00001111,00000001,{mod}011{r_m}:lidt{WW} {mod}{r_m}
|
||||
00001111,00000000,{mod}010{r_m}:lldt{WW} {mod}{r_m}
|
||||
00001111,00000001,{mod}110{r_m}:lmsw {mod}{r_m}
|
||||
11110000:lock
|
||||
1010110{w}:{R}lods {ds_si},{ax}{w}
|
||||
11100010,{disp8}:loop {disp8}
|
||||
11100001,{disp8}:loope {disp8}
|
||||
11100000,{disp8}:loopne {disp8}
|
||||
00001111,00000011,{mod}{reg}{r_m}:lsl {mod}{r_m},{reg}
|
||||
00001111,10110010,{mod}{reg}{r_m}:lss {mod}{r_m},{reg}
|
||||
00001111,00000000,{mod}011{r_m}:ltr {mod}{r_m}
|
||||
1000100{w},{mod}{reg}{r_m}:mov{w} {reg},{mod}{r_m}
|
||||
1000101{w},{mod}{reg}{r_m}:mov{w} {mod}{r_m},{reg}
|
||||
1100011{w},{mod}000{r_m},{imm}:mov{w} {imm},{mod}{r_m}
|
||||
1011{w}{reg},{imm}:mov{w} {imm},{reg}
|
||||
1010000{w},{abs}:mov {ax}{w},{abs}
|
||||
1010001{w},{abs}:mov {abs},{ax}{w}
|
||||
00001111,00100000,11{ccc}{reg}:mov {reg},{ccc}
|
||||
00001111,00100010,11{ccc}{reg}:mov {ccc},{reg}
|
||||
00001111,00100001,11{ddd}{reg}:mov {reg},{ddd}
|
||||
00001111,00100011,11{ddd}{reg}:mov {ddd},{reg}
|
||||
10001100,{mod}{sreg3}{r_m}:mov {sreg3},{mod}{r_m}
|
||||
10001110,{mod}{sreg3}{r_m}:mov {mod}{r_m},{sreg3}
|
||||
1010010{w}:{R}movs{w} {ds_si},{es_di}
|
||||
00001111,1011111{w},{mod}{reg}{r_m}:movsx{w} {mod}{r_m},{reg}
|
||||
00001111,1011011{w},{mod}{reg}{r_m}:movzx{w} {mod}{r_m},{reg}
|
||||
1111011{w},{mod}100{r_m}:mul{w} {mod}{r_m}
|
||||
1111011{w},{mod}011{r_m}:neg{w} {mod}{r_m}
|
||||
10010000:nop
|
||||
11110011,10010000:pause
|
||||
1111011{w},{mod}010{r_m}:not{w} {mod}{r_m}
|
||||
0000100{w},{mod}{reg}{r_m}:or{w} {reg},{mod}{r_m}
|
||||
0000101{w},{mod}{reg}{r_m}:or{w} {mod}{r_m},{reg}
|
||||
100000{s}{w},{mod}001{r_m},{imm}:or{w} {imm}{s},{mod}{r_m}
|
||||
0000110{w},{imm}:mov {imm}{w},{ax}{w}
|
||||
1110011{w},{imm8}:out {ax}{w},{imm8}
|
||||
1110111{w}:out {ax}{w},{dx}
|
||||
0110111{w}:{R}outs{w} {ds_si},{dx}
|
||||
10001111,{mod}000{r_m}:pop {mod}{r_m}
|
||||
01011{reg}:pop {reg}
|
||||
000{sreg2}111:pop {sreg2}
|
||||
00001111,10{sreg3}001:pop {sreg3}
|
||||
01100001:popa{W}
|
||||
10011101:popf{W}
|
||||
11111111,{mod}110{r_m}:push {mod}{r_m}
|
||||
01010{reg}:push {reg}
|
||||
011010{s}0,{imm}:push {imm}{s}
|
||||
000{sreg2}110:push {sreg2}
|
||||
00001111,10{sreg3}000:push {sreg3}
|
||||
01100000:pusha{W}
|
||||
10011100:pushf{W}
|
||||
1101000{w},{mod}010{r_m}:rcl{w} {mod}{r_m}
|
||||
1101001{w},{mod}010{r_m}:rcl{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}010{r_m},{imm8}:rcl{w} {imm8},{mod}{r_m}
|
||||
1101000{w},{mod}011{r_m}:rcr{w} {mod}{r_m}
|
||||
1101001{w},{mod}011{r_m}:rcr{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}011{r_m},{imm8}:rcr{w} {imm8},{mod}{r_m}
|
||||
00001111,00110010:rdmsr
|
||||
00001111,00110011:rdpmc
|
||||
00001111,00110001:rdtsc
|
||||
11000011:ret
|
||||
11000010,{imm16}:ret {imm16}
|
||||
11001011:lret
|
||||
11001010,{imm16}:lret {imm16}
|
||||
1101000{w},{mod}000{r_m}:rol{w} {mod}{r_m}
|
||||
1101001{w},{mod}000{r_m}:rol{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}000{r_m},{imm8}:rol{w} {imm8},{mod}{r_m}
|
||||
1101000{w},{mod}001{r_m}:ror{w} {mod}{r_m}
|
||||
1101001{w},{mod}001{r_m}:ror{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}001{r_m},{imm8}:ror{w} {imm8},{mod}{r_m}
|
||||
00001111,10101010:rsm
|
||||
10011110:sahf
|
||||
1101000{w},{mod}111{r_m}:sar{w} {mod}{r_m}
|
||||
1101001{w},{mod}111{r_m}:sar{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}111{r_m},{imm8}:sar{w} {imm8},{mod}{r_m}
|
||||
0001100{w},{mod}{reg}{r_m}:sbb{w} {reg},{mod}{r_m}
|
||||
0001101{w},{mod}{reg}{r_m}:sbb{w} {mod}{r_m},{reg}
|
||||
0001110{w},{imm}:sbb {imm}{w},{ax}{w}
|
||||
100000{s}{w},{mod}011{r_m},{imm}:sbb{w} {imm}{s},{mod}{r_m}
|
||||
1010111{w}:{RE}scas {es_di},{ax}{w}
|
||||
00001111,1001{tttn},{mod}000{r_m}:set{tttn} {mod}{r_m}
|
||||
00001111,00000001,{mod}000{r_m}:sgdt {mod}{r_m}
|
||||
1101000{w},{mod}100{r_m}:shl{w} {mod}{r_m}
|
||||
1101001{w},{mod}100{r_m}:shl{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}100{r_m},{imm8}:shl{w} {imm8},{mod}{r_m}
|
||||
1101000{w},{mod}101{r_m}:shr{w} {mod}{r_m}
|
||||
00001111,10100100,{mod}{reg}{r_m},{imm8}:shld {imm8},{reg},{mod}{r_m}
|
||||
00001111,10100101,{mod}{reg}{r_m}:shld %cl,{reg},{mod}{r_m}
|
||||
1101001{w},{mod}101{r_m}:shr{w} %cl,{mod}{r_m}
|
||||
1100000{w},{mod}101{r_m},{imm8}:shr{w} {imm8},{mod}{r_m}
|
||||
00001111,10101100,{mod}{reg}{r_m},{imm8}:shrd {imm8},{reg},{mod}{r_m}
|
||||
00001111,10101101,{mod}{reg}{r_m}:shrd %cl,{reg},{mod}{r_m}
|
||||
00001111,00000001,{mod}001{r_m}:sidt {mod}{r_m}
|
||||
00001111,00000000,{mod}000{r_m}:sldt {mod}{r_m}
|
||||
00001111,00000001,{mod}100{r_m}:smsw {mod}{r_m}
|
||||
11111001:stc
|
||||
11111101:std
|
||||
11111011:sti
|
||||
1010101{w}:{R}stos {ax}{w},{es_di}
|
||||
00001111,00000000,{mod}001{r_m}:str {mod}{r_m}
|
||||
0010100{w},{mod}{reg}{r_m}:sub{w} {reg},{mod}{r_m}
|
||||
0010101{w},{mod}{reg}{r_m}:sub{w} {mod}{r_m},{reg}
|
||||
0010110{w},{imm}:sub {imm}{w},{ax}{w}
|
||||
100000{s}{w},{mod}101{r_m},{imm}:sub{w} {imm}{s},{mod}{r_m}
|
||||
1000010{w},{mod}{reg}{r_m}:test{w} {reg},{mod}{r_m}{w}
|
||||
1000011{w},{mod}{reg}{r_m}:test{w} {mod}{r_m}{w},{reg}
|
||||
0010100{w},{imm}:test {imm}{w},{ax}{w}
|
||||
1111011{w},{mod}000{r_m},{imm}:test{w} {imm},{mod}{r_m}
|
||||
00001111,00001011:ud2a
|
||||
00001111,00000000,{mod}100{r_m}:verr {mod}{r_m}
|
||||
00001111,00000000,{mod}101{r_m}:verw {mod}{r_m}
|
||||
10011011:wait
|
||||
00001111,00001001:wbinvd
|
||||
00001111,00110000:wrmsr
|
||||
00001111,1100000{w},{mod}{reg}{r_m}:xadd{w} {reg},{mod}{r_m}
|
||||
1000011{w},{mod}{reg}{r_m}:xchg{w} {reg},{mod}{r_m}
|
||||
11010111:xlat
|
||||
0011000{w},{mod}{reg}{r_m}:xor{w} {reg},{mod}{r_m}
|
||||
0011001{w},{mod}{reg}{r_m}:xor{w} {mod}{r_m},{reg}
|
||||
0011010{w},{imm}:xor {imm}{w},{ax}{w}
|
||||
100000{s}{w},{mod}110{r_m},{imm}:xor{w} {imm}{s},{mod}{r_m}
|
||||
00001111,01110111:emms
|
||||
00001111,01101110,{mod}{mmxreg}{r_m}:movd {mod}{r_m},{mmxreg}
|
||||
00001111,01111110,{mod}{mmxreg}{r_m}:movd {mmxreg},{mod}{r_m}
|
||||
00001111,01101111,{MOD}{mmxreg}{R_M}:movq {MOD}{R_M},{mmxreg}
|
||||
00001111,01111111,{MOD}{mmxreg}{R_M}:movq {mmxreg},{MOD}{R_M}
|
||||
00001111,01101011,{MOD}{mmxreg}{R_M}:packssdw {MOD}{R_M},{mmxreg}
|
||||
00001111,01100011,{MOD}{mmxreg}{R_M}:packsswb {MOD}{R_M},{mmxreg}
|
||||
00001111,01100111,{MOD}{mmxreg}{R_M}:packuswb {MOD}{R_M},{mmxreg}
|
||||
00001111,111111{gg},{MOD}{mmxreg}{R_M}:padd{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,111111{0g},{MOD}{mmxreg}{R_M}:padds{0g} {MOD}{R_M},{mmxreg}
|
||||
00001111,110111{0g},{MOD}{mmxreg}{R_M}:paddus{0g} {MOD}{R_M},{mmxreg}
|
||||
00001111,11011011,{MOD}{mmxreg}{R_M}:pand {MOD}{R_M},{mmxreg}
|
||||
00001111,11011111,{MOD}{mmxreg}{R_M}:pandn {MOD}{R_M},{mmxreg}
|
||||
00001111,011101{gg},{MOD}{mmxreg}{R_M}:pcmpeq{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,011001{gg},{MOD}{mmxreg}{R_M}:pcmpgt{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,11110101,{MOD}{mmxreg}{R_M}:pmaddwd {MOD}{R_M},{mmxreg}
|
||||
00001111,11100101,{MOD}{mmxreg}{R_M}:pmulhw {MOD}{R_M},{mmxreg}
|
||||
00001111,11010101,{MOD}{mmxreg}{R_M}:pmullw {MOD}{R_M},{mmxreg}
|
||||
00001111,11101011,{MOD}{mmxreg}{R_M}:por {MOD}{R_M},{mmxreg}
|
||||
00001111,111100{GG},{MOD}{mmxreg}{R_M}:psll{GG} {MOD}{R_M},{mmxreg}
|
||||
00001111,011100{GG},11110{mmxreg},{imm8}:psll{GG} {imm8},{mmxreg}
|
||||
00001111,111000{gG},{MOD}{mmxreg}{R_M}:psra{gG} {MOD}{R_M},{mmxreg}
|
||||
00001111,011100{gG},11100{mmxreg},{imm8}:psra{gG} {imm8},{mmxreg}
|
||||
00001111,110100{GG},{MOD}{mmxreg}{R_M}:psrl{GG} {MOD}{R_M},{mmxreg}
|
||||
00001111,011100{GG},11010{mmxreg},{imm8}:psrl{GG} {imm8},{mmxreg}
|
||||
00001111,111110{gg},{MOD}{mmxreg}{R_M}:psub{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,111010{0g},{MOD}{mmxreg}{R_M}:psubs{0g} {MOD}{R_M},{mmxreg}
|
||||
00001111,110110{0g},{MOD}{mmxreg}{R_M}:psubus{0g} {MOD}{R_M},{mmxreg}
|
||||
00001111,011010{gg},{MOD}{mmxreg}{R_M}:punpckh{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,011000{gg},{MOD}{mmxreg}{R_M}:punpckl{gg} {MOD}{R_M},{mmxreg}
|
||||
00001111,11101111,{MOD}{mmxreg}{R_M}:pxor {MOD}{R_M},{mmxreg}
|
||||
00001111,01011000,{Mod}{xmmreg}{R_m}:addps {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,01011000,{Mod}{xmmreg}{R_m}:addss {Mod}{R_m},{xmmreg}
|
||||
00001111,01010101,{Mod}{xmmreg}{R_m}:andnps {Mod}{R_m},{xmmreg}
|
||||
00001111,01010100,{Mod}{xmmreg}{R_m}:andps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000000:cmpeqps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000001:cmpltps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000010:cmpleps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000011:cmpunordps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000100:cmpneqps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000101:cmpnltps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000110:cmpnleps {Mod}{R_m},{xmmreg}
|
||||
00001111,11000010,{Mod}{xmmreg}{R_m},00000111:cmpordps {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000000:cmpeqss {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000001:cmpltss {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000010:cmpless {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000011:cmpunordss {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000100:cmpneqss {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000101:cmpnltss {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000110:cmpnless {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,11000010,{Mod}{xmmreg}{R_m},00000111:cmpordss {Mod}{R_m},{xmmreg}
|
||||
00001111,00101111,{Mod}{xmmreg}{R_m}:comiss {Mod}{R_m},{xmmreg}
|
||||
00001111,00101010,{MOD}{xmmreg}{R_M}:cvtpi2ps {MOD}{R_M},{xmmreg}
|
||||
00001111,00101101,{MOD}{mmreg}{R_M}:cvtps2pi {MOD}{R_M},{mmreg}
|
||||
11110011,00001111,00101010,{mod}{xmmreg}{r_m}:cvtsi2ss {mod}{r_m},{xmmreg}
|
||||
11110011,00001111,00101101,{Mod}{reg}{R_m}:cvtss2si {Mod}{R_m},{reg}
|
||||
00001111,00101100,{Mod}{mmreg}{R_m}:cvttps2pi {Mod}{R_m},{mmreg}
|
||||
11110011,00001111,00101100,{Mod}{reg}{R_m}:cvttss2si {Mod}{R_m},{reg}
|
||||
00001111,01011110,{Mod}{xmmreg}{R_m}:divps {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,01011110,{Mod}{xmmreg}{R_m}:divss {Mod}{R_m},{xmmreg}
|
||||
00001111,10101110,{mod}001{r_m}:fxrstor {mod}{r_m}
|
||||
00001111,10101110,{mod}000{r_m}:fxsave {mod}{r_m}
|
||||
00001111,10101110,{mod}010{r_m}:ldmxcsr {mod}{r_m}
|
||||
00001111,01011111,{Mod}{xmmreg}{R_m}:maxps {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,01011111,{Mod}{xmmreg}{R_m}:maxss {Mod}{R_m},{xmmreg}
|
||||
00001111,01011101,{Mod}{xmmreg}{R_m}:minps {Mod}{R_m},{xmmreg}
|
||||
11110011,00001111,01011101,{Mod}{xmmreg}{R_m}:minss {Mod}{R_m},{xmmreg}
|
||||
00001111,00101000,{Mod}{xmmreg}{R_m}:movaps {Mod}{R_m},{xmmreg}
|
||||
00001111,00101001,{Mod}{xmmreg}{R_m}:movaps {xmmreg},{Mod}{R_m}
|
||||
# ORDER:
|
||||
00001111,00010010,11{xmmreg1}{xmmreg2}:movhlps {xmmreg1},{xmmreg2}
|
||||
00001111,00010011,11{xmmreg1}{xmmreg2}:movhlps {xmmreg2},{xmmreg1}
|
||||
00001111,00010010,{Mod}{xmmreg}{R_m}:movlps {Mod}{R_m},{xmmreg}
|
||||
00001111,00010011,{Mod}{xmmreg}{R_m}:movlps {xmmreg},{Mod}{R_m}
|
||||
# ORDER END:
|
||||
# ORDER:
|
||||
00001111,00010110,11{xmmreg1}{xmmreg2}:movlhps {xmmreg1},{xmmreg2}
|
||||
00001111,00010111,11{xmmreg1}{xmmreg2}:movlhps {xmmreg2},{xmmreg1}
|
||||
00001111,00010110,{Mod}{xmmreg}{R_m}:movhps {Mod}{R_m},{xmmreg}
|
||||
00001111,00010111,{Mod}{xmmreg}{R_m}:movhps {xmmreg},{Mod}{R_m}
|
||||
# ORDER END:
|
||||
# BOGUS
|
||||
00000000,11{reg}111:fadd {reg}
|
||||
00001111,00000001,11000001:vmcall
|
||||
+412
-54
@@ -101,7 +101,7 @@ data_prefix (int *prefixes, char *bufp, size_t *bufcntp, size_t bufsize)
|
||||
else if (*prefixes & has_es)
|
||||
{
|
||||
ch = 'e';
|
||||
*prefixes &= has_es;
|
||||
*prefixes &= ~has_es;
|
||||
}
|
||||
else if (*prefixes & has_fs)
|
||||
{
|
||||
@@ -132,10 +132,26 @@ data_prefix (int *prefixes, char *bufp, size_t *bufcntp, size_t bufsize)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const char regs[8][4] =
|
||||
#ifdef X86_64
|
||||
static const char hiregs[8][4] =
|
||||
{
|
||||
"r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
|
||||
};
|
||||
static const char aregs[8][4] =
|
||||
{
|
||||
"rax", "rcx", "rdx", "rbx", "rsp", "rbp", "rsi", "rdi"
|
||||
};
|
||||
static const char dregs[8][4] =
|
||||
{
|
||||
"eax", "ecx", "edx", "ebx", "esp", "ebp", "esi", "edi"
|
||||
};
|
||||
#else
|
||||
static const char aregs[8][4] =
|
||||
{
|
||||
"eax", "ecx", "edx", "ebx", "esp", "ebp", "esi", "edi"
|
||||
};
|
||||
# define dregs aregs
|
||||
#endif
|
||||
|
||||
static int
|
||||
general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
@@ -158,7 +174,48 @@ general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
return r;
|
||||
|
||||
uint_fast8_t modrm = data[opoff1 / 8];
|
||||
if ((*prefixes & has_addr16) == 0)
|
||||
#ifndef X86_64
|
||||
if (unlikely ((*prefixes & has_addr16) != 0))
|
||||
{
|
||||
int16_t disp = 0;
|
||||
bool nodisp = false;
|
||||
|
||||
if ((modrm & 0xc7) == 6 || (modrm & 0xc0) == 0x80)
|
||||
/* 16 bit displacement. */
|
||||
disp = read_2sbyte_unaligned (&data[opoff1 / 8 + 1]);
|
||||
else if ((modrm & 0xc0) == 0x40)
|
||||
/* 8 bit displacement. */
|
||||
disp = *(const int8_t *) &data[opoff1 / 8 + 1];
|
||||
else if ((modrm & 0xc0) == 0)
|
||||
nodisp = true;
|
||||
|
||||
char tmpbuf[sizeof ("-0x1234(%rr,%rr)")];
|
||||
int n;
|
||||
if ((modrm & 0xc7) == 6)
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "0x%" PRIx16, disp);
|
||||
else
|
||||
{
|
||||
n = 0;
|
||||
if (!nodisp)
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "%s0x%" PRIx16,
|
||||
disp < 0 ? "-" : "", disp < 0 ? -disp : disp);
|
||||
|
||||
if ((modrm & 0x4) == 0)
|
||||
n += snprintf (tmpbuf + n, sizeof (tmpbuf) - n, "(%%b%c,%%%ci)",
|
||||
"xp"[(modrm >> 1) & 1], "sd"[modrm & 1]);
|
||||
else
|
||||
n += snprintf (tmpbuf + n, sizeof (tmpbuf) - n, "(%%%s)",
|
||||
((const char [4][3]) { "si", "di", "bp", "bx" })[modrm & 3]);
|
||||
}
|
||||
|
||||
if (*bufcntp + n + 1 > bufsize)
|
||||
return *bufcntp + n + 1 - bufsize;
|
||||
|
||||
memcpy (&bufp[*bufcntp], tmpbuf, n + 1);
|
||||
*bufcntp += n;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
if ((modrm & 7) != 4)
|
||||
{
|
||||
@@ -174,16 +231,53 @@ general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
else if ((modrm & 0xc0) == 0)
|
||||
nodisp = true;
|
||||
|
||||
char tmpbuf[sizeof ("-0x12345678(%rrr)")];
|
||||
char tmpbuf[sizeof ("-0x12345678(%rrrr)")];
|
||||
int n;
|
||||
if (nodisp)
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "(%%%s)", regs[modrm & 7]);
|
||||
{
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "(%%%s)",
|
||||
#ifdef X86_64
|
||||
(*prefixes & has_rex_b) ? hiregs[modrm & 7] :
|
||||
#endif
|
||||
aregs[modrm & 7]);
|
||||
#ifdef X86_64
|
||||
if (*prefixes & has_addr16)
|
||||
{
|
||||
if (*prefixes & has_rex_b)
|
||||
tmpbuf[n++] = 'd';
|
||||
else
|
||||
tmpbuf[2] = 'e';
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else if ((modrm & 0xc7) != 5)
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "%s0x%" PRIx32 "(%%%s)",
|
||||
disp < 0 ? "-" : "", disp < 0 ? -disp : disp,
|
||||
regs[modrm & 7]);
|
||||
{
|
||||
int p;
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "%s0x%" PRIx32 "(%%%n%s)",
|
||||
disp < 0 ? "-" : "", disp < 0 ? -disp : disp, &p,
|
||||
#ifdef X86_64
|
||||
(*prefixes & has_rex_b) ? hiregs[modrm & 7] :
|
||||
#endif
|
||||
aregs[modrm & 7]);
|
||||
#ifdef X86_64
|
||||
if (*prefixes & has_addr16)
|
||||
{
|
||||
if (*prefixes & has_rex_b)
|
||||
tmpbuf[n++] = 'd';
|
||||
else
|
||||
tmpbuf[p] = 'e';
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "0x%" PRIx32, disp);
|
||||
{
|
||||
#ifdef X86_64
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "%s0x%" PRIx32 "(%%rip)",
|
||||
disp < 0 ? "-" : "", disp < 0 ? -disp : disp);
|
||||
#else
|
||||
n = snprintf (tmpbuf, sizeof (tmpbuf), "0x%" PRIx32, disp);
|
||||
#endif
|
||||
}
|
||||
|
||||
if (*bufcntp + n + 1 > bufsize)
|
||||
return *bufcntp + n + 1 - bufsize;
|
||||
@@ -208,10 +302,14 @@ general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
else
|
||||
nodisp = true;
|
||||
|
||||
char tmpbuf[sizeof ("-0x12345678(%rrr,%rrr,N)")];
|
||||
char tmpbuf[sizeof ("-0x12345678(%rrrr,%rrrr,N)")];
|
||||
char *cp = tmpbuf;
|
||||
int n;
|
||||
if ((modrm & 0xc0) != 0 || (sib & 0x3f) != 0x25)
|
||||
if ((modrm & 0xc0) != 0 || (sib & 0x3f) != 0x25
|
||||
#ifdef X86_64
|
||||
|| (*prefixes & has_rex_x) != 0
|
||||
#endif
|
||||
)
|
||||
{
|
||||
if (!nodisp)
|
||||
{
|
||||
@@ -225,14 +323,40 @@ general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
if ((modrm & 0xc7) != 0x4 || (sib & 0x7) != 0x5)
|
||||
{
|
||||
*cp++ = '%';
|
||||
cp = mempcpy (cp, regs[sib & 7], 3);
|
||||
cp = stpcpy (cp,
|
||||
#ifdef X86_64
|
||||
(*prefixes & has_rex_b) ? hiregs[sib & 7] :
|
||||
(*prefixes & has_addr16) ? dregs[sib & 7] :
|
||||
#endif
|
||||
aregs[sib & 7]);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & (has_rex_b | has_addr16))
|
||||
== (has_rex_b | has_addr16))
|
||||
*cp++ = 'd';
|
||||
#endif
|
||||
}
|
||||
|
||||
if ((sib & 0x38) != 0x20)
|
||||
if ((sib & 0x38) != 0x20
|
||||
#ifdef X86_64
|
||||
|| (*prefixes & has_rex_x) != 0
|
||||
#endif
|
||||
)
|
||||
{
|
||||
*cp++ = ',';
|
||||
*cp++ = '%';
|
||||
cp = mempcpy (cp, regs[(sib >> 3) & 7], 3);
|
||||
cp = stpcpy (cp,
|
||||
#ifdef X86_64
|
||||
(*prefixes & has_rex_x)
|
||||
? hiregs[(sib >> 3) & 7] :
|
||||
(*prefixes & has_addr16)
|
||||
? dregs[(sib >> 3) & 7] :
|
||||
#endif
|
||||
aregs[(sib >> 3) & 7]);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & (has_rex_b | has_addr16))
|
||||
== (has_rex_b | has_addr16))
|
||||
*cp++ = 'd';
|
||||
#endif
|
||||
|
||||
*cp++ = ',';
|
||||
*cp++ = '0' + (1 << (sib >> 6));
|
||||
@@ -243,7 +367,13 @@ general_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
else
|
||||
{
|
||||
assert (! nodisp);
|
||||
n = snprintf (cp, sizeof (tmpbuf), "0x%" PRIx32, disp);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_addr16) == 0)
|
||||
n = snprintf (cp, sizeof (tmpbuf), "0x%" PRIx64,
|
||||
(int64_t) disp);
|
||||
else
|
||||
#endif
|
||||
n = snprintf (cp, sizeof (tmpbuf), "0x%" PRIx32, disp);
|
||||
cp += n;
|
||||
}
|
||||
|
||||
@@ -283,7 +413,7 @@ FCT_MOD$R_M (GElf_Addr addr __attribute__ ((unused)),
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
int needed;
|
||||
if (*prefixes & (has_rep | has_repne))
|
||||
needed = snprintf (&bufp[*bufcntp], avail, "%%%s", regs[byte]);
|
||||
needed = snprintf (&bufp[*bufcntp], avail, "%%%s", dregs[byte]);
|
||||
else
|
||||
needed = snprintf (&bufp[*bufcntp], avail, "%%mm%" PRIxFAST8, byte);
|
||||
if ((size_t) needed > avail)
|
||||
@@ -344,7 +474,13 @@ generic_abs (int *prefixes __attribute__ ((unused)),
|
||||
const uint8_t *end __attribute__ ((unused)),
|
||||
DisasmGetSymCB_t symcb __attribute__ ((unused)),
|
||||
void *symcbarg __attribute__ ((unused)),
|
||||
const char *absstring)
|
||||
const char *absstring
|
||||
#ifdef X86_64
|
||||
, int abslen
|
||||
#else
|
||||
# define abslen 4
|
||||
#endif
|
||||
)
|
||||
{
|
||||
int r = data_prefix (prefixes, bufp, bufcntp, bufsize);
|
||||
if (r != 0)
|
||||
@@ -352,12 +488,22 @@ generic_abs (int *prefixes __attribute__ ((unused)),
|
||||
|
||||
assert (opoff1 % 8 == 0);
|
||||
assert (opoff1 / 8 == 1);
|
||||
if (*param_start + 4 > end)
|
||||
if (*param_start + abslen > end)
|
||||
return -1;
|
||||
*param_start += 4;
|
||||
uint32_t absval = read_4ubyte_unaligned (&data[1]);
|
||||
*param_start += abslen;
|
||||
#ifndef X86_64
|
||||
uint32_t absval;
|
||||
# define ABSPRIFMT PRIx32
|
||||
#else
|
||||
uint64_t absval;
|
||||
# define ABSPRIFMT PRIx64
|
||||
if (abslen == 8)
|
||||
absval = read_8ubyte_unaligned (&data[1]);
|
||||
else
|
||||
#endif
|
||||
absval = read_4ubyte_unaligned (&data[1]);
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "%s0x%" PRIx32,
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "%s0x%" ABSPRIFMT,
|
||||
absstring, absval);
|
||||
if ((size_t) needed > avail)
|
||||
return needed - avail;
|
||||
@@ -383,7 +529,11 @@ FCT_absval (GElf_Addr addr __attribute__ ((unused)),
|
||||
{
|
||||
return generic_abs (prefixes, opoff1, bufp,
|
||||
bufcntp, bufsize, data, param_start, end, symcb,
|
||||
symcbarg, "$");
|
||||
symcbarg, "$"
|
||||
#ifdef X86_64
|
||||
, 4
|
||||
#endif
|
||||
);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -404,7 +554,11 @@ FCT_abs (GElf_Addr addr __attribute__ ((unused)),
|
||||
{
|
||||
return generic_abs (prefixes, opoff1, bufp,
|
||||
bufcntp, bufsize, data, param_start, end, symcb,
|
||||
symcbarg, "");
|
||||
symcbarg, ""
|
||||
#ifdef X86_64
|
||||
, 8
|
||||
#endif
|
||||
);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -576,7 +730,12 @@ FCT_ds_xx (const char *reg,
|
||||
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "(%%%s%s)",
|
||||
*prefixes & idx_addr16 ? "" : "e", reg);
|
||||
#ifdef X86_64
|
||||
*prefixes & idx_addr16 ? "e" : "r",
|
||||
#else
|
||||
*prefixes & idx_addr16 ? "" : "e",
|
||||
#endif
|
||||
reg);
|
||||
if ((size_t) needed > avail)
|
||||
return (size_t) needed - avail;
|
||||
*bufcntp += needed;
|
||||
@@ -665,7 +824,12 @@ FCT_es_di (GElf_Addr addr __attribute__ ((unused)),
|
||||
{
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "%%es:(%%%sdi)",
|
||||
*prefixes & idx_addr16 ? "" : "e");
|
||||
#ifdef X86_64
|
||||
*prefixes & idx_addr16 ? "e" : "r"
|
||||
#else
|
||||
*prefixes & idx_addr16 ? "" : "e"
|
||||
#endif
|
||||
);
|
||||
if ((size_t) needed > avail)
|
||||
return (size_t) needed - avail;
|
||||
*bufcntp += needed;
|
||||
@@ -757,9 +921,14 @@ FCT_imms (GElf_Addr addr __attribute__ ((unused)),
|
||||
void *symcbarg __attribute__ ((unused)))
|
||||
{
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
int_fast8_t byte = *(*param_start)++;
|
||||
int8_t byte = *(*param_start)++;
|
||||
#ifdef X86_64
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "$0x%" PRIx64,
|
||||
(int64_t) byte);
|
||||
#else
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "$0x%" PRIx32,
|
||||
(int32_t) byte);
|
||||
#endif
|
||||
if ((size_t) needed > avail)
|
||||
return (size_t) needed - avail;
|
||||
*bufcntp += needed;
|
||||
@@ -793,8 +962,13 @@ FCT_imm$s (GElf_Addr addr __attribute__ ((unused)),
|
||||
{
|
||||
if (*param_start + 4 > end)
|
||||
return -1;
|
||||
uint32_t word = read_4ubyte_unaligned_inc (*param_start);
|
||||
int32_t word = read_4sbyte_unaligned_inc (*param_start);
|
||||
#ifdef X86_64
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "$0x%" PRIx64,
|
||||
(int64_t) word);
|
||||
#else
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "$0x%" PRIx32, word);
|
||||
#endif
|
||||
if ((size_t) needed > avail)
|
||||
return (size_t) needed - avail;
|
||||
*bufcntp += needed;
|
||||
@@ -893,7 +1067,6 @@ FCT_imm8 (GElf_Addr addr __attribute__ ((unused)),
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef X86_64
|
||||
static int
|
||||
FCT_rel (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
@@ -913,15 +1086,19 @@ FCT_rel (GElf_Addr addr __attribute__ ((unused)),
|
||||
size_t avail = bufsize - *bufcntp;
|
||||
if (*param_start + 4 > end)
|
||||
return -1;
|
||||
uint32_t rel = read_4ubyte_unaligned_inc (*param_start);
|
||||
int32_t rel = read_4sbyte_unaligned_inc (*param_start);
|
||||
#ifdef X86_64
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "0x%" PRIx64,
|
||||
(uint64_t) (addr + rel + (*param_start - data)));
|
||||
#else
|
||||
int needed = snprintf (&bufp[*bufcntp], avail, "0x%" PRIx32,
|
||||
(uint32_t) (addr + rel + (*param_start - data)));
|
||||
#endif
|
||||
if ((size_t) needed > avail)
|
||||
return (size_t) needed - avail;
|
||||
*bufcntp += needed;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int
|
||||
FCT_mmxreg (GElf_Addr addr __attribute__ ((unused)),
|
||||
@@ -971,14 +1148,33 @@ FCT_mod$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
uint_fast8_t modrm = data[opoff1 / 8];
|
||||
if ((modrm & 0xc0) == 0xc0)
|
||||
{
|
||||
if (*prefixes & has_addr16)
|
||||
return -1;
|
||||
|
||||
int is_16bit = (*prefixes & has_data16) != 0;
|
||||
|
||||
if (*bufcntp + 5 - is_16bit > bufsize)
|
||||
return *bufcntp + 5 - is_16bit - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
memcpy (&bufp[*bufcntp], regs[modrm & 7] + is_16bit,
|
||||
sizeof (regs[0]) - is_16bit);
|
||||
*bufcntp += 3 - is_16bit;
|
||||
|
||||
char *cp;
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_b) != 0 && !is_16bit)
|
||||
{
|
||||
cp = stpcpy (&bufp[*bufcntp], hiregs[modrm & 7]);
|
||||
if ((*prefixes & has_rex_w) == 0)
|
||||
*cp++ = 'd';
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
cp = stpcpy (&bufp[*bufcntp], dregs[modrm & 7] + is_16bit);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_w) != 0)
|
||||
bufp[*bufcntp] = 'r';
|
||||
#endif
|
||||
}
|
||||
*bufcntp = cp - bufp;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1013,6 +1209,9 @@ FCT_moda$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
uint_fast8_t modrm = data[opoff1 / 8];
|
||||
if ((modrm & 0xc0) == 0xc0)
|
||||
{
|
||||
if (*prefixes & has_addr16)
|
||||
return -1;
|
||||
|
||||
if (*bufcntp + 3 > bufsize)
|
||||
return *bufcntp + 3 - bufsize;
|
||||
|
||||
@@ -1029,6 +1228,14 @@ FCT_moda$r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef X86_64
|
||||
static const char rex_8bit[8][3] =
|
||||
{
|
||||
[0] = "a", [1] = "c", [2] = "d", [3] = "b",
|
||||
[4] = "sp", [5] = "bp", [6] = "si", [7] = "di"
|
||||
};
|
||||
#endif
|
||||
|
||||
static int
|
||||
FCT_mod$r_m$w (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
@@ -1053,24 +1260,60 @@ FCT_mod$r_m$w (GElf_Addr addr __attribute__ ((unused)),
|
||||
uint_fast8_t modrm = data[opoff1 / 8];
|
||||
if ((modrm & 0xc0) == 0xc0)
|
||||
{
|
||||
if (*prefixes & has_addr16)
|
||||
return -1;
|
||||
|
||||
if (*bufcntp + 5 > bufsize)
|
||||
return *bufcntp + 5 - bufsize;
|
||||
|
||||
if ((data[opoff3 / 8] & (1 << (7 - (opoff3 & 7)))) == 0)
|
||||
{
|
||||
if (*bufcntp + 3 > bufsize)
|
||||
return *bufcntp + 3 - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
bufp[(*bufcntp)++] = "acdb"[modrm & 3];
|
||||
bufp[(*bufcntp)++] = "lh"[(modrm & 4) >> 2];
|
||||
|
||||
#ifdef X86_64
|
||||
if (*prefixes & has_rex)
|
||||
{
|
||||
if (*prefixes & has_rex_r)
|
||||
*bufcntp += snprintf (bufp + *bufcntp, bufsize - *bufcntp,
|
||||
"r%db", 8 + (modrm & 7));
|
||||
else
|
||||
{
|
||||
char *cp = stpcpy (bufp + *bufcntp, hiregs[modrm & 7]);
|
||||
*cp++ = 'l';
|
||||
*bufcntp = cp - bufp;
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
bufp[(*bufcntp)++] = "acdb"[modrm & 3];
|
||||
bufp[(*bufcntp)++] = "lh"[(modrm & 4) >> 2];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
int is_16bit = (*prefixes & has_data16) != 0;
|
||||
|
||||
if (*bufcntp + 5 - is_16bit > bufsize)
|
||||
return *bufcntp + 5 - is_16bit - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
memcpy (&bufp[*bufcntp], regs[modrm & 7] + is_16bit,
|
||||
sizeof (regs[0]) - is_16bit);
|
||||
*bufcntp += 3 - is_16bit;
|
||||
|
||||
char *cp;
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_b) != 0 && !is_16bit)
|
||||
{
|
||||
cp = stpcpy (&bufp[*bufcntp], hiregs[modrm & 7]);
|
||||
if ((*prefixes & has_rex_w) == 0)
|
||||
*cp++ = 'd';
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
cp = stpcpy (&bufp[*bufcntp], dregs[modrm & 7] + is_16bit);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_w) != 0)
|
||||
bufp[*bufcntp] = 'r';
|
||||
#endif
|
||||
}
|
||||
*bufcntp = cp - bufp;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -1081,7 +1324,6 @@ FCT_mod$r_m$w (GElf_Addr addr __attribute__ ((unused)),
|
||||
}
|
||||
|
||||
|
||||
#ifndef X86_64
|
||||
static int
|
||||
FCT_mod$8r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
@@ -1114,7 +1356,6 @@ FCT_mod$8r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
bufcntp, bufsize, data, param_start, end,
|
||||
symcb, symcbarg);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int
|
||||
FCT_mod$16r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
@@ -1140,7 +1381,7 @@ FCT_mod$16r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
if (*bufcntp + 3 > bufsize)
|
||||
return *bufcntp + 3 - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
memcpy (&bufp[*bufcntp], regs[byte] + 1, sizeof (regs[0]) - 1);
|
||||
memcpy (&bufp[*bufcntp], dregs[byte] + 1, sizeof (dregs[0]) - 1);
|
||||
*bufcntp += 2;
|
||||
return 0;
|
||||
}
|
||||
@@ -1150,6 +1391,45 @@ FCT_mod$16r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
symcb, symcbarg);
|
||||
}
|
||||
|
||||
#ifdef X86_64
|
||||
static int
|
||||
FCT_mod$64r_m (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
const char *op1str __attribute__ ((unused)),
|
||||
size_t opoff1 __attribute__ ((unused)),
|
||||
size_t opoff2 __attribute__ ((unused)),
|
||||
size_t opoff3 __attribute__ ((unused)),
|
||||
char *bufp __attribute__ ((unused)),
|
||||
size_t *bufcntp __attribute__ ((unused)),
|
||||
size_t bufsize __attribute__ ((unused)),
|
||||
const uint8_t *data __attribute__ ((unused)),
|
||||
const uint8_t **param_start __attribute__ ((unused)),
|
||||
const uint8_t *end __attribute__ ((unused)),
|
||||
DisasmGetSymCB_t symcb __attribute__ ((unused)),
|
||||
void *symcbarg __attribute__ ((unused)))
|
||||
{
|
||||
assert (opoff1 % 8 == 0);
|
||||
uint_fast8_t modrm = data[opoff1 / 8];
|
||||
if ((modrm & 0xc0) == 0xc0)
|
||||
{
|
||||
uint_fast8_t byte = data[opoff1 / 8] & 7;
|
||||
if (*bufcntp + 4 > bufsize)
|
||||
return *bufcntp + 4 - bufsize;
|
||||
char *cp = &bufp[*bufcntp];
|
||||
*cp++ = '%';
|
||||
cp = stpcpy (cp, (*prefixes & has_rex_b) ? hiregs[byte] : aregs[byte]);
|
||||
*bufcntp = cp - bufp;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return general_mod$r_m (addr, prefixes, op1str, opoff1, opoff2, opoff3, bufp,
|
||||
bufcntp, bufsize, data, param_start, end,
|
||||
symcb, symcbarg);
|
||||
}
|
||||
#else
|
||||
static typeof (FCT_mod$r_m) FCT_mod$64r_m __attribute__ ((alias ("FCT_mod$r_m")));
|
||||
#endif
|
||||
|
||||
static int
|
||||
FCT_reg (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
@@ -1171,11 +1451,69 @@ FCT_reg (GElf_Addr addr __attribute__ ((unused)),
|
||||
byte >>= 8 - (opoff1 % 8 + 3);
|
||||
byte &= 7;
|
||||
int is_16bit = (*prefixes & has_data16) != 0;
|
||||
if (*bufcntp + 4 > bufsize)
|
||||
return *bufcntp + 4 - bufsize;
|
||||
if (*bufcntp + 5 > bufsize)
|
||||
return *bufcntp + 5 - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
memcpy (&bufp[*bufcntp], regs[byte] + is_16bit, sizeof (regs[0]) - is_16bit);
|
||||
*bufcntp += 3 - is_16bit;
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_r) != 0 && !is_16bit)
|
||||
{
|
||||
*bufcntp += snprintf (&bufp[*bufcntp], bufsize - *bufcntp, "r%d",
|
||||
8 + byte);
|
||||
if ((*prefixes & has_rex_w) == 0)
|
||||
bufp[(*bufcntp)++] = 'd';
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
memcpy (&bufp[*bufcntp], dregs[byte] + is_16bit, 3 - is_16bit);
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_w) != 0 && !is_16bit)
|
||||
bufp[*bufcntp] = 'r';
|
||||
#endif
|
||||
*bufcntp += 3 - is_16bit;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
FCT_reg64 (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
const char *op1str __attribute__ ((unused)),
|
||||
size_t opoff1 __attribute__ ((unused)),
|
||||
size_t opoff2 __attribute__ ((unused)),
|
||||
size_t opoff3 __attribute__ ((unused)),
|
||||
char *bufp __attribute__ ((unused)),
|
||||
size_t *bufcntp __attribute__ ((unused)),
|
||||
size_t bufsize __attribute__ ((unused)),
|
||||
const uint8_t *data __attribute__ ((unused)),
|
||||
const uint8_t **param_start __attribute__ ((unused)),
|
||||
const uint8_t *end __attribute__ ((unused)),
|
||||
DisasmGetSymCB_t symcb __attribute__ ((unused)),
|
||||
void *symcbarg __attribute__ ((unused)))
|
||||
{
|
||||
uint_fast8_t byte = data[opoff1 / 8];
|
||||
assert (opoff1 % 8 + 3 <= 8);
|
||||
byte >>= 8 - (opoff1 % 8 + 3);
|
||||
byte &= 7;
|
||||
if ((*prefixes & has_data16) != 0)
|
||||
return -1;
|
||||
if (*bufcntp + 5 > bufsize)
|
||||
return *bufcntp + 5 - bufsize;
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
#ifdef X86_64
|
||||
if ((*prefixes & has_rex_r) != 0)
|
||||
{
|
||||
*bufcntp += snprintf (&bufp[*bufcntp], bufsize - *bufcntp, "r%d",
|
||||
8 + byte);
|
||||
if ((*prefixes & has_rex_w) == 0)
|
||||
bufp[(*bufcntp)++] = 'd';
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
memcpy (&bufp[*bufcntp], aregs[byte], 3);
|
||||
*bufcntp += 3;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1202,15 +1540,34 @@ FCT_reg$w (GElf_Addr addr __attribute__ ((unused)),
|
||||
assert (opoff1 % 8 + 3 <= 8);
|
||||
byte >>= 8 - (opoff1 % 8 + 3);
|
||||
byte &= 7;
|
||||
if (*bufcntp + 3 > bufsize)
|
||||
return *bufcntp + 3 - bufsize;
|
||||
|
||||
if (*bufcntp + 4 > bufsize)
|
||||
return *bufcntp + 4 - bufsize;
|
||||
|
||||
bufp[(*bufcntp)++] = '%';
|
||||
bufp[(*bufcntp)++] = "acdb"[byte & 3];
|
||||
bufp[(*bufcntp)++] = "lh"[byte >> 2];
|
||||
|
||||
#ifdef X86_64
|
||||
if (*prefixes & has_rex)
|
||||
{
|
||||
if (*prefixes & has_rex_r)
|
||||
*bufcntp += snprintf (bufp + *bufcntp, bufsize - *bufcntp,
|
||||
"r%db", 8 + byte);
|
||||
else
|
||||
{
|
||||
char* cp = stpcpy (bufp + *bufcntp, rex_8bit[byte]);
|
||||
*cp++ = 'l';
|
||||
*bufcntp = cp - bufp;
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
bufp[(*bufcntp)++] = "acdb"[byte & 3];
|
||||
bufp[(*bufcntp)++] = "lh"[byte >> 2];
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef X86_64
|
||||
static int
|
||||
FCT_freg (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
@@ -1238,6 +1595,7 @@ FCT_freg (GElf_Addr addr __attribute__ ((unused)),
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef X86_64
|
||||
static int
|
||||
FCT_reg16 (GElf_Addr addr __attribute__ ((unused)),
|
||||
int *prefixes __attribute__ ((unused)),
|
||||
|
||||
+97
-21
@@ -90,7 +90,12 @@ static const unsigned short int mneidx[] =
|
||||
|
||||
enum
|
||||
{
|
||||
idx_cs = 0,
|
||||
idx_rex_b = 0,
|
||||
idx_rex_x,
|
||||
idx_rex_r,
|
||||
idx_rex_w,
|
||||
idx_rex,
|
||||
idx_cs,
|
||||
idx_ds,
|
||||
idx_es,
|
||||
idx_fs,
|
||||
@@ -106,6 +111,11 @@ enum
|
||||
enum
|
||||
{
|
||||
#define prefbit(pref) has_##pref = 1 << idx_##pref
|
||||
prefbit (rex_b),
|
||||
prefbit (rex_x),
|
||||
prefbit (rex_r),
|
||||
prefbit (rex_w),
|
||||
prefbit (rex),
|
||||
prefbit (cs),
|
||||
prefbit (ds),
|
||||
prefbit (es),
|
||||
@@ -226,7 +236,7 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
while (data < end)
|
||||
{
|
||||
unsigned int i;
|
||||
for (i = 0; i < nknown_prefixes; ++i)
|
||||
for (i = idx_cs; i < nknown_prefixes; ++i)
|
||||
if (known_prefixes[i] == *data)
|
||||
break;
|
||||
if (i == nknown_prefixes)
|
||||
@@ -237,6 +247,11 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
++data;
|
||||
}
|
||||
|
||||
#ifdef X86_64
|
||||
if (data < end && (*data & 0xf0) == 0x40)
|
||||
prefixes |= ((*data++) & 0xf) | has_rex;
|
||||
#endif
|
||||
|
||||
assert (data <= end);
|
||||
if (data == end)
|
||||
{
|
||||
@@ -407,19 +422,29 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
{
|
||||
uint_fast8_t modrm = codep[-1];
|
||||
|
||||
if ((prefixes & has_addr16) == 0)
|
||||
#ifndef X86_64
|
||||
if (likely ((prefixes & has_addr16) != 0))
|
||||
{
|
||||
/* Account for displacement. */
|
||||
if ((modrm & 0xc7) == 6 || (modrm & 0xc0) == 0x80)
|
||||
param_start += 2;
|
||||
else if ((modrm & 0xc0) == 0x40)
|
||||
param_start += 1;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
/* Account for SIB. */
|
||||
if ((modrm & 0xc0) != 0xc0 && (modrm & 0x7) == 0x4)
|
||||
param_start += 1;
|
||||
}
|
||||
|
||||
/* Account for displacement. */
|
||||
if ((modrm & 0xc7) == 5 || (modrm & 0xc0) == 0x80
|
||||
|| ((modrm & 0xc7) == 0x4 && (codep[0] & 0x7) == 0x5))
|
||||
param_start += 4;
|
||||
else if ((modrm & 0xc0) == 0x40)
|
||||
param_start += 1;
|
||||
/* Account for displacement. */
|
||||
if ((modrm & 0xc7) == 5 || (modrm & 0xc0) == 0x80
|
||||
|| ((modrm & 0xc7) == 0x4 && (codep[0] & 0x7) == 0x5))
|
||||
param_start += 4;
|
||||
else if ((modrm & 0xc0) == 0x40)
|
||||
param_start += 1;
|
||||
}
|
||||
|
||||
if (unlikely (param_start > end))
|
||||
goto not;
|
||||
@@ -484,6 +509,7 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
size_t start_idx = bufcnt;
|
||||
switch (*fmt++)
|
||||
{
|
||||
char mnebuf[16];
|
||||
const char *str;
|
||||
|
||||
case 'm':
|
||||
@@ -493,15 +519,6 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
{
|
||||
switch (*data)
|
||||
{
|
||||
case 0x90:
|
||||
if (prefixes & ~has_rep)
|
||||
goto print_prefix;
|
||||
/* Discard the 'rep' prefix string possibly
|
||||
already in the buffer. */
|
||||
bufcnt = 0;
|
||||
str = prefixes & has_rep ? "pause" : "nop";
|
||||
break;
|
||||
|
||||
case 0x98:
|
||||
if (prefixes & ~has_data16)
|
||||
goto print_prefix;
|
||||
@@ -517,9 +534,56 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
case 0xe3:
|
||||
if (prefixes & ~has_addr16)
|
||||
goto print_prefix;
|
||||
#ifdef X86_64
|
||||
str = prefixes & has_addr16 ? "jecxz" : "jrcxz";
|
||||
#else
|
||||
str = prefixes & has_addr16 ? "jcxz" : "jecxz";
|
||||
#endif
|
||||
break;
|
||||
|
||||
case 0x0f:
|
||||
#ifdef X86_64
|
||||
if (data[1] == 0xc7)
|
||||
{
|
||||
str = ((prefixes & has_rex_w)
|
||||
? "cmpxchg16b" : "cmpxchg8b");
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
if (data[1] == 0xc2)
|
||||
{
|
||||
if (param_start >= end)
|
||||
goto not;
|
||||
if (*param_start > 7)
|
||||
goto not;
|
||||
static const char cmpops[][9] =
|
||||
{
|
||||
[0] = "cmpeq",
|
||||
[1] = "cmplt",
|
||||
[2] = "cmple",
|
||||
[3] = "cmpunord",
|
||||
[4] = "cmpneq",
|
||||
[5] = "cmpnlt",
|
||||
[6] = "cmpnle",
|
||||
[7] = "cmpord"
|
||||
};
|
||||
char *cp = stpcpy (mnebuf, cmpops[*param_start]);
|
||||
if (correct_prefix & (has_rep | has_repne))
|
||||
*cp++ = 's';
|
||||
else
|
||||
*cp++ = 'p';
|
||||
if (correct_prefix & (has_data16 | has_repne))
|
||||
*cp++ = 'd';
|
||||
else
|
||||
*cp++ = 's';
|
||||
*cp = '\0';
|
||||
str = mnebuf;
|
||||
/* Eat the immediate byte indicating the
|
||||
operation. */
|
||||
++param_start;
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
assert (! "INVALID not handled");
|
||||
}
|
||||
@@ -565,11 +629,23 @@ i386_disasm (const uint8_t **startp, const uint8_t *end, GElf_Addr addr,
|
||||
ADD_CHAR ('w');
|
||||
prefixes &= ~has_data16;
|
||||
}
|
||||
#ifdef x86_64
|
||||
#ifdef X86_64
|
||||
else
|
||||
abort ();
|
||||
ADD_CHAR ('q');
|
||||
#endif
|
||||
break;
|
||||
case suffix_W1:
|
||||
if (prefixes & has_data16)
|
||||
{
|
||||
ADD_CHAR ('w');
|
||||
prefixes &= ~has_data16;
|
||||
}
|
||||
#ifdef X86_64
|
||||
else if (prefixes & has_rex_w)
|
||||
ADD_CHAR ('q');
|
||||
#endif
|
||||
break;
|
||||
|
||||
case suffix_tttn:;
|
||||
static const char tttn[16][3] =
|
||||
{
|
||||
|
||||
+4
-1
@@ -108,7 +108,7 @@ struct instruction
|
||||
|
||||
/* Suffix. */
|
||||
enum { suffix_none = 0, suffix_w, suffix_w0, suffix_W, suffix_tttn,
|
||||
suffix_w1, suffix_D } suffix;
|
||||
suffix_w1, suffix_W1, suffix_D } suffix;
|
||||
|
||||
/* Flag set if modr/m is used. */
|
||||
int modrm;
|
||||
@@ -324,6 +324,8 @@ instr: bytes ':' bitfieldopt kID bitfieldopt optargs
|
||||
newp->suffix = suffix_w1;
|
||||
else if (strcmp ($5->name, "W") == 0)
|
||||
newp->suffix = suffix_W;
|
||||
else if (strcmp ($5->name, "W1") == 0)
|
||||
newp->suffix = suffix_W1;
|
||||
else if (strcmp ($5->name, "D") == 0)
|
||||
newp->suffix = suffix_D;
|
||||
else
|
||||
@@ -1130,6 +1132,7 @@ instrtable_out (void)
|
||||
EMIT_SUFFIX (tttn);
|
||||
EMIT_SUFFIX (D);
|
||||
EMIT_SUFFIX (w1);
|
||||
EMIT_SUFFIX (W1);
|
||||
|
||||
fputc_unlocked ('\n', outfile);
|
||||
|
||||
|
||||
@@ -1,3 +1,14 @@
|
||||
2008-01-08 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* Makefile.am (TESTS): Add run-disasm-x86-64.sh.
|
||||
(EXTRA): Add testfile45.S.bz2, testfile45.expect.bz2,
|
||||
run-disasm-x86-64.sh.
|
||||
* run-disasm-x86-64.sh: New file.
|
||||
* testfile45.S.bz2: New file.
|
||||
* testfile45.expect.bz2: New file.
|
||||
* testfile44.S.bz2: New tests.
|
||||
* testfile44.expect.bz2: Adjust.
|
||||
|
||||
2008-01-04 Ulrich Drepper <drepper@redhat.com>
|
||||
|
||||
* testfile44.S.bz2: New tests.
|
||||
|
||||
+4
-3
@@ -1,6 +1,6 @@
|
||||
## Process this file with automake to create Makefile.in
|
||||
##
|
||||
## Copyright (C) 1996-2002, 2003, 2004, 2005, 2006, 2007 Red Hat, Inc.
|
||||
## Copyright (C) 1996-2002, 2003, 2004, 2005, 2006, 2007, 2008 Red Hat, Inc.
|
||||
## This file is part of Red Hat elfutils.
|
||||
##
|
||||
## Red Hat elfutils is free software; you can redistribute it and/or modify
|
||||
@@ -84,7 +84,7 @@ TESTS = run-arextract.sh run-arsymtest.sh newfile test-nlist \
|
||||
dwfl-bug-addr-overflow run-addrname-test.sh \
|
||||
dwfl-bug-fd-leak dwfl-bug-report \
|
||||
run-dwfl-bug-offline-rel.sh run-dwfl-addr-sect.sh \
|
||||
run-disasm.sh
|
||||
run-disasm-x86.sh run-disasm-x86-64.sh
|
||||
# run-show-ciefde.sh
|
||||
|
||||
if !STANDALONE
|
||||
@@ -135,7 +135,8 @@ EXTRA_DIST = run-arextract.sh run-arsymtest.sh \
|
||||
testfile37.bz2 testfile37.debug.bz2 \
|
||||
testfile38.bz2 testfile39.bz2 testfile40.bz2 testfile40.debug.bz2 \
|
||||
testfile41.bz2 testfile42.bz2 testfile43.bz2 \
|
||||
testfile44.S.bz2 testfile44.expect.bz2 run-disasm.sh
|
||||
testfile44.S.bz2 testfile44.expect.bz2 run-disasm-x86.sh \
|
||||
testfile45.S.bz2 testfile45.expect.bz2 run-disasm-x86-64.sh
|
||||
|
||||
installed_TESTS_ENVIRONMENT = libdir=$(DESTDIR)$(libdir) \
|
||||
bindir=$(DESTDIR)$(bindir) \
|
||||
|
||||
Executable
+36
@@ -0,0 +1,36 @@
|
||||
#! /bin/sh
|
||||
# Copyright (C) 2007, 2008 Red Hat, Inc.
|
||||
# This file is part of Red Hat elfutils.
|
||||
#
|
||||
# Red Hat elfutils is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by the
|
||||
# Free Software Foundation; version 2 of the License.
|
||||
#
|
||||
# Red Hat elfutils is distributed in the hope that it will be useful, but
|
||||
# WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License along
|
||||
# with Red Hat elfutils; if not, write to the Free Software Foundation,
|
||||
# Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301 USA.
|
||||
#
|
||||
# Red Hat elfutils is an included package of the Open Invention Network.
|
||||
# An included package of the Open Invention Network is a package for which
|
||||
# Open Invention Network licensees cross-license their patents. No patent
|
||||
# license is granted, either expressly or impliedly, by designation as an
|
||||
# included package. Should you wish to participate in the Open Invention
|
||||
# Network licensing program, please visit www.openinventionnetwork.com
|
||||
# <http://www.openinventionnetwork.com>.
|
||||
|
||||
. $srcdir/test-subr.sh
|
||||
|
||||
# Run x86-64 test.
|
||||
case "$(arch)" in
|
||||
x86_64)
|
||||
tempfiles testfile45.o
|
||||
testfiles testfile45.S testfile45.expect
|
||||
gcc -m64 -c -o testfile45.o testfile45.S
|
||||
testrun_compare ../src/objdump -d testfile45.o < testfile45.expect
|
||||
;;
|
||||
esac
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Reference in New Issue
Block a user