Thread local storage is static but it behaves quite differently from simple static storage.
When you declare a variable static there is exactly one instance of the variable. The compiler/runtime system guarantees that it will be initialized for you sometime before you actually use it, without specifying exactly when (some details omitted here.)
C++11 guarantees that this initialization will be thread safe, however before C++11 this thread safety was not guaranteed. For example
static X * pointer = new X;
could leak instances of X if more than one thread hit the static initialization code at the same time.
When you declare a variable thread local there are potentially many instances of the variable. You could think of them as being in a map that was indexed by thread-id. That means each thread sees its own copy of the variable.
Once again, if the variable is initialized the compiler/runtime system guarantees that this initialization will happen before the data is used and that the initialization will happen for each thread that uses the variable. The compiler also guarantees that initiation will be thread safe.
The thread safety guarantees means that there can be quite a bit of behind-the-scenes code to make the variable behave the way you expect it to -- especially considering that the compiler has no way of knowing ahead of time exactly how many threads will exist in your program and how many of these will touch the thread local variable.
thread_local
local variable makes no sense to begin with … each thread has its own call stack. – Weaponrystatic
rather thanstatic thread_local
does not initialize one instance of the variable for each thread. – Chishimastatic
vsstatic thread_local
but rather aboutauto
vsthread_local
, using the pre-C++11 meaning ofauto
(i.e. automatic storage). – Weaponry