Хотел бы обратится к сообществу для прояснения не совсем ясной мне ситуации.
Речь идет о exception_ptr, rethrow_exception и current_exception в boost. Суть проблемы следующая: должно ли быть потокебезопасно выполнение current_exception (в нескольких потоках) после rethrow_exception для общего объекта исключения.
#include <iostream>
#include <exception>
#include <stdexcept>
#include <vector>
//#define USE_CPP11
#ifdef __GXX_EXPERIMENTAL_CXX0X__
#include <thread>
#include <future>
#include <memory>
#else
#include <boost>
#include <boost>
using namespace boost;
#endif
using namespace std;
void executer(mutex& mtx, exception_ptr ex)
{
for(int i = 0; i < 9999999; i++)
{
try
{
lock_guard<mutex> lck(mtx);
rethrow_exception(ex);
}
catch(...)
{
current_exception(); // <- run concurrently
}
}
}
void test()
{
exception_ptr ex;
try
{
throw runtime_error("O_o");
}
catch(...)
{
// use current_exception() it's compulsory condition
// because only in this case will be used unsafe detail::refcount_ptr
// (in current_exception_std_exception_wrapper inherited from exception)
ex = current_exception();
}
mutex mtx;
vector<shared_ptr> > group;
for(int i = 0; i < 10; i++)
group.push_back(shared_ptr<thread>(new thread(bind(executer, ref(mtx), ex))));
vector<shared_ptr> >::iterator it = group.begin();
for(; it != group.end(); it++)
(*it)->join();
}
void version()
{
#ifdef __GXX_EXPERIMENTAL_CXX0X__
cout << "use c++11 implementation\n";
#else
cout << "use boost implementation\n";
#endif
}
int main()
{
version();
cout << "Start\n";
test();
cout << "Exit\n";
}
</shared_ptr></thread></shared_ptr></mutex></boost></boost></memory></future></thread></vector></stdexcept></exception></iostream>
данный пример падает если использовать boost и не падает если использовать std реализацию (-std=c++11).
Стандарт по этому поводу пишет следующее
18.8.5 Exception propagation ... For purposes of determining the presence of a data race, operations onexception_ptr objects shall access and modify only the exception_ptrobjects themselves and not the exceptions they refer to. Use of rethrow_exceptionon exception_ptr objects that refer to the same exception object shallnot introduce a data race. [Note: if rethrow_exception rethrows the same exception object (ratherthan a copy), concurrent access to that rethrown exception object may introduce a data race. Changesin the number ofexception_ptrobjects that refer to a particular exception do not introduce a datarace.—end note]
То что описано в note это как раз моя ситуация, только я не понимаю, так должно быть или так не должно быть?