標準/拡張機能 | C/C++ | 依存項目 |
---|---|---|
POSIX.4a |
両方 | POSIX(ON) |
#define _OPEN_THREADS
#include <pthread.h>
int pthread_getspecific(pthread_key_t key, void **value);
#define _UNIX03_THREADS
#include <pthread.h>
void *pthread_getspecific(pthread_key_t key);
現行スレッドで指定された key と関連したスレッド固有のデータを 戻します。スレッド固有のデータが key に設定されていない場合には、NULL 値が value に戻されます。
多くのマルチスレッド・アプリケーションでは、各スレッドが固有の値をとるストレージをスレッド間で共用することが必要です。スレッド固有のデータ・キーはスレッドによって作成された ID で、それに対してプロセス内の各スレッドは固有のキー value を 設定できます。
pthread_key_t は、システムがキー ID を入れるストレージです。キーを作成する場合、スレッドは pthread_key_create() を使用します。 この関数は、キー ID を pthread_key_t 型のストレージ域に戻します。 この時点で、アプリケーションの各スレッドは、そのキーを使用でき、 pthread_setspecific() を使用してその固有値を設定できます。 スレッドは、pthread_getspecific() を使用して固有の値を取得します。
⁄* CELEBP31 *⁄
#ifndef _OPEN_THREADS
#define _OPEN_THREADS
#endif
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <pthread.h>
#define threads 3
#define BUFFSZ 48
pthread_key_t key;
void *threadfunc(void *parm)
{
int status;
void *value;
int threadnum;
int *tnum;
void *getvalue;
char Buffer[BUFFSZ];
tnum = parm;
threadnum = *tnum;
printf("Thread %d executing¥n", threadnum);
if (!(value = malloc(sizeof(Buffer))))
printf("Thread %d could not allocate storage, errno = %d¥n",
threadnum, errno);
status = pthread_setspecific(key, (void *) value);
if ( status < 0) {
printf("pthread_setspecific failed, thread %d, errno %d",
threadnum, errno);
pthread_exit((void *)12);
}
printf("Thread %d setspecific value: %d¥n", threadnum, value);
getvalue = 0;
status = pthread_getspecific(key, &getvalue);
if ( status < 0) {
printf("pthread_getspecific failed, thread %d, errno %d",
threadnum, errno);
pthread_exit((void *)13);
}
if (getvalue != value)
{
printf("getvalue not valid, getvalue=%d", (int)getvalue);
pthread_exit((void *)68);
}
pthread_exit((void *)0);
}
void destr_fn(void *parm)
{
printf("Destructor function invoked¥n");
free(parm);
}
main() {
int getvalue;
int status;
int i;
int threadparm[threads];
pthread_t threadid[threads];
int thread_stat[threads];
if ((status = pthread_key_create(&key, destr_fn )) < 0) {
printf("pthread_key_create failed, errno=%d", errno);
exit(1);
}
⁄* create 3 threads, pass each its number *⁄
for (i=0; i<threads; i++) {
threadparm[i] = i+1;
status = pthread_create( &threadid[i],
NULL,
threadfunc,
(void *)&threadparm[i]);
if ( status < 0) {
printf("pthread_create failed, errno=%d", errno);
exit(2);
}
}
for ( i=0; i<threads; i++) {
status = pthread_join( threadid[i], (void *)&thread_stat[i]);
if ( status < 0) {
printf("pthread_join failed, thread %d, errno=%d¥n", i+1, errno);
}
if (thread_stat[i] != 0) {
printf("bad thread status, thread %d, status=%d¥n", i+1,
thread_stat[i]);
}
}
exit(0);
}
CELEBP70
⁄* CELEBP70 *⁄
⁄* Example using SUSv3 pthread_getspecific() interface *⁄
#define _UNIX03_THREADS 1
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <pthread.h>
#define threads 3
#define BUFFSZ 48
pthread_key_t key;
void *threadfunc(void *parm)
{
int status;
void *value;
int threadnum;
int *tnum;
void *getvalue;
char Buffer[BUFFSZ];
tnum = parm;
threadnum = *tnum;
printf("Thread %d executing¥n", threadnum);
if (!(value = malloc(sizeof(Buffer))))
printf("Thread %d could not allocate storage, errno = %d¥n",
threadnum, errno);
status = pthread_setspecific(key, (void *) value);
if ( status < 0) {
printf("pthread_setspecific failed, thread %d, errno %d",
threadnum, errno);
pthread_exit((void *)12);
}
printf("Thread %d setspecific value: %d¥n", threadnum, value);
getvalue = 0;
getvalue = pthread_getspecific(key);
if ( getvalue == 0) {
printf("pthread_getspecific failed, thread %d", threadnum);
printf(" rc= %d, errno %d, ejr %08x¥n",(int)getvalue, errno, __errno2());
pthread_exit((void *)13);
} else {
printf("Success!¥n");
printf("Returned value: %d matches set value: %d¥n", getvalue, value);
}
if (getvalue != value)
{
printf("getvalue not valid, getvalue=%d", (int)getvalue);
pthread_exit((void *)68);
}
pthread_exit((void *)0);
}
void destr_fn(void *parm)
{
printf("Destructor function invoked¥n");
free(parm);
}
int main(void)
{
int status;
int i;
int threadparm[threads];
pthread_t threadid[threads];
int thread_stat[threads];
if ((status = pthread_key_create(&key, destr_fn )) < 0) {
printf("pthread_key_create failed, errno=%d", errno);
exit(1);
}
⁄* create 3 threads, pass each its number *⁄
for (i=0; i<threads; i++) {
threadparm[i] = i+1;
status = pthread_create( &threadid[i],
NULL,
threadfunc,
(void *)&threadparm[i]);
if ( status < 0) {
printf("pthread_create failed, errno=%d", errno);
exit(2);
}
}
for ( i=0; i<threads; i++) {
status = pthread_join( threadid[i], (void *)&thread_stat[i]);
if ( status < 0) {
printf("pthread_join failed, thread %d, errno=%d¥n", i+1, errno);
}
if (thread_stat[i] != 0) {
printf("bad thread status, thread %d, status=%d¥n", i+1,
thread_stat[i]);
}
}
exit(0);
}