Rüd*_*ehn 5 multithreading thread-local thread-local-storage rust
Rust 标准库中的线程局部变量是如何工作的?我查看了代码,但在间接中迷失了方向。线程本地存储、OS 依赖模式和快速模式似乎有不同的配置。哪一个是默认的,我该如何选择使用哪一个?特别是,在 crate 中使用线程本地存储对 crate 用户有什么影响?
使用线程本地存储非常简单,生成的程序集看起来非常高效,但如果不完全理解其含义,我无法在库中使用该功能。
我也问过:
您看到的不同配置与 相关#[thread_local],该功能旨在替换thread_local!宏以使用户代码更简单,例如:
#![feature(thread_local)]
#[thread_local]
pub static mut VAR: u64 = 42;
Run Code Online (Sandbox Code Playgroud)
但是,在撰写本文时,此功能尚未完全实现(您可以在此处找到跟踪问题)。它是在编译的代码虽然在内部使用,那就是你在实际的“快”看到神奇的实施std::thread::LocalKey:
#[thread_local]
#[cfg(all(
target_thread_local,
not(all(target_arch = "wasm32", not(target_feature = "atomics"))),
))]
static __KEY: $crate::thread::__FastLocalKeyInner<$t> =
$crate::thread::__FastLocalKeyInner::new();
Run Code Online (Sandbox Code Playgroud)
注意#[thread_local]顶部的属性。然后将其转换为 LLVM IR,因此 TLS(线程本地存储)的实际实现由 LLVM 承载并实现ELF TLS 模型。这是默认配置。
我该如何选择使用哪一种?
您需要编译自己的rustc版本,并target_thread_local省略该功能。在这种情况下,os变的std::thread::LocalKey将被使用,然后,根据在一个平台上,它可以使用并行线程(UNIX) ,或Windows API的,或别的东西。
WebAssembly 是一个特例:由于它不支持线程,TLS 将被转换为简单的静态变量。