diff options
Diffstat (limited to 'gcc/fold-const.c')
-rw-r--r-- | gcc/fold-const.c | 31 |
1 files changed, 21 insertions, 10 deletions
diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 1539ad21387..3403938edc3 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -206,15 +206,9 @@ fit_double_type (unsigned HOST_WIDE_INT l1, HOST_WIDE_INT h1, { unsigned HOST_WIDE_INT low0 = l1; HOST_WIDE_INT high0 = h1; - unsigned int prec; + unsigned int prec = int_or_pointer_precision (type); int sign_extended_type; - if (POINTER_TYPE_P (type) - || TREE_CODE (type) == OFFSET_TYPE) - prec = POINTER_SIZE; - else - prec = TYPE_PRECISION (type); - /* Size types *are* sign extended. */ sign_extended_type = (!TYPE_UNSIGNED (type) || (TREE_CODE (type) == INTEGER_TYPE @@ -2647,8 +2641,16 @@ fold_convert_loc (location_t loc, tree type, tree arg) switch (TREE_CODE (type)) { + case POINTER_TYPE: + case REFERENCE_TYPE: + /* Handle conversions between pointers to different address spaces. */ + if (POINTER_TYPE_P (orig) + && (TYPE_ADDR_SPACE (TREE_TYPE (type)) + != TYPE_ADDR_SPACE (TREE_TYPE (orig)))) + return fold_build1_loc (loc, ADDR_SPACE_CONVERT_EXPR, type, arg); + /* fall through */ + case INTEGER_TYPE: case ENUMERAL_TYPE: case BOOLEAN_TYPE: - case POINTER_TYPE: case REFERENCE_TYPE: case OFFSET_TYPE: if (TREE_CODE (arg) == INTEGER_CST) { @@ -3179,6 +3181,12 @@ operand_equal_p (const_tree arg0, const_tree arg1, unsigned int flags) || POINTER_TYPE_P (TREE_TYPE (arg0)) != POINTER_TYPE_P (TREE_TYPE (arg1))) return 0; + /* We cannot consider pointers to different address space equal. */ + if (POINTER_TYPE_P (TREE_TYPE (arg0)) && POINTER_TYPE_P (TREE_TYPE (arg1)) + && (TYPE_ADDR_SPACE (TREE_TYPE (TREE_TYPE (arg0))) + != TYPE_ADDR_SPACE (TREE_TYPE (TREE_TYPE (arg1))))) + return 0; + /* If both types don't have the same precision, then it is not safe to strip NOPs. */ if (TYPE_PRECISION (TREE_TYPE (arg0)) != TYPE_PRECISION (TREE_TYPE (arg1))) @@ -8682,6 +8690,11 @@ fold_unary_loc (location_t loc, enum tree_code code, tree type, tree op0) tem = fold_convert_const (code, type, op0); return tem ? tem : NULL_TREE; + case ADDR_SPACE_CONVERT_EXPR: + if (integer_zerop (arg0)) + return fold_convert_const (code, type, arg0); + return NULL_TREE; + case FIXED_CONVERT_EXPR: tem = fold_convert_const (code, type, arg0); return tem ? tem : NULL_TREE; @@ -10134,7 +10147,6 @@ fold_binary_loc (location_t loc, tem = fold_build2_loc (loc, code, type, fold_convert_loc (loc, TREE_TYPE (op0), TREE_OPERAND (arg0, 1)), op1); - protected_set_expr_location (tem, loc); tem = build2 (COMPOUND_EXPR, type, TREE_OPERAND (arg0, 0), tem); goto fold_binary_exit; } @@ -10144,7 +10156,6 @@ fold_binary_loc (location_t loc, tem = fold_build2_loc (loc, code, type, op0, fold_convert_loc (loc, TREE_TYPE (op1), TREE_OPERAND (arg1, 1))); - protected_set_expr_location (tem, loc); tem = build2 (COMPOUND_EXPR, type, TREE_OPERAND (arg1, 0), tem); goto fold_binary_exit; } |