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 <ubiz...@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 <ubiz...@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.
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)))]