欢迎来到天天文库
浏览记录
ID:1754550
大小:56.00 KB
页数:5页
时间:2017-11-13
《linux kernel tips》由会员上传分享,免费在线阅读,更多相关内容在教育资源-天天文库。
1、LinuxKernelTips__builtin_constant_p__builtin_constant_p是编译器gcc内置函数,用于判断一个值是否为编译时常量。如果是常数,函数返回1,否则返回0。此内置函数的典型用法是在宏中用于手动编译时优化likelyandunlikely#definelikely(x)__builtin_expect((x),1)#defineunlikely(x)__builtin_expect((x),0)__builtin_expect()宏是gcc(version>=2.9)引入的预
2、先定义的宏,这个宏的主要作用是帮助编译器判断条件跳转的预期值。看看下面这个例子:if(__builtin_expect(x,0))foo();这里例子中,代码是在说预期x的值为“假”,并且不太期望程序执行foo()函数。而这段代码就等价于:if(unlikely(x))foo();由此可见,likely和unlikely仅仅是在帮助编译器产生更优代码,而对真值的判断没有影响。container_of该宏定义在include/linux/kernel.h中,首先来贴出它的代码:1.439/**2.440 * contai
3、ner_of - cast a member of a structure out to the containing structure3.441 * @ptr: the pointer to the member.4.442 * @type: the type of the container struct this is embedded in.5.443 * @member: the name of the member within the struct.6.444 *1.4
4、45 */2.446#define container_of(ptr, type, member) ({ /3.447 const typeof( ((type *)0)->member ) *__mptr = (ptr); /4.448 (type *)( (char *)__mptr - offsetof(type,member) );})它的作用是根据一个结构体变量中的一个域成员变量的指针来获取指向整个结构体变量的指针。比如,有一个结构体
5、变量,其定义如下:1.struct demo_struct {2. type1 member1;3. type2 member2;4. type3 member3;5. type4 member4;6.};7.8.struct demo_struct demo;同时,在另一个地方,获得了变量demo中的某一个域成员变量的指针,比如:1.type3 *memp = get_member_pointer_from_somewhere();此时,如果需要获取指向整个结构体变量的指针,而不仅仅只是其某一
6、个域成员变量的指针,我们就可以这么做:1.struct demo_struct *demop = container_of(memp, struct demo_struct, member3);这样,我们就通过一个结构体变量的一个域成员变量的指针获得了整个结构体变量的指针。下面说一说我对于这个container_of的实现的理解:首先,我们将container_of(memp,structdemo_struct,type3)根据宏的定义进行展开如下:1.struct demo_struct *demop = ({
7、 /2. const typeof( ((struct demo_struct *)0)->member3 ) *__mptr = (memp); /3. (struct demo_struct *)( (char *)__mptr - offsetof(struct demo_struct, member3) );})其中,typeof是GNUC对标准C的扩展,它的作用是根据变量获取变量的类型。因此,上述代码中的第2行的作用是首先使用typeof获取结构体域变量m
8、ember3的类型为type3,然后定义了一个type3指针类型的临时变量__mptr,并将实际结构体变量中的域变量的指针memp的值赋给临时变量__mptr。假设结构体变量demo在实际内存中的位置如下图所示: demo +-------------+0xA000
9、 member1
10、 +---
此文档下载收益归作者所有