Bug 32261 - Thread race segfault in std::string::append with -O and -s
Summary: Thread race segfault in std::string::append with -O and -s
Status: VERIFIED DUPLICATE of bug 21334
Alias: None
Product: gcc
Classification: Unclassified
Component: libstdc++ (show other bugs)
Version: 3.3.6
: P3 normal
Target Milestone: 3.4.6
Assignee: Not yet assigned to anyone
URL:
Keywords:
Depends on: 33394
Blocks:
  Show dependency treegraph
 
Reported: 2007-06-08 19:32 UTC by bennet brauer
Modified: 2015-03-24 14:12 UTC (History)
10 users (show)

See Also:
Host:
Target: i686-pc-linux-gnu
Build:
Known to work:
Known to fail:
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description bennet brauer 2007-06-08 19:32:03 UTC
Compiling with:
g++ -g -O3 gccbug.cpp -pthread -o gccbug -s

Note that removing the -s eliminates the segfault, as does removing optimizations with -O0.

This occurs with gcc 3.3 and 3.3.6 but does not occur with the gcc 3.2.3 delivered as part of RedHat ES3.0u5.  It is also fixed in 3.4.6.

#include <pthread.h>
#include <string>

void* thread_function(void*) {
    for (int k = 0; k < 50000; k++) {
        std::string my_str;
        my_str += "foo";
    }
    return 0;
}

int main()
{
    pthread_t thread1, thread2;

    pthread_create(&thread1, NULL, thread_function, NULL);
    pthread_create(&thread2, NULL, thread_function, NULL);

    void* exitcode;
    pthread_join(thread1, &exitcode);
    pthread_join(thread2, &exitcode);

    return 0;
}

Example stack trace (as a courtesy to future googlers looking for this issue):
#0  0x00d3d4cc in memcpy () from /lib/libc.so.6
#1  0x00ba9120 in std::string::_Rep::_M_clone (this=0x804a700, __alloc=@0x2012783, __res=28) at /build_gnu_build/gcc-3.3.6/i386-redhat-linux/libstdc++-v3/include/bits/char_traits.h:155
#2  0x00ba7519 in std::string::reserve (this=0xb6bf43b0, __res=28) at /build_gnu_build/gcc-3.3.6/i386-redhat-linux/libstdc++-v3/include/bits/basic_string.h:257
#3  0x00ba77be in std::string::append (this=0xb6bf43b0, __str=@0xb6bf43a0) at /build_gnu_build/gcc-3.3.6/i386-redhat-linux/libstdc++-v3/include/bits/basic_string.tcc:680
#4  0x08048c21 in ?? ()
#5  0x080490da in ?? ()
#6  0x08049093 in ?? ()
#7  0x08048fa6 in ?? ()
#8  0x003ef9d9 in start_thread (arg=0xb6bf4bb0) at pthread_create.c:261
#9  0x00d86f0e in clone () from /lib/libc.so.6
Comment 1 Andrew Pinski 2007-06-08 19:50:41 UTC
>It is also fixed in 3.4.6.

Well then it is fixed as 3.3.x is no longer being maintained and has not been for over a year (or two).
Comment 2 bennet brauer 2007-06-11 16:01:40 UTC
I wouldn't consider the bugzilla itself to be fixed until a regression test has been added to the gcc test suite.

Can you confirm that this test case has been added to the gcc regression test suite?  I searched the testsuites for 3.4.6 and don't see anything comprable to my test case.
Comment 3 jlawson-gcc 2007-06-12 01:36:10 UTC
This seems like a rather unexpected crash given the seemingly valid example code.  Can anyone from the GCC team indicate the actual compiler issue that might cause this example to fail, and specifically indicate an existing bugzilla number that addressed it?

I'm worried that this issue may very well have been unintentionally hidden and not actually fixed.  (For example, a casual code change might have altered segment alignments and symbol offsets happen to overflow differently.)
Comment 4 bennet brauer 2007-06-13 17:38:52 UTC
Yes in addition to the issue of adding a test case, it is quite unsettling to not know what might have fixed it.  Reopening pending response to comment 2 and comment 3.
Comment 5 Andrew Pinski 2007-06-14 01:27:59 UTC

*** This bug has been marked as a duplicate of 21334 ***
Comment 6 jlawson-gcc 2007-06-14 02:42:31 UTC
bug 21334 seems to deal with multiple threads accessing the same shared object at the same time.  However, the sample code provided here involves separate private objects so there should not be any such issues.  If it is not possible to assume that separate threads can access unrelated STL objects at the same time, then this would imply that all STL operations (regardless of the object) must be serialized!
Comment 7 pinskia@gmail.com 2007-06-14 02:56:35 UTC
Subject: Re:  Thread race segfault in std::string::append with -O and -s

> bug 21334 seems to deal with multiple threads accessing the same shared object
> at the same time.  However, the sample code provided here involves separate
> private objects so there should not be any such issues.  If it is not possible
> to assume that separate threads can access unrelated STL objects at the same
> time, then this would imply that all STL operations (regardless of the object)
> must be serialized!

The empty string is the same object really.

-- Pinski
Comment 8 Paolo Carlini 2007-06-14 08:15:51 UTC
Note, however, that startiing with 3.4.x (vs 3.3.x) the empty string representation is not not reference counted anymore. First blush, the *specific* code snippet in this PR should be safe.
Comment 9 bennet brauer 2007-06-25 23:41:23 UTC
So does this being marked dupe of bug 21334 mean that as long as <string> (not ext/vstring.h) is in use, that std::string is subject to other possible race conditions, even if the original test case succeeds in gcc 3.4.x?
Comment 10 Paolo Carlini 2007-06-25 23:50:45 UTC
Probably, the answer is yes. In this area, when writing portable code, always remember that C++03 says *nothing* about threads, and concurrent programming, and so on. Different implementations, historically, made different choices, different routes and trade-offs. That means that in general, if you cannot optimize for the implementation defined details of a specific implementation, you end-up locking a lot, for safety. That's unfortunate, I agree. The next C++ standard (and ext/vstring.h ;) will be better, certainly.
Comment 11 bennet brauer 2007-07-09 23:21:00 UTC
I've been unable to reproduce any issues in 3.4.6, even with tests that do not rely on the empty string.  I suspect there is something more specific that was fixed somewhere between 3.3.x and 3.4.6.

It doesn't seem appropriate to have marked this as a dupe of bug 21334, since bug 21334 has had no code changes made, but clearly a code change was made at some point to fix the comment 0 report.

I recommend the comment 0 test be added to the gcc regression test suite, after which this zilla could be reclassified as 'fixed'.
Comment 12 bennet brauer 2007-09-24 17:48:06 UTC
Due to lack of responsiveness, a separate Bug 33394 was opened for the missing test case.  Verified this is generically in concept a duplicate of bug 21334, although the technical details are in fact not the same.
Comment 13 Jonathan Wakely 2015-03-24 14:12:08 UTC
For the record, I believe this was fixed by https://gcc.gnu.org/r67912