In: Computer Science
refund quesetion
/**************************************************************** * FILE: dotprod_mutex.c * DESCRIPTION: * This example program illustrates the use of mutex variables * in a threads program. This version was obtained by modifying the * serial version of the program (dotprod_serial.c) which performs a * dot product. The main data is made available to all threads through * a globally accessible structure. Each thread works on a different * part of the data. The main thread waits for all the threads to complete * their computations, and then it prints the resulting sum. * SOURCE: Vijay Sonnad, IBM * LAST REVISED: 01/29/09 Blaise Barney ******************************************************************************/ #include #include #include /* The following structure contains the necessary information to allow the function "dotprod" to access its input data and place its output into the structure. This structure is unchanged from the sequential version. */ typedef struct { double *a; double *b; double sum; int veclen; } DOTDATA; /* Define globally accessible variables and a mutex */ /* now moved to main */ // #define NUMTHRDS 10 // #define VECLEN 100000 // pthread_t callThd[NUMTHRDS]; pthread_mutex_t mutexsum; DOTDATA dotstr; /* The function dotprod is activated when the thread is created. As before, all input to this routine is obtained from a structure of type DOTDATA and all output from this function is written into this structure. The benefit of this approach is apparent for the multi-threaded program: when a thread is created we pass a single argument to the activated function - typically this argument is a thread number. All the other information required by the function is accessed from the globally accessible structure. */ void *dotprod(void *arg) { /* Define and use local variables for convenience */ int i, start, end, len ; long offset; double mysum, *x, *y; offset = (long)arg; len = dotstr.veclen; start = offset*len; end = start + len; x = dotstr.a; y = dotstr.b; /* Perform the dot product and assign result to the appropriate variable in the structure. */ mysum = 0; for (i=start; i
dotprod_mutex.c
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
typedef struct
{
double *a;
double *b;
double sum;
int veclen;
}DOTDATA;
//Define globally accessible variables and a mutex
#define NUMTHRDS 4
#define VECLEN 100000
DOTDATA dotstr;
pthread_t callThd[NUMTHRDS];
pthread_mutex_t mutexsum;
void *dotprod(void *arg)
{
//Define and use local variables for convenience
int i, start, end, len ;
long offset;
double mysum, *x, *y;
offset = (long)arg;
len = dotstr.veclen;
start = offset*len;
end = start + len;
x = dotstr.a;
y = dotstr.b;
//Perform the dot product and assign the result to the appropriate variable in the structure.
mysum = 0;
for (i=start; i<end ; i++)
{
mysum += (x[i] * y[i]);
}
//Lock a mutex prior to updating the value in the shared structure, and unlock it upon updating.
pthread_mutex_lock (&mutexsum);
dotstr.sum += mysum;
printf("Thread %ld did %d to %d: mysum=%f global sum=%f\n",offset,start,end,mysum,dotstr.sum);
pthread_mutex_unlock (&mutexsum);
pthread_exit((void*) 0);
}
int main (int argc, char *argv[])
{
long i;
double *a, *b;
void *status;
pthread_attr_t attr;
//Assign storage and initialize values
a = (double*) malloc (NUMTHRDS*VECLEN*sizeof(double));
b = (double*) malloc (NUMTHRDS*VECLEN*sizeof(double));
for (i=0; i<VECLEN*NUMTHRDS; i++)
{
a[i]=1;
b[i]=a[i];
}
dotstr.veclen = VECLEN;
dotstr.a = a;
dotstr.b = b;
dotstr.sum=0;
pthread_mutex_init(&mutexsum, NULL);
//Create threads to perform the dotproduct
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
for(i=0;i<NUMTHRDS;i++)
{
/* Each thread works on a different set of data.
* The offset is specified by 'i'. The size of
* the data for each thread is indicated by VECLEN.
*/
pthread_create(&callThd[i], &attr, dotprod, (void *)i);
}
pthread_attr_destroy(&attr);
//Wait on the other threads
for(i=0;i<NUMTHRDS;i++)
{
pthread_join(callThd[i], &status);
}
//After joining, print out the results and cleanup
printf ("Sum = %f \n", dotstr.sum);
free (a);
free (b);
pthread_mutex_destroy(&mutexsum);
pthread_exit(NULL);
}
dotprod_serial.c
#include <stdio.h>
#include <stdlib.h>
typedef struct
{
double *a;
double *b;
double sum;
int veclen;
}DOTDATA;
#define VECLEN 100000
DOTDATA dotstr;
void dotprod()
{
// Define and use local variables for convenience
int start, end, i;
double mysum, *x, *y;
start=0;
end = dotstr.veclen;
x = dotstr.a;
y = dotstr.b;
//Perform the dot product and assign result to the appropriate variable in the structure.
mysum = 0;
for (i=start; i<end ; i++)
{
mysum += (x[i] * y[i]);
}
dotstr.sum = mysum;
}
//The main program initializes data and calls the dotprd() function. Finally, it prints the result.
int main (int argc, char *argv[])
{
int i,len;
double *a, *b;
// Assign storage and initialize values
len = VECLEN;
a = (double*) malloc (len*sizeof(double));
b = (double*) malloc (len*sizeof(double));
for (i=0; i<len; i++)
{
a[i]=1;
b[i]=a[i];
}
dotstr.veclen = len;
dotstr.a = a;
dotstr.b = b;
dotstr.sum=0;
//Perform the dotproduct
dotprod ();
//Print result and release storage
printf ("Sum = %f \n", dotstr.sum);
free (a);
free (b);
}
NOTE: The above-provided source code will help you with your question. If in case you face any error then please do let me know through comments.
UPVOTE!!!Please... Thank You!!!!