Add another e500 subreg pattern.
authorJoseph Myers <joseph@codesourcery.com>
Wed, 23 Nov 2016 23:32:54 +0000 (23:32 +0000)
committerJoseph Myers <jsm28@gcc.gnu.org>
Wed, 23 Nov 2016 23:32:54 +0000 (23:32 +0000)
Building glibc for powerpc-linux-gnuspe --enable-e500-double, given
the patch <https://gcc.gnu.org/ml/gcc-patches/2016-11/msg02404.html>
applied, fails with errors such as:

../sysdeps/ieee754/ldbl-128ibm/s_modfl.c: In function '__modfl':
../sysdeps/ieee754/ldbl-128ibm/s_modfl.c:91:1: error: unrecognizable insn:
 }
 ^
(insn 31 30 32 2 (set (reg:DF 203)
        (subreg:DF (reg:TI 202) 8)) "../sysdeps/ieee754/ldbl-128ibm/s_modfl.c":44 -1
     (nil))
../sysdeps/ieee754/ldbl-128ibm/s_modfl.c:91:1: internal compiler error: in extract_insn, at recog.c:2311

This patch adds an insn pattern similar to various patterns already
present to handle extracting such a subreg.  This allows the glibc
build to get further, until it runs into an assembler error for which
I have another patch.

gcc:
* config/rs6000/spe.md (*frob_<SPE64:mode>_ti_8): New insn
pattern.

gcc/testsuite:
* gcc.c-torture/compile/20161123-1.c: New test.

From-SVN: r242813

gcc/ChangeLog
gcc/config/rs6000/spe.md
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.c-torture/compile/20161123-1.c [new file with mode: 0644]

index 1cd24041b5b7b0159caf41c1b36f93aa59496be1..27e032df6d9efddf207532c0bea969979937d5ac 100644 (file)
@@ -1,3 +1,8 @@
+2016-11-23  Joseph Myers  <joseph@codesourcery.com>
+
+       * config/rs6000/spe.md (*frob_<SPE64:mode>_ti_8): New insn
+       pattern.
+
 2016-11-23  Segher Boessenkool  <segher@kernel.crashing.org>
 
        * combine.c (change_zero_ext): Only change the mode of a hard register
index 4b2220d38bba517ca69a3773cdc4d9d41ba3e71f..4d33210becde32d3ce2b00eca98de9c1174f39d2 100644 (file)
     }
 })
 
+(define_insn "*frob_<SPE64:mode>_ti_8"
+  [(set (match_operand:SPE64 0 "nonimmediate_operand" "=r")
+        (subreg:SPE64 (match_operand:TI 1 "input_operand" "r") 8))]
+  "(TARGET_E500_DOUBLE && <SPE64:MODE>mode == DFmode)
+   || (TARGET_SPE && <SPE64:MODE>mode != DFmode)"
+{
+  if (WORDS_BIG_ENDIAN)
+    return "evmergelo %0,%Y1,%Z1";
+  else
+    return "evmergelo %0,%Z1,%Y1";
+})
+
 (define_insn "*frob_tf_ti"
   [(set (match_operand:TF 0 "gpc_reg_operand" "=r")
         (subreg:TF (match_operand:TI 1 "gpc_reg_operand" "r") 0))]
index 77ada38e93bba4181a4791729ec48ab8252949f7..0af543cc9e0c1bdd7e6e58f8649069e990e67be6 100644 (file)
@@ -1,3 +1,7 @@
+2016-11-23  Joseph Myers  <joseph@codesourcery.com>
+
+       * gcc.c-torture/compile/20161123-1.c: New test.
+
 2016-11-23  Steven G. Kargl  <kargl@gcc.gnu.org>
 
        PR fortran/78297
diff --git a/gcc/testsuite/gcc.c-torture/compile/20161123-1.c b/gcc/testsuite/gcc.c-torture/compile/20161123-1.c
new file mode 100644 (file)
index 0000000..b8b2f1b
--- /dev/null
@@ -0,0 +1,7 @@
+double
+f (long double x)
+{
+  union { long double ld; double d[2]; } u;
+  u.ld = x;
+  return u.d[1];
+}