Chromium Code Reviews| Index: third_party/WebKit/Source/wtf/ThreadSpecific.h |
| diff --git a/third_party/WebKit/Source/wtf/ThreadSpecific.h b/third_party/WebKit/Source/wtf/ThreadSpecific.h |
| index 377a82f4e24e405aafb5c707a672de58ddc39ce6..5b197de00b5e533550547a6575b3cc4d7f3dfa1a 100644 |
| --- a/third_party/WebKit/Source/wtf/ThreadSpecific.h |
| +++ b/third_party/WebKit/Source/wtf/ThreadSpecific.h |
| @@ -44,6 +44,7 @@ |
| #include "wtf/Allocator.h" |
| #include "wtf/Noncopyable.h" |
| +#include "wtf/StackUtil.h" |
| #include "wtf/StdLibExtras.h" |
| #include "wtf/WTF.h" |
| #include "wtf/WTFExport.h" |
| @@ -113,6 +114,8 @@ class ThreadSpecific { |
| #elif OS(WIN) |
| int m_index; |
| #endif |
| + // This member must only be accessed or modified on the main thread. |
| + T* m_mainThreadStorage = nullptr; |
| }; |
| #if OS(POSIX) |
| @@ -261,17 +264,29 @@ inline bool ThreadSpecific<T>::isSet() { |
| template <typename T> |
| inline ThreadSpecific<T>::operator T*() { |
| - T* ptr = static_cast<T*>(get()); |
| - if (!ptr) { |
| - // Set up thread-specific value's memory pointer before invoking |
| - // constructor, in case any function it calls |
| - // needs to access the value, to avoid recursion. |
| - ptr = static_cast<T*>(Partitions::fastZeroedMalloc( |
| + T* offThreadPtr; |
| +#if defined(__GLIBC__) || OS(ANDROID) || OS(FREEBSD) |
| + // TLS is fast on these platforms. |
| + // TODO(csharrison): Qualify this statement for Android. |
| + T** ptr = &offThreadPtr; |
| + offThreadPtr = static_cast<T*>(get()); |
| +#else |
| + T** ptr = &m_mainThreadStorage; |
| + if (UNLIKELY(internal::mayNotBeMainThread())) { |
| + offThreadPtr = static_cast<T*>(get()); |
| + ptr = &offThreadPtr; |
| + } |
| +#endif |
| + // Set up thread-specific value's memory pointer before invoking constructor, |
| + // in case any function it calls needs to access the value, to avoid |
| + // recursion. |
| + if (UNLIKELY(!*ptr)) { |
|
haraken
2017/01/18 05:29:42
Can we just use if(!offThreadPtr) ? I don't fully
haraken
2017/01/18 05:29:42
Not related to this CL but we might want to remove
Charlie Harrison
2017/01/18 16:29:55
Acknowledged, though I wonder if that would lead t
Charlie Harrison
2017/01/18 16:29:55
We use pointer indirection here because ptr can po
haraken
2017/01/19 01:04:38
Thread initialization is already heavy, so I don't
|
| + *ptr = static_cast<T*>(Partitions::fastZeroedMalloc( |
| sizeof(T), WTF_HEAP_PROFILER_TYPE_NAME(T))); |
| - set(ptr); |
| - new (NotNull, ptr) T; |
| + set(*ptr); |
| + new (NotNull, *ptr) T; |
| } |
| - return ptr; |
| + return *ptr; |
| } |
| template <typename T> |