2016-04-11 62 views
-1

Ben UNIX boruları ve sinyalleri hayranlarıyla sorun kullanılarak şu soru çözmek için nasıl karıştı aşağıdaki- olarakUNIX boruları ve sinyalleri kullanarak aşağıdaki Uygulamak

There are N players (numbered 0 to N-1) that sit in a circle and play the following game. The first person 
(player 0) starts with a token of initial value Tok_value. If the value of the token is not 0 it decrements the 
value of token by one and passes it to the next person (player 1). The receiver (player 1) checks if the 
token is 0 or not, if not the receiver just decrements the value of the token by one and passes it to the next 
person (player 2) and so-on. Otherwise, if the value of token was zero the receiver collects a point and 
passes a new token with initial value of Tok_value to the next player. The first player to collect Pt points 
wins and then kills all the others. 
For example: If N = 9, Tok_value = 4 and Pt = 2, the players are numbered 0 to 8. Player 4 gets the first 
point then player 0 gains a point and so on. In this example players gain points in the following order 4, 0, 
5, 1, 6, 2, 7, 3, 8, 4 and 4 wins because it is the first one to get Pt=2 points. 
Write a program to simulate the above game. You program should get the inputs N, Tok_value and Pt from 
the user. It then spawns N processes and then links the last process to the first. The linking is being done 
through unnamed pipes (i.e. there should be a pipe between two consecutive persons). The i th process 
represents the i th person in the circle. Note that the first process has to generate two pipes, one to 
communicate with the second process and one with the last process. The token is passed using UNIX 
unnamed pipes. The winner kills the losers by sending the signal SIGTERM along the circle. (Refer to 
kill() system call for this). Before each loser is killed, he has to close the pipes which he uses (i.e., you 
have to write a signal handler for SIGTERM). 
You must output the progress of the game. E.g. when a receiver gets a token it prints something like the 
following: - 
I am player number <X>. I have received a token with value <Y> and I am now sending token to player 
<Z>. My current points are <W>. 
If a player wins it prints: 
I am player number <X>. I have <Y> points. I have won!!! 
Each player that is killed prints before exiting: 
I am player number <X>. I have been killed. 

herkes bu ilgili çözümleri veya ipuçları paylaşabilir misiniz . Kod çözümü takdir edilecektir.

cevap

0

İyi bir başlangıç, ancak kurallar beri düzeltmek gerekir oyun kim vb

#include <signal.h> 
#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <sys/types.h> 
#include <unistd.h> 
#include <wait.h> 

struct player 
{ 
     int stdin_fd; 
     int stdout_fd; 
     pid_t pid; 
}; 

static int game_finished = 0; 

static void parent_SIGUSR1(int sig) 
{ 
     game_finished = 1; 
} 

static void game(int whoami, int Tok_value, int Pt) 
{ 
     char buffer[20]; 
     int value; 
     int score = 0; 

     while (1) 
     { 
       fgets (buffer, 20, stdin); 
       value = atoi(buffer); 

       fprintf (stderr, "Player %d received token %d\n", whoami, value); 

       value--; 


       if (value == 0) 
       { 
         score++; 
         if (score == Pt) 
         { 
           fprintf (stderr, "Player %d won\n", whoami); 
           kill (getppid(), SIGUSR1); 
           return; 
         } 
         value = Tok_value; 
       } 
       printf ("%d\n", value); 
       fflush (stdout); 
     } 
} 

static void usage() 
{ 
     fprintf (stderr, "Please provide 3 numeric positive arguments, N Tok_value and Pt\n"); 
} 

int main(int argc, char *argv[]) 
{ 
     int N; 
     int Tok_value; 
     int Pt; 

     struct player *players; 

     int i; 

     int fd[2]; 

     if (argc != 4) 
     { 
       usage(); 
       return 1; 
     } 
     N = atoi(argv[1]); 
     Tok_value = atoi (argv[2]); 
     Pt = atoi (argv[3]); 

     if ((N < 1) || (Tok_value < 1) || (Pt < 1)) 
     { 
       usage(); 
       return 1; 
     } 

     signal (SIGUSR1, parent_SIGUSR1); 

     players = malloc (sizeof (struct player) * N); 

     for (i = 0; i < N; i++) 
     { 
       pipe (fd); 
       players[ i  ].stdout_fd = fd[1]; 
       players[(i+1)%N].stdin_fd = fd[0]; 
     } 

     for (i = 0; i < N; i++) 
     { 
       players[i].pid = fork(); 
       if (players[i].pid == 0) 
       { 
         close (0); 
         close (1); 
         dup (players[i].stdin_fd); 
         dup (players[i].stdout_fd); 
         game(i, Tok_value, Pt); 
         exit(0); 
       } 
     } 

     { /* start the game by simulating that the last player writes to the first */ 
       char buffer[20]; 
       snprintf (buffer, sizeof (buffer), "%d\n", Tok_value); 
       write (players[N-1].stdout_fd, buffer, strlen (buffer)); 
     } 

     while (!game_finished) 
     { 
       pause(); 
     } 

     for (i = 0; i < N; i++) 
     { 
       int status; 
       kill (players[i].pid, SIGTERM); 
       wait(&status); 
     } 

     return 0; 
} 
öldürür ilgili bitmeli nasıl başka Kur vardır