線程私有數據可以用來存儲線程本地的信息,tcmalloc就是用了該機制來減少鎖的開銷,加快內存分配。
下面給出了一個測試用例
通過pthread_key_create創建一個線程私有數據的key,並設置這個key對應私有數據的釋放函數;調用pthread_setspecific將key和私有數據進行關聯;可以調用pthread_getspecific進行獲取私有數據。
#include <stdio.h>
#include <string.h>
#include <pthread.h>
#include <stdlib.h>
static pthread_once_t once = PTHREAD_ONCE_INIT;
static pthread_key_t str_test_key;
#define MAX_STR_TEST_LEN 256
static void destructor(void * buf) {
free(buf);
}
static void create_key(void) {
int s;
s = pthread_key_create(&str_test_key, destructor);
if (s != 0) {
printf("pthread_key_create failed");
exit(-1);
}
}
char * str_test(char * arg) {
int s;
char *buf;
s = pthread_once(&once, create_key);
if (s != 0) {
printf("pthread_once failed");
exit(-1);
}
buf = pthread_getspecific(str_test_key);
if (buf == NULL) {
buf = malloc(MAX_STR_TEST_LEN);
if (buf == NULL) {
printf("pthread_once failed");
exit(-1);
}
s = pthread_setspecific(str_test_key, buf);
if (s != 0) {
printf("pthread_setspecific failed");
exit(-1);
}
}
strncpy(buf, arg, MAX_STR_TEST_LEN - 1);
}
static void * thread_func(void * arg) {
char *str;
printf("Other thread about to call str_test()\n");
str = str_test((char *) arg);
printf("Other thread: str (%p) = %s\n", str, str);
str = pthread_getspecific(str_test_key);
printf("Other thread: tsd (%p) = %s\n", str, str);
return NULL;
}
int main(int argc, char *argv[])
{
pthread_t t;
int s;
char *str;
str = str_test("hello world");
printf("Main thread has called str_test()\n");
s = pthread_create(&t, NULL, thread_func, "this is a test");
if (s != 0) {
printf("pthread_create failed");
return -1;
}
s = pthread_join(t, NULL);
if (s != 0) {
printf("pthread_join failed");
return -1;
}
printf("Main thread: str (%p) = %s\n", str, str);
return 0;
}
結果: