#include <unistd.h>
#include <stdio.h>
#include <signal.h>
#include <sys/types.h>
enum { FALSE, TRUE };

sigset_t sig_m1, sig_m2, sig_null;
int signal_flag=FALSE;

void sig_func(int signr)
{
 start_signalmenge();
 signal_flag = TRUE;
}


void start_signalmenge()
{
 if(signal(SIGUSR1, sig_func) == SIG_ERR)
  exit(0);
 if(signal(SIGUSR2, sig_func) == SIG_ERR)
  exit(0);

 sigemptyset(&sig_m1);
 sigemptyset(&sig_null);
 sigaddset(&sig_m1,SIGUSR1);
 sigaddset(&sig_m1,SIGUSR2);

 if(sigprocmask(SIG_BLOCK, &sig_m1, &sig_m2) <0)
   exit(0);
}

void message_for_parents(pid_t pid)
{
 kill(pid,SIGUSR2);
}

void wait_for_parents()
{
 while(signal_flag == FALSE)
  sigsuspend(&sig_null);
 signal_flag = FALSE;
 if(sigprocmask(SIG_SETMASK, &sig_m2, NULL)<0)
  exit(0);
}

void message_for_child(pid_t pid)
{
 kill(pid, SIGUSR1);
}

void wait_for_child(void)
{
 while(signal_flag == FALSE)
  sigsuspend(&sig_null);
 signal_flag = FALSE;
 if(sigprocmask(SIG_SETMASK, &sig_m2, NULL)<0)
   exit(0);
}


int main()
{
 pid_t pid;
 char x,y;
 start_signalmenge();

 switch( pid = fork())
  {
   case -1 : fprintf(stderr, "Fehler bei fork()\n");
             exit(0);
   case  0 : /*...im Kindprozess...*/
              for(x=2;x<=10;x+=2)
              {
               wait_for_parents();
               write(STDOUT_FILENO, "ping-",strlen("ping-"));
               message_for_parents(getppid());
              }

             exit(0);
   default : /*...im Elternprozess....*/
              for(y=1;y<=9;y+=2)
              {
               write(STDOUT_FILENO, "pong-", strlen("pong-"));
               message_for_child(pid);
               wait_for_child();
              }

   }
 printf("\n\n");
 return 0;
}