设为首页 加入收藏

TOP

用C模拟异常
2014-11-23 21:45:49 来源: 作者: 【 】 浏览:12
Tags:模拟 异常
/** 
 * @file test_try_catch.c 
 * @Brief  使用形如C++的异常来检测超时  
 * @author email:huangkq1989@gmail.com blog:http://blog.csdn.net/kangquan2008 
 * @version 1.0 
 * @date 2013-10-22 
 */  
#include   
#include   
#include   
#include   
#include   
  
#define  __WITH_TIME_OUT_IMPOSSIBLE__  
#ifdef __WITH_TIME_OUT_IMPOSSIBLE__  
  
static sigjmp_buf __time_out_jump;  
  
typedef void (* __sigfunc)(int);  
static void __do_time_out(int sig)  
{  
  fprintf(stdout,"time out here\n");  
  siglongjmp(__time_out_jump, 1);  
  
}  
  
static void __time_out_reset(__sigfunc store)  
{  
  alarm(0);  
  signal(SIGALRM, store);  
  
}  
  
#define TIME_OUT_TRY(x) \  
{\  
  // 设置超时处理函数,将调用longjmp,使得能进入else,即catch  
  __sigfunc save = signal(SIGALRM, __do_time_out);\  
  // 保存堆栈,返回值为0时表示不是由longjmp返回,  
  // 否则为调用了longjmp后返回的  
  // 参数 1,是为了保存当前进程的信号屏蔽字  
  if(!sigsetjmp(__time_out_jump, 1)) {\  
    //计时  
    alarm(x);  
  
#define TIME_OUT_CATCH \  
  }\  
  // 由于sigsetjmp返回非0,进入CATCH  
  else {\  
  
#define TIME_OUT_END \  
  } \  
  // 恢复SIGALRM的信号处理函数  
  __time_out_reset(save);\  
}  
  
#define TIME_OUT_RETURN(x)  { __time_out_reset(save); return (x);  }  
#define TIME_OUT_RETUR_VOID { __time_out_reset(save); return ;  }  
  
#endif //__WITH_TIME_OUT_IMPOSSIBLE__  
  
int main()  
{  
  int timeout = 10;  
  TIME_OUT_TRY(timeout) {  
    sleep(11);  
  }  
  TIME_OUT_CATCH{  
    TIME_OUT_RETURN(-1);  
  }  
  TIME_OUT_END;  
  
  return 0;  
}  

至于为什么用sigsetjmp而不是setjmp:
如果在信号处理函数中调用异常处理,那么这一信号会加入被屏蔽信号集(信号不排队),当用longjmp退出时,影响了原进程的屏蔽信号集!
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇小小的C语言问题指针数组赋值----.. 下一篇c语言输入三个分数,并进行按从高..

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: