On 2012-12-07 02:49, Marc Glisse wrote:
> The root problem is that we model the subs[sd] instructions as taking
> a 128-bit second operand, when Intel's documentation says they take a
> 32/64-bit operand, which is an important difference for memory
> operands (and constants). Writing a pattern that reconstructs the
> result from a scalar operation also seems more natural than
> pretending we are doing a parallel operation and dropping most of it
> (easier for recog and friends).

I agree this is a problem with the current representation.

> For 2-element vectors, vec_concat does seem more natural than
> vec_merge. If we chose vec_merge as the canonical representation, we
> should chose it for setting an element in a vector
> (ix86_expand_vector_set) everywhere, not just those scalarish
> operations.

I'd hate to enshrine vec_merge over vec_concat for the benefit of x86,
and to the detriment of e.g. mips.  There are plenty of embedded simd
implementations that are V2xx only.

If we simply pull the various x86 patterns into one common form, set
and extract included, does that buy us most of what we'd get for
playing games in combine?


As for your xmmintrin.h changes, I'd like to see a test case that verifies
that _mm_add_ss(a, b) does not add extra insns to extract __B[0].

> +(define_insn "<sse>_vm<plusminus_insn><mode>3<vec_merge_or_concat>"
>    [(set (match_operand:VF_128 0 "register_operand" "=x,x")
>       (vec_merge:VF_128
> -       (plusminus:VF_128
> -         (match_operand:VF_128 1 "register_operand" "0,x")
> -         (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm"))
> +       (vec_duplicate:VF_128
> +         (plusminus:<ssescalarmode>
> +           (vec_select:<ssescalarmode>
> +             (match_operand:VF_128 1 "register_operand" "0,x")
> +             (parallel [(const_int 0)]))
> +           (match_operand:<ssescalarmode> 2 "nonimmediate_operand" "xm,xm")))
>         (match_dup 1)
>         (const_int 1)))]
>    "TARGET_SSE"
>    "@
>     <plusminus_mnemonic><ssescalarmodesuffix>\t{%2, %0|%0, %2}
>     v<plusminus_mnemonic><ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
>    [(set_attr "isa" "noavx,avx")
>     (set_attr "type" "sseadd")
>     (set_attr "prefix" "orig,vex")
>     (set_attr "mode" "<ssescalarmode>")])

Did this really trigger as a substitution?  It's not supposed to have, since
you didn't add (set_attr "replace_vec_merge_with_vec_concat" "yes")...


r~

Reply via email to