diff options
author | Richard Kenner <kenner@vlsi1.ultra.nyu.edu> | 1999-11-27 13:59:20 +0000 |
---|---|---|
committer | Richard Kenner <kenner@gcc.gnu.org> | 1999-11-27 08:59:20 -0500 |
commit | 667c1c2c84c36658a58f86a399dbee45ee982a09 (patch) | |
tree | 38a2610f874887ae242389a841d4d604f30ace51 /gcc | |
parent | 1baa375feaa22e3dbf6df7a066ba0d4a2b3a02d8 (diff) | |
download | gcc-667c1c2c84c36658a58f86a399dbee45ee982a09.zip gcc-667c1c2c84c36658a58f86a399dbee45ee982a09.tar.gz gcc-667c1c2c84c36658a58f86a399dbee45ee982a09.tar.bz2 |
combine.c (try_combine): Add code to try to merge a set of a two-word pseudo to a constant with a...
* combine.c (try_combine): Add code to try to merge a set of a
two-word pseudo to a constant with a setting of one of those words
to a constant.
From-SVN: r30674
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 4 | ||||
-rw-r--r-- | gcc/combine.c | 46 |
2 files changed, 50 insertions, 0 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index ec399ec..97f5d00 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,5 +1,9 @@ Sat Nov 27 08:38:26 1999 Richard Kenner <kenner@vlsi1.ultra.nyu.edu> + * combine.c (try_combine): Add code to try to merge a set of a + two-word pseudo to a constant with a setting of one of those words + to a constant. + * fold-const.c (negate_expr, associate_trees, extract_muldiv): New. (split_tree): Completely rework to make more general. (make_range, fold): Call negate_expr. diff --git a/gcc/combine.c b/gcc/combine.c index a853129..d028a93 100644 --- a/gcc/combine.c +++ b/gcc/combine.c @@ -1563,6 +1563,52 @@ try_combine (i3, i2, i1) } } + /* If I2 is setting a double-word pseudo to a constant and I3 is setting + one of those words to another constant, merge them by making a new + constant. */ + if (i1 == 0 + && (temp = single_set (i2)) != 0 + && (GET_CODE (SET_SRC (temp)) == CONST_INT + || GET_CODE (SET_SRC (temp)) == CONST_DOUBLE) + && GET_CODE (SET_DEST (temp)) == REG + && GET_MODE_CLASS (GET_MODE (SET_DEST (temp))) == MODE_INT + && GET_MODE_SIZE (GET_MODE (SET_DEST (temp))) == 2 * UNITS_PER_WORD + && GET_CODE (PATTERN (i3)) == SET + && GET_CODE (SET_DEST (PATTERN (i3))) == SUBREG + && SUBREG_REG (SET_DEST (PATTERN (i3))) == SET_DEST (temp) + && GET_MODE_CLASS (GET_MODE (SET_DEST (PATTERN (i3)))) == MODE_INT + && GET_MODE_SIZE (GET_MODE (SET_DEST (PATTERN (i3)))) == UNITS_PER_WORD + && GET_CODE (SET_SRC (PATTERN (i3))) == CONST_INT) + { + HOST_WIDE_INT lo, hi; + + if (GET_CODE (SET_SRC (temp)) == CONST_INT) + lo = INTVAL (SET_SRC (temp)), hi = lo < 0 ? -1 : 0; + else + { + lo = CONST_DOUBLE_LOW (SET_SRC (temp)); + hi = CONST_DOUBLE_HIGH (SET_SRC (temp)); + } + + if (subreg_lowpart_p (SET_DEST (PATTERN (i3)))) + lo = INTVAL (SET_SRC (PATTERN (i3))); + else + hi = INTVAL (SET_SRC (PATTERN (i3))); + + combine_merges++; + subst_insn = i3; + subst_low_cuid = INSN_CUID (i2); + added_sets_2 = added_sets_1 = 0; + i2dest = SET_DEST (temp); + + SUBST (SET_SRC (temp), + immed_double_const (lo, hi, GET_MODE (SET_DEST (temp)))); + + newpat = PATTERN (i2); + i3_subst_into_i2 = 1; + goto validate_replacement; + } + #ifndef HAVE_cc0 /* If we have no I1 and I2 looks like: (parallel [(set (reg:CC X) (compare:CC OP (const_int 0))) |