This is the mail archive of the
mailing list for the GCC project.
Re: C++ PATCH: PR 16405
Jason Merrill wrote:
The problem was that the front-end generates:
memcpy (&a, *(const T*)&<target_expr operator+(b, c)>, sizeof (T))
The gimplifier could not see through the INDIRECT_REF/ADDR_EXPR
combination to find the underlying TARGET_EXPR, and so generate a
temporary for it.
I don't see where the second temporary you mention is coming from. I
would expect the gimplifier to generate a temporary to store the address
of the TARGET_EXPR temporary, but that's just a scalar.
The result of operator+ is a class object, not a scalar. The TARGET_EXPR
contains the result of the call to operator+.
Yes, that's the first, expected temporary. Where's the second?
The return value from the operator+ is created in a temporary and then
copied to another temporary. Here's the t08.gimple output without my patch:
void f() ()
struct T t;
struct T & v;
struct T * const this;
this = (struct T * const) &b;
v = (struct T &) &c;
struct T t;
t = *this;
operator+= (&t, v);
D.1949 = t;
D.1953 = &D.1949;
a = *D.1953;
It's confusing to me that there are two t variables, especially since
one of them doesn't seem to be initialized before use, but I assume this
is just something about the pretty-printer?
After my patch, the final three lines collapse to just "a = t".
D.1949 is the variable created by the C++ front end as the TARGET_EXPR
temporary variable. So, are you suggesting that the problem is that the
NRV and inliner are not replacing the inner t with D.1949? If so, do
you think my patch was incorrect? (From a C++ perspective, I do not
think it is; we're merely eliding a bitwise copy of a temporary.)