This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
Re: fold_convert question
On Sat, 2004-10-16 at 06:33, Eric Botcazou wrote:
> > If there's anything I can do to help you investigate/fix c61008a
> > that avoids further degenerating the middle-end's type system, I'd
> > be happy to help. Ultimately, this might be a loosing crusade,
> > but I couldn't forgive myself if I didn't try. Worst case scenario
> > of tweaking useless_type_conversions is that we miss some optimizations
> > (until we get a tree-ssa combiner), but of perverting fold_convert
> > is that we regress many difficult to diagnose code generation bugs.
>
> I ran into another problem with tree_ssa_useless_type_conversion, which
> prevents the Ada RTS from building on SPARC and PPC (PR middle-end/17793).
>
> The front-end generates
>
> ADDR_EXPR <pointer_type <record_type>>
> VIEW_CONVERT_EXPR <record_type>
> NOP_EXPR <integer_type1>
> ARRAY_REF <integer_type2>
>
> with integer_type1 and integer_type2 not compatible.
>
> The gimplifier (gimplify_addr_expr) turns this into
>
> ADDR_EXPR <pointer_type <integer_type1>>
> NOP_EXPR <integer_type1>
> ARRAY_REF <integer_type2>
>
> and then STRIP_USELESS_TYPE_CONVERSION removes the NOP because of
>
> /* If both the inner and outer types are integral types, then the
> conversion is not necessary if they have the same mode and
> signedness and precision, and both or neither are boolean. Some
> code assumes an invariant that boolean types stay boolean and do
> not become 1-bit bit-field types. Note that types with precision
> not using all bits of the mode (such as bit-field types in C)
> mean that testing of precision is necessary. */
> else if (INTEGRAL_TYPE_P (inner_type)
> && INTEGRAL_TYPE_P (outer_type)
> && TYPE_MODE (inner_type) == TYPE_MODE (outer_type)
> && TYPE_UNSIGNED (inner_type) == TYPE_UNSIGNED (outer_type)
> && TYPE_PRECISION (inner_type) == TYPE_PRECISION (outer_type))
> {
> bool first_boolean = (TREE_CODE (inner_type) == BOOLEAN_TYPE);
> bool second_boolean = (TREE_CODE (outer_type) == BOOLEAN_TYPE);
> if (first_boolean == second_boolean)
> return true;
> }
>
> so we end up with
>
> ADDR_EXPR <pointer_type <integer_type1>>
> ARRAY_REF <integer_type2>
>
> which causes the gimplifier to later ICE in check_pointer_types_r because
> cpt_same_type returns false for (integer_type1, integer_type2).
>
>
> On the one hand, it seems to me that this is a consistency problem within the
> gimplifier and that cpt_same_type should accept the pairs of types deemed
> equivalent by tree_ssa_useless_type_conversion. On the other hand,
> check_pointer_types_r seems to be very strict on purpose so perhaps the NOP
> should not have been stripped in the first place.
>
> What do (both of) you think about that? Thanks in advance.
It seems to me we'd be best off turning:
ADDR_EXPR <pointer_type <record_type>>
VIEW_CONVERT_EXPR <record_type>
NOP_EXPR <integer_type1>
ARRAY_REF <integer_type2>
Into
NOP_EXPR <integer_type1>
ADDR_EXPR <pointer_type <integer_type2>>
ARRAY_REF <integer_type2>
I don't know how difficult that would be though.
Jeff