diff mbox

[i386] Fix PR 64688, ICE: Max. number of generated reload insns per insn is achieved (90)

Message ID CAFULd4am5i+jBcAWg6db+qtnNHsWHv4dkYaCE-iYWm=bHmgmNg@mail.gmail.com
State New
Headers show

Commit Message

Uros Bizjak Jan. 22, 2015, 2:41 p.m. UTC
Hello!

Attached patch fixes PR 64688. Operand constraints were wrong for
reg-to-vec targets.

The patch also fixes PR 64477.

2015-22-01  Uros Bizjak  <ubizjak@gmail.com>

        PR target/64688
        PR target/64477
        * config/i386/sse.md (vec_set<mode>_0): Use (Yi/r/C) constraints
        for alternative 3.

testsuite/ChangeLog:

2015-22-01  Uros Bizjak  <ubizjak@gmail.com>

        PR target/64688
        * g++.dg/pr64688.C: New test.

Bootstrapped and regression tested on x86_64-linux-gnu {,-m32}.

Committed to mainline, will be backported to release branches.

Uros.
diff mbox

Patch

Index: testsuite/g++.dg/pr64688.C
===================================================================
--- testsuite/g++.dg/pr64688.C	(revision 0)
+++ testsuite/g++.dg/pr64688.C	(revision 0)
@@ -0,0 +1,71 @@ 
+// { dg-do compile { target i?86-*-* x86_64-*-* } }
+// { dg-options "-std=c++11 -O3 -march=westmere" }
+
+template <typename T> struct A { typedef typename T::next type; };
+template <typename> struct B;
+template <typename T> struct N : T {};
+template <int N> struct C {
+  static const int value = N;
+  typedef C<N + 1> next;
+};
+template <typename Sequence>
+struct R : N<typename B<typename Sequence::tag>::template P<Sequence>> {};
+template <typename Base> struct O : Base {
+  typedef typename A<typename Base::size>::type size;
+};
+template <typename = int> struct D {
+  typedef int tag;
+  typedef C<0> size;
+};
+template <> struct B<int> {
+  template <typename> struct P : O<O<O<D<>>>>::size {};
+};
+template <typename> struct F;
+template <typename> struct G;
+template <typename, typename, int> struct H;
+template <typename Element, typename Layout> struct H<Element, Layout, 3> {};
+template <int, typename E, typename L, int N> unsigned char at_c(H<E, L, N>) {}
+template <typename> class I;
+template <typename> class J;
+template <typename> class K;
+template <typename, typename> struct Q;
+struct L {
+  typedef Q<unsigned char, F<O<O<O<D<>>>>>> *type;
+};
+template <typename XIterator> struct M { typedef K<J<I<XIterator>>> view_t; };
+template <typename, typename>
+struct Q : H<unsigned, F<int>, R<O<O<O<D<>>>>>::value> {};
+template <typename Iterator> struct G<I<Iterator>> { typedef Iterator type; };
+template <typename> class J {
+public:
+  typedef G<I<Q<unsigned, int> *>>::type x_iterator;
+};
+template <typename> class K {
+public:
+  J<int>::x_iterator row_begin(int);
+};
+template <typename Op> void measure_time(Op p1) { p1(); }
+template <typename, typename> struct fill_nongil_t;
+template <typename T, typename P>
+struct fill_nongil_t<K<J<I<Q<T, F<O<O<O<D<>>>>>> *>>>, P> {
+  typedef K<J<I<Q<T, F<O<O<O<D<>>>>>> *>>> View;
+  View _v;
+  P _p;
+  fill_nongil_t(View, P);
+  void operator()() {
+    T *first = (T *)_v.row_begin(0);
+    T last;
+    while (first != &last) {
+      first[0] = first[1] = at_c<1>(_p);
+      first[2] = at_c<2>(_p);
+      first += 3;
+    }
+  }
+};
+template <typename, typename> void test_fill(int) {
+  M<L::type>::view_t __trans_tmp_1;
+  measure_time(fill_nongil_t<K<J<I<Q<unsigned char, F<O<O<O<D<>>>>>> *>>>,
+                             Q<unsigned char, F<O<O<O<D<>>>>>>>(
+      __trans_tmp_1, Q<unsigned char, F<O<O<O<D<>>>>>>()));
+}
+void performance_testtest_method() { test_fill<K<int>, Q<unsigned, int>>(0); }
Index: config/i386/sse.md
===================================================================
--- config/i386/sse.md	(revision 219987)
+++ config/i386/sse.md	(working copy)
@@ -6391,11 +6391,11 @@ 
 ;; see comment above inline_secondary_memory_needed function in i386.c
 (define_insn "vec_set<mode>_0"
   [(set (match_operand:VI4F_128 0 "nonimmediate_operand"
-	  "=Yr,*v,v,v ,x,x,v,Yr ,*x ,x  ,m ,m   ,m")
+	  "=Yr,*v,v,Yi,x,x,v,Yr ,*x ,x  ,m ,m   ,m")
 	(vec_merge:VI4F_128
 	  (vec_duplicate:VI4F_128
 	    (match_operand:<ssescalarmode> 2 "general_operand"
-	  " Yr,*v,m,*r,m,x,v,*rm,*rm,*rm,!x,!*re,!*fF"))
+	  " Yr,*v,m,r ,m,x,v,*rm,*rm,*rm,!x,!*re,!*fF"))
 	  (match_operand:VI4F_128 1 "vector_move_operand"
 	  " C , C,C,C ,C,0,v,0  ,0  ,x  ,0 ,0   ,0")
 	  (const_int 1)))]