public inbox for gcc-prs@sourceware.org
help / color / mirror / Atom feed
From: niemayer@isg.de
To: gcc-gnats@gcc.gnu.org
Subject: c++/8826: "a >> b" differs from "a.operator>>(b)" in that virtual function calls are not avoided
Date: Thu, 05 Dec 2002 10:56:00 -0000	[thread overview]
Message-ID: <20021205185304.22787.qmail@sources.redhat.com> (raw)


>Number:         8826
>Category:       c++
>Synopsis:       "a >> b" differs from "a.operator>>(b)" in that virtual function calls are not avoided
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    unassigned
>State:          open
>Class:          pessimizes-code
>Submitter-Id:   net
>Arrival-Date:   Thu Dec 05 10:56:02 PST 2002
>Closed-Date:
>Last-Modified:
>Originator:     Peter Niemayer
>Release:        gcc-3.x (x < 3)
>Organization:
>Environment:
linux / x86
>Description:
The compiler tries to avoid unneccessary virtual function
calls, which can sometimes cause dramatic performance 
improvements, but alas, it fails to do so when one of two
possible (and IMHO equivalent) syntaxes is used when invoking
an operator member function.

This may seem very harmless as the code still works, but
the optimization is missing in a very often used scenario,
for calls that are done very frequently... 


>How-To-Repeat:
Compile the following tiny piece of C++ source optimized
into assember, and have a look at the two code sequences
between the "testlabel?" pairs:

class A {
public:	
	virtual int operator>>(int x) { return x+1; }
};

int testfunc1(int y) {
	A a;
	asm volatile("testlabel1: ");
	int r = a >> y;
	asm volatile("testlabel2: ");
	return r;
}

int testfunc2(int y) {
	A a;
	asm volatile("testlabel3: ");
	int r = a.operator>>(y);
	asm volatile("testlabel4: ");
	return r;
}

(use "gcc -S test.cxx -O3" or similar)

You'll see that while the second function body is well
optimized, inlining just the necessary addition, the first
and most often used form is turned into badly optimized
code, doing an unneccessary virtual function call:

 ...
        testlabel1: 
#NO_APP
        movl    %edx, (%esp)
        movl    8(%ebp), %eax
        movl    %eax, 4(%esp)
        call    *_ZTV1A+8
#APP
        testlabel2: 

- versus -

        testlabel3: 
#NO_APP
        movl    8(%ebp), %eax
        incl    %eax
#APP
        testlabel4: 
>Fix:
The only work-around I've found is to use the awkward
"a.operator>>(b)" syntax, which is not only clumsy to
type but also fails to be valid when the operator function
is a two-argument global function rather than a member
function.
>Release-Note:
>Audit-Trail:
>Unformatted:


             reply	other threads:[~2002-12-05 18:56 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2002-12-05 10:56 niemayer [this message]
2002-12-05 11:34 bangerth
2003-05-02 12:06 Giovanni Bajo

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20021205185304.22787.qmail@sources.redhat.com \
    --to=niemayer@isg.de \
    --cc=gcc-gnats@gcc.gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).