This is the mail archive of the gcc-bugs@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Bug libstdc++/58104] New: std::call_once appears to fail on standard code


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

            Bug ID: 58104
           Summary: std::call_once appears to fail on standard code
           Product: gcc
           Version: 4.8.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: libstdc++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: barto at visionpro dot com

When using std::call_once the code on Linux(gcc 4.7.0) or MacOS (gcc 4.7.3 or
4.8.1) fails to execute

562_ /opt/local/bin/gcc-mp-4.8 -v
Using built-in specs.
COLLECT_GCC=/opt/local/bin/gcc-mp-4.8
COLLECT_LTO_WRAPPER=/opt/local/libexec/gcc/x86_64-apple-darwin12/4.8.1/lto-wrapper
Target: x86_64-apple-darwin12
Configured with: ../gcc-4.8.1/configure --prefix=/opt/local
--build=x86_64-apple-darwin12
--enable-languages=c,c++,objc,obj-c++,lto,fortran,java
--libdir=/opt/local/lib/gcc48 --includedir=/opt/local/include/gcc48
--infodir=/opt/local/share/info --mandir=/opt/local/share/man
--datarootdir=/opt/local/share/gcc-4.8 --with-local-prefix=/opt/local
--with-system-zlib --disable-nls --program-suffix=-mp-4.8
--with-gxx-include-dir=/opt/local/include/gcc48/c++/ --with-gmp=/opt/local
--with-mpfr=/opt/local --with-mpc=/opt/local --with-ppl=/opt/local
--with-cloog=/opt/local --enable-cloog-backend=isl
--disable-cloog-version-check --enable-stage1-checking --enable-lto
--enable-libstdcxx-time --with-as=/opt/local/bin/as --with-ld=/opt/local/bin/ld
--with-ar=/opt/local/bin/ar --with-bugurl=https://trac.macports.org/newticket
--with-pkgversion='MacPorts gcc48 4.8.1_1+universal'
Thread model: posix
gcc version 4.8.1 (MacPorts gcc48 4.8.1_1+universal) 

The code that fails is taken directly from the c++ documentation site:

http://en.cppreference.com/w/cpp/thread/call_once

#include <iostream>
#include <thread>
#include <mutex>

std::once_flag flag;

void do_once()
{
    std::call_once(flag, [](){ std::cout << "Called once" << std::endl; });
}

int main()
{
    std::thread t1(do_once);
    std::thread t2(do_once);
    std::thread t3(do_once);
    std::thread t4(do_once);

    t1.join();
    t2.join();
    t3.join();
    t4.join();
}

The bug appears in the call to call_once (thanks for detail from Jeremy
Huddleston Sequoia on the MacPorts mailing list for the assembly trace)

__once_proxy is just looking up some other function (__once_call) using
__emutls_get_address and executing it (makes sense based on the name).
__emutls_get_address is returning 3 in this instance, so something looks wrong
with emutls:

(lldb) disassemble -n __once_proxy
libstdc++.6.dylib`__once_proxy:
  0x1000e974e:  pushq  %rbp
  0x1000e974f:  movq   %rsp, %rbp
  0x1000e9752:  leaq   463719(%rip), %rdi        ; __emutls_v._ZSt11
_ZSt11__once_call
  0x1000e9759:  callq  0x100101880               ;
libstdc++.6.dylib.__TEXT.__text + 602364
-> 0x1000e975e:  movq   (%rax), %rax
  0x1000e9761:  callq  *%rax
  0x1000e9763:  popq   %rbp
  0x1000e9764:  ret    
(lldb) disassemble -s 0x100101880
libstdc++.6.dylib`__emutls_get_address:
...
(lldb) register read
General Purpose Registers:
      rax = 0x0000000000000003
...

Further this has been shown to fail on 4.7 [gcc version 4.7.3 (MacPorts gcc47
4.7.3_1+universal)]
and in the development build for gcc 4.9 (again through Jeremy)

If this is a configuration issue, what configuration flag is required to make
the feature work?

What versions of the Mac/Linux version of gcc have been shown to work?


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]