Subject: [Boost-bugs] [Boost C++ Libraries] #2939: Possible thread-safety issue with Boost Function
From: Boost C++ Libraries (noreply_at_[hidden])
Date: 2009-04-12 04:56:23
#2939: Possible thread-safety issue with Boost Function
---------------------------------------+------------------------------------
Reporter: boost-trac_at_[hidden] | Owner: dgregor
Type: Bugs | Status: new
Milestone: Boost 1.39.0 | Component: function
Version: Boost 1.38.0 | Severity: Problem
Keywords: |
---------------------------------------+------------------------------------
Hi, I realize this might slip through the mailing lists so I am posting it
here:
http://article.gmane.org/gmane.comp.lib.boost.devel/188442
I was just looking through the Boost Function source and noticed the
following in assign_to:
{{{
// Note: it is extremely important that this initialization use
// static initialization. Otherwise, we will have a race
// condition here in multi-threaded code. See
// http://thread.gmane.org/gmane.comp.lib.boost.devel/164902/.
static vtable_type stored_vtable =
{ { &manager_type::manage }, &invoker_type::invoke };
}}}
However, my copy of the C++ standard seems to say this regarding local
statics in section 6.7:
The zero-initialization (8.5) of all local objects with static storage
duration (3.7.1) is performed before any other initialization takes place.
A local object of POD type (3.9) with static storage duration initialized
with constant-expressions is initialized before its block is first
entered. An implementation is permitted to perform early initialization of
other local objects with static storage duration under the same conditions
that an implementation is permitted to statically initialize an object
with static storage duration in namespace scope.
I read this to mean that an implementation may decide to initialize
stored_vtable statically or the first time the block is entered. So I
think that this means we cannot rely on static initialization behaviour.
If you agree, then a simple fix for this might just be:
{{{
template<typename VTable, typename Invoker, typename Manager>
struct vtable_static_constructor
{
static VTable vtable;
};
template<...>
VTable vtable_static_constructor<V,I,M>::vtable =
{ {&Manager::manage, &Manager::invoke } };
assign_to()
{
...
vtable_type & stored_vtable =
vtable_static_constructor<vtable_type,invoker_type,manager_type>::vtable;
...
}
}}}
If not, could you please point me to where in the standard this is
guaranteed to be statically initialized? It would help me decide whether
or not to fix some other code that has a similar pattern, if nothing else.
Thanks in advance!
-- Ticket URL: <https://svn.boost.org/trac/boost/ticket/2939> Boost C++ Libraries <http://www.boost.org/> Boost provides free peer-reviewed portable C++ source libraries.
This archive was generated by hypermail 2.1.7 : 2017-02-16 18:50:00 UTC