printk函数的用法

本文详细解读了内核日志函数 printk 的用法,包括日志级别设置、控制台级别管理,以及如何通过dmesg和/proc/kmsg查看未在控制台显示的打印信息。介绍了修改内核源码、bootargs设置和/proc/sys/kernel/printk文件调整日志级别的方法。
摘要由CSDN通过智能技术生成

printk在内核源码中用来记录日志信息的函数,只能在内核源码范围内使用。用法和printf非常相似

printk函数主要做两件事情:第一件就是将信息记录到log中,而第二件事就是调用控制台驱动来将信息输出

1.日志级别

printk相比printf来说还多了个:日志级别的设置,用来控制printk打印的这条信息是否在终端上显示的,当日志级别的数值小于控制台级别时,printk要打印的信息才会在控制台打印出来,否则不会显示在控制台!

在我们内核中一共有8种级别,他们分别为

#define	KERN_EMERG	"<0>"	/* system is unusable			*/
#define	KERN_ALERT	"<1>"	/* action must be taken immediately	*/
#define	KERN_CRIT	"<2>"	/* critical conditions			*/
#define	KERN_ERR	"<3>"	/* error conditions			*/
#define	KERN_WARNING	"<4>"	/* warning conditions			*/
#define	KERN_NOTICE	"<5>"	/* normal but significant condition	*/
#define	KERN_INFO	"<6>"	/* informational			*/
#define	KERN_DEBUG	"<7>"	/* debug-level messages			*/

2.控制台级别

#define MINIMUM_CONSOLE_LOGLEVEL  1   /*可以使用的最小日志级别*/
#define DEFAULT_CONSOLE_LOGLEVEL  7 /*比KERN_DEBUG 更重要的消息都被打印*/
#define DEFAULT_MESSAGE_LOGLEVEL 4 /* KERN_WARNING */
 
int console_printk[4] = {
DEFAULT_CONSOLE_LOGLEVEL,/*控制台日志级别,优先级高于该值的消息将在控制台显示*/
/*默认消息日志级别,printk没定义优先级时,打印这个优先级以上的消息*/
DEFAULT_MESSAGE_LOGLEVEL,
/*最小控制台日志级别,控制台日志级别可被设置的最小值(最高优先级)*/
MINIMUM_CONSOLE_LOGLEVEL,
DEFAULT_CONSOLE_LOGLEVEL,/* 默认的控制台日志级别*/
};

在进行查看的时候,可以使用命令 cat /proc/sys/kernel/printk来查看这四个值

3.printk函数使用

在使用printk时我们会将日志级别放到最开始的位置,如

printk(KERN_EMERG "EMERG\n");

我们没有设置日志级别时,会为他设一个默认的日志级别:default_message_loglevel。

当 printk() 中的消息日志级别小于当前控制台日志级别(console_printk[0])时,printk 的信息就会在控制台上显示。

但无论当前控制台日志级别是何值,即使没有在控制台打印出来,可以通过两种方法查看日志:

第一种是使用dmesg命令打印。第二种是通过cat /proc/kmsg来打印

另外如果配置好并运行了 syslogd 或 klogd,没有在控制台上显示的 printk 的信息也会追加到 /var/log/messages.log 中。

4.日志级别的设置

printk可以根据设置的日志级别来确定这个语句最后是否能够打印出来。例如我们知道我们默认的控制台级别为4,如何才能更改这个控制台级别呢?

方法1:修改内核源码

我们可以将default_message_loglevel设为我们想设的值,然后重新编译内核,烧写内核即可。不过不建议直接修改内核源码,因为容易出问题。

方法2:

在uboot的bootargs中加入“loglevel=X”的语句,而其他的语句不变。其中X就是我们想要设置的console_loglevel的值。他的实现原理其实跟设置“console=ttySAC0”一样。通过__setup来设置console_loglevel:

__setup("loglevel=", loglevel);
    具体代码我就不分析了。而同时我们会发现还有两个__setup的设置,他们的代码为:

__setup("debug", debug_kernel);
__setup("quiet", quiet_kernel);

而他们的功能我们通过他们相应的函数设置函数可以知道就是分别将console_loglevel设为10和4 。他们的代码说明为:

static int __init debug_kernel(char *str)
{
    if (*str)
        return 0;
    console_loglevel = 10;
    return 1;
}
 
static int __init quiet_kernel(char *str)
{
    if (*str)
        return 0;
    console_loglevel = 4;
    return 1;
}

方法3:修改/proc/sys/kernel/printk文件

将要设置的值写入到/proc/sys/kernel/printk中。我们要先cat /proc/sys/kernel/printk来看一下这个文件中都有什么值。然后我们再写入。其中这里的格式为:控制台的日志级别、默认消息日志级别、最小控制台日志级别和默认控制台日志级别。而我们要设置的就是第一个控制台的日志级别。我们通过echo “W   X    Y    Z” > /proc/sys/kernel/printk 将我们想要设置的四个值写入到/proc/sys/kernel/printk中。
但是这种方法要在成功开启内核后才可以使用。

 

REF:

https://blog.csdn.net/W1107101310/article/details/80526039

https://www.cnblogs.com/king-77024128/articles/2262023.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值