Lines 2518-2524
shorten_binary_op (tree result_type, tre
Link Here
|
2518 |
} |
2518 |
} |
2519 |
|
2519 |
|
2520 |
/* Checks if expression EXPR of real/integer type cannot be converted |
2520 |
/* Checks if expression EXPR of real/integer type cannot be converted |
2521 |
to the real/integer type TYPE. Function returns true when: |
2521 |
to the real/integer type TYPE. Function returns non-zero when: |
2522 |
* EXPR is a constant which cannot be exactly converted to TYPE |
2522 |
* EXPR is a constant which cannot be exactly converted to TYPE |
2523 |
* EXPR is not a constant and size of EXPR's type > than size of TYPE, |
2523 |
* EXPR is not a constant and size of EXPR's type > than size of TYPE, |
2524 |
for EXPR type and TYPE being both integers or both real. |
2524 |
for EXPR type and TYPE being both integers or both real. |
Lines 2526-2537
shorten_binary_op (tree result_type, tre
Link Here
|
2526 |
* EXPR is not a constant of integer type which cannot be |
2526 |
* EXPR is not a constant of integer type which cannot be |
2527 |
exactly converted to real type. |
2527 |
exactly converted to real type. |
2528 |
Function allows conversions between types of different signedness and |
2528 |
Function allows conversions between types of different signedness and |
2529 |
does not return true in that case. Function can produce signedness |
2529 |
can return SAFE_CONVERSION (zero) in that case. Function can produce |
2530 |
warnings if PRODUCE_WARNS is true. */ |
2530 |
signedness warnings if PRODUCE_WARNS is true. */ |
2531 |
bool |
2531 |
enum conversion_safety |
2532 |
unsafe_conversion_p (tree type, tree expr, bool produce_warns) |
2532 |
unsafe_conversion_p (tree type, tree expr, bool produce_warns) |
2533 |
{ |
2533 |
{ |
2534 |
bool give_warning = false; |
2534 |
enum conversion_safety give_warning = SAFE_CONVERSION; /* is 0 or false */ |
2535 |
tree expr_type = TREE_TYPE (expr); |
2535 |
tree expr_type = TREE_TYPE (expr); |
2536 |
location_t loc = EXPR_LOC_OR_HERE (expr); |
2536 |
location_t loc = EXPR_LOC_OR_HERE (expr); |
2537 |
|
2537 |
|
Lines 2543-2549
unsafe_conversion_p (tree type, tree exp
Link Here
|
2543 |
&& TREE_CODE (type) == INTEGER_TYPE) |
2543 |
&& TREE_CODE (type) == INTEGER_TYPE) |
2544 |
{ |
2544 |
{ |
2545 |
if (!real_isinteger (TREE_REAL_CST_PTR (expr), TYPE_MODE (expr_type))) |
2545 |
if (!real_isinteger (TREE_REAL_CST_PTR (expr), TYPE_MODE (expr_type))) |
2546 |
give_warning = true; |
2546 |
give_warning = UNSAFE_REAL; |
2547 |
} |
2547 |
} |
2548 |
/* Warn for an integer constant that does not fit into integer type. */ |
2548 |
/* Warn for an integer constant that does not fit into integer type. */ |
2549 |
else if (TREE_CODE (expr_type) == INTEGER_TYPE |
2549 |
else if (TREE_CODE (expr_type) == INTEGER_TYPE |
Lines 2564-2570
unsafe_conversion_p (tree type, tree exp
Link Here
|
2564 |
" constant value to negative integer"); |
2564 |
" constant value to negative integer"); |
2565 |
} |
2565 |
} |
2566 |
else |
2566 |
else |
2567 |
give_warning = true; |
2567 |
give_warning = UNSAFE_OTHER; |
2568 |
} |
2568 |
} |
2569 |
else if (TREE_CODE (type) == REAL_TYPE) |
2569 |
else if (TREE_CODE (type) == REAL_TYPE) |
2570 |
{ |
2570 |
{ |
Lines 2573-2579
unsafe_conversion_p (tree type, tree exp
Link Here
|
2573 |
{ |
2573 |
{ |
2574 |
REAL_VALUE_TYPE a = real_value_from_int_cst (0, expr); |
2574 |
REAL_VALUE_TYPE a = real_value_from_int_cst (0, expr); |
2575 |
if (!exact_real_truncate (TYPE_MODE (type), &a)) |
2575 |
if (!exact_real_truncate (TYPE_MODE (type), &a)) |
2576 |
give_warning = true; |
2576 |
give_warning = UNSAFE_REAL; |
2577 |
} |
2577 |
} |
2578 |
/* Warn for a real constant that does not fit into a smaller |
2578 |
/* Warn for a real constant that does not fit into a smaller |
2579 |
real type. */ |
2579 |
real type. */ |
Lines 2582-2588
unsafe_conversion_p (tree type, tree exp
Link Here
|
2582 |
{ |
2582 |
{ |
2583 |
REAL_VALUE_TYPE a = TREE_REAL_CST (expr); |
2583 |
REAL_VALUE_TYPE a = TREE_REAL_CST (expr); |
2584 |
if (!exact_real_truncate (TYPE_MODE (type), &a)) |
2584 |
if (!exact_real_truncate (TYPE_MODE (type), &a)) |
2585 |
give_warning = true; |
2585 |
give_warning = UNSAFE_REAL; |
2586 |
} |
2586 |
} |
2587 |
} |
2587 |
} |
2588 |
} |
2588 |
} |
Lines 2591-2597
unsafe_conversion_p (tree type, tree exp
Link Here
|
2591 |
/* Warn for real types converted to integer types. */ |
2591 |
/* Warn for real types converted to integer types. */ |
2592 |
if (TREE_CODE (expr_type) == REAL_TYPE |
2592 |
if (TREE_CODE (expr_type) == REAL_TYPE |
2593 |
&& TREE_CODE (type) == INTEGER_TYPE) |
2593 |
&& TREE_CODE (type) == INTEGER_TYPE) |
2594 |
give_warning = true; |
2594 |
give_warning = UNSAFE_REAL; |
2595 |
|
2595 |
|
2596 |
else if (TREE_CODE (expr_type) == INTEGER_TYPE |
2596 |
else if (TREE_CODE (expr_type) == INTEGER_TYPE |
2597 |
&& TREE_CODE (type) == INTEGER_TYPE) |
2597 |
&& TREE_CODE (type) == INTEGER_TYPE) |
Lines 2629-2635
unsafe_conversion_p (tree type, tree exp
Link Here
|
2629 |
&& int_fits_type_p (op1, c_common_signed_type (type)) |
2629 |
&& int_fits_type_p (op1, c_common_signed_type (type)) |
2630 |
&& int_fits_type_p (op1, |
2630 |
&& int_fits_type_p (op1, |
2631 |
c_common_unsigned_type (type)))) |
2631 |
c_common_unsigned_type (type)))) |
2632 |
return false; |
2632 |
return SAFE_CONVERSION; |
2633 |
/* If constant is unsigned and fits in the target |
2633 |
/* If constant is unsigned and fits in the target |
2634 |
type, then the result will also fit. */ |
2634 |
type, then the result will also fit. */ |
2635 |
else if ((TREE_CODE (op0) == INTEGER_CST |
2635 |
else if ((TREE_CODE (op0) == INTEGER_CST |
Lines 2638-2649
unsafe_conversion_p (tree type, tree exp
Link Here
|
2638 |
|| (TREE_CODE (op1) == INTEGER_CST |
2638 |
|| (TREE_CODE (op1) == INTEGER_CST |
2639 |
&& unsigned1 |
2639 |
&& unsigned1 |
2640 |
&& int_fits_type_p (op1, type))) |
2640 |
&& int_fits_type_p (op1, type))) |
2641 |
return false; |
2641 |
return SAFE_CONVERSION; |
2642 |
} |
2642 |
} |
2643 |
} |
2643 |
} |
2644 |
/* Warn for integer types converted to smaller integer types. */ |
2644 |
/* Warn for integer types converted to smaller integer types. */ |
2645 |
if (TYPE_PRECISION (type) < TYPE_PRECISION (expr_type)) |
2645 |
if (TYPE_PRECISION (type) < TYPE_PRECISION (expr_type)) |
2646 |
give_warning = true; |
2646 |
give_warning = UNSAFE_OTHER; |
2647 |
|
2647 |
|
2648 |
/* When they are the same width but different signedness, |
2648 |
/* When they are the same width but different signedness, |
2649 |
then the value may change. */ |
2649 |
then the value may change. */ |
Lines 2679-2692
unsafe_conversion_p (tree type, tree exp
Link Here
|
2679 |
|
2679 |
|
2680 |
if (!exact_real_truncate (TYPE_MODE (type), &real_low_bound) |
2680 |
if (!exact_real_truncate (TYPE_MODE (type), &real_low_bound) |
2681 |
|| !exact_real_truncate (TYPE_MODE (type), &real_high_bound)) |
2681 |
|| !exact_real_truncate (TYPE_MODE (type), &real_high_bound)) |
2682 |
give_warning = true; |
2682 |
give_warning = UNSAFE_OTHER; |
2683 |
} |
2683 |
} |
2684 |
|
2684 |
|
2685 |
/* Warn for real types converted to smaller real types. */ |
2685 |
/* Warn for real types converted to smaller real types. */ |
2686 |
else if (TREE_CODE (expr_type) == REAL_TYPE |
2686 |
else if (TREE_CODE (expr_type) == REAL_TYPE |
2687 |
&& TREE_CODE (type) == REAL_TYPE |
2687 |
&& TREE_CODE (type) == REAL_TYPE |
2688 |
&& TYPE_PRECISION (type) < TYPE_PRECISION (expr_type)) |
2688 |
&& TYPE_PRECISION (type) < TYPE_PRECISION (expr_type)) |
2689 |
give_warning = true; |
2689 |
give_warning = UNSAFE_REAL; |
2690 |
} |
2690 |
} |
2691 |
|
2691 |
|
2692 |
return give_warning; |
2692 |
return give_warning; |
Lines 2700-2707
conversion_warning (tree type, tree expr
Link Here
|
2700 |
{ |
2700 |
{ |
2701 |
tree expr_type = TREE_TYPE (expr); |
2701 |
tree expr_type = TREE_TYPE (expr); |
2702 |
location_t loc = EXPR_LOC_OR_HERE (expr); |
2702 |
location_t loc = EXPR_LOC_OR_HERE (expr); |
|
|
2703 |
enum conversion_safety conversion_kind; |
2703 |
|
2704 |
|
2704 |
if (!warn_conversion && !warn_sign_conversion) |
2705 |
if (!warn_conversion && !warn_sign_conversion && !warn_float_conversion) |
2705 |
return; |
2706 |
return; |
2706 |
|
2707 |
|
2707 |
switch (TREE_CODE (expr)) |
2708 |
switch (TREE_CODE (expr)) |
Lines 2728-2734
conversion_warning (tree type, tree expr
Link Here
|
2728 |
|
2729 |
|
2729 |
case REAL_CST: |
2730 |
case REAL_CST: |
2730 |
case INTEGER_CST: |
2731 |
case INTEGER_CST: |
2731 |
if (unsafe_conversion_p (type, expr, true)) |
2732 |
conversion_kind = unsafe_conversion_p (type, expr, true); |
|
|
2733 |
if (conversion_kind == UNSAFE_REAL) |
2734 |
warning_at (loc, OPT_Wfloat_conversion, |
2735 |
"conversion to %qT alters %qT constant value", |
2736 |
type, expr_type); |
2737 |
else if (conversion_kind) |
2732 |
warning_at (loc, OPT_Wconversion, |
2738 |
warning_at (loc, OPT_Wconversion, |
2733 |
"conversion to %qT alters %qT constant value", |
2739 |
"conversion to %qT alters %qT constant value", |
2734 |
type, expr_type); |
2740 |
type, expr_type); |
Lines 2747-2753
conversion_warning (tree type, tree expr
Link Here
|
2747 |
} |
2753 |
} |
2748 |
|
2754 |
|
2749 |
default: /* 'expr' is not a constant. */ |
2755 |
default: /* 'expr' is not a constant. */ |
2750 |
if (unsafe_conversion_p (type, expr, true)) |
2756 |
conversion_kind = unsafe_conversion_p (type, expr, true); |
|
|
2757 |
if (conversion_kind == UNSAFE_REAL) |
2758 |
warning_at (loc, OPT_Wfloat_conversion, |
2759 |
"conversion to %qT from %qT may alter its value", |
2760 |
type, expr_type); |
2761 |
else if (conversion_kind) |
2751 |
warning_at (loc, OPT_Wconversion, |
2762 |
warning_at (loc, OPT_Wconversion, |
2752 |
"conversion to %qT from %qT may alter its value", |
2763 |
"conversion to %qT from %qT may alter its value", |
2753 |
type, expr_type); |
2764 |
type, expr_type); |