summaryrefslogtreecommitdiff
path: root/gcc/config/arm
diff options
context:
space:
mode:
authorirar <irar@138bc75d-0d04-0410-961f-82ee72b054a4>2011-10-18 09:39:04 +0000
committerirar <irar@138bc75d-0d04-0410-961f-82ee72b054a4>2011-10-18 09:39:04 +0000
commit6083c152b1604d974f9691123617353e94bb15c6 (patch)
tree003e1d024145ae0b6a8fe049fd43e175358d9b1e /gcc/config/arm
parent6fc569059b7a519c78eb12d7fa32cf4eec3bc436 (diff)
downloadgcc-6083c152b1604d974f9691123617353e94bb15c6.tar.gz
* doc/md.texi (vec_widen_ushiftl_hi, vec_widen_ushiftl_lo,
vec_widen_sshiftl_hi, vec_widen_sshiftl_lo): Document. * tree-pretty-print.c (dump_generic_node): Handle WIDEN_LSHIFT_EXPR, VEC_WIDEN_LSHIFT_HI_EXPR and VEC_WIDEN_LSHIFT_LO_EXPR. (op_code_prio): Likewise. (op_symbol_code): Handle WIDEN_LSHIFT_EXPR. * optabs.c (optab_for_tree_code): Handle VEC_WIDEN_LSHIFT_HI_EXPR and VEC_WIDEN_LSHIFT_LO_EXPR. (init-optabs): Initialize optab codes for vec_widen_u/sshiftl_hi/lo. * optabs.h (enum optab_index): Add OTI_vec_widen_u/sshiftl_hi/lo. * genopinit.c (optabs): Initialize the new optabs. * expr.c (expand_expr_real_2): Handle VEC_WIDEN_LSHIFT_HI_EXPR and VEC_WIDEN_LSHIFT_LO_EXPR. * gimple-pretty-print.c (dump_binary_rhs): Likewise. * tree-vectorizer.h (NUM_PATTERNS): Increase to 8. * tree.def (WIDEN_LSHIFT_EXPR, VEC_WIDEN_LSHIFT_HI_EXPR, VEC_WIDEN_LSHIFT_LO_EXPR): New. * cfgexpand.c (expand_debug_expr): Handle new tree codes. * tree-vect-patterns.c (vect_vect_recog_func_ptrs): Add vect_recog_widen_shift_pattern. (vect_handle_widen_mult_by_const): Rename... (vect_handle_widen_op_by_const): ...to this. Handle shifts. Add a new argument, update documentation. (vect_recog_widen_mult_pattern): Assume that only second operand can be constant. Update call to vect_handle_widen_op_by_const. (vect_recog_over_widening_pattern): Fix typo. (vect_recog_widen_shift_pattern): New. * tree-vect-stmts.c (vectorizable_type_promotion): Handle widening shifts. (supportable_widening_operation): Likewise. * tree-inline.c (estimate_operator_cost): Handle new tree codes. * tree-vect-generic.c (expand_vector_operations_1): Likewise. * tree-cfg.c (verify_gimple_assign_binary): Likewise. * config/arm/neon.md (neon_vec_<US>shiftl_<mode>): New. (vec_widen_<US>shiftl_lo_<mode>, neon_vec_<US>shiftl_hi_<mode>, vec_widen_<US>shiftl_hi_<mode>, neon_vec_<US>shift_left_<mode>): Likewise. * config/arm/predicates.md (const_neon_scalar_shift_amount_operand): New. * config/arm/iterators.md (V_innermode): New. * tree-vect-slp.c (vect_build_slp_tree): Require same shift operand for widening shift. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@180128 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/config/arm')
-rw-r--r--gcc/config/arm/iterators.md3
-rw-r--r--gcc/config/arm/neon.md66
-rw-r--r--gcc/config/arm/predicates.md5
3 files changed, 74 insertions, 0 deletions
diff --git a/gcc/config/arm/iterators.md b/gcc/config/arm/iterators.md
index 85dd641d597..08874ff0411 100644
--- a/gcc/config/arm/iterators.md
+++ b/gcc/config/arm/iterators.md
@@ -414,6 +414,9 @@
(V4QQ "8") (V2HQ "16") (QQ "8") (HQ "16")
(V2HA "16") (HA "16") (SQ "") (SA "")])
+;; Mode attribute for vshll.
+(define_mode_attr V_innermode [(V8QI "QI") (V4HI "HI") (V2SI "SI")])
+
;;----------------------------------------------------------------------------
;; Code attributes
;;----------------------------------------------------------------------------
diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md
index ea09da246ff..5cbe5bed2cc 100644
--- a/gcc/config/arm/neon.md
+++ b/gcc/config/arm/neon.md
@@ -5335,6 +5335,44 @@
}
)
+(define_insn "neon_vec_<US>shiftl_<mode>"
+ [(set (match_operand:<V_widen> 0 "register_operand" "=w")
+ (SE:<V_widen> (ashift:VW (match_operand:VW 1 "register_operand" "w")
+ (match_operand:<V_innermode> 2 "const_neon_scalar_shift_amount_operand" ""))))]
+ "TARGET_NEON"
+{
+ return "vshll.<US><V_sz_elem> %q0, %P1, %2";
+}
+ [(set_attr "neon_type" "neon_shift_1")]
+)
+
+(define_expand "vec_widen_<US>shiftl_lo_<mode>"
+ [(match_operand:<V_unpack> 0 "register_operand" "")
+ (SE:<V_unpack> (match_operand:VU 1 "register_operand" ""))
+ (match_operand:SI 2 "immediate_operand" "i")]
+ "TARGET_NEON && !BYTES_BIG_ENDIAN"
+ {
+ emit_insn (gen_neon_vec_<US>shiftl_<V_half> (operands[0],
+ simplify_gen_subreg (<V_HALF>mode, operands[1], <MODE>mode, 0),
+ operands[2]));
+ DONE;
+ }
+)
+
+(define_expand "vec_widen_<US>shiftl_hi_<mode>"
+ [(match_operand:<V_unpack> 0 "register_operand" "")
+ (SE:<V_unpack> (match_operand:VU 1 "register_operand" ""))
+ (match_operand:SI 2 "immediate_operand" "i")]
+ "TARGET_NEON && !BYTES_BIG_ENDIAN"
+ {
+ emit_insn (gen_neon_vec_<US>shiftl_<V_half> (operands[0],
+ simplify_gen_subreg (<V_HALF>mode, operands[1], <MODE>mode,
+ GET_MODE_SIZE (<V_HALF>mode)),
+ operands[2]));
+ DONE;
+ }
+)
+
;; Vectorize for non-neon-quad case
(define_insn "neon_unpack<US>_<mode>"
[(set (match_operand:<V_widen> 0 "register_operand" "=w")
@@ -5411,6 +5449,34 @@
}
)
+(define_expand "vec_widen_<US>shiftl_hi_<mode>"
+ [(match_operand:<V_double_width> 0 "register_operand" "")
+ (SE:<V_double_width> (match_operand:VDI 1 "register_operand" ""))
+ (match_operand:SI 2 "immediate_operand" "i")]
+ "TARGET_NEON"
+ {
+ rtx tmpreg = gen_reg_rtx (<V_widen>mode);
+ emit_insn (gen_neon_vec_<US>shiftl_<mode> (tmpreg, operands[1], operands[2]));
+ emit_insn (gen_neon_vget_high<V_widen_l> (operands[0], tmpreg));
+
+ DONE;
+ }
+)
+
+(define_expand "vec_widen_<US>shiftl_lo_<mode>"
+ [(match_operand:<V_double_width> 0 "register_operand" "")
+ (SE:<V_double_width> (match_operand:VDI 1 "register_operand" ""))
+ (match_operand:SI 2 "immediate_operand" "i")]
+ "TARGET_NEON"
+ {
+ rtx tmpreg = gen_reg_rtx (<V_widen>mode);
+ emit_insn (gen_neon_vec_<US>shiftl_<mode> (tmpreg, operands[1], operands[2]));
+ emit_insn (gen_neon_vget_low<V_widen_l> (operands[0], tmpreg));
+
+ DONE;
+ }
+)
+
; FIXME: These instruction patterns can't be used safely in big-endian mode
; because the ordering of vector elements in Q registers is different from what
; the semantics of the instructions require.
diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md
index 2c1a138b0df..92eb004ae14 100644
--- a/gcc/config/arm/predicates.md
+++ b/gcc/config/arm/predicates.md
@@ -136,6 +136,11 @@
(match_operand 0 "s_register_operand"))
(match_operand 0 "const_int_operand")))
+(define_predicate "const_neon_scalar_shift_amount_operand"
+ (and (match_code "const_int")
+ (match_test "((unsigned HOST_WIDE_INT) INTVAL (op)) <= GET_MODE_BITSIZE (mode)
+ && ((unsigned HOST_WIDE_INT) INTVAL (op)) > 0")))
+
(define_predicate "arm_add_operand"
(ior (match_operand 0 "arm_rhs_operand")
(match_operand 0 "arm_neg_immediate_operand")))