I use FreeBSD,and use signal,like follows:
signal(SIGHUP,sig_hup);
signal(SIGIO,sig_io);
when I run call following code,it can run,but I find a puzzled question,it should print some information,such as printf("execute main()") will print execute main(),but in fact,printf fuction print none!!! Why printf function do not go work?
Another question:
I use a udp client to send message to this code,this code can run well,when upd client quit,this code should call sig_hup(),but when the client quit,this code don't call sig_hup(),why? How to correct my code to call sig_hup() when client quit?
my code is follows:
#include "sys/ioctl.h"
#include "unp.h"
static int sockfd;
#define QSIZE 8
#define MAXDG 4096
typedef struct{
void *dg_data;
size_t dg_len;
struct sockaddr *dg_sa;
socklen_t dg_salen;
}DG;
static DG dg[QSIZE];
static long cntread[QSIZE+1];
static int iget;
static int iput;
static int nqueue;
static socklen_t clilen;
static void sig_io(int);
static void sig_hup(int);
int main(int argc,char **argv){
printf("execute main()");
int sockfd;
struct sockaddr_in servaddr,cliaddr;
sockfd=socket(AF_INET,SOCK_DGRAM,0);
bzero(&servaddr,sizeof(servaddr));
servaddr.sin_family=AF_INET;
servaddr.sin_addr.s_addr=htonl(INADDR_ANY);
servaddr.sin_port=htons(SERV_PORT);
bind(sockfd,(SA *)&servaddr,sizeof(servaddr));
dg_echo(sockfd,(SA *)&cliaddr,sizeof(cliaddr));
}
void dg_echo(int sockfd_arg,SA *pcliaddr,socklen_t clilen_arg){
printf("called dg_echo");
int i;
const int on=1;
sigset_t zeromask,newmask,oldmask;
sockfd=sockfd_arg;
clilen=clilen_arg;
for(i=0;i<QSIZE;i++){
dg.dg_data=malloc(MAXDG);
dg.dg_sa=malloc(clilen);
dg.dg_salen=clilen;
}
iget=iput=nqueue=0;
signal(SIGHUP,sig_hup);
signal(SIGIO,sig_io);
fcntl(sockfd,F_SETOWN,getpid());
ioctl(sockfd,FIOASYNC,&on);
ioctl(sockfd,FIONBIO,&on);
sigemptyset(&zeromask);
sigemptyset(&oldmask);
sigemptyset(&newmask);
sigaddset(&newmask,SIGIO);
sigprocmask(SIG_BLOCK,&newmask,&oldmask);
for(;;){
while(nqueue==0)
sigsuspend(&zeromask);
sigprocmask(SIG_SETMASK,&oldmask,NULL);
sendto(sockfd,dg[iget].dg_data,dg[iget].dg_len,0,dg[iget].dg_sa,dg[iget].dg_salen);
if(++iget>=QSIZE)
iget=0;
sigprocmask(SIG_BLOCK,&newmask,&oldmask);
nqueue--;
}
}
static void sig_io(int signo){
printf("sig_io called");
ssize_t len;
int nread;
DG *ptr;
for(nread=0;;){
if(nqueue>=QSIZE)
err_quit("receive overflow");
ptr=&dg[iput];
ptr->dg_salen=clilen;
len=recvfrom(sockfd,ptr->dg_data,MAXDG,0,ptr->dg_sa,&ptr->dg_salen);
if(len<0){
if(errno==EWOULDBLOCK)
break;
else
err_sys("recvfrom error");
}
ptr->dg_len=len;
nread++;
nqueue++;
if(++iput>=QSIZE)
iput=0;
}
cntread[nread]++;
}
static void sig_hup(int signo){
printf("sig_hup called");
int i;
for(i=0;i<=QSIZE;i++)
printf("cntread[%d]=%ld\n",i,cntread);
}