1 //=== llvm/Support/Unix/ThreadLocal.inc - Unix Thread Local Data -*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file implements the Unix specific (non-pthread) ThreadLocal class. 11 // 12 //===----------------------------------------------------------------------===// 13 14 //===----------------------------------------------------------------------===// 15 //=== WARNING: Implementation here must contain only generic UNIX code that 16 //=== is guaranteed to work on *all* UNIX variants. 17 //===----------------------------------------------------------------------===// 18 19 #if defined(HAVE_PTHREAD_H) && defined(HAVE_PTHREAD_GETSPECIFIC) 20 21 #include <cassert> 22 #include <pthread.h> 23 #include <stdlib.h> 24 25 namespace llvm { 26 using namespace sys; 27 28 ThreadLocalImpl::ThreadLocalImpl() : data() { 29 static_assert(sizeof(pthread_key_t) <= sizeof(data), "size too big"); 30 pthread_key_t* key = reinterpret_cast<pthread_key_t*>(&data); 31 int errorcode = pthread_key_create(key, nullptr); 32 assert(errorcode == 0); 33 (void) errorcode; 34 } 35 36 ThreadLocalImpl::~ThreadLocalImpl() { 37 pthread_key_t* key = reinterpret_cast<pthread_key_t*>(&data); 38 int errorcode = pthread_key_delete(*key); 39 assert(errorcode == 0); 40 (void) errorcode; 41 } 42 43 void ThreadLocalImpl::setInstance(const void* d) { 44 pthread_key_t* key = reinterpret_cast<pthread_key_t*>(&data); 45 int errorcode = pthread_setspecific(*key, d); 46 assert(errorcode == 0); 47 (void) errorcode; 48 } 49 50 void *ThreadLocalImpl::getInstance() { 51 pthread_key_t* key = reinterpret_cast<pthread_key_t*>(&data); 52 return pthread_getspecific(*key); 53 } 54 55 void ThreadLocalImpl::removeInstance() { 56 setInstance(nullptr); 57 } 58 59 } 60 #else 61 namespace llvm { 62 using namespace sys; 63 ThreadLocalImpl::ThreadLocalImpl() : data() { } 64 ThreadLocalImpl::~ThreadLocalImpl() { } 65 void ThreadLocalImpl::setInstance(const void* d) { data = const_cast<void*>(d);} 66 void *ThreadLocalImpl::getInstance() { return data; } 67 void ThreadLocalImpl::removeInstance() { setInstance(0); } 68 } 69 #endif 70