linux内核earlyprink,内核启动参数机制学习笔记

前两天把内核关于内核启动参数的一些知识彻底地分析了一遍《Linux内核源码分析--内核启动命令行的传递过程(Linux-3.0 ARMv7)》,发现了一些以前没有注意的细节问题,这里总结如下:

一、2.6.32以后的内核不再对cmdline中的未知参数输出警告信息

以前在移植内核的时候,如果cmdline中有未知的参数,内核一般会打印如下警告:

Unknown boot option `**********': ignoring    但是这次我在uboot的bootargs中添加了内核未知的参数,比如“hello_linux.tekkaman=ninja”,但是在内核启动信息和dmesg中一点错误信息都没有,我感觉很奇怪,然后我又在同事的板子上试了下,一样没有任何错误信息。我查了下代码,按照逻辑,是不会有错误信息输出。哪以前怎么会有错误信息?

后来我通过Git查找了内核针对这方面的修改,发现了如下提交:

commit f066a4f6df68f03b565dfe867dde54dfeb26576e

Author: Rusty Russell

Date: Tue Dec 1 14:56:44 2009 +1030

param: don't complain about unused module parameters.

参数:不抱怨未使用的模块参数。

Jon confirms that recent modprobe will look in /proc/cmdline, so these

cmdline options can still be used.

乔恩证实:新的modprobe会读取/proc/cmdline,所以这些

命令行选项仍然可能被使用。

See

Reported-by: Adam Williamson

Cc: stable@kernel.org

Signed-off-by: Rusty Russell

Signed-off-by: Linus Torvalds

也就是说由于新版本的module-init-tool中的modprobe可以在挂外部.ko模块的时候读取/proc/cmdline(也就是内核启动参数cmdline的备份)中的参数,所有在内核启动的时候还暂时未知的参数可能在系统运行起来,挂载模块的时候被使用。所以在启动的时候提出警告实属不必要。所有这个警信代码被删除了。

这个提交的补丁如下:

$ git diff f066a4f6df^..f066a4f6df

diff --git a/init/main.c b/init/main.c

index 5988deb..4051d75 100644

--- a/init/main.c

+++ b/init/main.c

@@ -251,7 +251,7 @@ early_param("loglevel", loglevel);

/*

* Unknown boot options get handed to init, unless they look like

- * failed parameters

+ * unused parameters (modprobe will find them in /proc/cmdline).

*/

static int __init unknown_bootoption(char *param, char *val)

{

@@ -272,14 +272,9 @@ static int __init unknown_bootoption(char *param, char *val)

if (obsolete_checksetup(param))

return 0;

- /*

- * Preemptive maintenance for "why didn't my misspelled command

- * line work?"

- */

- if (strchr(param, '.') && (!val || strchr(param, '.') < val)) {

- printk(KERN_ERR "Unknown boot option `%s': ignoring\n", param);

+ /* Unused module parameter. */

+ if (strchr(param, '.') && (!val || strchr(param, '.') < val))

return 0;

- }

if (panic_later)

return 0;

这个提交在2.6.32发布前被并入主线:

$ git tag --contains f066a4f6df

v2.6.32

v2.6.33

v2.6.33-rc1

v2.6.33-rc2

v2.6.33-rc3

v2.6.33-rc4

v2.6.33-rc5

v2.6.33-rc6

v2.6.33-rc7

v2.6.33-rc8

就这个问题在:

点击(此处)折叠或打开

From 2009-09-11 16:28:54

When passing a kernel parameter of the type:

radeon.modeset=0

the kernel will throw a warning message that says "Unknown boot option

'radeon.modeset=0'. Ignoring..." However, the parameter is not ignored, it is

passed to (and parsed by) the radeon module.

We (Fedora QA/BugZappers) find people are often confused or worried by this

message when we ask them to use such a parameter, and worry that it is not

being applied correctly. The kernel should not print this warning/error message

when the parameter is of a format that will cause it to be passed to a kernel

module.

-------Comment  From 2009-09-22 02:50:17-------

Is this because modern modprobe is scraping these options from /proc/cmdline?

If so, yes, we should suppress those messages altogether.

CC'd Jon, he'd know.

-------Comment  From 2009-09-22 04:51:52-------

I don't know how it's implemented, exactly, that may well be how it works. I

just know that you can pass any module parameter as a kernel command line

parameter in that format (modulename.moduleparameter=value) and it gets passed

on somehow.

-------Comment  From 2009-11-26 17:43:30-------

ping? this still regularly causes confusion for users when we're trying to

debug various issues, see

for a recent example: it's a 'cosmetic' bug but with unfortunate effects.

-------Comment  From 2010-03-21 12:03:01-------

Yea, exactly that's what happens. Modprobe pulls out those arguments and

processes them.

I don't know why I missed this bug, but that should be fixed now. I even have

daily reminders setup and should get CC'd on every module issue from now on.

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

二、使用modprobe挂载.ko模块可以从cmdline中获取参数

从上面的发现又牵出了一个新的发现,原来单独编译的内核模块参数是可以用modprobe挂载的时候从内核的cmdline中获得的。这个是我以前没有注意到的。于是我做了个实验:写一个简单的模块(仅在init函数中打印模块参数),然后在内核启动参数中增加这个参数的初始化。经几次实验,证实了这个功能。

其实通过模块挂载的原理和模块的二进制结构的了解(详见《深入Linux内核构件》 第七章 模块),可以知道:其实这个功能是modprobe实现的。所以实现这个功能的必要条件是modprobe工具必须支持从/proc/cmdline读取字符串,并通过格式(模块名).(变量名)=(值)过滤出参数。

这个大家特别注意一下参数的格式 :

(模块名).(变量名)=(值)

在嵌入式中,高版本的busybox是支持的,现在最新的肯定支持,但是注意了,要配置busybox的时候不能选择"简化版的挂载工具",要配置为编译全功能的modprobe。

在PC系统下也是支持的,在grub的内核启动参数中添加 hello_linux.tekkaman=ninja ,再用modprobe挂载模块。用dmesg看内核信息就可以看到实验结果。实验用的PC信息如下:

Linux Amethyst 3.2.12-gentoo #1 SMP Mon Apr 16 14:16:04 CST 2012 i686 AMD Athlon(tm) 64 X2 Dual Core Processor 4800+ AuthenticAMD GNU/Linuxmodule-init-tools version 3.16

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

嵌入式实验现象如下:

# busybox modprobe hello_linux

Hello, Linux !

(0) Hello, ninja

# cat /proc/cmdline

console=ttyO2,115200n8 root=/dev/nfsroot nfsroot=10.10.10.2:/media/6a55c5a3-f467-4b31-a56a-73b57c5cd2a2/C6A816x/development/targetfs,nolock rw mem=176M@0x80000000 mem=39M@0x9BD00000 vram=90M notifyk.vpssm3_sva=0xBF900000 ip=10.10.10.10:10.10.10.2:0.0.1:255.255.255.0::eth0:off noinitrd earlyprink hello_linux.tekkaman=ninja实验代码如下:zip.gif test_module_i686.zip

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值