In the following program, we will try to test a deadlock scenario.
In this scenario, we are creating two threads, MY_THREAD_1 and MY_THREAD_2 . Moreover, we have two resources, resourceA and resourceB .
Source code of deadlock.c
#include <pthread.h>
#include <stdio.h>
#include <sched.h>
#include <time.h>
#define NUM_OF_THREADS 2
#define MY_THREAD_1 1
#define MY_THREAD_2 2
pthread_t threads[NUM_OF_THREADS];
struct sched_param nrt_param;
pthread_mutex_t resourceA, resourceB;
volatile int resourceACount=0, resourceBCount=0, noWait=0;
void *grabresources(void *threadid)
{
if((int)threadid == MY_THREAD_1)
{
printf("Thread-1 is grabbing resources...\n");
pthread_mutex_lock(&resourceA);
resourceACount++;
if(!noWait)
sleep(1000000);
printf("Thread-1 has received resource-A, trying for resource-B...\n");
pthread_mutex_lock(&resourceB);
resourceBCount++;
printf("Thread-1 has received resource-A and resource-B...\n");
pthread_mutex_unlock(&resourceB);
pthread_mutex_unlock(&resourceA);
printf("Thread-1 is complete...\n");
}
else
{
printf("Thread-2 is grabbing resources...\n");
pthread_mutex_lock(&resourceB);
resourceBCount++;
if(!noWait)
usleep(1000000);
printf("Thread-2 has received resource-B, trying for resource-A...\n");
pthread_mutex_lock(&resourceA);
resourceACount++;
printf("Thread-2 has received resource-B and resource-A...\n");
pthread_mutex_unlock(&resourceA);
pthread_mutex_unlock(&resourceB);
printf("Thread-2 is complete...\n");
}
pthread_exit(NULL);
}
int main (int argc, char *argv[])
{
int status, safe=0;
resourceACount=0, resourceBCount=0, noWait=0;
if(argc < 2)
{
printf("Will set up unsafe deadlock scenario...\n");
}
else if(argc == 2)
{
if(strncmp("safe", argv[1], 4) == 0)
safe=1;
else if(strncmp("race", argv[1], 4) == 0)
noWait=1;
else
printf("Will set up unsafe deadlock scenario...\n");
}
else
{
printf("Usage: deadlock [safe|race|unsafe]\n");
}
pthread_mutex_init(&resourceA, NULL);
pthread_mutex_init(&resourceB, NULL);
printf("Creating thread %d\n", MY_THREAD_1);
status = pthread_create(&threads[0], NULL, grabresources, (void *)MY_THREAD_1);
if (rc)
{
printf("ERROR: pthread_create() status is %d\n", status);
perror(NULL);
exit(-1);
}
printf("Thread-1 spawned\n");
if(safe)
{
if(pthread_join(threads[0], NULL) == 0)
printf("Thread-1: %d done\n", threads[0]);
else
perror("Thread-1");
}
printf("Creating thread %d\n", MY_THREAD_2);
status = pthread_create(&threads[1], NULL, grabresources, (void *)MY_THREAD_2);
if (rc)
{
printf("ERROR: pthread_create() status is %d\n", status);
perror(NULL);
exit(-1);
}
printf("Thread-2 spawned\n");
printf("resourceACount=%d, resourceBCount=%d\n", resourceACount, resourceBCount);
printf("will try to join CS threads unless they deadlock\n");
if(!safe)
{
if(pthread_join(threads[0], NULL) == 0)
printf("Thread-1: %d done\n", threads[0]);
else
perror("Thread-1");
}
if(pthread_join(threads[1], NULL) == 0)
printf("Thread-2: %d done\n", threads[1]);
else
perror("Thread-2");
if(pthread_mutex_destroy(&resourceA) != 0)
perror("mutex A destroy");
if(pthread_mutex_destroy(&resourceB) != 0)
perror("mutex B destroy");
printf("Everyting is complete...\n");
exit(0);
}
To compile the Program use
$gcc deadlock.c -o deadlock -lpthread
To run
$./deadlock
No comments:
Post a Comment
Note: Only a member of this blog may post a comment.