errno陷阱

一 errno出现的原因

由于一般的函数返回值只会返回执行成功与否,根据返回值并不能得到出错的真正原因,还有一种情况是返回值可以返回任何值,比如-1也是合法的,这时errno就出现了,记录具体的错误原因。它由libc定义:

int errno = 0;

是一个int类型的变量。


二 常见的使用误区

  • 根据errno来判断执行是否成功
errno是用来记录错误的,所以函数执行成功并不会修改errno的值,errno在程序启动时被初始化为0,任何库函数都不会设置errno为0,在函数执行出错时才会设置errno,如果根据errno来判断函数执行成功与否显然是不行的,因为你不知是前一个函数没执行成功还是前前一个函数没执行成功,除非在调用函数之前手动设置errno为0

  • errno判断位置不对
if (somecall() == -1) {
printf("somecall() failed\n");
if (errno == ...) { ... }
}
这样的例子并不能得到somecall这个函数的运行所产生的错误代码 ,因为很可能是printf这个函数产生的。正确的做法是errno的判断应该紧随函数调用之后。

  • errno线程安全问题
在多线程编程应用中,一定要注意libc是否支持线程TLS,如果不是,则使用errno就会出现问题,举例说明:

if (somecall() == -1) {
if (errno == ...) { ... }
}
如果是多线程的,可能执行完 somecall() 后刚好进程切换,切换到同应用中的其他线程,其他线程可能调用库函数修改了errno,如果errno又不是线程局部变量,这时再切换到本线程执行,结果显然是不正确的。

  • 哪些函数会设置errno?
并不是所有的函数出错后都会设置errno,libc中好像是这样的,对于其他的开源库,可能根本没有使用到errno。


基于上述原因,个人认为errno并不是一种很好的存在,使用时一定要非常谨慎。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值