public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
From: "dino at concisoft dot com" <gcc-bugzilla@gcc.gnu.org>
To: gcc-bugs@gcc.gnu.org
Subject: [Bug c++/36149]  New: -O2 optimization generates wrong code
Date: Tue, 06 May 2008 07:14:00 -0000	[thread overview]
Message-ID: <bug-36149-16153@http.gcc.gnu.org/bugzilla/> (raw)

GCC version:
gcc (GCC) 4.1.2 20070925 (Red Hat 4.1.2-27)

It is really hard to reproduce and goes away even with minimal code changes.

Happens in a unit test. 

Host is x86_64: "model name      : Intel(R) Core(TM)2 CPU          6300  @
1.86GHz" from /proc/cpuinfo.

The following snippets might be useful to someone perhaps:

C code:

    void pRemove(CLASS *d)
    {
      LC(d)->m_back->m_fwd = LC(d)->m_fwd;
      LC(d)->m_fwd->m_back = LC(d)->m_back;
    }

    void prepend(CLASS *a)
    {
        pRemove(a);
        LC(a)->m_fwd = head.m_fwd;
        head.m_fwd->m_back = LC(a);
        LC(a)->m_back = &head;
        head.m_fwd = LC(a);
    }

MapList::add():
            // ...
            m_list.remove(removed);
            if (fTop) {
                  m_list.prepend(item);
            } else {
            // ...


Disassembly w/ comments:

 8053c7f:       80 7d 8f 00             cmpb   $0x0,0xffffff8f(%ebp)        ###
if (fTop)
 8053c83:       89 02                   mov    %eax,(%edx)
 8053c85:       8b 07                   mov    (%edi),%eax
 8053c87:       89 3f                   mov    %edi,(%edi)
 8053c89:       89 50 04                mov    %edx,0x4(%eax)
 8053c8c:       89 7f 04                mov    %edi,0x4(%edi)

The above few lines perform the remove(removed) call and the if test out of
order, which is OK. After that, variables look like this:
14: item.m_back = (Vapi::DoubleLink *) 0x81d4400
13: item.m_fwd = (Vapi::DoubleLink *) 0x81d4400
12: item = (DownloadQueue::DQ_Item *) 0x81d4400
11: this->m_list.head.m_back = (Vapi::DoubleLink *) 0xffc26b3c
10: this->m_list.head.m_fwd = (Vapi::DoubleLink *) 0xffc26b3c
9: &this->m_list.head = (Vapi::DoubleLink *) 0xffc26b3c
8: removed.m_back = (Vapi::DoubleLink *) 0x81d43b0
7: removed.m_fwd = (Vapi::DoubleLink *) 0x81d43b0
6: removed = (DownloadQueue::DQ_Item *) 0x81d43b0

The m_list.head is empty, item is on no list, and removed is on no list.

Then the code for prepend(item) is supposed to execute:

 8053c8f:       0f 84 bf 01 00 00       je     8053e54
<DownloadQueue::DQ_MapList::add(DownloadQueue::DQ_Item*, bool)+0x354>
 8053c95:       8b 55 0c                mov    0xc(%ebp),%edx               ###
edx = item
 8053c98:       8b 42 04                mov    0x4(%edx),%eax               ###
eax = item->m_back (in pRemove)
 8053c9b:       89 d3                   mov    %edx,%ebx                    ###
ebx = item
 8053c9d:       8b 12                   mov    (%edx),%edx                  ###
edx = item->m_fwd
 8053c9f:       89 10                   mov    %edx,(%eax)                  ###
item->m_back->m_fwd = edx (item->m_fwd)
 8053ca1:       8b 13                   mov    (%ebx),%edx                  ###
edx = item->m_fwd
 8053ca3:       89 0b                   mov    %ecx,(%ebx)                  ###
item->m_fwd = %ecx (removed?!)
 8053ca5:       89 42 04                mov    %eax,0x4(%edx)               ###
item->m_fwd->m_back = item->m_back
 8053ca8:       8b 45 9c                mov    0xffffff9c(%ebp),%eax        ###
eax = head
 8053cab:       8b 55 98                mov    0xffffff98(%ebp),%edx        ###
??
 8053cae:       89 59 04                mov    %ebx,0x4(%ecx)               ###
removed->m_back = item (?!)
 8053cb1:       89 43 04                mov    %eax,0x4(%ebx)               ###
item->m_back = head
 8053cb4:       89 5a 04                mov    %ebx,0x4(%edx)               ###
?? head->m_back = item
 8053cb7:       8b 5f 20                mov    0x20(%edi),%ebx

But that doesn't look all that great. The compiler somehow tries to interleave
the pRemove and the rest of prepend, but the result is pretty bad:

14: item.m_back = (Vapi::DoubleLink *) 0xffc26b3c
13: item.m_fwd = (Vapi::DoubleLink *) 0x81d43b0
12: item = (DownloadQueue::DQ_Item *) 0x81d4400
11: this->m_list.head.m_back = (Vapi::DoubleLink *) 0xffc26b3c
10: this->m_list.head.m_fwd = (Vapi::DoubleLink *) 0x81d4400
9: &this->m_list.head = (Vapi::DoubleLink *) 0xffc26b3c
8: removed.m_back = (Vapi::DoubleLink *) 0x81d4400
7: removed.m_fwd = (Vapi::DoubleLink *) 0x81d43b0
6: removed = (DownloadQueue::DQ_Item *) 0x81d43b0

Item and removed point to each other, with one of their pointers, m_list.head
points to item but not with both pointers, item points to head with one of its
pointers...

May not be able to provide full source that reproduces the problem (couldn't
generate a short piece of code that reproduces the problem.) But, could perhaps
provide additional info.


-- 
           Summary: -O2 optimization generates wrong code
           Product: gcc
           Version: 4.1.2
            Status: UNCONFIRMED
          Severity: major
          Priority: P3
         Component: c++
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: dino at concisoft dot com


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=36149


             reply	other threads:[~2008-05-06  7:14 UTC|newest]

Thread overview: 15+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2008-05-06  7:14 dino at concisoft dot com [this message]
2008-05-06  7:19 ` [Bug c++/36149] " dino at concisoft dot com
2008-05-06  8:24 ` pinskia at gcc dot gnu dot org
2008-05-06 14:19 ` dino at concisoft dot com
2008-05-06 15:23 ` pinskia at gcc dot gnu dot org
2008-05-06 15:43 ` dino at concisoft dot com
2008-05-06 15:46 ` pinskia at gcc dot gnu dot org
2008-05-06 16:55 ` dino at concisoft dot com
2008-05-07  4:18 ` bangerth at dealii dot org
2008-05-07  6:15 ` dino at concisoft dot com
2008-05-07 19:30 ` rguenth at gcc dot gnu dot org
2008-05-11  7:25 ` pinskia at gcc dot gnu dot org
2008-06-06 21:13 ` [Bug middle-end/36149] " dino at concisoft dot com
2008-06-06 21:33 ` rguenth at gcc dot gnu dot org
2008-12-28  6:08 ` pinskia at gcc dot gnu dot org

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=bug-36149-16153@http.gcc.gnu.org/bugzilla/ \
    --to=gcc-bugzilla@gcc.gnu.org \
    --cc=gcc-bugs@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).