C和Linux的细小知识点

宏定义

#if defined与#ifdef的区别:

#if defined 与#if !defined后可以加表达式。#ifdef与#ifndef后面不可以加表达式。

#if defined A && !defined B
printf("1");
#endif

宏连接符

#define czg(x) #@x    //czg(3) = '3' 字符常量
#define czg(x) #x    //czg(3) = "3" 字符串
#defineczg(x,y) x##y //:czg(love,9728)= love9728

__attrubute__()关键词

是一个编译器指令,告诉编译器声明的特性,或者让编译器进行更多的错误检查和高级优化,

# define __visible         __attribute__((__externally_visible__))

externally_visible:附加到全局变量或函数的该属性使整个程序命令行选项,因此该对象在当前编译单元外部任然可见,如果 -整个程序 与 -flto和 gold被用作连接体插件, externally_visible属性被自动地添加到功能。对于其他无法生成解析文件的链接器,externally_visible仍然需要显式属性。
externally_visible的作用就是使该对象在当前编译单元外部仍然可见。
 

# define __iomem    __attribute__((noderef, address_space(2)))

主要用于编译器的检查,检查地址空间的有效性。

noderef:必须是非解除参考,即这个变量地址必须是有效的

address_space(2):变量所在的地址空间必须是2,即io存储空间。0,1,2,3分别对应内核空间、用户空间、io存储空间、cpu空间

弱函数:

一般会有一个同名的函数,编译时会自动编译另一个函数,若没有,则编译弱函数。

void __weak fun(){}

printf输出格式: 

%06x:以16进制输出,输出字符至少占据6个字符,若不够则左边填0

%6x:以16进制输出,输出字符至少占据6个字符,若不够则左边填空格

%p:可输出指针地址

__init fun(){}函数前__init含义:

__init宏告诉编译器,将变量或函数放在一个特殊的区域(在vmlinux.lds中被定义),该区域在.init.text这个代码区。__initdata将数据放在“.init.data”这个数据区中。标记为初始化的函数,该函数只能在初始化期间使用,在模块装载后,就会将初始化函数扔掉,这样可以将该函数占用的内存释放。

__exit宏告知编译器,将函数放在".exit.text"这个区域,__exitdata宏则放在".exitdata"这个区域,exit.*区域仅仅对模块是有用的:如果编译稳定的话,exit函数将永远不会被调用,只有当模块支持无效的时候,exit.*区域将被丢弃。

函数或符号前加EXPORT_SYMBOL的作用:

是对全部内核代码公开,不用修改内核代码就可以在内核模块中直接调用。

使用方法:在模块函数定义之后使用"EXPORT-SYMBOL(函数名)"来声明,在调用该函数的另外一个模块中使用extern对之声明,先加载定义该函数的模块,再加载调用该函数的模块。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值