OSDN Git Service

gas/
authorJan Beulich <jbeulich@novell.com>
Wed, 14 Dec 2005 08:57:06 +0000 (08:57 +0000)
committerJan Beulich <jbeulich@novell.com>
Wed, 14 Dec 2005 08:57:06 +0000 (08:57 +0000)
2005-12-14  Jan Beulich  <jbeulich@novell.com>

* config/tc-i386.c (add_prefix): More fine-grained handling of
REX prefixes. Or new prefix value into i.prefix instead of
assigning.

gas/testsuite/
2005-12-14  Jan Beulich  <jbeulich@novell.com>

* gas/i386/rex.[sd]: New.
* gas/i386/i386.exp: Run new test.

gas/ChangeLog
gas/config/tc-i386.c
gas/testsuite/ChangeLog
gas/testsuite/gas/i386/i386.exp
gas/testsuite/gas/i386/rex.d [new file with mode: 0644]
gas/testsuite/gas/i386/rex.s [new file with mode: 0644]

index 3f2897a..68e748b 100644 (file)
@@ -1,3 +1,9 @@
+2005-12-14  Jan Beulich  <jbeulich@novell.com>
+
+       * config/tc-i386.c (add_prefix): More fine-grained handling of
+       REX prefixes. Or new prefix value into i.prefix instead of
+       assigning.
+
 2005-12-13  DJ Delorie  <dj@redhat.com>
 
        * config/tc-m32c.c (m32c_md_end): Only pad code sections.
index b95a664..f9804e0 100644 (file)
@@ -730,55 +730,66 @@ add_prefix (prefix)
      unsigned int prefix;
 {
   int ret = 1;
-  int q;
+  unsigned int q;
 
   if (prefix >= REX_OPCODE && prefix < REX_OPCODE + 16
       && flag_code == CODE_64BIT)
-    q = REX_PREFIX;
+    {
+      if ((i.prefix[REX_PREFIX] & prefix & REX_MODE64)
+         || ((i.prefix[REX_PREFIX] & (REX_EXTX | REX_EXTY | REX_EXTZ))
+             && (prefix & (REX_EXTX | REX_EXTY | REX_EXTZ))))
+       ret = 0;
+      q = REX_PREFIX;
+    }
   else
-    switch (prefix)
-      {
-      default:
-       abort ();
-
-      case CS_PREFIX_OPCODE:
-      case DS_PREFIX_OPCODE:
-      case ES_PREFIX_OPCODE:
-      case FS_PREFIX_OPCODE:
-      case GS_PREFIX_OPCODE:
-      case SS_PREFIX_OPCODE:
-       q = SEG_PREFIX;
-       break;
+    {
+      switch (prefix)
+       {
+       default:
+         abort ();
+
+       case CS_PREFIX_OPCODE:
+       case DS_PREFIX_OPCODE:
+       case ES_PREFIX_OPCODE:
+       case FS_PREFIX_OPCODE:
+       case GS_PREFIX_OPCODE:
+       case SS_PREFIX_OPCODE:
+         q = SEG_PREFIX;
+         break;
 
-      case REPNE_PREFIX_OPCODE:
-      case REPE_PREFIX_OPCODE:
-       ret = 2;
-       /* fall thru */
-      case LOCK_PREFIX_OPCODE:
-       q = LOCKREP_PREFIX;
-       break;
+       case REPNE_PREFIX_OPCODE:
+       case REPE_PREFIX_OPCODE:
+         ret = 2;
+         /* fall thru */
+       case LOCK_PREFIX_OPCODE:
+         q = LOCKREP_PREFIX;
+         break;
 
-      case FWAIT_OPCODE:
-       q = WAIT_PREFIX;
-       break;
+       case FWAIT_OPCODE:
+         q = WAIT_PREFIX;
+         break;
 
-      case ADDR_PREFIX_OPCODE:
-       q = ADDR_PREFIX;
-       break;
+       case ADDR_PREFIX_OPCODE:
+         q = ADDR_PREFIX;
+         break;
 
-      case DATA_PREFIX_OPCODE:
-       q = DATA_PREFIX;
-       break;
-      }
+       case DATA_PREFIX_OPCODE:
+         q = DATA_PREFIX;
+         break;
+       }
+      if (i.prefix[q] != 0)
+       ret = 0;
+    }
 
-  if (i.prefix[q] != 0)
+  if (ret)
     {
-      as_bad (_("same type of prefix used twice"));
-      return 0;
+      if (!i.prefix[q])
+       ++i.prefixes;
+      i.prefix[q] |= prefix;
     }
+  else
+    as_bad (_("same type of prefix used twice"));
 
-  i.prefixes += 1;
-  i.prefix[q] = prefix;
   return ret;
 }
 
index a5d1124..a7e9c9f 100644 (file)
@@ -1,3 +1,8 @@
+2005-12-14  Jan Beulich  <jbeulich@novell.com>
+
+       * gas/i386/rex.[sd]: New.
+       * gas/i386/i386.exp: Run new test.
+
 2005-12-12  Nathan Sidwell  <nathan@codesourcery.com>
 
        * gas/mt: Renamed from ms1 dir.  Update file names as needed.
index 718514f..6638d4b 100644 (file)
@@ -133,6 +133,21 @@ if [expr ([istarget "i*86-*-*"] || [istarget "x86_64-*-*"]) && [gas_64_check]] t
     run_dump_test "immed64"
     run_dump_test "x86-64-prescott"
 
+    if { ![istarget "*-*-aix*"]
+      && ![istarget "*-*-beos*"]
+      && ![istarget "*-*-*bsd*"]
+      && ![istarget "*-*-chaos*"]
+      && ![istarget "*-*-kaos*"]
+      && ![istarget "*-*-lynx*"]
+      && ![istarget "*-*-moss*"]
+      && ![istarget "*-*-nto-qnx*"]
+      && ![istarget "*-*-rtems*"]
+      && ![istarget "*-*-sco*"]
+      && ![istarget "*-*-solaris*"]
+      && ![istarget "*-*-sysv*"] } then {
+       run_dump_test "rex"
+    }
+
     # For ELF targets verify that @unwind works.
     if { ([istarget "*-*-elf*"] || [istarget "*-*-linux*"]
          || [istarget "*-*-solaris2.*"])
diff --git a/gas/testsuite/gas/i386/rex.d b/gas/testsuite/gas/i386/rex.d
new file mode 100644 (file)
index 0000000..dab6b12
--- /dev/null
@@ -0,0 +1,17 @@
+#objdump: -dw
+#name: x86-64 manual rex prefix use
+
+.*: +file format elf64-x86-64
+
+Disassembly of section .text:
+
+0+ <_start>:
+[       ]*[0-9a-f]+:[   ]+40 0f ae 00[  ]+rex fxsavel?[         ]+\(%rax\)
+[       ]*[0-9a-f]+:[   ]+48 0f ae 00[  ]+(rex64 )?fxsaveq?[    ]+\(%rax\)
+[       ]*[0-9a-f]+:[   ]+41 0f ae 00[  ]+fxsavel?[     ]+\(%r8\)
+[       ]*[0-9a-f]+:[   ]+49 0f ae 00[  ]+(rex64Z? )?fxsaveq?[  ]+\(%r8\)
+[       ]*[0-9a-f]+:[   ]+42 0f ae 04 05 00 00 00 00[   ]+fxsavel?[     ]+(0x0)?\(,%r8(,1)?\)
+[       ]*[0-9a-f]+:[   ]+4a 0f ae 04 05 00 00 00 00[   ]+(rex64Y? )?fxsaveq?[  ]+(0x0)?\(,%r8(,1)?\)
+[       ]*[0-9a-f]+:[   ]+43 0f ae 04 00[       ]+fxsavel?[     ]+\(%r8,%r8(,1)?\)
+[       ]*[0-9a-f]+:[   ]+4b 0f ae 04 00[       ]+(rex64(YZ)? )?fxsaveq?[       ]+\(%r8,%r8(,1)?\)
+#pass
diff --git a/gas/testsuite/gas/i386/rex.s b/gas/testsuite/gas/i386/rex.s
new file mode 100644 (file)
index 0000000..a142312
--- /dev/null
@@ -0,0 +1,11 @@
+ .text
+
+_start:
+       rex/fxsave (%rax)
+       rex64/fxsave (%rax)
+       rex/fxsave (%r8)
+       rex64/fxsave (%r8)
+       rex/fxsave (,%r8)
+       rex64/fxsave (,%r8)
+       rex/fxsave (%r8,%r8)
+       rex64/fxsave (%r8,%r8)