aboutsummaryrefslogtreecommitdiff
path: root/gcc/expr.c
diff options
context:
space:
mode:
authorRichard Henderson <rth@redhat.com>2011-12-10 12:43:03 -0800
committerRichard Henderson <rth@gcc.gnu.org>2011-12-10 12:43:03 -0800
commitccdfb0e2c6ad7c93ca7657a79a773f0af8f40be7 (patch)
tree64952c5ea5b975ebfc52549bce82d112fa6ee2eb /gcc/expr.c
parenta7de2c2a71940a25408c1320498c1c1ca2472313 (diff)
downloadgcc-ccdfb0e2c6ad7c93ca7657a79a773f0af8f40be7.zip
gcc-ccdfb0e2c6ad7c93ca7657a79a773f0af8f40be7.tar.gz
gcc-ccdfb0e2c6ad7c93ca7657a79a773f0af8f40be7.tar.bz2
Force the creation of a CONST_VECTOR for expand_vec_perm.
* expr.c (expand_expr_real_2) [VEC_PERM_EXPR]: Avoid passing a CONST_INT to expand_vec_perm as the selector. * optabs.c (expand_vec_perm): Assert the selector is of a proper mode. From-SVN: r182192
Diffstat (limited to 'gcc/expr.c')
-rw-r--r--gcc/expr.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/gcc/expr.c b/gcc/expr.c
index b2166bd..aa78468 100644
--- a/gcc/expr.c
+++ b/gcc/expr.c
@@ -8716,6 +8716,23 @@ expand_expr_real_2 (sepops ops, rtx target, enum machine_mode tmode,
case VEC_PERM_EXPR:
expand_operands (treeop0, treeop1, target, &op0, &op1, EXPAND_NORMAL);
op2 = expand_normal (treeop2);
+
+ /* Careful here: if the target doesn't support integral vector modes,
+ a constant selection vector could wind up smooshed into a normal
+ integral constant. */
+ if (CONSTANT_P (op2) && GET_CODE (op2) != CONST_VECTOR)
+ {
+ tree sel_type = TREE_TYPE (treeop2);
+ enum machine_mode vmode
+ = mode_for_vector (TYPE_MODE (TREE_TYPE (sel_type)),
+ TYPE_VECTOR_SUBPARTS (sel_type));
+ gcc_assert (GET_MODE_CLASS (vmode) == MODE_VECTOR_INT);
+ op2 = simplify_subreg (vmode, op2, TYPE_MODE (sel_type), 0);
+ gcc_assert (op2 && GET_CODE (op2) == CONST_VECTOR);
+ }
+ else
+ gcc_assert (GET_MODE_CLASS (GET_MODE (op2)) == MODE_VECTOR_INT);
+
temp = expand_vec_perm (mode, op0, op1, op2, target);
gcc_assert (temp);
return temp;