From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 25603 invoked by alias); 7 Jul 2004 11:56:26 -0000 Mailing-List: contact gcc-bugs-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Archive: List-Post: List-Help: Sender: gcc-bugs-owner@gcc.gnu.org Received: (qmail 25547 invoked by uid 48); 7 Jul 2004 11:56:21 -0000 Date: Wed, 07 Jul 2004 11:56:00 -0000 From: "guillaume dot melquiond at ens-lyon dot fr" To: gcc-bugs@gcc.gnu.org Message-ID: <20040707115615.16405.guillaume.melquiond@ens-lyon.fr> Reply-To: gcc-bugzilla@gcc.gnu.org Subject: [Bug c++/16405] New: Non optimized code when using default copy constructor X-Bugzilla-Reason: CC X-SW-Source: 2004-07/txt/msg00600.txt.bz2 List-Id: I have been compiling the following snippet with g++ version 3.3.4, 3.4.0, 3.5.0. They are Debian packages, so the 3.4.0 version is a bit old (and a prerelease), sorry. So maybe the bug has already been fixed in g++ 3.4. However it is still present in a recent snapshot of the trunk. In the following, the function goes from using only one temporary in g++ 3.3 to using four temporaries in g++ 3.5. -------------------------------------------------------------------- struct T { int a[128]; // T(T const &v); T &operator+=(T const &v); T operator+(T const &v) const { T t = *this; t += v; return t; } }; extern T a, b, c; void f() { a = b + c; } -------------------------------------------------------------------- So the code just describes a big plain structure and its operator+ is defined with its operator+=. The function f computes an addition and operator+ is inlined into it. When compiling with g++ 3.3, the generated assembly is optimal: there is only one temporary, b is copied into this temporary, c is added to this temporary, the result is then assigned to a. When compiling with g++ 3.4, it is no more optimal: there are two temporaries, b is copied into one, c is added to this temporary holding b, the result is copied into the other temporary, and the temporary is then assigned to a. Maybe the NRVO did not kick in? When compiling with g++ 3.5, it is even worse: there are four temporaries, b is copied into one, c is added to this temporary holding b, the result then goes into two successive temporaries before being assigned to a. So there is one copy that does not mean anything with respect to the code? And please note there is one temporary that just lies on the stack and is never used (since only three temporaries are used, not four). If a copy constructor is added (just comment out the line), the three compilers generate a similar code: only one temporary is ever used. It is the expected and optimal code generation. So it seems g++ has some kind of problem with the default copy constructor starting with 3.4. As a side note, even with a non-default copy constructor, g++ 3.5 still allocates a temporary that is never used. Maybe it is an unrelated bug? The snippet is each time compiled with $ g++-... -Wall -O3 -S test.cpp Here are the exact versions used. $ LANG=C g++-3.3 -v Reading specs from /usr/lib/gcc-lib/i486-linux/3.3.4/specs Configured with: ../src/configure -v --enable-languages=c,c++,java,f77,pascal,objc,ada,treelang --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --with-gxx-include-dir=/usr/include/c++/3.3 --enable-shared --with-system-zlib --enable-nls --without-included-gettext --enable-__cxa_atexit --enable-clocale=gnu --enable-debug --enable-java-gc=boehm --enable-java-awt=xlib --enable-objc-gc i486-linux Thread model: posix gcc version 3.3.4 (Debian 1:3.3.4-2) $ LANG=C g++-3.4 -v Reading specs from /usr/lib/gcc/i486-linux/3.4.0/specs Configured with: ../src/configure -v --enable-languages=c,c++,java,f77,pascal,objc,ada,treelang --prefix=/usr --libexecdir=/usr/lib --with-gxx-include-dir=/usr/include/c++/3.4 --enable-shared --with-system-zlib --enable-nls --enable-threads=posix --without-included-gettext --program-suffix=-3.4 --enable-__cxa_atexit --enable-clocale=gnu --enable-libstdcxx-debug --enable-java-gc=boehm --enable-java-awt=gtk --disable-werror i486-linux Thread model: posix gcc version 3.4.0 20040403 (prerelease) (Debian) $ LANG=C g++-snapshot -v Reading specs from /usr/lib/gcc-snapshot/lib/gcc/i486-linux-gnu/3.5.0/specs Configured with: ../src/configure -v --enable-languages=c,c++,java,f95,objc --prefix=/usr/lib/gcc-snapshot --enable-shared --with-system-zlib --enable-nls --enable-threads=posix --without-included-gettext --disable-werror --enable-__cxa_atexit --enable-clocale=gnu --enable-libstdcxx-debug --enable-java-gc=boehm --enable-java-awt=gtk i486-linux-gnu Thread model: posix gcc version 3.5.0 20040704 (experimental) -- Summary: Non optimized code when using default copy constructor Product: gcc Version: 3.4.0 Status: UNCONFIRMED Severity: normal Priority: P2 Component: c++ AssignedTo: unassigned at gcc dot gnu dot org ReportedBy: guillaume dot melquiond at ens-lyon dot fr CC: gcc-bugs at gcc dot gnu dot org GCC host triplet: i486-linux-gnu http://gcc.gnu.org/bugzilla/show_bug.cgi?id=16405