前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >container of()函数用法简介

container of()函数用法简介

作者头像
无刺鱼
发布2022-03-29 13:18:08
1.6K0
发布2022-03-29 13:18:08
举报
文章被收录于专栏:许唯宇

在Linux 内核编程中,会经常见到一个宏函数container_of(ptr,type,member)。已知结构体type的成员member的地址ptr,求结结构体type的起始地址。

container_of

在已知一个结构体的成员的名字,以及其地址的情况向,反推该结构体的首地址

offsetof

获取一个结构体成员在结构里面的偏移,结构体首地址 = 成员地址- 成员偏移

以下是一个container of函数例子:

代码语言:javascript
复制
#include <stdio.h>  
#include <stdlib.h>
 
#define offsetof(TYPE,MEMBER) ((int) &((TYPE *)0)->MEMBER)   //为什么这样就能得到偏移
 
#define container_of(ptr, type , member) ({ \
	const typeof(((type *)0)->member) *__mptr = (ptr) ; \
	(type *)((char *)__mptr - offsetof(type,member)) ;})
 
#pragma pack(4)  
struct ptr  
{  
    char a ;   
    short b ;   
    int  c ;   
    double d ;  
};  
#pragma pack()  
int main(void)  
{  
    struct ptr Pt ;  
    struct ptr *pt ;
    printf("ptr:%d\n",sizeof(struct ptr));//16  
    //获取结构体的首地址 
    printf("ptr:%p\n",&Pt); //0028FEA8
    Pt.a = 'a';
    Pt.b = 2 ;
    Pt.c = 4 ;
    Pt.d = 12.04 ;
    //通过container of获取结构体的首地址 
    pt = container_of(&Pt.c, struct ptr , c);
    printf("pt:%p\n",pt);  //0028FEA8
    printf("a:%c\n",pt->a) ;  //'a'
    printf("b:%d\n",pt->b) ;  //2
    printf("c:%d\n",pt->c) ;  //4
    printf("d:%.2lf\n",pt->d);//12.04
    return 0 ;  
}  

linux 内核宏container_of(ptr, type, member)

通过计算member的地址,获取 ptr 所在的结构体type的首地址。

代码语言:javascript
复制
#define container_of(ptr, type, member) ({  \         
const typeof(((type *)0)->member) *__mptr = (ptr);\         
(type *)((char *)__mptr - offsetof(type,member));})

#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)

typeof 获取成员类型

const typeof( ((type *)0)->member ) *__mptr = (ptr); 将ptr 赋值给 __mptr,如果ptr的类型和member指针的类型不一致,这个赋值会有警告,这个是代码严谨性的体现。

#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER) 成员member 在结构体TYPE中的相对地址

ptr - offset 获取ptr所在的结构体的地址。

嵌入式Linux与物联网软件开发:C语言内核深度解析

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022/01/29 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • container_of
  • offsetof
  • linux 内核宏container_of(ptr, type, member)
  • typeof 获取成员类型
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档