index.html (Is libstdc++-v3 thread-safe?): Rewrite.
* docs/html/faq/index.html (Is libstdc++-v3 thread-safe?): Rewrite. * docs/html/23_containers/howto.html (Containers and multithreading): Update. From-SVN: r46175
This commit is contained in:
parent
eb9d8e4d0b
commit
ac3636f297
@ -1,3 +1,9 @@
|
|||||||
|
2001-10-11 Loren J. Rittle <ljrittle@acm.org>
|
||||||
|
|
||||||
|
* docs/html/faq/index.html (Is libstdc++-v3 thread-safe?): Rewrite.
|
||||||
|
* docs/html/23_containers/howto.html (Containers and multithreading):
|
||||||
|
Update.
|
||||||
|
|
||||||
2001-10-09 Phil Edwards <pme@gcc.gnu.org>
|
2001-10-09 Phil Edwards <pme@gcc.gnu.org>
|
||||||
|
|
||||||
* docs/html/17_intro/howto.html: Tweak markup and value type.
|
* docs/html/17_intro/howto.html: Tweak markup and value type.
|
||||||
|
@ -192,68 +192,55 @@
|
|||||||
|
|
||||||
<hr>
|
<hr>
|
||||||
<h2><a name="3">Containers and multithreading</a></h2>
|
<h2><a name="3">Containers and multithreading</a></h2>
|
||||||
<p>This section will mention some of the problems in designing MT
|
<p>This section discusses issues surrounding the design of
|
||||||
programs that use Standard containers. For information on other
|
multithreaded applications which use Standard C++ containers.
|
||||||
aspects of multithreading (e.g., the library as a whole), see
|
All information in this section is current as of the gcc 3.0
|
||||||
the Received Wisdom on Chapter 17. This section only applies
|
release and all later point releases. Although earlier gcc
|
||||||
when gcc and libstdc++-v3 were configured with --enable-threads.
|
releases had a different approach to threading configuration and
|
||||||
</p>
|
proper compilation, the basic code design rules presented here
|
||||||
<p>Two excellent pages to read when working with templatized containers
|
were similar. For information on all other aspects of
|
||||||
and threads are
|
multithreading as it relates to libstdc++, including details on
|
||||||
|
the proper compilation of threaded code (and compatibility between
|
||||||
|
threaded and non-threaded code), see Chapter 17.
|
||||||
|
</p>
|
||||||
|
<p>Two excellent pages to read when working with the Standard C++
|
||||||
|
containers and threads are
|
||||||
<a href="http://www.sgi.com/tech/stl/thread_safety.html">SGI's
|
<a href="http://www.sgi.com/tech/stl/thread_safety.html">SGI's
|
||||||
http://www.sgi.com/tech/stl/thread_safety.html</a> and
|
http://www.sgi.com/tech/stl/thread_safety.html</a> and
|
||||||
<a href="http://www.sgi.com/tech/stl/Allocators.html">SGI's
|
<a href="http://www.sgi.com/tech/stl/Allocators.html">SGI's
|
||||||
http://www.sgi.com/tech/stl/Allocators.html</a>. The
|
http://www.sgi.com/tech/stl/Allocators.html</a>.
|
||||||
libstdc++-v3 uses the same definition of thread safety
|
</p>
|
||||||
when discussing design. A key point that beginners may miss is the
|
<p><em>However, please ignore all discussions about the user-level
|
||||||
|
configuration of the lock implementation inside the STL
|
||||||
|
container-memory allocator on those pages. For the sake of this
|
||||||
|
discussion, libstdc++-v3 configures the SGI STL implementation,
|
||||||
|
not you. This is quite different from how gcc pre-3.0 worked.
|
||||||
|
In particular, past advice was for people using g++ to
|
||||||
|
explicitly define _PTHREADS or other macros or port-specific
|
||||||
|
compilation options on the command line to get a thread-safe
|
||||||
|
STL. This is no longer required for any port and should no
|
||||||
|
longer be done unless you really know what you are doing and
|
||||||
|
assume all responsibility.</em>
|
||||||
|
</p>
|
||||||
|
<p>Since the container implementation of libstdc++-v3 uses the SGI
|
||||||
|
code, we use the same definition of thread safety as SGI when
|
||||||
|
discussing design. A key point that beginners may miss is the
|
||||||
fourth major paragraph of the first page mentioned above
|
fourth major paragraph of the first page mentioned above
|
||||||
("For most clients,"...), pointing
|
("For most clients,"...), which points out that
|
||||||
out that locking must nearly always be done outside the container,
|
locking must nearly always be done outside the container, by
|
||||||
by client code (that'd be you, not us *grin*).
|
client code (that'd be you, not us). There is a notable
|
||||||
<em>However, please take caution when considering the discussion
|
exceptions to this rule. Allocators called while a container or
|
||||||
about the user-level configuration of the mutex lock
|
element is constructed uses an internal lock obtained and
|
||||||
implementation inside the STL container-memory allocator on that
|
released solely within libstdc++-v3 code (in fact, this is the
|
||||||
page. For the sake of this discussion, libstdc++-v3 configures
|
reason STL requires any knowledge of the thread configuration).
|
||||||
the SGI STL implementation, not you. We attempt to configure
|
</p>
|
||||||
the mutex lock as is best for your platform. In particular,
|
|
||||||
past advice was for people using g++ to explicitly define
|
|
||||||
_PTHREADS on the command line to get a thread-safe STL. This
|
|
||||||
is no longer required for your port. It may or may not be
|
|
||||||
a good idea for your port. Extremely big caution: if you
|
|
||||||
compile some of your application code against the STL with one
|
|
||||||
set of threading flags and macros and another portion of the
|
|
||||||
code with different flags and macros that influence the
|
|
||||||
selection of the mutex lock, you may well end up with multiple
|
|
||||||
locking mechanisms in use which don't impact each other in the
|
|
||||||
manner that they should. Everything might link and all code
|
|
||||||
might have been built with a perfectly reasonable thread model
|
|
||||||
but you may have two internal ABIs in play within the
|
|
||||||
application. This might produce races, memory leaks and fatal
|
|
||||||
crashes. In any multithreaded application using STL, this
|
|
||||||
is the first thing to study well before blaming the allocator.</em>
|
|
||||||
</p>
|
|
||||||
<p>You didn't read it, did you? *sigh* I'm serious, go read the
|
|
||||||
SGI page. It's really good and doesn't take long, and makes most
|
|
||||||
of the points that would otherwise have to be made here (and does
|
|
||||||
a better job).
|
|
||||||
</p>
|
|
||||||
<p>That's much better. Now, the issue of MT has been brought up on
|
|
||||||
the libstdc++-v3 mailing list as well as the main GCC mailing list
|
|
||||||
several times. The Chapter 17 HOWTO has some links into the mail
|
|
||||||
archives, so you can see what's been thrown around. The usual
|
|
||||||
container (or pseudo-container, depending on how you look at it)
|
|
||||||
that people have in mind is <code>string</code>, which is one of the
|
|
||||||
points where libstdc++ departs from the SGI STL. As of the
|
|
||||||
2.90.8 snapshot, the libstdc++-v3 string class is safe for
|
|
||||||
certain kinds of multithreaded access.
|
|
||||||
</p>
|
|
||||||
<p>For implementing a container which does its own locking, it is
|
<p>For implementing a container which does its own locking, it is
|
||||||
trivial to (as SGI suggests) provide a wrapper class which obtains
|
trivial to provide a wrapper class which obtains the lock (as
|
||||||
the lock, performs the container operation, then releases the lock.
|
SGI suggests), performs the container operation, and then
|
||||||
This could be templatized <em>to a certain extent</em>, on the
|
releases the lock. This could be templatized <em>to a certain
|
||||||
underlying container and/or a locking mechanism. Trying to provide
|
extent</em>, on the underlying container and/or a locking
|
||||||
a catch-all general template solution would probably be more trouble
|
mechanism. Trying to provide a catch-all general template
|
||||||
than it's worth.
|
solution would probably be more trouble than it's worth.
|
||||||
</p>
|
</p>
|
||||||
<p>Return <a href="#top">to top of page</a> or
|
<p>Return <a href="#top">to top of page</a> or
|
||||||
<a href="../faq/index.html">to the FAQ</a>.
|
<a href="../faq/index.html">to the FAQ</a>.
|
||||||
|
@ -686,19 +686,58 @@ http://clisp.cons.org/~haible/gccinclude-glibc-2.2-compat.diff
|
|||||||
|
|
||||||
<hr>
|
<hr>
|
||||||
<h2><a name="5_6">5.6 Is libstdc++-v3 thread-safe?</a></h2>
|
<h2><a name="5_6">5.6 Is libstdc++-v3 thread-safe?</a></h2>
|
||||||
<p>Quick answer: no, as of 3.0, most of the library is not
|
<p>When the system's libc is itself thread-safe, libstdc++-v3
|
||||||
safe for multithreaded access. The string class is MT-safe.
|
strives to be thread-safe. The user-code must guard against
|
||||||
|
concurrent method calls which may access any particular
|
||||||
|
library object's state. Typically, the application
|
||||||
|
programmer may infer what object locks must be held based on
|
||||||
|
the objects referenced in a method call. Without getting
|
||||||
|
into great detail, here is an example which requires
|
||||||
|
user-level locks:
|
||||||
</p>
|
</p>
|
||||||
<p>This is assuming that your idea of "multithreaded"
|
<pre>
|
||||||
is the same as ours... The general question of multithreading
|
library_class_a shared_object_a;
|
||||||
and libstdc++-v3 is addressed in the chapter-specific advice for
|
|
||||||
<a href="../17_intro/howto.html#3">Library Introduction</a>.
|
thread_main () {
|
||||||
Threadsafe containers are covered in more detail in
|
library_class_b *object_b = new library_class_b;
|
||||||
<a href="../23_containers/howto.html">the Received Wisdom section
|
shared_object_a.add_b (object_b); // must hold lock for shared_object_a
|
||||||
on containers</a>. Threading and I/O are discussed in
|
shared_object_a.mutate (); // must hold lock for shared_object_a
|
||||||
<a href="../27_io/howto.html">the I/O chapter</a>.
|
}
|
||||||
<!-- I have successfully evaded the topic; my work here is
|
|
||||||
done- no, wait, I have to write those other sections... -->
|
// Multiple copies of thread_main() are started in independent threads.
|
||||||
|
</pre>
|
||||||
|
<p>Under the assumption that object_a and object_b are never
|
||||||
|
exposed to another thread, here is an example that should not
|
||||||
|
require any user-level locks:
|
||||||
|
</p>
|
||||||
|
<pre>
|
||||||
|
thread_main () {
|
||||||
|
library_class_a object_a;
|
||||||
|
library_class_b *object_b = new library_class_b;
|
||||||
|
object_a.add_b (object_b);
|
||||||
|
object_a.mutate ();
|
||||||
|
}
|
||||||
|
</pre>
|
||||||
|
<p>However, as of gcc 3.0 and point releases, beware that there
|
||||||
|
may be cases where shared nested or global objects (neither
|
||||||
|
of which are visible to user-code) are affected or used
|
||||||
|
without any internal locking.
|
||||||
|
<!-- Is this warning still required? - Loren -->
|
||||||
|
</p>
|
||||||
|
<p>In some cases, a stronger thread-safe claim is made. The
|
||||||
|
string class is thread-safe without user-code guards (i.e. a
|
||||||
|
string object may be shared and accessed between threads
|
||||||
|
without user-level locking). The IO classes are thread-safe
|
||||||
|
with user-code guards whenever the same user-visible object
|
||||||
|
may be accessed by multiple threads. The container classes
|
||||||
|
are thread-safe with user-code guards whenever the same
|
||||||
|
container may be accessed by multiple threads. All accesses
|
||||||
|
to hidden shared objects (e.g. the global allocator objects)
|
||||||
|
are believed to be properly guarded within the library.
|
||||||
|
</p>
|
||||||
|
<p>See chapters <a href="../17_intro/howto.html#3">17</a>,
|
||||||
|
<a href="../23_containers/howto.html#3">23</a> and
|
||||||
|
<a href="../27_io/howto.html#9">27</a> for more information.
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
<hr>
|
<hr>
|
||||||
|
Loading…
Reference in New Issue
Block a user