I'm far from an expert on this, but perhaps when you CTRL-C cat it doesn't close the pipe properly. What happens if you use CTRL-D to quit cat instead (which should result in normal exit)?
[edit] By the way, post your code here on CBoard. More people will be inclined to help that way, and the code won't disappear. Here it is for posterity's sake.
Code:
/* Scrivere un programma C che prese in input da riga comando il pathname
* di molteplici FIFO (almeno 1, numero imprecisato) metta in output tutt
* o cio' che arriva da qualsiasi di esse. Il programma non deve usare fo
* rk ma una chiamata a scelta fra select o poll.
*/
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/select.h>
#include <limits.h>
#define BUFFER PIPE_BUF
int max(int a[], int num_elements)
{
int i, max = a[0];
for (i=0; i<num_elements; i++)
{
if (a[i] > max)
{
max = a[i];
}
}
return (max);
}
int main(int argc, char **argv)
{
register int i;
int* fifos;
int ready_fd;
int nfds;
int buff_count,count;
fd_set fdset,tmpset;
char buff[BUFFER];
struct stat buf_fstat;
// buff = (char *)malloc(sizeof(char)*4096);
if (argc==1) /* wrong usage of args*/
{
printf("Usage: ./a.out 1st-fifo-path [2nd-fifo-path] ... [n-fifo-path]\n");
return(-1);
}
else /* right usage of args */
{
FD_ZERO(&fdset); /* clear the fd_set */
fifos = (int*) malloc(sizeof(int) * (argc-1));
for (i=0;i<argc-1;i++)
{
if ((fifos[i] = open(argv[i+1],O_RDWR|O_NONBLOCK))<0)
{
perror("open");
return(-2);
}
else
{
if (fstat(fifos[i],&buf_fstat))
perror("fstat");
else if (! S_ISFIFO(buf_fstat.st_mode))
{
printf("%s is not a pipe. Aborting\n",argv[i+1]);
return(-2);
}
else
FD_SET(fifos[i],&fdset);
}
}
nfds = max(fifos,(argc-1))+1;
memcpy((void *) &tmpset,(void *) &fdset, sizeof(fd_set));
while (1)
{
/* we will use timeout=NULL to block indefinitely */
if ((ready_fd = select(nfds,&fdset,NULL,NULL,NULL))<0)
perror("select");
else
{
#ifdef DEBUG
printf("ready fd: %d\n",ready_fd);
#endif
for (i=0,count=0;count<ready_fd||i<=(argc-1);i++)
{
if (FD_ISSET(fifos[i],&fdset))
{
count++;
#ifdef DEBUG
printf("fifo: %d\n",i);
#endif
if ((buff_count=read(fifos[i],&buff,BUFFER))<0)
perror("read");
else
{
#ifdef DEBUG
printf("read %d bytes\n",buff_count);
#endif
if (write(STDOUT_FILENO, buff, sizeof(char) * (unsigned int) buff_count)<0)
perror("write");
}
}
}
memcpy((void *) &fdset,(void *) &tmpset, sizeof(fd_set));
}
}
}
}
[/edit]