diff options
Diffstat (limited to 'gcc/fold-const.c')
| -rw-r--r-- | gcc/fold-const.c | 15 |
1 files changed, 11 insertions, 4 deletions
diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 030bcb1..ce68929 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -7323,7 +7323,8 @@ fold_unary (enum tree_code code, tree type, tree op0) type via an object of identical or wider precision, neither conversion is needed. */ if (TYPE_MAIN_VARIANT (inside_type) == TYPE_MAIN_VARIANT (type) - && ((inter_int && final_int) || (inter_float && final_float)) + && (((inter_int || inter_ptr) && final_int) + || (inter_float && final_float)) && inter_prec >= final_prec) return fold_build1 (code, type, TREE_OPERAND (op0, 0)); @@ -7362,10 +7363,13 @@ fold_unary (enum tree_code code, tree type, tree op0) - the initial type is a pointer type and the precisions of the intermediate and final types differ, or - the final type is a pointer type and the precisions of the - initial and intermediate types differ. */ + initial and intermediate types differ. + - the final type is a pointer type and the initial type not + - the initial type is a pointer to an array and the final type + not. */ if (! inside_float && ! inter_float && ! final_float && ! inside_vec && ! inter_vec && ! final_vec - && (inter_prec > inside_prec || inter_prec > final_prec) + && (inter_prec >= inside_prec || inter_prec >= final_prec) && ! (inside_int && inter_int && inter_unsignedp != inside_unsignedp && inter_prec < final_prec) @@ -7375,7 +7379,10 @@ fold_unary (enum tree_code code, tree type, tree op0) && ! (final_ptr && inside_prec != inter_prec) && ! (final_prec != GET_MODE_BITSIZE (TYPE_MODE (type)) && TYPE_MODE (type) == TYPE_MODE (inter_type)) - && ! final_ptr) + && final_ptr == inside_ptr + && ! (inside_ptr + && TREE_CODE (TREE_TYPE (inside_type)) == ARRAY_TYPE + && TREE_CODE (TREE_TYPE (type)) != ARRAY_TYPE)) return fold_build1 (code, type, TREE_OPERAND (op0, 0)); } |
