我一直在尝试使用信号在C中开发3人游戏,但它没有提供所需的输出。
#define _POSIX_SOURCE //to use functionality from the POSIX.1 standard as ANCI C does not support kill()
#include <sys/wait.h>
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <signal.h>
#include <fcntl.h>
#include <time.h>
void action(){}
void child(char *);
int main(){
pid_t pid1, pid2, pid3;
printf("This is a 3-players game with a referee\n\n");
if((pid1=fork()) == 0) child("TOTO");
sleep(1);
if((pid2=fork()) == 0) child("TITI");
sleep(1);
if((pid3=fork()) == 0) child("TUTU");
sleep(1);
while(1){
signal(SIGUSR1, action);
printf("Refree: TOTO plays\n\n");
kill(pid1, SIGUSR1);
pause();
printf("Refree: TITI plays\n\n");
kill(pid2, SIGUSR1);
pause();
printf("Refree: TUTU plays\n\n");
kill(pid3, SIGUSR1);
pause();
}
}
void child(char *s){
int points=0, dice;
srand(time(NULL));
while(1){
signal(SIGUSR1, action); // block myself
pause();
sleep(1);
printf("%s: playing my dice\n", s);
dice = rand() % 10 + 1;
printf("%s: got %d points\n", s, dice);
points+=dice;
printf("%s: Total so far %d\n\n", s, points);
sleep(3);
if(points >= 100){
printf("%s: game over I won\n", s);
kill(0, SIGTERM);
}
kill(getppid(), SIGUSR1);
}
}
我得到的输出是:
This is a 3-players game with a referee
Refree: TOTO plays
TOTO: playing my dice
TOTO: got 8 points
TOTO: Total so far 8
Refree: TITI plays
TITI: playing my dice
TITI: got 2 points
TITI: Total so far 2
User defined signal 1
它永远不会显示&#34; TUTU&#34;玩骰子并使用注册为空白信号的用户定义信号1终止。该程序应在玩家获胜后终止。
有什么建议吗?
答案 0 :(得分:0)
当裁判收到TOTO的信号时,它的处置会重置为SIG_DFL
,因此TITI的信号确实会杀死他。在每个signal(SIGUSR1, action)
之前,裁判必须每个循环调用kill()
三次。
另一种选择是#define _BSD_SOURCE
(仔细阅读man 2 signal
的可移植性部分),它强加了不重置处置的BSD语义