Tuesday, August 13, 2013

Thread Specific Data

Thread Specific Data
Thread Specific Data means data related to a particular thread,Think of a pool of different data for different threads that each thread can access with a public key...
All things revolves around a key to get the particular data..
what to do--
1.)Create a key
2.)set the specific data for the thread using the key
3.)get the specific data using the key only for a specific thread
Example:suppose there are 4 Threads running and every threads has to create a log file of the task that is performing,so each thread wants a file pointer specific to that thread so we can keep those file pointers as the TSD and can use a key to access the TSD for each thread..
For creating a key use the following function:
int pthread_key_create(pthread_key_t *key, void (*destructor) (void *));
first argument-The key which you have defined...
second argument-The function which you want to run after the completion of the thread,generally for cleanup,descrutor kind of thing.
Note-If you pass a function pointer here, GNU/Linux automatically calls that function when each thread exits, passing the thread-specific value corresponding to that key. This is particularly handy because the cleanup function is called even if the thread is canceled at some arbitrary point in its execution. If the thread-specific value is null, the thread cleanup function is not called. If you don't need a cleanup function, you may pass NULL instead of a function pointer.
For setting the value use the following function:
pthread_setspecific(key, value);
For getting the value use the following function:
pthread_getspecific(key);

Return Value From Thread

As we have seen in the examples the return type of the functions that runs as the threads is the void*,it means we can return a value from the thread,but the point is how to capture that returned value in the main function...
The answer is the join again,as we have seen in the join the function prototype is
int pthread_join(pthread_t,void **)
Here the 2nd argument is the pointer to the value returned by the thread...
In the main funtion we can capture and use the value returned by the thread using the pthread_join.

Let us capture the return value...
#include<stdio.h>
#include<stdlib.h>
#include<pthread.h>
void* myfunc1(void *ptr)
{
    char *msg;
    int i=0;
    msg=(char*)ptr;
    while(1)
    {
        sleep(1);
        if(i>5)
            break;
        else
        {
            printf("i in thread1=%d\n",i);i++;
        }
    }
    printf("Thread1 completed\n");
    return "hello";
}
void *myfunc2(void *ptr)
{
    char *msg;
    int i=0;
    msg=(char*)ptr;
    while(1)
    {
        sleep(1);
        if(i>10)
            break;
        else
        {
            printf("i in thread2=%d\n",i);i++;
        }
    }
    printf("Thread2 completed\n");
    return "Hi";
}
int main()
{
    pthread_t thread1,thread2;
    int val1,val2;
    int status;
    char *msg1="Thread1";
    char *msg2="Thread2";
    void **ret_val1=malloc(sizeof(void*));
    void **ret_val2=malloc(sizeof(void*));
    printf("In the main funciton\n");
    pthread_create(&thread1,NULL,myfunc1,(void*)msg1);
    pthread_create(&thread2,NULL,myfunc2,(void*)msg2);
    pthread_join(thread1,ret_val1);
    pthread_join(thread2,ret_val2);
    printf("return value from thread1  is:%s\n",*ret_val1);
    printf("return value from thread2 is:%s\n",*ret_val2);
    printf("Now main ends");
    return 0;
}