Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <pthread.h>
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <fcntl.h>
- #include <sys/shm.h>
- #include <sys/stat.h>
- #include <sys/mman.h>
- #include <sys/wait.h>
- #include <unistd.h>
- #include <errno.h>
- #include <time.h>
- #include <sys/types.h>
- #include <unistd.h>
- #include <semaphore.h>
- #define THREAD_COUNT 3
- #define SIGINT 2
- #define SIGCONT 18
- #define SIGSTOP 19
- #define MEMBAR __sync_synchronize()
- volatile int tickets[THREAD_COUNT];
- volatile int choosing[THREAD_COUNT];
- int activeConnections = 0;
- int calculationComplete = 0;
- char* threeGrades, *threeWeights, gradeWeightAnswer[1024];
- int currentGrade[20];
- int currentWeight[20];
- typedef struct {
- pthread_mutex_t mutex;
- sem_t fullR;
- sem_t emptyR;
- sem_t fullC;
- sem_t emptyC;
- sem_t fullP;
- sem_t emptyP;
- int threadNum;
- } Context;
- Context* context2[4];
- void* shmemAnswer[2];
- void* shmemConn[2];
- void *shmemGrades;
- void *shmemWeight;
- int shm_fdAnswer[2], shm_fdGrades, shm_fdWeight;
- int shm_fdConn[2];
- char* calcMultiple[8];
- int flag[2];
- int turn, count=0;
- void *retrieveMarksClient(void *param); /* threads call this function */
- void *retrieveMarksServer(void *param); /* threads call this function */
- void *calculateMarks(void *param);
- void *printMarks(void *param);
- void *multiplyMarks(void *param1);
- volatile int resource;
- void lock(int current);
- void unlock(int current);
- void critical_section(int thread);
- int main(int argc, char *argv[])
- {
- pthread_t tidMult[3]; /* the thread identifier */
- pthread_attr_t attr, attr2, attr3; /* set of thread attributes */
- pid_t pid[10];
- resource = 0;
- /* Start of using shared memory */
- shm_fdConn[0] = shm_open("ServerConn1", O_CREAT | O_RDWR, 0666);
- shm_fdConn[1] = shm_open("ServerConn2", O_CREAT | O_RDWR, 0666);
- for (int i = 0; i < 2; i++) {
- ftruncate(shm_fdConn[i], 1024);
- shmemConn[i] = mmap(NULL, 1024, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fdConn[i], 0);
- }
- shm_fdGrades = shm_open("ServerClientGrades", O_CREAT | O_RDWR, 0666);
- ftruncate(shm_fdGrades, 1024);
- shmemGrades = mmap(NULL, 1024, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fdGrades, 0);
- shm_fdWeight = shm_open("ServerClientWeight", O_CREAT | O_RDWR, 0666);
- ftruncate(shm_fdWeight, 1024);
- shmemWeight = mmap(NULL, 1024, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fdWeight, 0);
- shm_fdAnswer[0] = shm_open("ServerAnswer1", O_CREAT | O_RDWR, 0666);
- shm_fdAnswer[1] = shm_open("ServerAnswer2", O_CREAT | O_RDWR, 0666);
- for (int i = 0; i < 2; i++) {
- ftruncate(shm_fdAnswer[i], 1024);
- shmemAnswer[i] = mmap(NULL, 1024, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fdAnswer[i], 0);
- }
- printf("Got here\n");
- int shm_fdMult[6];
- shm_fdMult[0] = shm_open("SharedMemMult1", O_CREAT | O_RDWR, 0666);
- shm_fdMult[1] = shm_open("SharedMemMult2", O_CREAT | O_RDWR, 0666);
- shm_fdMult[2] = shm_open("SharedMemMult3", O_CREAT | O_RDWR, 0666);
- shm_fdMult[3] = shm_open("SharedMemMult4", O_CREAT | O_RDWR, 0666);
- shm_fdMult[4] = shm_open("SharedMemMult5", O_CREAT | O_RDWR, 0666);
- shm_fdMult[5] = shm_open("SharedMemMult6", O_CREAT | O_RDWR, 0666);
- /* End of using shared memory */
- Context context[10];
- int status = 0;
- for (int i = 0; i < 10; i++) {
- status = pthread_mutex_init(&context[i].mutex, NULL);
- status = sem_init(&context[i].fullR, 0, 0);
- status = sem_init(&context[i].emptyR, 0, 1);
- status = sem_init(&context[i].fullC, 0, 0);
- status = sem_init(&context[i].emptyC, 0, 0);
- status = sem_init(&context[i].fullP, 0, 0);
- status = sem_init(&context[i].emptyP, 0, 0);
- context->threadNum = i;
- }
- int child;
- /* get the default attributes */
- int totalConnections = 0;
- while (totalConnections < 10)
- {
- if (activeConnections > 2) {
- printf("Too many active connections, waiting on child\n");
- wait(&child);
- }
- if (activeConnections == 1) {
- sprintf(shmemConn[0], "One");
- while(strstr((char*)shmemConn[0], "One") > 0) {
- sleep(1);
- }
- sprintf(shmemConn[0], "%s", "Two");
- printf("Creating Server Instance\n");
- }
- else {
- printf("Waiting for client 2\n");
- sprintf(shmemConn[0], "Two");
- while(strstr((char*)shmemConn[0], "Two") > 0){
- sleep(1);
- }
- sprintf(shmemConn[0], "%s", "Two");
- printf("Creating Server Instance\n");
- }
- pid[totalConnections] = fork();
- if(pid[totalConnections] == 0) { //Child Process
- printf("Server 1\n");
- pthread_t tid, tid2, tid3;
- activeConnections++;
- printf("Server 1 started\n");
- /* get the default attributes */
- int rc = pthread_create(&tid,NULL, &retrieveMarksServer, &context[totalConnections]);
- if (rc != 0) {
- errno = rc;
- perror("child: pthread create");
- exit(1);
- }
- int rc2 = pthread_create(&tid3,NULL, &calculateMarks, &context[totalConnections]);
- if (rc2 != 0) {
- errno = rc;
- perror("child: pthread create");
- exit(1);
- }
- int rc3 = pthread_create(&tid2,NULL, &printMarks, &context[totalConnections]);
- if (rc3 != 0) {
- errno = rc3;
- perror("child: pthread create");
- exit(1);
- }
- printf("Waiting for threads to join\n");
- //pthread_create(&tid2,&attr2, &printMarks, &context);
- /* create the threads for the server */
- void *status;
- int rc4 = pthread_join(tid, &status);
- if (rc4 != 0) {
- errno = rc4;
- perror("child: pthread_join");
- exit(1);
- }
- int rc5 = pthread_join(tid3, &status);
- if (rc5 != 0) {
- errno = rc4;
- perror("child: pthread_join");
- exit(1);
- }
- int rc6 = pthread_join(tid2, &status);
- if (rc6 != 0) {
- errno = rc6;
- perror("child: pthread_join");
- exit(1);
- }
- printf("Current printed to shmemAnswer0 is end %s\n", shmemAnswer[0]);
- printf("Current printed to shmemAnswer1 is end %s\n", shmemAnswer[1]);
- printf("Cleaned up answer shared memory\n");
- activeConnections--;
- exit(0);
- }
- else if(pid[totalConnections] == -1) {
- printf("Error");
- }
- else { //parent process
- printf("Server waiting for the child\n");
- //pid_t waitForChild = wait(&child);
- //if (waitForChild == -1) {
- // perror("there was an error\n");
- // exit(1);
- // }
- if (WIFEXITED(child)) {
- fprintf(stderr, "parent: child exited: %d\n", WEXITSTATUS(child));
- } else if (WIFSIGNALED(child)) {
- fprintf(stderr, "parent: child exited with signal: %s\n", strsignal(WTERMSIG(child)));
- } else {
- fprintf(stderr, "parent: child exited with status: %d\n", child);
- }
- printf("Done waiting for child\n");
- totalConnections++;
- printf("Exiting Server Thread\n");
- }
- }
- pthread_exit(NULL);
- //kill(pid[0], SIGINT);
- //printf("sum = %d\n",sum);
- exit(0);
- }
- /* The thread will begin control in this function */
- void *retrieveMarksClient(void *param)
- {
- /*pointer used for access to shared memory segment */
- char sum[1024];
- char weights[1024];
- Context* context = (Context*) param;
- sem_wait(&context->emptyR);
- //pthread_mutex_lock(&(context->mutex));
- printf("List your three grades, separated by a comma (eg. 95,85,75)\n");
- fgets(sum, sizeof sum, stdin);
- sprintf(threeGrades, sum);
- printf("List the weighting of each of these grades (eg 30, 30, 40)\n");
- fgets(weights, sizeof weights, stdin);
- sprintf(threeWeights, weights);
- //pthread_mutex_unlock(&(context->mutex));
- sem_post(&context->emptyP);
- return NULL;
- }
- void *retrieveMarksServer(void *param)
- {
- /*pointer used for access to shared memory segment */
- char sum[1024];
- char weights[1024];
- printf("The retrieve numbers started\n");
- Context* context = (Context*) param;
- //wait for the signal from client, the post to server calculate
- //sprintf(shmem3, "Server: start of retrieve");
- while(strlen((char*) shmemWeight) < 2){
- sleep(1);
- printf("Waiting for buffer to fill, shmemWeight %s \n", shmemWeight);
- }
- printf("Received numbers\n");
- sem_post(&context->fullR);
- //sprintf(shmem3, "Server: end of retrieve");
- return NULL;
- }
- /* The thread will begin control in this function */
- void *calculateMarks(void *param)
- {
- pthread_t tidMult[4];
- pthread_attr_t attMult[4];
- float numberGrades, weightGrades;
- float lastGrade;
- int count = 0;
- char* saveptr1 = NULL;
- char* token = NULL;
- char* saveptr2 = NULL;
- char* token2 = NULL;
- Context* context = (Context*) param;
- sem_wait(&context->fullR);
- printf("Threads started calculating\n");
- printf("Shmem grades %s end\n", shmemGrades);
- int calcSpot1 = 0;
- char theGrades[120];
- sprintf(theGrades, "%s", shmemGrades);
- printf(" %s\n", theGrades);
- printf("%d\n", theGrades[0]);
- printf("%d\n", theGrades[1]);
- char* strptr;
- token = strtok_r(theGrades, ",", &strptr);
- currentGrade[0] = atoi(token);
- currentGrade[1] = atoi(strtok_r(NULL, ",", &strptr));
- currentGrade[2] = atoi(strtok_r(NULL, ",", &strptr));
- printf("Midway calculating\n");
- char theWeights[120];
- sprintf(theWeights, "%s", shmemWeight);
- token2 = strtok(theWeights, ",");
- //token2 = strtok_r(NULL, ",", &saveptr2);
- currentWeight[0] = atoi(token2);
- currentWeight[1] = atoi(strtok(NULL, ","));
- currentWeight[2] = atoi(strtok(NULL, ","));
- for (int k = 0; k < THREAD_COUNT; k++) {
- pthread_create(&tidMult[k], NULL, &multiplyMarks, (void*) ((long) k) );
- }
- for (int m = 0; m < THREAD_COUNT; m++) {
- pthread_join(tidMult[m],NULL);
- }
- printf("Threads done calculating\n");
- sem_post(&context->emptyP);
- return NULL;
- }
- void *multiplyMarks(void *param1) {
- long thread = (long) param1;
- lock(thread);
- critical_section(thread);
- unlock(thread);
- return NULL;
- }
- void critical_section(int thread) {
- float totalMark;
- int retrieve;
- retrieve = thread * 2;
- int retrieve2;
- retrieve2 = thread * 2 + 1;
- printf("in the critical section %d thread\n", thread);
- //printf("threadNum %d", context->threadNum);
- printf("shmem %d\n", currentGrade[0]);
- printf("shmem %d\n", currentWeight[0]);
- totalMark = atof(gradeWeightAnswer) + ((float) currentGrade[0]) * ((float) currentWeight[0]) / 100.0f;
- printf("end of calculation in critical section\n");
- sprintf(gradeWeightAnswer, "%f", totalMark);
- printf("end of critical section\n");
- }
- void *printMarks(void *param)
- {
- float currentGrade[20];
- float numberGrades = 0.0;
- float lastGrade;
- int count = 0;
- Context* context = (Context*) param;
- //while (1)
- //{
- sem_wait(&context->emptyP);
- if (activeConnections == 1) {
- sprintf(shmemAnswer[0], gradeWeightAnswer);
- }
- else if(activeConnections == 2)
- {
- sprintf(shmemAnswer[1], gradeWeightAnswer);
- } //sem_post(&context->emptyP);
- //}
- return NULL;
- }
- void lock(int thread)
- {
- // Before getting the ticket number
- //"choosing" variable is set to be true
- choosing[thread] = 1;
- MEMBAR;
- // Memory barrier applied
- int max_ticket = 0;
- // Finding Maximum ticket value among current threads
- for (int i = 0; i < THREAD_COUNT; ++i) {
- int ticket = tickets[i];
- max_ticket = ticket > max_ticket ? ticket : max_ticket;
- }
- // Allotting a new ticket value as MAXIMUM + 1
- tickets[thread] = max_ticket + 1;
- MEMBAR;
- choosing[thread] = 0;
- MEMBAR;
- // The ENTRY Section starts from here
- for (int other = 0; other < THREAD_COUNT; ++other) {
- // Applying the bakery algorithm conditions
- while (choosing[other]) {
- }
- MEMBAR;
- while (tickets[other] != 0 && (tickets[other]
- < tickets[thread]
- || (tickets[other]
- == tickets[thread]
- && other < thread))) {
- }
- }
- }
- // EXIT Section
- void unlock(int thread)
- {
- MEMBAR;
- tickets[thread] = 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement