public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug tree-optimization/29415]  New: [4.2] bad code reordering around inline asm block
@ 2006-10-10 15:38 christophe at saout dot de
  2006-10-10 15:40 ` [Bug tree-optimization/29415] " christophe at saout dot de
                   ` (18 more replies)
  0 siblings, 19 replies; 20+ messages in thread
From: christophe at saout dot de @ 2006-10-10 15:38 UTC (permalink / raw)
  To: gcc-bugs

Using gcc 4.2 snapshot 20061007 on x86, the compiler is miscompiling glibc 2.5
(see http://sourceware.org/bugzilla/show_bug.cgi?id=3328)

What is happening is that a test of a variable after an inline asm block is
moved around so that the load of the struct member is moved above the asm block
even though it should not do that.

The miscompilation only seems to appear in that particular constellation, all
tries to reproduce the problem using a simpler hand-made test case have failed.
So I've attached the whole preprocessed source file.

Compiler simply called with "gcc -O2 -o test.o -c pthread_mutex_lock.c".

The problem appears in the function __pthread_mutex_lock. There's a switch
statement with some common stuff in the different cases which the compiler
seems to optimize. The case in question (the most common one):

switch (__builtin_expect (mutex->__data.__kind, PTHREAD_MUTEX_TIMED_NP)) {
...
    case PTHREAD_MUTEX_TIMED_NP:
    simple:
      /* Normal mutex.  */
      LLL_MUTEX_LOCK (mutex->__data.__lock);
      assert (mutex->__data.__owner == 0);
      break;
...
}

The LLL_MUTEX_LOCK is a macro with an inline assembler statement (cmpxchg and a
conditional jump to another section) that is annotated to tell the compiler
that it clobbers memory, so gcc should never move loads around the inline asm
block. But in this case the load from mutex->__data.__owner (for the assertion)
is executed above LLL_MUTEX_LOCK and the register content is tested below
LLL_MUTEX_LOCK. The content will have changed, but the old value in the
register is wrong and the assertion triggers.

The broken generated code looks like (note that the jump to <_L_mutex_lock_78>
is just an out-of-line call to another function that can wait for some time,
modify the mutex->__data.__owner = 0x8(%ebx) here, and then jump back):

loading mutex->__data.__owner (into %edx):
  2f:   8b 53 08                mov    0x8(%ebx),%edx
lll_mutex_lock:
  32:   31 c0                   xor    %eax,%eax
  34:   b9 01 00 00 00          mov    $0x1,%ecx
  39:   f0 0f b1 0b             lock cmpxchg %ecx,(%ebx)
  3d:   0f 85 f3 05 00 00       jne    636 <_L_mutex_lock_78>
testing mutex->__data.__owner (%edx from above!):
  43:   85 d2                   test   %edx,%edx
  45:   0f 85 7f 04 00 00       jne    4ca <__pthread_mutex_lock+0x4ca>
                                        -> __assert_fail

In constrast, gcc 4.1.1 generated the following correct piece of code:

acquiring mutex (lll_mutex_lock):
  3d:   31 c0                   xor    %eax,%eax
  3f:   b9 01 00 00 00          mov    $0x1,%ecx
  44:   f0 0f b1 0b             lock cmpxchg %ecx,(%ebx)
  48:   0f 85 ed 05 00 00       jne    63b <_L_mutex_lock_86>
loading and testing owner:
  4e:   8b 43 08                mov    0x8(%ebx),%eax
  51:   85 c0                   test   %eax,%eax
  53:   0f 85 71 05 00 00       jne    5ca <__pthread_mutex_lock+0x5ca>
                                        -> __assert_fail


-- 
           Summary: [4.2] bad code reordering around inline asm block
           Product: gcc
           Version: 4.2.0
            Status: UNCONFIRMED
          Severity: critical
          Priority: P3
         Component: tree-optimization
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: christophe at saout dot de
 GCC build triplet: i686-pc-linux-gnu
  GCC host triplet: i686-pc-linux-gnu
GCC target triplet: i686-pc-linux-gnu


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


^ permalink raw reply	[flat|nested] 20+ messages in thread

end of thread, other threads:[~2007-11-30 15:48 UTC | newest]

Thread overview: 20+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2006-10-10 15:38 [Bug tree-optimization/29415] New: [4.2] bad code reordering around inline asm block christophe at saout dot de
2006-10-10 15:40 ` [Bug tree-optimization/29415] " christophe at saout dot de
2006-10-10 16:46 ` pinskia at gcc dot gnu dot org
2006-10-10 18:55 ` jakub at gcc dot gnu dot org
2006-10-11  0:48 ` [Bug middle-end/29415] " pinskia at gcc dot gnu dot org
2006-10-11  0:57 ` [Bug tree-optimization/29415] [4.2 regression] ] " pinskia at gcc dot gnu dot org
2006-10-11  1:05 ` pinskia at gcc dot gnu dot org
2006-10-11  2:35 ` pinskia at gcc dot gnu dot org
2006-10-11  2:37 ` pinskia at gcc dot gnu dot org
2006-10-11  2:43 ` dberlin at gcc dot gnu dot org
2006-10-11  2:46 ` dberlin at gcc dot gnu dot org
2006-10-13 17:18 ` [Bug tree-optimization/29415] [4.2 Regression] " steven at gcc dot gnu dot org
2006-10-13 17:45 ` pinskia at gcc dot gnu dot org
2006-10-13 17:49 ` dberlin at gcc dot gnu dot org
2006-10-15 21:23 ` mmitchel at gcc dot gnu dot org
2006-10-19 23:06 ` dberlin at gcc dot gnu dot org
2006-10-19 23:07 ` dberlin at gcc dot gnu dot org
2007-11-30 15:25 ` cfriedt at visible-assets dot com
2007-11-30 15:27 ` rguenth at gcc dot gnu dot org
2007-11-30 15:48 ` cfriedt at visible-assets dot com

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).