Re: return value aliasing ?

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Thu, 27 Mar 2014, Joachim Schöberl wrote:

I am experimenting with AVX optimization of a complex code, and discovered
this simplified test-case already for scalar code:

I compiled this code

class MyDouble
{
 double data;
public:
 MyDouble (const MyDouble & v2) : data(v2.data) { ; }
 MyDouble (double d) : data(d) { ; }

 MyDouble & operator+= (MyDouble d)
 { data += d.data; return *this; }
};

MyDouble MyFuncBad (int m, MyDouble x)
{
 MyDouble sum = 0.0;
 for (int i = 0; i < m; i++) sum += x;
 return sum;
}

MyDouble MyFuncGood (int m, MyDouble x)
{
 MyDouble sum = 0.0;
 for (int i = 0; i < m; i++) sum += x;
 return MyDouble(sum);
}

with 'gcc-4.8 -O3 -S testdouble.cpp' and got the assembly code below.
I would expect that both functions are equivalent.

In MyFuncBad, the intermediate sum is written to memory in every
iteration, while in MyFuncGood just the final result is brought to
memory. Is this necessary for correctness ?
Can the return-value alias the call-by-value argument ?

In the AVX-code the performance difference was about 30 percent.

If I use the default copy-constructor, I also get the faster code.
Is there something wrong with my (of course here unnecessary) copy-constructor
?

Please file a PR in bugzilla for this missed optimization. C++ copy elision makes us use the return slot for sum, and we don't manage to avoid the memory accesses. Removing the user-defined copy constructor changes the ABI to return in a register, and copy elision doesn't apply.

--
Marc Glisse




[Index of Archives]     [Linux C Programming]     [Linux Kernel]     [eCos]     [Fedora Development]     [Fedora Announce]     [Autoconf]     [The DWARVES Debugging Tools]     [Yosemite Campsites]     [Yosemite News]     [Linux GCC]

  Powered by Linux