2005-07-05  Jan Beulich  <jbeulich@novell.com>

	* config/tc-i386.h (CpuSVME): New.
	(CpuUnknownFlags): Include CpuSVME.
	* config/tc-i386.c (cpu_arch): Add .pacifica and .svme. Add opteron
	as alias of sledgehammer.
	(md_assemble): Include invlpga in the check for insns with two source
	operands.
	(process_operands): Include SVME insns in the check for ignored
	segment overrides. Adjust diagnostic.
	(i386_index_check): Special-case SVME insns with memory operands.

gas/testsuite/
2005-07-05  Jan Beulich  <jbeulich@novell.com>

	* gas/i386/svme.d: New.
	* gas/i386/svme.s: New.
	* gas/i386/svme64.d: New.
	* gas/i386/i386.exp: Run new tests.

include/opcode/
2005-07-05  Jan Beulich  <jbeulich@novell.com>

	* i386.h (i386_optab): Add new insns.

opcodes/
2005-07-05  Jan Beulich  <jbeulich@novell.com>

	* i386-dis.c (SVME_Fixup): New.
	(grps): Use it for the lidt entry.
	(PNI_Fixup): Call OP_M rather than OP_E.
	(INVLPG_Fixup): Likewise.
This commit is contained in:
Jan Beulich
2005-07-05 07:16:54 +00:00
parent b35d266b30
commit 3012383869
12 changed files with 264 additions and 7 deletions

View File

@ -1,3 +1,15 @@
2005-07-05 Jan Beulich <jbeulich@novell.com>
* config/tc-i386.h (CpuSVME): New.
(CpuUnknownFlags): Include CpuSVME.
* config/tc-i386.c (cpu_arch): Add .pacifica and .svme. Add opteron
as alias of sledgehammer.
(md_assemble): Include invlpga in the check for insns with two source
operands.
(process_operands): Include SVME insns in the check for ignored
segment overrides. Adjust diagnostic.
(i386_index_check): Special-case SVME insns with memory operands.
2005-07-04 Khem Raj <kraj@mvista.com> 2005-07-04 Khem Raj <kraj@mvista.com>
Nick Clifton <nickc@redhat.com> Nick Clifton <nickc@redhat.com>

View File

@ -429,12 +429,15 @@ static const arch_entry cpu_arch[] = {
{"k6_2", Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|CpuK6|CpuMMX|Cpu3dnow }, {"k6_2", Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|CpuK6|CpuMMX|Cpu3dnow },
{"athlon", Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuK6|CpuAthlon|CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA }, {"athlon", Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuK6|CpuAthlon|CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA },
{"sledgehammer",Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuK6|CpuAthlon|CpuSledgehammer|CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA|CpuSSE|CpuSSE2 }, {"sledgehammer",Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuK6|CpuAthlon|CpuSledgehammer|CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA|CpuSSE|CpuSSE2 },
{"opteron", Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuK6|CpuAthlon|CpuSledgehammer|CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA|CpuSSE|CpuSSE2 },
{".mmx", CpuMMX }, {".mmx", CpuMMX },
{".sse", CpuMMX|CpuMMX2|CpuSSE }, {".sse", CpuMMX|CpuMMX2|CpuSSE },
{".sse2", CpuMMX|CpuMMX2|CpuSSE|CpuSSE2 }, {".sse2", CpuMMX|CpuMMX2|CpuSSE|CpuSSE2 },
{".3dnow", CpuMMX|Cpu3dnow }, {".3dnow", CpuMMX|Cpu3dnow },
{".3dnowa", CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA }, {".3dnowa", CpuMMX|CpuMMX2|Cpu3dnow|Cpu3dnowA },
{".padlock", CpuPadLock }, {".padlock", CpuPadLock },
{".pacifica", CpuSVME },
{".svme", CpuSVME },
{NULL, 0 } {NULL, 0 }
}; };
@ -1403,6 +1406,7 @@ md_assemble (line)
have two immediate operands. */ have two immediate operands. */
if (intel_syntax && i.operands > 1 if (intel_syntax && i.operands > 1
&& (strcmp (mnemonic, "bound") != 0) && (strcmp (mnemonic, "bound") != 0)
&& (strcmp (mnemonic, "invlpga") != 0)
&& !((i.types[0] & Imm) && (i.types[1] & Imm))) && !((i.types[0] & Imm) && (i.types[1] & Imm)))
swap_operands (); swap_operands ();
@ -2846,8 +2850,10 @@ process_operands ()
default_seg = &ds; default_seg = &ds;
} }
if (i.tm.base_opcode == 0x8d /* lea */ && i.seg[0] && !quiet_warnings) if ((i.tm.base_opcode == 0x8d /* lea */
as_warn (_("segment override on `lea' is ineffectual")); || (i.tm.cpu_flags & CpuSVME))
&& i.seg[0] && !quiet_warnings)
as_warn (_("segment override on `%s' is ineffectual"), i.tm.name);
/* If a segment was explicitly specified, and the specified segment /* If a segment was explicitly specified, and the specified segment
is not the default, use an opcode prefix to select it. If we is not the default, use an opcode prefix to select it. If we
@ -4194,7 +4200,30 @@ i386_index_check (operand_string)
tryprefix: tryprefix:
#endif #endif
ok = 1; ok = 1;
if (flag_code == CODE_64BIT) if ((current_templates->start->cpu_flags & CpuSVME)
&& current_templates->end[-1].operand_types[0] == AnyMem)
{
/* Memory operands of SVME insns are special in that they only allow
rAX as their memory address and ignore any segment override. */
unsigned RegXX;
/* SKINIT is even more restrictive: it always requires EAX. */
if (strcmp (current_templates->start->name, "skinit") == 0)
RegXX = Reg32;
else if (flag_code == CODE_64BIT)
RegXX = i.prefix[ADDR_PREFIX] == 0 ? Reg64 : Reg32;
else
RegXX = (flag_code == CODE_16BIT) ^ (i.prefix[ADDR_PREFIX] != 0)
? Reg16
: Reg32;
if (!i.base_reg
|| !(i.base_reg->reg_type & Acc)
|| !(i.base_reg->reg_type & RegXX)
|| i.index_reg
|| (i.types[0] & Disp))
ok = 0;
}
else if (flag_code == CODE_64BIT)
{ {
unsigned RegXX = (i.prefix[ADDR_PREFIX] == 0 ? Reg64 : Reg32); unsigned RegXX = (i.prefix[ADDR_PREFIX] == 0 ? Reg64 : Reg32);

View File

@ -184,13 +184,16 @@ typedef struct
#define Cpu3dnowA 0x10000 /* 3dnow!Extensions support required */ #define Cpu3dnowA 0x10000 /* 3dnow!Extensions support required */
#define CpuPNI 0x20000 /* Prescott New Instructions required */ #define CpuPNI 0x20000 /* Prescott New Instructions required */
#define CpuPadLock 0x40000 /* VIA PadLock required */ #define CpuPadLock 0x40000 /* VIA PadLock required */
#define CpuSVME 0x80000 /* AMD Secure Virtual Machine Ext-s required */
/* These flags are set by gas depending on the flag_code. */ /* These flags are set by gas depending on the flag_code. */
#define Cpu64 0x4000000 /* 64bit support required */ #define Cpu64 0x4000000 /* 64bit support required */
#define CpuNo64 0x8000000 /* Not supported in the 64bit mode */ #define CpuNo64 0x8000000 /* Not supported in the 64bit mode */
/* The default value for unknown CPUs - enable all features to avoid problems. */ /* The default value for unknown CPUs - enable all features to avoid problems. */
#define CpuUnknownFlags (Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686|CpuP4|CpuSledgehammer|CpuMMX|CpuMMX2|CpuSSE|CpuSSE2|CpuPNI|Cpu3dnow|Cpu3dnowA|CpuK6|CpuAthlon|CpuPadLock) #define CpuUnknownFlags (Cpu086|Cpu186|Cpu286|Cpu386|Cpu486|Cpu586|Cpu686 \
|CpuP4|CpuSledgehammer|CpuMMX|CpuMMX2|CpuSSE|CpuSSE2|CpuPNI \
|Cpu3dnow|Cpu3dnowA|CpuK6|CpuAthlon|CpuPadLock|CpuSVME)
/* the bits in opcode_modifier are used to generate the final opcode from /* the bits in opcode_modifier are used to generate the final opcode from
the base_opcode. These bits also are used to detect alternate forms of the base_opcode. These bits also are used to detect alternate forms of

View File

@ -1,3 +1,10 @@
2005-07-05 Jan Beulich <jbeulich@novell.com>
* gas/i386/svme.d: New.
* gas/i386/svme.s: New.
* gas/i386/svme64.d: New.
* gas/i386/i386.exp: Run new tests.
2005-07-04 Zack Weinberg <zack@codesourcery.com> 2005-07-04 Zack Weinberg <zack@codesourcery.com>
* lib/gas-defs.exp (run_dump_tests): New proc. * lib/gas-defs.exp (run_dump_tests): New proc.

View File

@ -74,6 +74,7 @@ if [expr ([istarget "i*86-*-*"] || [istarget "x86_64-*-*"]) && [gas_32_check]]
run_dump_test "padlock" run_dump_test "padlock"
run_dump_test "crx" run_dump_test "crx"
run_list_test "cr-err" "" run_list_test "cr-err" ""
run_dump_test "svme"
# These tests require support for 8 and 16 bit relocs, # These tests require support for 8 and 16 bit relocs,
# so we only run them for ELF and COFF targets. # so we only run them for ELF and COFF targets.
@ -128,6 +129,7 @@ if [expr ([istarget "i*86-*-*"] || [istarget "x86_64-*-*"]) && [gas_64_check]] t
run_list_test "x86-64-segment" "-al" run_list_test "x86-64-segment" "-al"
run_list_test "x86-64-inval-seg" "-al" run_list_test "x86-64-inval-seg" "-al"
run_dump_test "x86-64-branch" run_dump_test "x86-64-branch"
run_dump_test "svme64"
# For ELF targets verify that @unwind works. # For ELF targets verify that @unwind works.
if { ([istarget "*-*-elf*"] || [istarget "*-*-linux*"] if { ([istarget "*-*-elf*"] || [istarget "*-*-linux*"]

View File

@ -0,0 +1,29 @@
#objdump: -dw
#name: 32-bit SVME
.*: +file format .*
Disassembly of section .text:
0+000 <common>:
[ ]*[0-9a-f]+:[ ]+0f 01 dd[ ]+clgi[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 dc[ ]+stgi[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d9[ ]+vmmcall[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
[0-9a-f]+ <att32>:
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
[0-9a-f]+ <intel32>:
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
#pass

View File

@ -0,0 +1,36 @@
.text
common:
clgi
invlpga
skinit
stgi
vmload
vmmcall
vmrun
vmsave
.macro do_args arg1, arg2
invlpga \arg1, \arg2
vmload \arg1
vmrun \arg1
vmsave \arg1
.endm
.ifdef __amd64__
att64:
do_args (%rax), %ecx
.endif
att32:
skinit (%eax)
do_args (%eax), %ecx
.intel_syntax noprefix
.ifdef __amd64__
intel64:
do_args [rax], ecx
.endif
intel32:
skinit [eax]
do_args [eax], ecx
.p2align 4,0

View File

@ -0,0 +1,41 @@
#as: --defsym __amd64__=1
#objdump: -dw
#name: 64-bit SVME
#source: svme.s
.*: +file format .*
Disassembly of section .text:
0+000 <common>:
[ ]*[0-9a-f]+:[ ]+0f 01 dd[ ]+clgi[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 dc[ ]+stgi[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d9[ ]+vmmcall[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
[0-9a-f]+ <att64>:
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
[0-9a-f]+ <att32>:
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+67 0f 01 df[ ]+(addr32 )?invlpga[ ]*\(%eax\),[ ]*%ecx
[ ]*[0-9a-f]+:[ ]+67 0f 01 da[ ]+(addr32 )?vmload[ ]*\(%eax\)
[ ]*[0-9a-f]+:[ ]+67 0f 01 d8[ ]+(addr32 )?vmrun[ ]*\(%eax\)
[ ]*[0-9a-f]+:[ ]+67 0f 01 db[ ]+(addr32 )?vmsave[ ]*\(%eax\)
[0-9a-f]+ <intel64>:
[ ]*[0-9a-f]+:[ ]+0f 01 df[ ]+invlpga[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 da[ ]+vmload[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 d8[ ]+vmrun[ ]*
[ ]*[0-9a-f]+:[ ]+0f 01 db[ ]+vmsave[ ]*
[0-9a-f]+ <intel32>:
[ ]*[0-9a-f]+:[ ]+0f 01 de[ ]+skinit[ ]*
[ ]*[0-9a-f]+:[ ]+67 0f 01 df[ ]+(addr32 )?invlpga[ ]*\(%eax\),[ ]*%ecx
[ ]*[0-9a-f]+:[ ]+67 0f 01 da[ ]+(addr32 )?vmload[ ]*\(%eax\)
[ ]*[0-9a-f]+:[ ]+67 0f 01 d8[ ]+(addr32 )?vmrun[ ]*\(%eax\)
[ ]*[0-9a-f]+:[ ]+67 0f 01 db[ ]+(addr32 )?vmsave[ ]*\(%eax\)
#pass

View File

@ -1,3 +1,7 @@
2005-07-05 Jan Beulich <jbeulich@novell.com>
* i386.h (i386_optab): Add new insns.
2005-07-01 Nick Clifton <nickc@redhat.com> 2005-07-01 Nick Clifton <nickc@redhat.com>
* sparc.h: Add typedefs to structure declarations. * sparc.h: Add typedefs to structure declarations.

View File

@ -1383,6 +1383,22 @@ static const template i386_optab[] =
{"swapgs", 0, 0x0f01, 0xf8, Cpu64, NoSuf|ImmExt, { 0, 0, 0} }, {"swapgs", 0, 0x0f01, 0xf8, Cpu64, NoSuf|ImmExt, { 0, 0, 0} },
{"rdtscp", 0, 0x0f01, 0xf9, CpuSledgehammer,NoSuf|ImmExt, { 0, 0, 0} }, {"rdtscp", 0, 0x0f01, 0xf9, CpuSledgehammer,NoSuf|ImmExt, { 0, 0, 0} },
/* AMD Pacifica additions. */
{"clgi", 0, 0x0f01, 0xdd, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"invlpga", 0, 0x0f01, 0xdf, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
/* Need to ensure only "invlpga ...,%ecx" is accepted. */
{"invlpga", 2, 0x0f01, 0xdf, CpuSVME, NoSuf|ImmExt, { AnyMem, Reg32, 0 } },
{"skinit", 0, 0x0f01, 0xde, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"skinit", 1, 0x0f01, 0xde, CpuSVME, NoSuf|ImmExt, { AnyMem, 0, 0 } },
{"stgi", 0, 0x0f01, 0xdc, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"vmload", 0, 0x0f01, 0xda, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"vmload", 1, 0x0f01, 0xda, CpuSVME, NoSuf|ImmExt, { AnyMem, 0, 0 } },
{"vmmcall", 0, 0x0f01, 0xd9, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"vmrun", 0, 0x0f01, 0xd8, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"vmrun", 1, 0x0f01, 0xd8, CpuSVME, NoSuf|ImmExt, { AnyMem, 0, 0 } },
{"vmsave", 0, 0x0f01, 0xdb, CpuSVME, NoSuf|ImmExt, { 0, 0, 0 } },
{"vmsave", 1, 0x0f01, 0xdb, CpuSVME, NoSuf|ImmExt, { AnyMem, 0, 0 } },
/* VIA PadLock extensions. */ /* VIA PadLock extensions. */
{"xstore-rng",0, 0x000fa7, 0xc0, Cpu686|CpuPadLock, NoSuf|IsString|ImmExt, { 0, 0, 0} }, {"xstore-rng",0, 0x000fa7, 0xc0, Cpu686|CpuPadLock, NoSuf|IsString|ImmExt, { 0, 0, 0} },
{"xcrypt-ecb",0, 0xf30fa7, 0xc8, Cpu686|CpuPadLock, NoSuf|IsString|ImmExt, { 0, 0, 0} }, {"xcrypt-ecb",0, 0xf30fa7, 0xc8, Cpu686|CpuPadLock, NoSuf|IsString|ImmExt, { 0, 0, 0} },

View File

@ -1,3 +1,10 @@
2005-07-05 Jan Beulich <jbeulich@novell.com>
* i386-dis.c (SVME_Fixup): New.
(grps): Use it for the lidt entry.
(PNI_Fixup): Call OP_M rather than OP_E.
(INVLPG_Fixup): Likewise.
2005-07-04 H.J. Lu <hongjiu.lu@intel.com> 2005-07-04 H.J. Lu <hongjiu.lu@intel.com>
* tic30-dis.c (cnvt_tmsfloat_ieee): Use HUGE_VALF if defined. * tic30-dis.c (cnvt_tmsfloat_ieee): Use HUGE_VALF if defined.

View File

@ -95,6 +95,7 @@ static void OP_3DNowSuffix (int, int);
static void OP_SIMD_Suffix (int, int); static void OP_SIMD_Suffix (int, int);
static void SIMD_Fixup (int, int); static void SIMD_Fixup (int, int);
static void PNI_Fixup (int, int); static void PNI_Fixup (int, int);
static void SVME_Fixup (int, int);
static void INVLPG_Fixup (int, int); static void INVLPG_Fixup (int, int);
static void BadOp (void); static void BadOp (void);
static void SEG_Fixup (int, int); static void SEG_Fixup (int, int);
@ -1374,7 +1375,7 @@ static const struct dis386 grps[][8] = {
{ "sgdtIQ", M, XX, XX }, { "sgdtIQ", M, XX, XX },
{ "sidtIQ", PNI_Fixup, 0, XX, XX }, { "sidtIQ", PNI_Fixup, 0, XX, XX },
{ "lgdt{Q|Q||}", M, XX, XX }, { "lgdt{Q|Q||}", M, XX, XX },
{ "lidt{Q|Q||}", M, XX, XX }, { "lidt{Q|Q||}", SVME_Fixup, 0, XX, XX },
{ "smswQ", Ev, XX, XX }, { "smswQ", Ev, XX, XX },
{ "(bad)", XX, XX, XX }, { "(bad)", XX, XX, XX },
{ "lmsw", Ew, XX, XX }, { "lmsw", Ew, XX, XX },
@ -4445,7 +4446,77 @@ PNI_Fixup (int extrachar ATTRIBUTE_UNUSED, int sizeflag)
codep++; codep++;
} }
else else
OP_E (0, sizeflag); OP_M (0, sizeflag);
}
static void
SVME_Fixup (int bytemode, int sizeflag)
{
const char *alt;
char *p;
switch (*codep)
{
case 0xd8:
alt = "vmrun";
break;
case 0xd9:
alt = "vmmcall";
break;
case 0xda:
alt = "vmload";
break;
case 0xdb:
alt = "vmsave";
break;
case 0xdc:
alt = "stgi";
break;
case 0xdd:
alt = "clgi";
break;
case 0xde:
alt = "skinit";
break;
case 0xdf:
alt = "invlpga";
break;
default:
OP_M (bytemode, sizeflag);
return;
}
/* Override "lidt". */
p = obuf + strlen (obuf) - 4;
/* We might have a suffix. */
if (*p == 'i')
--p;
strcpy (p, alt);
if (!(prefixes & PREFIX_ADDR))
{
++codep;
return;
}
used_prefixes |= PREFIX_ADDR;
switch (*codep++)
{
case 0xdf:
strcpy (op2out, names32[1]);
two_source_ops = 1;
/* Fall through. */
case 0xd8:
case 0xda:
case 0xdb:
*obufp++ = open_char;
if (mode_64bit || (sizeflag & AFLAG))
alt = names32[0];
else
alt = names16[0];
strcpy (obufp, alt);
obufp += strlen (alt);
*obufp++ = close_char;
*obufp = '\0';
break;
}
} }
static void static void
@ -4462,7 +4533,7 @@ INVLPG_Fixup (int bytemode, int sizeflag)
alt = "rdtscp"; alt = "rdtscp";
break; break;
default: default:
OP_E (bytemode, sizeflag); OP_M (bytemode, sizeflag);
return; return;
} }
/* Override "invlpg". */ /* Override "invlpg". */