日期:2014-05-16  浏览次数:20689 次

关于setitimer与子进程的问题
我是用setitimer定时产生子进程执行任务,之前在子进程的程序内没有加exit(EXIT_SUCCESS);的时候,只有第一次执行,就不会继续下去,请问这是什么原因呢?
void do_something(int signo)
{
  int status, i;
  for(i = 0; i < 1; i++){
  status = fork();
  }  
  if(status == 0){ 
  printf("Child %d\n", getpid());
  exit(EXIT_SUCCESS); //就是这里
  }else{
  printf("Parent %d\n", getpid());
  wait(NULL);
  }  
}

void init_sigaction(void)
{
  struct sigaction act;
  act.sa_handler = do_something;
  act.sa_flags = 0;
  sigaction(SIGALRM, &act, NULL);
}

void init_time(void)
{
  struct itimerval val;
  val.it_value.tv_sec = 5;
  val.it_value.tv_usec = 0;
  val.it_interval = val.it_value;
  setitimer(ITIMER_REAL, &val, NULL);
}

int main()
{
  init_sigaction();
  init_time();
  while(1)
  ;
  return 1;
}  


------解决方案--------------------
很有意思的一个问题.
首先要注意,fork过后父子进程是共享地址空间的,copy on write时才会copy
所以在没有exit()函数的时候,子进程执行完printf("Child %d\n", getpid());会去执行while(1)循环,而父进程则一直在等待子进程结束,hung在wait()函数上, 所以父进程这时无法处理新来signal alerm信号

需要测试的话,可以在while里加一句打印当前进程id号就看得非常清楚了
int main()
{
init_sigaction();
init_time();
while(1)
{
printf("while pid %d\n", getpid());
sleep(1);
}
return 1;
}

输出结果:
while pid 27703
while pid 27703
while pid 27703
while pid 27703
while pid 27703
Parent 27703
Child 27710
while pid 27710 <===变成子进程执行while了,父进程hung住
while pid 27710
while pid 27710