http://gcc.gnu.org/bugzilla/show_bug.cgi?id=58794

Richard Biener <rguenth at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |ebotcazou at gcc dot gnu.org

--- Comment #4 from Richard Biener <rguenth at gcc dot gnu.org> ---
(In reply to Richard Biener from comment #3)
> The issue being that &a.f and &a.f are not equal because even with
> OEP_CONSTANT_ADDRESS_OF set we get into
> 
>         case COMPONENT_REF:
>           /* Handle operand 2 the same as for ARRAY_REF.  Operand 0
>              may be NULL when we're called to compare MEM_EXPRs.  */
>           if (!OP_SAME_WITH_NULL (0))
>             return 0;
>           flags &= ~OEP_CONSTANT_ADDRESS_OF;
>           return OP_SAME (1) && OP_SAME_WITH_NULL (2);
> 
> and thus drop it before comparing the two FIELD_DECLs which have
> TREE_SIDE_EFFECTS set.  Fixed with
> 
> Index: gcc/fold-const.c
> ===================================================================
> --- gcc/fold-const.c    (revision 203886)
> +++ gcc/fold-const.c    (working copy)
> @@ -2715,10 +2715,11 @@ operand_equal_p (const_tree arg0, const_
>         case COMPONENT_REF:
>           /* Handle operand 2 the same as for ARRAY_REF.  Operand 0
>              may be NULL when we're called to compare MEM_EXPRs.  */
> -         if (!OP_SAME_WITH_NULL (0))
> +         if (!OP_SAME_WITH_NULL (0)
> +             || !OP_SAME (1))
>             return 0;
>           flags &= ~OEP_CONSTANT_ADDRESS_OF;
> -         return OP_SAME (1) && OP_SAME_WITH_NULL (2);
> +         return OP_SAME_WITH_NULL (2);
>  
>         case BIT_FIELD_REF:
>           if (!OP_SAME (0))
> 
> I spotted this earlier but for some reason chickeded out to make this
> change.  Hmm.  Trying to remember why ...

I think it was because the offsets in the FIELD_DECL could have side-effects.
So you could argue that it is the C/C++ frontends that shouldn't set
TREE_SIDE_EFFECTS on the FIELD_DECL if that isn't the case for tem.
But of course then this bit should vanish again at the point we lower
COMPONENT_REFs to populate their operand 2 with any non-constant offfsets
(and thus side-effects).

For C and C++ TREE_SIDE_EFFECTS comes from

c_apply_type_quals_to_decl (type_quals=2, decl=<field_decl 0x7ffff6e3b130 f2>)
    at /space/rguenther/src/svn/trunk/gcc/c-family/c-common.c:4719
4719          TREE_THIS_VOLATILE (decl) = 1;

and ultimately grokdeclarator.

I don't see a way out of this as we possibly overload TREE_SIDE_EFFECTS with
both, volatility of the field itself (ok to skip with OEP_CONSTANT_ADDRESS_OF)
and side-effects inside DECL_FIELD_OFFSET (a volatile load therein, or
other side-effects).

I'm sure that we can build such FIELD_DECL only with Ada though, so, Eric,
can you provide a testcase where that happens - thus, that shows that
side-effects cannot be ignored here by for example comparing
&f.x and &f.x for a case where that is not equal?  I think we need to
concern ourselves only with mutating side-effects, not a volatile load.

The question is whether the patch is ok as-is or if I have to make
behavior dependent on is_gimple_form (ugh).  A testcase that breaks
if not guarding it that way would be nice to have (I'll check if anything
existing triggers).

Reply via email to