]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
x86: CPU-qualify {disp16} / {disp32}
authorJan Beulich <jbeulich@suse.com>
Fri, 17 Nov 2023 10:23:20 +0000 (11:23 +0100)
committerJan Beulich <jbeulich@suse.com>
Fri, 17 Nov 2023 10:23:20 +0000 (11:23 +0100)
{disp16} is invalid to use in 64-bit mode, while {disp32} is invalid to
use on pre-386 CPUs. The latter, also affecting other (real) prefixes,
further requires that like for insns we fully check the CPU flags; till
now only Cpu64/CpuNo64 were taken into consideration.

gas/config/tc-i386.c
gas/testsuite/gas/i386/prefix32.l
gas/testsuite/gas/i386/prefix32.s
gas/testsuite/gas/i386/prefix64.l
gas/testsuite/gas/i386/prefix64.s
opcodes/i386-opc.tbl
opcodes/i386-tbl.h

index 96065ae3b71cc41c33cbb99d88a0e7d786101923..6e788d8ee97a1e2a79915a94052861a3f7c28654 100644 (file)
@@ -5769,7 +5769,8 @@ parse_insn (const char *line, char *mnemonic, bool prefix_only)
          && current_templates
          && current_templates->start->opcode_modifier.isprefix)
        {
-         if (!cpu_flags_check_cpu64 (current_templates->start))
+         supported = cpu_flags_match (current_templates->start);
+         if (!(supported & CPU_FLAGS_64BIT_MATCH))
            {
              as_bad ((flag_code != CODE_64BIT
                       ? _("`%s' is only supported in 64-bit mode")
@@ -5777,6 +5778,14 @@ parse_insn (const char *line, char *mnemonic, bool prefix_only)
                      insn_name (current_templates->start));
              return NULL;
            }
+         if (supported != CPU_FLAGS_PERFECT_MATCH)
+           {
+             as_bad (_("`%s' is not supported on `%s%s'"),
+                     insn_name (current_templates->start),
+                     cpu_arch_name ? cpu_arch_name : default_arch,
+                     cpu_sub_arch_name ? cpu_sub_arch_name : "");
+             return NULL;
+           }
          /* If we are in 16-bit mode, do not allow addr16 or data16.
             Similarly, in 32-bit mode, do not allow addr32 or data32.  */
          if ((current_templates->start->opcode_modifier.size == SIZE16
index e43abbdc292fd96388696199ee3490824a8df55c..72d7972f1eb17b3f39f931dea4ad7736605aa997 100644 (file)
 .*:20: Error: data size .* `vaddps'
 .*:21: Error: data size .* `vaddpd'
 .*:25: Error: same type of prefix .*
+.*:31: Error: `xacquire' is not supported on `i386'
+.*:32: Error: `notrack' is not supported on `i386'
+.*:33: Error: `bnd' is not supported on `i386'
+.*:38: Error: `gs' is not supported on `i286'
+.*:39: Error: `data32' is not supported on `i286'
+.*:40: Error: `addr32' is not supported on `i286'
+.*:41: Error: .*disp32.* is not supported on `i286'
 GAS LISTING .*
 #...
 [      ]*1[    ]+\.text
@@ -40,4 +47,18 @@ GAS LISTING .*
 [      ]*26[   ]+\?\?\?\? 3E8B4500[    ]+ds mov                %ss:\(%ebp\), %eax
 [      ]*27[   ]+\?\?\?\? 3E8B4500[    ]+ds mov                %ds:\(%ebp\), %eax
 [      ]*28[   ]*
+[      ]*[0-9]+[       ]+\.L386:
+[      ]*[0-9]+[       ]+\.arch i386
+[      ]*[0-9]+[       ]+xacquire lock add \[esi\], eax
+[      ]*[0-9]+[       ]+notrack call eax
+[      ]*[0-9]+[       ]+bnd call eax
+[      ]*[0-9]+[       ]*
+[      ]*[0-9]+[       ]+\.L286:
+[      ]*[0-9]+[       ]+\.code16
+[      ]*[0-9]+[       ]+\.arch i286
+[      ]*[0-9]+[       ]+gs inc word ptr \[si\]
+[      ]*[0-9]+[       ]+data32 nop
+[      ]*[0-9]+[       ]+addr32 nop
+[      ]*[0-9]+[       ]+\{disp32\} nop
+[      ]*[0-9]+[       ]*
 #pass
index 598b0a775b65bc2f8213cd0520f97527c2fd32a5..9274f662d288ed469f41c9f02f7724e15f4fa7c3 100644 (file)
@@ -26,4 +26,18 @@ prefix:
        ds mov          %ss:(%ebp), %eax
        ds mov          %ds:(%ebp), %eax
 
+.L386:
+       .arch i386
+       xacquire lock add [esi], eax
+       notrack call eax
+       bnd call eax
+
+.L286:
+       .code16
+       .arch i286
+       gs inc word ptr [si]
+       data32 nop
+       addr32 nop
+       {disp32} nop
+
        .p2align        4,0
index 712f4e0d688c3b8a735498ce84bdaea2ef41f499..9bf85035af1fd2a80ca5a3df3491d4e774849fef 100644 (file)
@@ -3,12 +3,13 @@
 .*:7: Error: invalid .* `addss' after `repne'
 .*:8: Error: invalid .* `vaddss' after `repe'
 .*:9: Error: invalid .* `vaddss' after `repne'
-.*:14: Error: same type of prefix .*
-.*:15: Error: same type of prefix .*
-.*:18: Error: data size .* `addps'
-.*:19: Error: data size .* `addpd'
-.*:20: Error: data size .* `vaddps'
-.*:21: Error: data size .* `vaddpd'
+.*:11: Error: .*disp16.* is not supported .*
+.*:16: Error: same type of prefix .*
+.*:17: Error: same type of prefix .*
+.*:20: Error: data size .* `addps'
+.*:21: Error: data size .* `addpd'
+.*:22: Error: data size .* `vaddps'
+.*:23: Error: data size .* `vaddpd'
 GAS LISTING .*
 #...
 [      ]*1[    ]+\.text
@@ -21,16 +22,18 @@ GAS LISTING .*
 [      ]*8[    ]+repe vaddss   %xmm0, %xmm0, %xmm0
 [      ]*9[    ]+repne vaddss  %xmm0, %xmm0, %xmm0
 [      ]*10[   ]*
-[      ]*11[   ]+\.Lrep_ret:
-[      ]*12[   ]+\?\?\?\? F2C3[        ]+bnd ret
-[      ]*13[   ]+\?\?\?\? F3C3[        ]+rep ret
-[      ]*14[   ]+bnd rep ret
-[      ]*15[   ]+rep bnd ret
-[      ]*16[   ]*
-[      ]*17[   ]+\.Ldata16:
-[      ]*18[   ]+data16 addps  %xmm0, %xmm0
-[      ]*19[   ]+data16 addpd  %xmm0, %xmm0
-[      ]*20[   ]+data16 vaddps %xmm0, %xmm0, %xmm0
-[      ]*21[   ]+data16 vaddpd %xmm0, %xmm0, %xmm0
-[      ]*22[   ]*
+[      ]*[0-9]+[       ]+\{disp16\} nop
+[      ]*[0-9]+[       ]*
+[      ]*[0-9]+[       ]+\.Lrep_ret:
+[      ]*[0-9]+[       ]+\?\?\?\? F2C3[        ]+bnd ret
+[      ]*[0-9]+[       ]+\?\?\?\? F3C3[        ]+rep ret
+[      ]*[0-9]+[       ]+bnd rep ret
+[      ]*[0-9]+[       ]+rep bnd ret
+[      ]*[0-9]+[       ]*
+[      ]*[0-9]+[       ]+\.Ldata16:
+[      ]*[0-9]+[       ]+data16 addps  %xmm0, %xmm0
+[      ]*[0-9]+[       ]+data16 addpd  %xmm0, %xmm0
+[      ]*[0-9]+[       ]+data16 vaddps %xmm0, %xmm0, %xmm0
+[      ]*[0-9]+[       ]+data16 vaddpd %xmm0, %xmm0, %xmm0
+[      ]*[0-9]+[       ]*
 #pass
index 32091c7c05adba07904fb9644a92c8dc2da4f99b..4a0ec6a6851f7b0c68f68b5a7b0d469cd3a3be66 100644 (file)
@@ -8,6 +8,8 @@ prefix:
        repe vaddss     %xmm0, %xmm0, %xmm0
        repne vaddss    %xmm0, %xmm0, %xmm0
 
+       {disp16} nop
+
 .Lrep_ret:
        bnd ret
        rep ret
index c31bf20f2e6c4845f2c7513bb4da0a191d88bb92..167c0a0249f7e95f4ab46ef963a44883ece46381 100644 (file)
@@ -892,7 +892,7 @@ rex.wrxb, 0x4f, x64, NoSuf|IsPrefix, {}
 
 // Pseudo prefixes (base_opcode == PSEUDO_PREFIX)
 
-<pseudopfx:ident:cpu, disp8:Disp8:0, disp16:Disp16:0, disp32:Disp32:0, +
+<pseudopfx:ident:cpu, disp8:Disp8:0, disp16:Disp16:No64, disp32:Disp32:i386, +
                       load:Load:0, store:Store:0, +
                       vex:VEX:0, vex2:VEX:0, vex3:VEX3:0, evex:EVEX:0, +
                       rex:REX:x64, nooptimize:NoOptimize:0>
index 527793c5bf6591129bf1764f2b4916ac4cab28b3..e662a5017f08694d7e61823aff9a3845824c36fd 100644 (file)
@@ -5164,7 +5164,7 @@ static const insn_template i386_optab[] =
     { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0,
       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
       0 },
-    { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } },
+    { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0 } },
     { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } },
     { { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
          0, 0, 0, 0, 0, 0 } } } },
@@ -5172,7 +5172,7 @@ static const insn_template i386_optab[] =
     { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0,
       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
       0 },
-    { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } },
+    { { 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } },
     { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } },
     { { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
          0, 0, 0, 0, 0, 0 } } } },