diff options
author | Aldy Hernandez <aldyh@gcc.gnu.org> | 2002-02-19 02:53:41 +0000 |
---|---|---|
committer | Aldy Hernandez <aldyh@gcc.gnu.org> | 2002-02-19 02:53:41 +0000 |
commit | 69ef87e2bc8b929b7af75c3f03aafd1f12121b67 (patch) | |
tree | 2c0a4b4f6d2f35e63ff2d03006bbc29f28ccb665 /gcc/config | |
parent | 336669e7b08e8dc86bd324702013a0a968151bea (diff) | |
download | gcc-69ef87e2bc8b929b7af75c3f03aafd1f12121b67.zip gcc-69ef87e2bc8b929b7af75c3f03aafd1f12121b67.tar.gz gcc-69ef87e2bc8b929b7af75c3f03aafd1f12121b67.tar.bz2 |
i386.md ("mmx_uavgv8qi3"): Use const_vector.
2002-02-19 Aldy Hernandez <aldyh@redhat.com>
* config/i386/i386.md ("mmx_uavgv8qi3"): Use const_vector.
("mmx_uavgv4hi3"): Same.
("pmulhrwv4hi3"): Same.
* tree-inline.c (walk_tree): Handle vectors.
* c-common.c (constant_expression_warning): Handle vectors.
(overflow_warning): Same.
* sched-deps.c (sched_analyze_2): Handle vectors.
* rtlanal.c (rtx_unstable_p): Handle vectors.
(rtx_varies_p): Same.
(count_occurrences): Same.
(regs_set_between_p): Same.
(modified_between_p): Same.
(modified_in_p): Same.
(volatile_insn_p): Same.
(volatile_refs_p): Same.
(side_effects_p): Same.
(may_trap_p): Same.
(inequality_comparisons_p): Same.
(replace_regs): Same.
(computed_jump_p_1): Same.
* rtl.c (DEF_MACHMODE): Change all definitions to accept 8th
argument.
(inner_mode_array): New.
(copy_rtx): Handle vectors.
(copy_most_rtx): Same.
(rtx_equal_p): Same.
(get_mode_alignment): Adjust for vectors.
* resource.c (mark_referenced_resources): Handle vectors.
(mark_set_resources): Same.
* reload1.c (eliminate_regs): Handle vectors.
(elimination_effects): Same.
(scan_paradoxical_subregs): Same.
* reload.c (subst_reg_equivs): Handle vectors.
* regrename.c (scan_rtx): Handle vectors.
* regclass.c (reg_scan_mark_refs): Handle vectors.
* recog.c (find_single_use_1): Handle vectors.
* local-alloc.c (equiv_init_varies_p): Handle vectors.
(contains_replace_regs): Same.
(memref_referenced_p): Same.
* integrate.c (copy_rtx_and_substitute): Handle vectors.
(subst_constants): Same.
* genattrtab.c (attr_copy_rtx): Handle vectors.
(encode_units_mask): Same.
(clear_struct_flag): Same.
(count_sub_rtxs): Same.
* gcse.c (want_to_gcse_p): Handle vectors.
(oprs_unchanged_p): Same.
(hash_expr_1): Same.
(oprs_not_set_p): Same.
(expr_killed_p): Same.
(compute_transp): Same.
(store_ops_ok): Same.
* function.c (purge_addressof_1): Do not allow paradoxical subregs
of vectors.
(fixup_var_refs_1): Same.
(instantiate_virtual_regs_1): Same.
* fold-const.c (operand_equal_p): Handle vectors.
(fold): Same.
(rtl_expr_nonnegative_p): Same.
* flow.c (mark_used_regs): Handle vectors.
* df.c (df_uses_record): Handle vectors.
* cselib.c (cselib_subst_to_values): Handle vectors.
(cselib_mem_conflict_p): Same.
(hash_rtx): Same.
* cse.c (canon_reg): Handle vectors.
(fold_rt): Same.
(cse_process_notes): Same.
(count_reg_usage): Same.
(canon_hash): Same.
* alias.c (nonlocal_mentioned_p): Add case for CONST_VECTOR.
* combine.c (mark_used_regs_combine): Add case for CONST_VECTOR.
* emit-rtl.c (init_emit_once): Generate const0_rtx for vectors.
(gen_rtx): Handle CONST_VECTOR.
(gen_const_vector_0): New.
(copy_rtx_if_shared): CONST_VECTORs can be shared.
(reset_used_flags): Same.
(copy_insn_1): Same.
(initializer_constant_valid_p): Handle VECTOR_CST.
* doc/c-tree.texi (Expression trees): Document VECTOR_CST.
* doc/rtl.texi (Constants): Document const_vector.
(CONST0_RTX): Update for vectors.
(RTL sharing): Same.
* print-tree.c (print_node): Add case for VECTOR_CST.
* tree.h (TREE_VECTOR_CST_ELTS): New.
(struct tree_vector): New.
(union tree_node): Add vector node.
(build_vector): Add prototype.
* tree.def (VECTOR_CST): New.
* tree.c (build_vector): New.
* expmed.c (make_tree): Handle CONST_VECTOR.
* rtl.h (CONSTANT_P): CONST_VECTORs are constants too.
(CONST_VECTOR_ELT): New.
(CONST_VECTOR_NUNITS): New.
* machmode.h (GET_MODE_INNER): New.
(DEF_MACHMODE): Accept 8th arg.
* machmode.def: Add 8th argument for vector inner mode.
Add inner vector modes for vectors.
* rtl.def (VEC_CONST): Remove.
(CONST_VECTOR): New.
* expr.c (clear_storage): Allow vectors.
(is_zeros_p): Handle VECTOR_CST.
* varasm.c (output_constant_pool): Handle vectors.
(rtx_const): Add veclo and vechi fields.
(kind): Add RTX_VECTOR.
(decode_rtx_const): Add case for vector.
* config/rs6000/rs6000-protos.h: Add zero_constant.
* config/rs6000/rs6000.c (rs6000_emit_move): Handle vector
constants. Force easy vector constants into memory.
(easy_vector_constant): New.
(emit_easy_vector_constant): New.
(rs6000_legitimize_reload_address): Do not generate bad reloads on
darwin.
* config/rs6000/rs6000.md ("altivec_lvx"): Reflect what
instruction does.
("altivec_lvxl"): Same.
(altivec_lvebx): Same.
(altivec_lvehx): Same.
(altivec_lvewx): Same.
("*movv4si_const0"): New.
("*movv4sf_const0"): New.
("*movv8hi_const0"): New.
("*movv16qi_const0"): New.
From-SVN: r49853
Diffstat (limited to 'gcc/config')
-rw-r--r-- | gcc/config/i386/i386.md | 35 | ||||
-rw-r--r-- | gcc/config/rs6000/rs6000-protos.h | 1 | ||||
-rw-r--r-- | gcc/config/rs6000/rs6000.c | 61 | ||||
-rw-r--r-- | gcc/config/rs6000/rs6000.h | 11 | ||||
-rw-r--r-- | gcc/config/rs6000/rs6000.md | 76 |
5 files changed, 140 insertions, 44 deletions
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index b0ec9f2..1d7091d 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -18999,14 +18999,14 @@ (plus:V8QI (plus:V8QI (match_operand:V8QI 1 "register_operand" "0") (match_operand:V8QI 2 "nonimmediate_operand" "ym")) - (vec_const:V8QI (parallel [(const_int 1) - (const_int 1) - (const_int 1) - (const_int 1) - (const_int 1) - (const_int 1) - (const_int 1) - (const_int 1)]))) + (const_vector:V8QI [(const_int 1) + (const_int 1) + (const_int 1) + (const_int 1) + (const_int 1) + (const_int 1) + (const_int 1) + (const_int 1)])) (const_int 1)))] "TARGET_SSE || TARGET_3DNOW_A" "pavgb\t{%2, %0|%0, %2}" @@ -19018,10 +19018,10 @@ (plus:V4HI (plus:V4HI (match_operand:V4HI 1 "register_operand" "0") (match_operand:V4HI 2 "nonimmediate_operand" "ym")) - (vec_const:V4HI (parallel [(const_int 1) - (const_int 1) - (const_int 1) - (const_int 1)]))) + (const_vector:V4HI [(const_int 1) + (const_int 1) + (const_int 1) + (const_int 1)])) (const_int 1)))] "TARGET_SSE || TARGET_3DNOW_A" "pavgw\t{%2, %0|%0, %2}" @@ -19735,12 +19735,11 @@ (match_operand:V4HI 1 "register_operand" "0")) (sign_extend:V4SI (match_operand:V4HI 2 "nonimmediate_operand" "ym"))) - (vec_const:V4SI - (parallel [(const_int 32768) - (const_int 32768) - (const_int 32768) - (const_int 32768)]))) - (const_int 16))))] + (const_vector:V4SI [(const_int 32768) + (const_int 32768) + (const_int 32768) + (const_int 32768)])) + (const_int 16))))] "TARGET_3DNOW" "pmulhrw\\t{%2, %0|%0, %2}" [(set_attr "type" "mmx")]) diff --git a/gcc/config/rs6000/rs6000-protos.h b/gcc/config/rs6000/rs6000-protos.h index a588360..19aeb07 100644 --- a/gcc/config/rs6000/rs6000-protos.h +++ b/gcc/config/rs6000/rs6000-protos.h @@ -52,6 +52,7 @@ extern int got_no_const_operand PARAMS ((rtx, enum machine_mode)); extern int num_insns_constant PARAMS ((rtx, enum machine_mode)); extern int easy_fp_constant PARAMS ((rtx, enum machine_mode)); extern int zero_fp_constant PARAMS ((rtx, enum machine_mode)); +extern int zero_constant PARAMS ((rtx, enum machine_mode)); extern int volatile_mem_operand PARAMS ((rtx, enum machine_mode)); extern int offsettable_mem_operand PARAMS ((rtx, enum machine_mode)); extern int mem_or_easy_const_operand PARAMS ((rtx, enum machine_mode)); diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c index 8cd6646..5e3a735 100644 --- a/gcc/config/rs6000/rs6000.c +++ b/gcc/config/rs6000/rs6000.c @@ -174,6 +174,7 @@ static void is_altivec_return_reg PARAMS ((rtx, void *)); int vrsave_operation PARAMS ((rtx, enum machine_mode)); static rtx generate_set_vrsave PARAMS ((rtx, rs6000_stack_t *, int)); static void altivec_frame_fixup PARAMS ((rtx, rtx, HOST_WIDE_INT)); +static int easy_vector_constant PARAMS ((rtx)); /* Default register names. */ char rs6000_reg_names[][8] = @@ -1194,6 +1195,54 @@ easy_fp_constant (op, mode) abort (); } +/* Return 1 if the operand is a CONST_INT and can be put into a + register with one instruction. */ + +static int +easy_vector_constant (op) + rtx op; +{ + rtx elt; + int units, i; + + if (GET_CODE (op) != CONST_VECTOR) + return 0; + + units = CONST_VECTOR_NUNITS (op); + + /* We can generate 0 easily. Look for that. */ + for (i = 0; i < units; ++i) + { + elt = CONST_VECTOR_ELT (op, i); + + /* We could probably simplify this by just checking for equality + with CONST0_RTX for the current mode, but let's be safe + instead. */ + + if (GET_CODE (elt) == CONST_INT && INTVAL (elt) != 0) + return 0; + + if (GET_CODE (elt) == CONST_DOUBLE + && (CONST_DOUBLE_LOW (elt) != 0 + || CONST_DOUBLE_HIGH (elt) != 0)) + return 0; + } + + /* We could probably generate a few other constants trivially, but + gcc doesn't generate them yet. FIXME later. */ + return 0; +} + +/* Return 1 if the operand is the constant 0. This works for scalars + as well as vectors. */ +int +zero_constant (op, mode) + rtx op; + enum machine_mode mode; +{ + return op == CONST0_RTX (mode); +} + /* Return 1 if the operand is 0.0. */ int zero_fp_constant (op, mode) @@ -1892,6 +1941,7 @@ rs6000_legitimize_reload_address (x, mode, opnum, type, ind_levels, win) #if TARGET_MACHO if (GET_CODE (x) == SYMBOL_REF && DEFAULT_ABI == ABI_DARWIN + && !ALTIVEC_VECTOR_MODE (mode) && flag_pic) { /* Darwin load of floating point constant. */ @@ -2186,9 +2236,10 @@ rs6000_emit_move (dest, source, mode) /* Handle the case where reload calls us with an invalid address; and the case of CONSTANT_P_RTX. */ - if (! general_operand (operands[1], mode) - || ! nonimmediate_operand (operands[0], mode) - || GET_CODE (operands[1]) == CONSTANT_P_RTX) + if (!VECTOR_MODE_P (mode) + && (! general_operand (operands[1], mode) + || ! nonimmediate_operand (operands[0], mode) + || GET_CODE (operands[1]) == CONSTANT_P_RTX)) { emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1])); return; @@ -2218,8 +2269,8 @@ rs6000_emit_move (dest, source, mode) case V8HImode: case V4SFmode: case V4SImode: - /* fixme: aldyh -- allow vector constants when they are implemented. */ - if (CONSTANT_P (operands[1])) + if (CONSTANT_P (operands[1]) + && !easy_vector_constant (operands[1])) operands[1] = force_const_mem (mode, operands[1]); break; diff --git a/gcc/config/rs6000/rs6000.h b/gcc/config/rs6000/rs6000.h index ebbede4..cdbe336 100644 --- a/gcc/config/rs6000/rs6000.h +++ b/gcc/config/rs6000/rs6000.h @@ -638,10 +638,13 @@ extern int rs6000_altivec_abi; /* A bitfield declared as `int' forces `int' alignment for the struct. */ #define PCC_BITFIELD_TYPE_MATTERS 1 -/* Make strings word-aligned so strcpy from constants will be faster. */ -#define CONSTANT_ALIGNMENT(EXP, ALIGN) \ - (TREE_CODE (EXP) == STRING_CST \ - && (ALIGN) < BITS_PER_WORD ? BITS_PER_WORD : (ALIGN)) +/* Make strings word-aligned so strcpy from constants will be faster. + Make vector constants quadword aligned. */ +#define CONSTANT_ALIGNMENT(EXP, ALIGN) \ + (TREE_CODE (EXP) == STRING_CST \ + && (ALIGN) < BITS_PER_WORD \ + ? BITS_PER_WORD \ + : (ALIGN)) /* Make arrays of chars word-aligned for the same reasons. Align vectors to 128 bits. */ diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md index 7a5bce5..d83538b 100644 --- a/gcc/config/rs6000/rs6000.md +++ b/gcc/config/rs6000/rs6000.md @@ -14017,6 +14017,36 @@ "mtvrsave %1" [(set_attr "type" "altivec")]) +;; Vector clears +(define_insn "*movv4si_const0" + [(set (match_operand:V4SI 0 "altivec_register_operand" "=v") + (match_operand:V4SI 1 "zero_constant" ""))] + "TARGET_ALTIVEC" + "vxor %0,%0,%0" + [(set_attr "type" "vecsimple")]) + +(define_insn "*movv4sf_const0" + [(set (match_operand:V4SF 0 "altivec_register_operand" "=v") + (match_operand:V4SF 1 "zero_constant" ""))] + + "TARGET_ALTIVEC" + "vxor %0,%0,%0" + [(set_attr "type" "vecsimple")]) + +(define_insn "*movv8hi_const0" + [(set (match_operand:V8HI 0 "altivec_register_operand" "=v") + (match_operand:V8HI 1 "zero_constant" ""))] + "TARGET_ALTIVEC" + "vxor %0,%0,%0" + [(set_attr "type" "vecsimple")]) + +(define_insn "*movv16qi_const0" + [(set (match_operand:V16QI 0 "altivec_register_operand" "=v") + (match_operand:V16QI 1 "zero_constant" ""))] + "TARGET_ALTIVEC" + "vxor %0,%0,%0" + [(set_attr "type" "vecsimple")]) + ;; Simple binary operations. (define_insn "addv16qi3" @@ -15481,49 +15511,61 @@ "lvsr %0,%1,%2" [(set_attr "type" "vecload")]) +;; Parallel some of the LVE* and STV*'s with unspecs because some have +;; identical rtl but different instructions-- and gcc gets confused. + (define_insn "altivec_lvebx" - [(set (match_operand:V16QI 0 "register_operand" "=v") - (unspec:V16QI [(match_operand:SI 1 "register_operand" "b") - (match_operand:SI 2 "register_operand" "r")] 196))] + [(parallel + [(set (match_operand:V16QI 0 "register_operand" "=v") + (mem:V16QI (plus:SI (match_operand:SI 1 "register_operand" "b") + (match_operand:SI 2 "register_operand" "r")))) + (unspec [(const_int 0)] 196)])] "TARGET_ALTIVEC" "lvebx %0,%1,%2" [(set_attr "type" "vecload")]) (define_insn "altivec_lvehx" - [(set (match_operand:V8HI 0 "register_operand" "=v") - (unspec:V8HI [(match_operand:SI 1 "register_operand" "b") - (match_operand:SI 2 "register_operand" "r")] 197))] + [(parallel + [(set (match_operand:V8HI 0 "register_operand" "=v") + (mem:V8HI + (and:SI (plus:SI (match_operand:SI 1 "register_operand" "b") + (match_operand:SI 2 "register_operand" "r")) + (const_int -2)))) + (unspec [(const_int 0)] 197)])] "TARGET_ALTIVEC" "lvehx %0,%1,%2" [(set_attr "type" "vecload")]) (define_insn "altivec_lvewx" - [(set (match_operand:V4SI 0 "register_operand" "=v") - (unspec:V4SI [(match_operand:SI 1 "register_operand" "b") - (match_operand:SI 2 "register_operand" "r")] 198))] + [(parallel + [(set (match_operand:V4SI 0 "register_operand" "=v") + (mem:V4SI + (and:SI (plus:SI (match_operand:SI 1 "register_operand" "b") + (match_operand:SI 2 "register_operand" "r")) + (const_int -4)))) + (unspec [(const_int 0)] 198)])] "TARGET_ALTIVEC" "lvewx %0,%1,%2" [(set_attr "type" "vecload")]) (define_insn "altivec_lvxl" - [(set (match_operand:V4SI 0 "register_operand" "=v") - (unspec:V4SI [(match_operand:SI 1 "register_operand" "b") - (match_operand:SI 2 "register_operand" "r")] 199))] + [(parallel + [(set (match_operand:V4SI 0 "register_operand" "=v") + (mem:V4SI (plus:SI (match_operand:SI 1 "register_operand" "b") + (match_operand:SI 2 "register_operand" "r")))) + (unspec [(const_int 0)] 213)])] "TARGET_ALTIVEC" "lvxl %0,%1,%2" [(set_attr "type" "vecload")]) (define_insn "altivec_lvx" [(set (match_operand:V4SI 0 "register_operand" "=v") - (unspec:V4SI [(match_operand:SI 1 "register_operand" "b") - (match_operand:SI 2 "register_operand" "r")] 200))] + (mem:V4SI (plus:SI (match_operand:SI 1 "register_operand" "b") + (match_operand:SI 2 "register_operand" "r"))))] "TARGET_ALTIVEC" "lvx %0,%1,%2" [(set_attr "type" "vecload")]) -;; Parallel the STV*'s with unspecs because some of them have -;; identical rtl but are different instructions-- and gcc gets confused. - (define_insn "altivec_stvx" [(parallel [(set (mem:V4SI |