Hi!

The following patch fixes a bunch of ICEs in rs6000 print_operand; we
shouldn't ICE on them when users write mess in their inline asm.

Bootstrapped/regtested on powerpc64{,le}-linux (including -m32 testing
on powerpc64-linux), ok for trunk?

2018-11-26  Jakub Jelinek  <ja...@redhat.com>

        PR target/88188
        * config/rs6000/rs6000.c (print_operand) <case 'D'>: Use
        output_operand_lossage instead of gcc_assert.
        <case 't'>: Likewise.
        <case 'z'>: Likewise.
        <case 'V'>: Use output_operand_lossage instead of gcc_unreachable.

        * gcc.target/powerpc/pr88188.c: New test.

--- gcc/config/rs6000/rs6000.c.jj       2018-11-16 21:35:42.497982764 +0100
+++ gcc/config/rs6000/rs6000.c  2018-11-26 10:56:28.079516458 +0100
@@ -20644,7 +20644,11 @@ print_operand (FILE *file, rtx x, int co
 
     case 'D':
       /* Like 'J' but get to the GT bit only.  */
-      gcc_assert (REG_P (x));
+      if (!REG_P (x))
+       {
+         output_operand_lossage ("invalid %%D value");
+         return;
+       }
 
       /* Bit 1 is GT bit.  */
       i = 4 * (REGNO (x) - CR0_REGNO) + 1;
@@ -20900,7 +20904,11 @@ print_operand (FILE *file, rtx x, int co
 
     case 't':
       /* Like 'J' but get to the OVERFLOW/UNORDERED bit.  */
-      gcc_assert (REG_P (x) && GET_MODE (x) == CCmode);
+      if (!REG_P (x) || GET_MODE (x) != CCmode)
+       {
+         output_operand_lossage ("invalid %%t value");
+         return;
+       }
 
       /* Bit 3 is OV bit.  */
       i = 4 * (REGNO (x) - CR0_REGNO) + 3;
@@ -20989,7 +20997,7 @@ print_operand (FILE *file, rtx x, int co
          fputs ("lge", file);  /* 5 */
          break;
        default:
-         gcc_unreachable ();
+         output_operand_lossage ("invalid %%V value");
        }
       break;
 
@@ -21059,7 +21067,11 @@ print_operand (FILE *file, rtx x, int co
         names.  If we are configured for System V (or the embedded ABI) on
         the PowerPC, do not emit the period, since those systems do not use
         TOCs and the like.  */
-      gcc_assert (GET_CODE (x) == SYMBOL_REF);
+      if (GET_CODE (x) != SYMBOL_REF)
+       {
+         output_operand_lossage ("invalid %%z value");
+         return;
+       }
 
       /* For macho, check to see if we need a stub.  */
       if (TARGET_MACHO)
--- gcc/testsuite/gcc.target/powerpc/pr88188.c.jj       2018-11-26 
11:02:56.077086682 +0100
+++ gcc/testsuite/gcc.target/powerpc/pr88188.c  2018-11-26 11:02:13.621786846 
+0100
@@ -0,0 +1,13 @@
+/* PR target/88188 */
+/* { dg-do compile } */
+
+int m;
+
+void
+foo (void)
+{
+  __asm volatile ("%D0" : : "m" (m));  /* { dg-error "invalid %D value" } */
+  __asm volatile ("%t0" : : "m" (m));  /* { dg-error "invalid %t value" } */
+  __asm volatile ("%V0" : : "r" (0));  /* { dg-error "invalid %V value" } */
+  __asm volatile ("%z0" : : "r" (0));  /* { dg-error "invalid %z value" } */
+}

        Jakub

Reply via email to