x86: fix 3-operand insn reverse-matching
authorJan Beulich <jbeulich@suse.com>
Wed, 6 Jul 2022 13:39:03 +0000 (15:39 +0200)
committerJan Beulich <jbeulich@suse.com>
Wed, 6 Jul 2022 13:39:03 +0000 (15:39 +0200)
The middle operand would have gone entirely unchecked, allowing e.g.

vmovss %xmm0, %esp, %xmm2

to assemble successfully, or e.g.

vmovss %xmm0, $4, %xmm2

causing an internal error. Alongside dealing with this also drop a
related comment, which hasn't been applicable anymore since the
introduction of 3-operand patterns with D set (and which perhaps never
had been logical to be there, as reverse-matched insns don't make it
there in the first place).

gas/config/tc-i386.c
gas/testsuite/gas/i386/inval-avx.l
gas/testsuite/gas/i386/inval-avx.s

index d915b15a6b2231a80ad29e068e422a239637ff8e..542f5cdf2d03616f0da5a1e843cf0f274846807e 100644 (file)
@@ -6724,8 +6724,12 @@ match_template (char mnem_suffix)
              /* Try reversing direction of operands.  */
              overlap0 = operand_type_and (i.types[0], operand_types[i.operands - 1]);
              overlap1 = operand_type_and (i.types[i.operands - 1], operand_types[0]);
+             overlap2 = operand_type_and (i.types[1], operand_types[1]);
+             gas_assert (t->operands != 3 || !check_register);
              if (!operand_type_match (overlap0, i.types[0])
                  || !operand_type_match (overlap1, i.types[i.operands - 1])
+                 || (t->operands == 3
+                     && !operand_type_match (overlap2, i.types[1]))
                  || (check_register
                      && !operand_type_register_match (i.types[0],
                                                       operand_types[i.operands - 1],
@@ -6797,8 +6801,6 @@ match_template (char mnem_suffix)
                    continue;
                  /* Fall through.  */
                case 3:
-                 /* Here we make use of the fact that there are no
-                    reverse match 3 operand instructions.  */
                  if (!operand_type_match (overlap2, i.types[2])
                      || ((check_register & 5) == 5
                          && !operand_type_register_match (i.types[0],
index 866987e784f446a410c04848ca1359f28a7228b7..0b475276dc716e72f39f930da544809910bf1626 100644 (file)
@@ -2,20 +2,13 @@
 .*:4: Error: .*
 .*:5: Error: .*
 .*:6: Error: .*
-.*:9: Error:.* ambiguous .* `vcvtpd2dq'
-.*:10: Error:.* ambiguous .* `vcvtpd2ps'
-.*:11: Error:.* ambiguous .* `vcvttpd2dq'
+.*:8: Error: .*
+.*:9: Error: .*
+.*:10: Error: .*
+.*:11: Error: .*
+.*:12: Error: .*
+.*:15: Error:.* ambiguous .* `vcvtpd2dq'
+.*:16: Error:.* ambiguous .* `vcvtpd2ps'
+.*:17: Error:.* ambiguous .* `vcvttpd2dq'
 GAS LISTING .*
-
-
-[      ]*1[    ]+\# Check illegal AVX instructions
-[      ]*2[    ]+\.text
-[      ]*3[    ]+_start:
-[      ]*4[    ]+vcvtpd2dq \(%ecx\),%xmm2
-[      ]*5[    ]+vcvtpd2ps \(%ecx\),%xmm2
-[      ]*6[    ]+vcvttpd2dq \(%ecx\),%xmm2
-[      ]*7[    ]+
-[      ]*8[    ]+\.intel_syntax noprefix
-[      ]*9[    ]+vcvtpd2dq xmm2,\[ecx\]
-[      ]*10[   ]+vcvtpd2ps xmm2,\[ecx\]
-[      ]*11[   ]+vcvttpd2dq xmm2,\[ecx\]
+#pass
index 94a64f62888b5a42d56dd0df8d6372263f66205a..741901a96cf36c4747e5222a3325b5dd3b74ff0e 100644 (file)
@@ -5,6 +5,12 @@ _start:
        vcvtpd2ps (%ecx),%xmm2
        vcvttpd2dq (%ecx),%xmm2
 
+       vmovss %xmm0, (%esp), %xmm2
+       vmovss %xmm0, $4, %xmm2
+       vmovss %xmm0, %cr0, %xmm2
+       vmovss %xmm0, %ymm4, %xmm2
+       vmovss %xmm0, %mm4, %xmm2
+
        .intel_syntax noprefix
        vcvtpd2dq xmm2,[ecx]
        vcvtpd2ps xmm2,[ecx]