MacOS 下居然没有类似 win32/*nix 的 __declspec(thread)/__thread TLS
// there's no tls support in macos, modified from
// http://alex.tapmania.org/2011/03/simple-thread-local-storage-with-pthreads.html
//
// usage:
// THREADLOCAL(int) val;
// val = 10;
//
// class MyFoo;
// THREADLOCAL(MyFoo*) ptr;
// if (!ptr) ptr = new MyFoo();
// ptr->someFunc();
// (*ptr).someFunc();
#include <assert.h>
#include <pthread.h>
class ThreadLocalStorageMacOSBase
{
private:
pthread_key_t key_;
public:
ThreadLocalStorageMacOSBase()
{
pthread_key_create(&key_, NULL);
}
~ThreadLocalStorageMacOSBase()
{
pthread_key_delete(key_);
}
bool operator!()
{
return pthread_getspecific(key_) == NULL;
}
protected:
void* internalGet()
{
return pthread_getspecific(key_);
}
void internalSet(void *v)
{
pthread_setspecific(key_, v);
}
};
// for int, object
class ThreadLocalStorageMacOS : public ThreadLocalStorageMacOSBase
{
public:
ThreadLocalStorageMacOS& operator =(const T& val)
{
T *ptr = static_cast<T*>(internalGet());
if (ptr == NULL)
{
ptr = new T; // TODO: memory leak
internalSet(ptr);
}
*ptr = val;
return *this;
}
const T& get()
{
T *ptr = static_cast<T*>(internalGet());
assert(ptr != NULL);
return *ptr;
}
};
// for pointer
template <typename T>
class ThreadLocalStorageMacOS<T*> : public ThreadLocalStorageMacOSBase
{
public:
ThreadLocalStorageMacOS& operator =(T* val)
{
internalSet(val);
return *this;
}
T& operator*()
{
return *(static_cast<T*>(internalGet()));
}
T* operator->()
{
return static_cast<T*>(internalGet());
}
};
#define THREADLOCAL(type) ThreadLocalStorageMacOS<type>
介绍 D language 如何实现 MacOS 下的 TLS
C++ 封装下 pthread_getspecific 来实现
讨论为啥 MacOS 下没有 TLS