patch: convert scalar literals to vector constants (PR/7277)
Aldy Hernandez
aldyh@redhat.com
Tue Jun 3 14:09:00 GMT 2003
Damn it, I'm attempting to be a good net-citizen by fixing PRs and all
I keep running into is SIMD bugs. I'm trying to get a reputation for
something, anything else, but SIMD stuff.
>> Do we even support casting scalars into vectors? I doubt it, but we
>> should at least make an exception for the 0 constant.
>
> Of course we do, from scalars of the same size. We consider it
> a bit-reinterpretation operation.
Well wadayaknow. News to me.
>> What I suggest is fixing convert_mode() to convert scalar 0 into
>> vector
>> 0. Is this an appropriate solution?
>
> Yes.
Aiiiight. Fix below.
Pending tests on x86-linux, ok?
2003-06-03 Aldy Hernandez <aldyh@redhat.com>
PR/7277
* expr.c (convert_modes): Handle scalar to vector conversion.
(convert_const_to_vector): New.
* testsuite/gcc.c-torture/compile/simd-7.c: New.
Index: expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.545
diff -c -p -r1.545 expr.c
*** expr.c 3 Jun 2003 08:57:52 -0000 1.545
--- expr.c 3 Jun 2003 13:49:54 -0000
*************** static void emit_single_push_insn PARAMS
*** 179,184 ****
--- 179,185 ----
#endif
static void do_tablejump PARAMS ((rtx, enum machine_mode, rtx, rtx,
rtx));
static rtx const_vector_from_tree PARAMS ((tree));
+ static rtx convert_const_to_vector (enum machine_mode, rtx);
/* Record for each mode whether we can move a register directly to or
from an object of that mode in memory. If we can't, we won't try
*************** convert_modes (mode, oldmode, x, unsigne
*** 1433,1443 ****
return gen_lowpart (mode, x);
}
temp = gen_reg_rtx (mode);
convert_move (temp, x, unsignedp);
return temp;
}
!
/* This macro is used to determine what the largest unit size that
move_by_pieces can use is. */
--- 1434,1496 ----
return gen_lowpart (mode, x);
}
+ if (VECTOR_MODE_P (mode) && CONSTANT_P (x))
+ return convert_const_to_vector (mode, x);
+
temp = gen_reg_rtx (mode);
convert_move (temp, x, unsignedp);
return temp;
}
!
! /* Convert a CONST_INT to a CONST_VECTOR. */
! static rtx
! convert_const_to_vector (enum machine_mode mode, rtx x)
! {
! rtvec v;
! int units, i, inner_bits;
! enum machine_mode inner;
! unsigned HOST_WIDE_INT cst[2];
!
! if (x == const0_rtx)
! return CONST0_RTX (mode);
!
! if (GET_CODE (x) == CONST_INT)
! {
! cst[0] = INTVAL (x);
! cst[1] = 0;
! }
! else if (GET_CODE (x) == CONST_DOUBLE)
! {
! cst[0] = CONST_DOUBLE_LOW (x);
! cst[1] = CONST_DOUBLE_HIGH (x);
! }
! else
! abort ();
!
! units = GET_MODE_NUNITS (mode);
! inner = GET_MODE_INNER (mode);
! inner_bits = GET_MODE_BITSIZE (inner);
! v = rtvec_alloc (units);
!
! /* Convert 0x6699 into:
! (const_vector:M (const_int 0x0)
! ...
! (const_int 0x66)
! (const_int 0x99)). */
!
! for (i = 0; i < units; ++i)
! {
! int idx;
!
! idx = (i * inner_bits + 1) > HOST_BITS_PER_WIDE_INT ? 1 : 0;
! RTVEC_ELT (v, units - i - 1)
! = gen_rtx_CONST_INT (inner, cst[idx] & ((1 << inner_bits) - 1));
! cst[idx] >>= inner_bits;
! }
!
! return gen_rtx_raw_CONST_VECTOR (mode, v);
! }
!
/* This macro is used to determine what the largest unit size that
move_by_pieces can use is. */
Index: testsuite/gcc.c-torture/compile/simd-7.c
===================================================================
RCS file: testsuite/gcc.c-torture/compile/simd-7.c
diff -N testsuite/gcc.c-torture/compile/simd-7.c
*** /dev/null 1 Jan 1970 00:00:00 -0000
--- testsuite/gcc.c-torture/compile/simd-7.c 3 Jun 2003 13:49:54 -0000
***************
*** 0 ****
--- 1,6 ----
+ typedef int v8qi __attribute__ ((mode(V8QI)));
+
+ v8qi null(void)
+ {
+ return (v8qi) 0x1122334455667788LL;
+ }
More information about the Gcc-patches
mailing list