1*447762daSMichael J. Spencer //===- ThreadLocal.cpp - Thread Local Data ----------------------*- C++ -*-===// 2*447762daSMichael J. Spencer // 3*447762daSMichael J. Spencer // The LLVM Compiler Infrastructure 4*447762daSMichael J. Spencer // 5*447762daSMichael J. Spencer // This file is distributed under the University of Illinois Open Source 6*447762daSMichael J. Spencer // License. See LICENSE.TXT for details. 7*447762daSMichael J. Spencer // 8*447762daSMichael J. Spencer //===----------------------------------------------------------------------===// 9*447762daSMichael J. Spencer // 10*447762daSMichael J. Spencer // This file implements the llvm::sys::ThreadLocal class. 11*447762daSMichael J. Spencer // 12*447762daSMichael J. Spencer //===----------------------------------------------------------------------===// 13*447762daSMichael J. Spencer 14*447762daSMichael J. Spencer #include "llvm/Config/config.h" 15*447762daSMichael J. Spencer #include "llvm/Support/ThreadLocal.h" 16*447762daSMichael J. Spencer 17*447762daSMichael J. Spencer //===----------------------------------------------------------------------===// 18*447762daSMichael J. Spencer //=== WARNING: Implementation here must contain only TRULY operating system 19*447762daSMichael J. Spencer //=== independent code. 20*447762daSMichael J. Spencer //===----------------------------------------------------------------------===// 21*447762daSMichael J. Spencer 22*447762daSMichael J. Spencer #if !defined(ENABLE_THREADS) || ENABLE_THREADS == 0 23*447762daSMichael J. Spencer // Define all methods as no-ops if threading is explicitly disabled 24*447762daSMichael J. Spencer namespace llvm { 25*447762daSMichael J. Spencer using namespace sys; 26*447762daSMichael J. Spencer ThreadLocalImpl::ThreadLocalImpl() { } 27*447762daSMichael J. Spencer ThreadLocalImpl::~ThreadLocalImpl() { } 28*447762daSMichael J. Spencer void ThreadLocalImpl::setInstance(const void* d) { data = const_cast<void*>(d);} 29*447762daSMichael J. Spencer const void* ThreadLocalImpl::getInstance() { return data; } 30*447762daSMichael J. Spencer void ThreadLocalImpl::removeInstance() { data = 0; } 31*447762daSMichael J. Spencer } 32*447762daSMichael J. Spencer #else 33*447762daSMichael J. Spencer 34*447762daSMichael J. Spencer #if defined(HAVE_PTHREAD_H) && defined(HAVE_PTHREAD_GETSPECIFIC) 35*447762daSMichael J. Spencer 36*447762daSMichael J. Spencer #include <cassert> 37*447762daSMichael J. Spencer #include <pthread.h> 38*447762daSMichael J. Spencer #include <stdlib.h> 39*447762daSMichael J. Spencer 40*447762daSMichael J. Spencer namespace llvm { 41*447762daSMichael J. Spencer using namespace sys; 42*447762daSMichael J. Spencer 43*447762daSMichael J. Spencer ThreadLocalImpl::ThreadLocalImpl() : data(0) { 44*447762daSMichael J. Spencer pthread_key_t* key = new pthread_key_t; 45*447762daSMichael J. Spencer int errorcode = pthread_key_create(key, NULL); 46*447762daSMichael J. Spencer assert(errorcode == 0); 47*447762daSMichael J. Spencer (void) errorcode; 48*447762daSMichael J. Spencer data = (void*)key; 49*447762daSMichael J. Spencer } 50*447762daSMichael J. Spencer 51*447762daSMichael J. Spencer ThreadLocalImpl::~ThreadLocalImpl() { 52*447762daSMichael J. Spencer pthread_key_t* key = static_cast<pthread_key_t*>(data); 53*447762daSMichael J. Spencer int errorcode = pthread_key_delete(*key); 54*447762daSMichael J. Spencer assert(errorcode == 0); 55*447762daSMichael J. Spencer (void) errorcode; 56*447762daSMichael J. Spencer delete key; 57*447762daSMichael J. Spencer } 58*447762daSMichael J. Spencer 59*447762daSMichael J. Spencer void ThreadLocalImpl::setInstance(const void* d) { 60*447762daSMichael J. Spencer pthread_key_t* key = static_cast<pthread_key_t*>(data); 61*447762daSMichael J. Spencer int errorcode = pthread_setspecific(*key, d); 62*447762daSMichael J. Spencer assert(errorcode == 0); 63*447762daSMichael J. Spencer (void) errorcode; 64*447762daSMichael J. Spencer } 65*447762daSMichael J. Spencer 66*447762daSMichael J. Spencer const void* ThreadLocalImpl::getInstance() { 67*447762daSMichael J. Spencer pthread_key_t* key = static_cast<pthread_key_t*>(data); 68*447762daSMichael J. Spencer return pthread_getspecific(*key); 69*447762daSMichael J. Spencer } 70*447762daSMichael J. Spencer 71*447762daSMichael J. Spencer void ThreadLocalImpl::removeInstance() { 72*447762daSMichael J. Spencer setInstance(0); 73*447762daSMichael J. Spencer } 74*447762daSMichael J. Spencer 75*447762daSMichael J. Spencer } 76*447762daSMichael J. Spencer 77*447762daSMichael J. Spencer #elif defined(LLVM_ON_UNIX) 78*447762daSMichael J. Spencer #include "Unix/ThreadLocal.inc" 79*447762daSMichael J. Spencer #elif defined( LLVM_ON_WIN32) 80*447762daSMichael J. Spencer #include "Windows/ThreadLocal.inc" 81*447762daSMichael J. Spencer #else 82*447762daSMichael J. Spencer #warning Neither LLVM_ON_UNIX nor LLVM_ON_WIN32 was set in System/ThreadLocal.cpp 83*447762daSMichael J. Spencer #endif 84*447762daSMichael J. Spencer #endif 85