likely和unlikely

首先明确:
       likely与unlikely互换或不用都不会影响程序的正确性。但可能会影响程序的效率。
在阅读linux内核代码时经常出现likely()和unlikely()两个宏函数,位于/include/linux/compiler.h中
  #define likely(x)    __builtin_expect(!!(x), 1)  
  #define unlikely(x)  __builtin_expect(!!(x), 0)  
  这里的__built_expect()函数是gcc(version >= 2.96)的内建函数,提供给程序员使用的,目的是将"分支转移"的信息提供给编译器,这样编译器对代码进行优化,以减少指令跳转带来的性能下降。
       在一条指令执行时,由于流水线的作用,CPU可以同时完成下一条指令的取指,这样可以提高CPU的利用率。在执行条件分支指令时,CPU也会预取下一条执行,但是如果条件分支的结果为跳转到了其他指令,那CPU预取的下一条指令就没用了,这样就降低了流水线的效率。因此跳转指令相对于顺序执行的指令会多消耗CPU时间,如果可以尽可能不执行跳转,也可以提高CPU性能。
       __buildin_expect((x), 1)表示x的值为真的可能性更大。
       __buildin_expect((x), 0)表示x的值为假的可能性更大。
       也就是说,使用likely(),执行if后面的语句的机会更大,使用unlikely(),执行else后面的语句机会更大一些。

       在内核代码中使用这两个宏,主要的目的是为了进行代码的优化,提高系统执行速度。例如:

if (likely(a>b)) {
  fun1();
}
if (unlikely(a>b)){
 fun2();
}

       这里就是程序员可以确定 a>b 在程序执行流程中出现的可能相比较大,因此运用了likely()告诉编译器将fun1()函数的二进制代码紧跟在前面程序的后面,这样就cache在预取数据时就可以将fun1()函数的二进制代码拿到cache中。这样,也就添加了cache的命中率。同样的,unlikely()的作用就是告诉编译器,a<=b可能行大,fun2()紧跟前面程序。

       总之,likely和unlikely的功能就是添加cache的命中率,提高系统执行速度。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值