__init和__exit宏的作用
原文地址:http://blog.csdn.net/zhenwenxian/article/details/8564574
内核的部分函数带有__init和__exit宏,负责“初始化”和“清理收尾”该函数。如果该模块被编译进内核,而不是动态加载。宏 __init的使用会在初始化完成后丢弃该函数并收回所占内存,
宏__initdata同__init 类似,只不过对变量有效。简单来说是指示gcc把标记的数据或者函数放到指定sector。
linux中把一些启动及初始化时候用的数据用__init标识,然后在适当的时候把它们释放,回收内存。
宏__exit将忽略“清理收尾”的函数如果该模块被编译进内核。同宏 __exit一样,对动态加载模块是无效的。这很容易理解。编译进内核的模块 是没有清理收尾工作的, 而动态加载的却需要自己完成这些工作。
这些宏在头文件linux/init.h定义,用来释放内核占用的内存。 当你在启动时看到这样的Freeing unused kernel memory: 236k freed内核输出,上面的 那些正是内核所释放的
下面是一些常用的宏:
· __init ,标记内核启动时使用的初始化代码,内核启动完成后不再需要。以此标记的代码位于.init.text 内存区域。它的宏定义是这样的:
·
#define _ _init _ _attribute_ _ ((_ _section_ _ (".text.init")))
· __exit ,标记退出代码,对于非模块无效。
· __initdata ,标记内核启动时使用的初始化数据结构,内核启动完成后不再需要。以此标记的代码位于.init.data 内存区域。
· __devinit ,标记设备初始化使用的代码。
· __devinitdata ,标记初始化设备数据结构的函数。
· __devexit ,标记移除设备时使用的代码。
· xxx_initcall ,一系列的初始化代码,按降序优先级排列。
初始化代码的内存结构
_init_begin -------------------
| .init.text | ---- __init
|-------------------|
| .init.data | ---- __initdata
_setup_start |-------------------|
| .init.setup | ---- __setup_param
__initcall_start |-------------------|
| .initcall1.init | ---- core_initcall
|-------------------|
| .initcall2.init | ---- postcore_initcall
|-------------------|
| .initcall3.init | ---- arch_initcall
|-------------------|
| .initcall4.init | ---- subsys_initcall
|-------------------|
| .initcall5.init | ---- fs_initcall
|-------------------|
| .initcall6.init | ---- device_initcall
|-------------------|
| .initcall7.init | ---- late_initcall
__initcall_end |-------------------|
| |
| ... ... ... |
| |
__init_end -------------------
初始化代码的特点是:在系统启动运行,且一旦运行后马上退出内存,不再占用内存。
__init和__exit宏的作用的更多相关文章
- Linux内核中的宏:__init and __exit
ZZ FROM: http://blog.csdn.net/musein/article/details/742609 ======================================== ...
- debug宏起作用应用
在linux内核中重新定义了printk,如pr_debug,dev_dbg等.要使用这些宏函数就需要定义DEBUG. 详见:kernel printk信息显示级别 那么DEBUG该定义在什么地方呢? ...
- C语言中宏的作用
在C语言#define机制中包括了一个规定,与允许把参数替换到文本中,这种实现通常称为宏或宏定义.下面是宏的声明方式: #define name(parameter-list) ...
- do{}while(0)宏的作用的定义
看到开放源代码,宏定义经常这样用 #define some() do { do_somt_thing(); } while (0) 为什么这样用? 能够试一下.假如一个普通宏定义 #define so ...
- php源码分析之PHPAPI宏的作用
在PHP源码中,我们经常会看到很多函数前面有个PHPAPI,但这是什么呢? 于是我在php源码/main/php.h中找到了它的定义 #ifdef PHP_WIN32 # include " ...
- Q_OBJECT宏的作用
The Q_OBJECT macro at the beginning of the class definition is necessary for all classes that define ...
- Cocos2d-x中常用宏的作用
1. CC_SYNTHESIZE(int, nTest, Test); 相当于: protected: int nTest; public: virtual nTest getTest(void) c ...
- Linux中__init、__devinit等内核优化宏【转】
转自:http://blog.csdn.net/joker0910/article/details/7171626 内核使用了大量不同的宏来标记具有不同作用的函数和数据结构.如宏__init .__d ...
- linux内核中经常用到的设备初始化宏
内核使用了大量不同的宏来标记具有不同作用的函数和数据结构.如宏__init.__devinit等.这些宏在include/linux/init.h头文件中定义.编译器通过这些宏可以把代码优化放到合适的 ...
随机推荐
- 【转】fread函数和fwrite函数
1.函数功能 用来读写一个数据块. 2.一般调用形式 fread(buffer,size,count,fp); fwrite(buffer,size,count,fp); 3.说明 ( ...
- lucene4入门(3)琐记
欢迎转载http://www.cnblogs.com/shizhongtao/p/3440486.html <--这个是lucene4.6的api下载地址,格式是chm的.需要的人可以下载htt ...
- UVaLive 7361(矩阵快速幂)
题意:矩阵快速幂求斐波那契数列. 分析:
- DQL_数据查询语言
2014年11月21日 21:43:53 DQL 基础查询-- 注意要点:1.用户友善的标题 ...
- 修改SSH端口为21
在交流群里面有一位兄弟问到能否将ssh端口号修改为21端口,后来经过测试可以设置,具体步骤如下: 一.修改ssh配置文件的默认端口 #vim /etc/ssh/sshd_config 找到#port ...
- sed- 文本流编辑器
sed [选项] [参数] -n 被操作行打印输出 ...
- Hits算法
HITS(HITS(Hyperlink - Induced Topic Search) ) 算法是由康奈尔大学( Cornell University ) 的Jon Kleinberg 博士于1997 ...
- 热键HotKeys
一:新建类HotKeys命名空间: using System.Runtime.InteropServices; 二:注册热键API [DllImport("user32")] pu ...
- 【原】EF简单使用
/// <summary> /// 数据上下文对象 /// </summary> static TestEntities te = new TestEntities(); st ...
- Spark Streaming揭秘 Day11 Receiver Tracker的具体实现
Spark Streaming揭秘 Day11 Receiver Tracker的具体实现 ReceiverTracker是运行在Driver上Receiver管理程序,今天让我们深入学习一下. 核心 ...