首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 其他教程 > 其他相关 >

用C模拟错误

2013-10-23 
用C模拟异常/** * @file test_try_catch.c * @Brief使用形如C的异常来检测超时* @author email:huangkq198

用C模拟异常

/** * @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 <stdio.h>#include <stdlib.h>#include <setjmp.h>#include <signal.h>#include <time.h>#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退出时,影响了原进程的屏蔽信号集!


热点排行