aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJohn Wehle <john@feith.com>2000-02-18 06:32:01 +0000
committerJohn Wehle <wehle@gcc.gnu.org>2000-02-18 06:32:01 +0000
commita49a6a680068d483645cbc0f63975760b5d57886 (patch)
tree3c30c190987a1ec418bb165199041649c8b305e1 /gcc
parent930b1f40d0f3b4ad09d916f2a6da33f9d20dfad9 (diff)
downloadgcc-a49a6a680068d483645cbc0f63975760b5d57886.zip
gcc-a49a6a680068d483645cbc0f63975760b5d57886.tar.gz
gcc-a49a6a680068d483645cbc0f63975760b5d57886.tar.bz2
loop.c (canonicalize_condition): New function, broken out of get_condition.
* loop.c (canonicalize_condition): New function, broken out of get_condition. (get_condition): Use it. * expr.h (canonicalize_condition): Prototype it. * tree.h (tree_int_cst_msb): Declare. * tree.c (tree_int_cst_msb): New function. From-SVN: r32045
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog10
-rw-r--r--gcc/expr.h7
-rw-r--r--gcc/loop.c93
-rw-r--r--gcc/tree.c18
-rw-r--r--gcc/tree.h1
5 files changed, 97 insertions, 32 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 84f36e5..6a5b400 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,13 @@
+Fri Feb 18 01:29:22 EST 2000 John Wehle (john@feith.com)
+
+ * loop.c (canonicalize_condition): New function,
+ broken out of get_condition.
+ (get_condition): Use it.
+ * expr.h (canonicalize_condition): Prototype it.
+
+ * tree.h (tree_int_cst_msb): Declare.
+ * tree.c (tree_int_cst_msb): New function.
+
2000-02-17 Mark Mitchell <mark@codesourcery.com>
* stmt.c (set_file_and_line_for_stmt): Don't crash if cfun->stmt
diff --git a/gcc/expr.h b/gcc/expr.h
index ef8622a..22af908 100644
--- a/gcc/expr.h
+++ b/gcc/expr.h
@@ -888,7 +888,12 @@ extern rtx emit_store_flag_force PARAMS ((rtx, enum rtx_code, rtx, rtx,
/* Functions from loop.c: */
-/* Given a JUMP_INSN, return a description of the test being made. */
+/* Given an insn and condition, return a canonical description of
+ the test being made. */
+extern rtx canonicalize_condition PARAMS ((rtx, rtx, int, rtx *));
+
+/* Given a JUMP_INSN, return a canonical description of the test
+ being made. */
extern rtx get_condition PARAMS ((rtx, rtx *));
/* Generate a conditional trap instruction. */
diff --git a/gcc/loop.c b/gcc/loop.c
index a364d20..c89718f 100644
--- a/gcc/loop.c
+++ b/gcc/loop.c
@@ -8995,32 +8995,34 @@ update_reg_last_use (x, insn)
}
}
-/* Given a jump insn JUMP, return the condition that will cause it to branch
- to its JUMP_LABEL. If the condition cannot be understood, or is an
- inequality floating-point comparison which needs to be reversed, 0 will
- be returned.
-
- If EARLIEST is non-zero, it is a pointer to a place where the earliest
- insn used in locating the condition was found. If a replacement test
- of the condition is desired, it should be placed in front of that
- insn and we will be sure that the inputs are still valid.
-
- The condition will be returned in a canonical form to simplify testing by
- callers. Specifically:
+/* Given an insn INSN and condition COND, return the condition in a
+ canonical form to simplify testing by callers. Specifically:
(1) The code will always be a comparison operation (EQ, NE, GT, etc.).
(2) Both operands will be machine operands; (cc0) will have been replaced.
(3) If an operand is a constant, it will be the second operand.
(4) (LE x const) will be replaced with (LT x <const+1>) and similarly
- for GE, GEU, and LEU. */
+ for GE, GEU, and LEU.
+
+ If the condition cannot be understood, or is an inequality floating-point
+ comparison which needs to be reversed, 0 will be returned.
+
+ If REVERSE is non-zero, then reverse the condition prior to canonizing it.
+
+ If EARLIEST is non-zero, it is a pointer to a place where the earliest
+ insn used in locating the condition was found. If a replacement test
+ of the condition is desired, it should be placed in front of that
+ insn and we will be sure that the inputs are still valid. */
rtx
-get_condition (jump, earliest)
- rtx jump;
+canonicalize_condition (insn, cond, reverse, earliest)
+ rtx insn;
+ rtx cond;
+ int reverse;
rtx *earliest;
{
enum rtx_code code;
- rtx prev = jump;
+ rtx prev = insn;
rtx set;
rtx tem;
rtx op0, op1;
@@ -9028,24 +9030,19 @@ get_condition (jump, earliest)
int did_reverse_condition = 0;
enum machine_mode mode;
- /* If this is not a standard conditional jump, we can't parse it. */
- if (GET_CODE (jump) != JUMP_INSN
- || ! condjump_p (jump) || simplejump_p (jump))
- return 0;
+ code = GET_CODE (cond);
+ mode = GET_MODE (cond);
+ op0 = XEXP (cond, 0);
+ op1 = XEXP (cond, 1);
- code = GET_CODE (XEXP (SET_SRC (PATTERN (jump)), 0));
- mode = GET_MODE (XEXP (SET_SRC (PATTERN (jump)), 0));
- op0 = XEXP (XEXP (SET_SRC (PATTERN (jump)), 0), 0);
- op1 = XEXP (XEXP (SET_SRC (PATTERN (jump)), 0), 1);
+ if (reverse)
+ {
+ code = reverse_condition (code);
+ did_reverse_condition ^= 1;
+ }
if (earliest)
- *earliest = jump;
-
- /* If this branches to JUMP_LABEL when the condition is false, reverse
- the condition. */
- if (GET_CODE (XEXP (SET_SRC (PATTERN (jump)), 2)) == LABEL_REF
- && XEXP (XEXP (SET_SRC (PATTERN (jump)), 2), 0) == JUMP_LABEL (jump))
- code = reverse_condition (code), did_reverse_condition ^= 1;
+ *earliest = insn;
/* If we are comparing a register with zero, see if the register is set
in the previous insn to a COMPARE or a comparison operation. Perform
@@ -9262,6 +9259,40 @@ get_condition (jump, earliest)
return gen_rtx_fmt_ee (code, VOIDmode, op0, op1);
}
+/* Given a jump insn JUMP, return the condition that will cause it to branch
+ to its JUMP_LABEL. If the condition cannot be understood, or is an
+ inequality floating-point comparison which needs to be reversed, 0 will
+ be returned.
+
+ If EARLIEST is non-zero, it is a pointer to a place where the earliest
+ insn used in locating the condition was found. If a replacement test
+ of the condition is desired, it should be placed in front of that
+ insn and we will be sure that the inputs are still valid. */
+
+rtx
+get_condition (jump, earliest)
+ rtx jump;
+ rtx *earliest;
+{
+ rtx cond;
+ int reverse;
+
+ /* If this is not a standard conditional jump, we can't parse it. */
+ if (GET_CODE (jump) != JUMP_INSN
+ || ! condjump_p (jump) || simplejump_p (jump))
+ return 0;
+
+ cond = XEXP (SET_SRC (PATTERN (jump)), 0);
+
+ /* If this branches to JUMP_LABEL when the condition is false, reverse
+ the condition. */
+ reverse
+ = GET_CODE (XEXP (SET_SRC (PATTERN (jump)), 2)) == LABEL_REF
+ && XEXP (XEXP (SET_SRC (PATTERN (jump)), 2), 0) == JUMP_LABEL (jump);
+
+ return canonicalize_condition (jump, cond, reverse, earliest);
+}
+
/* Similar to above routine, except that we also put an invariant last
unless both operands are invariants. */
diff --git a/gcc/tree.c b/gcc/tree.c
index d0313c4..c01d46e 100644
--- a/gcc/tree.c
+++ b/gcc/tree.c
@@ -4062,6 +4062,24 @@ tree_int_cst_lt (t1, t2)
return INT_CST_LT_UNSIGNED (t1, t2);
}
+/* Return the most significant bit of the integer constant T. */
+
+int
+tree_int_cst_msb (t)
+ tree t;
+{
+ register int prec;
+ HOST_WIDE_INT h;
+ HOST_WIDE_INT l;
+
+ /* Note that using TYPE_PRECISION here is wrong. We care about the
+ actual bits, not the (arbitrary) range of the type. */
+ prec = GET_MODE_BITSIZE (TYPE_MODE (TREE_TYPE (t))) - 1;
+ rshift_double (TREE_INT_CST_LOW (t), TREE_INT_CST_HIGH (t), prec,
+ 2 * HOST_BITS_PER_WIDE_INT, &l, &h, 0);
+ return (l & 1) == 1;
+ }
+
/* Return an indication of the sign of the integer constant T.
The return value is -1 if T < 0, 0 if T == 0, and 1 if T > 0.
Note that -1 will never be returned it T's type is unsigned. */
diff --git a/gcc/tree.h b/gcc/tree.h
index 8ea2204..02fa95b 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -1666,6 +1666,7 @@ extern int attribute_list_equal PARAMS ((tree, tree));
extern int attribute_list_contained PARAMS ((tree, tree));
extern int tree_int_cst_equal PARAMS ((tree, tree));
extern int tree_int_cst_lt PARAMS ((tree, tree));
+extern int tree_int_cst_msb PARAMS ((tree));
extern int tree_int_cst_sgn PARAMS ((tree));
extern int index_type_equal PARAMS ((tree, tree));
extern tree get_inner_array_type PARAMS ((tree));