将 boost::thread 与 C++11 std::mutex 混合使用是否安全?



在通过 boost 启动线程的程序中使用std::mutex及其亲属是否安全?

(使用std::thread对我来说不是一个选择(我认为),因为应用程序需要大量的堆栈空间,并且在某些平台上需要在创建时覆盖默认堆栈大小。

是的,您可以在使用boost::thread创建的线程中使用std::mutex

应用程序需要大量的堆栈空间,并且在某些平台上需要在创建时覆盖默认堆栈大小

std::thread使用pthread_create在支持 POSIX 的平台上创建线程。您的另一个选择是覆盖pthread_create,设置堆栈大小并调用原始pthread_create

一个有效的Linux示例(我无法访问MacOS在那里尝试):

#include <cstdio>
#include <thread>
#include <dlfcn.h>
namespace {
size_t const STACK_SIZE = 8 * 1024 * 1024;
int pthread_create_override(pthread_t* thread, pthread_attr_t const* attr, void*(*start_routine)(void*), void* arg) noexcept {
std::printf("%sn", __PRETTY_FUNCTION__);
pthread_attr_t attr2;
if(attr)
attr2 = *attr;
else
if(pthread_attr_init(&attr2))
std::abort();
size_t stacksize = 0;
pthread_attr_getstacksize(&attr2, &stacksize);
if(stacksize < STACK_SIZE) {
if(pthread_attr_setstacksize(&attr2, STACK_SIZE))
std::abort();
}
static auto const real_pthread_create = reinterpret_cast<decltype(&pthread_create)>(::dlsym(RTLD_NEXT, "pthread_create"));
int rc = real_pthread_create(thread, &attr2, start_routine, arg);
if(!attr)
pthread_attr_destroy(&attr2);
return rc;
}
} // namespace
extern "C" {
int pthread_create(pthread_t* thread, pthread_attr_t const* attr, void*(*start_routine)(void*), void* arg) {
return pthread_create_override(thread, attr, start_routine, arg);
}
} // namespace
int main() {
std::thread t([]() { std::printf("%sn", __PRETTY_FUNCTION__); });
t.join();
}

输出:

int {anonymous}::pthread_create_override(pthread_t*, const pthread_attr_t*, void* (*)(void*), void*)
main()::<lambda()>

启动线程(pthread_createboost::threadstd::thread)的方式与您使用的同步原语(stdvsboostvs Intel TBB vs libatomic vs 等)正交。

否则,您将无法在一个应用程序中混合和匹配使用这些不同 API 的库。

低级同步原语(如原子组学、互斥体和条件变量)可以放置在共享内存中,供不同的进程使用,而无需显式创建任何额外的线程。此外,主应用程序线程由操作系统内核为您创建,而无需使用任何用户空间 API。

最新更新