https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79937
--- Comment #16 from Jason Merrill <jason at gcc dot gnu.org> ---
(In reply to Jakub Jelinek from comment #13)
> E.g. could we walk into TARGET_EXPRs that have TARGET_EXPR_INITIAL
> AGGR_INIT_EXPR, but avoid those that have TARGET_EXPR_INITIAL a CONSTRUCTOR,
> or a CONSTRUCTOR with certain flags, or have some flags on TARGET_EXPRs?
No, the form of the TARGET_EXPR isn't sufficient to distinguish. Here's a
complete testcase:
struct X {
unsigned i;
unsigned n = i;
};
X bar(X x) {
return x;
}
struct Y
{
static Y bar(Y y) { return y; }
unsigned i;
unsigned n = bar(Y{2,i}).n;
};
int main()
{
X x { 1, bar(X{2}).n };
if (x.n != 2)
__builtin_abort();
Y y { 1 };
if (y.n != 1)
__builtin_abort();
}
Here, the initializers for x and y end up looking equivalent within
store_init_value, but the PLACEHOLDER_EXPRs are meant to refer to different
objects. There's no way for replace_placeholders to tell the difference.
I think to handle this we'll need to change process_init_constructor_record to
either not expose PLACEHOLDER_EXPRs, or adjust them to indicate better which
CONSTRUCTOR they refer to.