49 #ifndef ASTERISK_THREADSTORAGE_H
50 #define ASTERISK_THREADSTORAGE_H
65 #if defined(DEBUG_THREADLOCALS)
66 void __ast_threadstorage_object_add(
void *key,
size_t len,
const char *
file,
const char *
function,
unsigned int line);
67 void __ast_threadstorage_object_remove(
void *key);
68 void __ast_threadstorage_object_replace(
void *key_old,
void *key_new,
size_t len);
69 #define THREADSTORAGE_RAW_CLEANUP(v) {}
71 #define THREADSTORAGE_RAW_CLEANUP NULL
86 #define AST_THREADSTORAGE(name) \
87 AST_THREADSTORAGE_CUSTOM_SCOPE(name, NULL, ast_free_ptr, static)
88 #define AST_THREADSTORAGE_PUBLIC(name) \
89 AST_THREADSTORAGE_CUSTOM_SCOPE(name, NULL, ast_free_ptr,)
90 #define AST_THREADSTORAGE_EXTERNAL(name) \
91 extern struct ast_threadstorage name
92 #define AST_THREADSTORAGE_RAW(name) \
93 AST_THREADSTORAGE_CUSTOM_SCOPE(name, NULL, THREADSTORAGE_RAW_CLEANUP,)
111 #define AST_THREADSTORAGE_CUSTOM(a,b,c) AST_THREADSTORAGE_CUSTOM_SCOPE(a,b,c,static)
113 #if defined(PTHREAD_ONCE_INIT_NEEDS_BRACES)
114 # define AST_PTHREAD_ONCE_INIT { PTHREAD_ONCE_INIT }
116 # define AST_PTHREAD_ONCE_INIT PTHREAD_ONCE_INIT
119 #if !defined(DEBUG_THREADLOCALS)
120 #define AST_THREADSTORAGE_CUSTOM_SCOPE(name, c_init, c_cleanup, scope) \
121 static void __init_##name(void); \
122 scope struct ast_threadstorage name = { \
123 .once = AST_PTHREAD_ONCE_INIT, \
124 .key_init = __init_##name, \
125 .custom_init = c_init, \
127 static void __init_##name(void) \
129 pthread_key_create(&(name).key, c_cleanup); \
132 #define AST_THREADSTORAGE_CUSTOM_SCOPE(name, c_init, c_cleanup, scope) \
133 static void __init_##name(void); \
134 scope struct ast_threadstorage name = { \
135 .once = AST_PTHREAD_ONCE_INIT, \
136 .key_init = __init_##name, \
137 .custom_init = c_init, \
139 static void __cleanup_##name(void *data) \
141 __ast_threadstorage_object_remove(data); \
144 static void __init_##name(void) \
146 pthread_key_create(&(name).key, __cleanup_##name); \
179 #if !defined(DEBUG_THREADLOCALS)
186 if (!(
buf = pthread_getspecific(ts->
key))) {
194 pthread_setspecific(ts->
key,
buf);
202 void *__ast_threadstorage_get(
struct ast_threadstorage *ts,
size_t init_size,
const char *
file,
const char *
function,
unsigned int line),
207 if (!(
buf = pthread_getspecific(ts->
key))) {
215 pthread_setspecific(ts->
key,
buf);
216 __ast_threadstorage_object_add(
buf, init_size,
file,
function, line);
223 #define
ast_threadstorage_get(ts, init_size) __ast_threadstorage_get(ts, init_size, __FILE__, __PRETTY_FUNCTION__, __LINE__)
241 return pthread_getspecific(ts->
key);
261 return pthread_setspecific(ts->
key, ptr);
#define ast_calloc(num, len)
A wrapper for calloc()
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
Inlinable API function macro.
#define AST_INLINE_API(hdr, body)
data for a thread locally stored variable
int(* custom_init)(void *)
int ast_threadstorage_set_ptr(struct ast_threadstorage *ts, void *ptr)
Set a raw pointer from threadstorage.
void * ast_threadstorage_get_ptr(struct ast_threadstorage *ts)
Retrieve a raw pointer from threadstorage.
void * ast_threadstorage_get(struct ast_threadstorage *ts, size_t init_size)
Retrieve thread storage.