涉及文件:kernel/printk.c include/linux/kernel.h
用printk内核会根据日志级别把消息打印到当前控制台上。
信息正常输出前提是--日志输出级别(msg_log_level)小于控制台级别(console_loglevle),
内核中数字越小优先级越高。
没有指定日志级别的printk默认级别是DEFAULT_MESSAGE_LOGLEVEL,
默认级别一般为4,与KERN_WARNING一级别。
在kernel/printk.c中定义:
/* printk's without a loglevel use this.. */
#define DEFAULT_MESSAGE_LOGLEVEL 4 /* KERN_WARNING */

#define DEFAULT_MESSAGE_LOGLEVEL CONFIG_DEFAULT_MESSAGE_LOGLEVEL /*3.2内核中可通过配置内核make menuconfig配置默认消息(日志级别), kernel hacking-> CONFIG_DEFAULT_MESSAGE_LOGLEVEL*/

/* We show everything that is MORE important than this.. */
#define MINIMUM_CONSOLE_LOGLEVEL 1 /* Minimum loglevel we let people use */
#define DEFAULT_CONSOLE_LOGLEVEL 7 /* anything MORE serious than KERN_DEBUG */
69 int console_printk[4] = {
70 DEFAULT_CONSOLE_LOGLEVEL, /* console_loglevel */
71 DEFAULT_MESSAGE_LOGLEVEL, /* default_message_loglevel */
72 MINIMUM_CONSOLE_LOGLEVEL, /* minimum_console_loglevel */
73 DEFAULT_CONSOLE_LOGLEVEL, /* default_console_loglevel */
74 };
日志级别一共有8级,定义于include/linux/kernel.c中
102 #define KERN_EMERG "<0>" /* system is unusable */
103 #define KERN_ALERT "<1>" /* action must be taken immediately */
104 #define KERN_CRIT "<2>" /* critical conditions */
105 #define KERN_ERR "<3>" /* error conditions */
106 #define KERN_WARNING "<4>" /* warning conditions */
107 #define KERN_NOTICE "<5>" /* normal but significant condition */
108 #define KERN_INFO "<6>" /* informational */
109 #define KERN_DEBUG "<7>" /* debug-level messages */

111 /* Use the default kernel loglevel */
112 #define KERN_DEFAULT "<d>"
118 #define KERN_CONT "<c>"
119
120 extern int console_printk[];
121
122 #define console_loglevel (console_printk[0])
123 #define default_message_loglevel (console_printk[1])
124 #define minimum_console_loglevel (console_printk[2])
125 #define default_console_loglevel (console_printk[3])
------------------------------------------------------------------------------------------
其实printk始终是输出信息的,用户区/var/log/messages,
内核态/proc/kmsg(klogd没运行,消息不会到用户区)。
读写/proc/sys/kernel/printk可读取或修改控制台日志级别。
#cat /proc/sys/kernel/printk
6  4  1  7
==>控制台日志级别,默认消息日志级别,最低的控制台日志级别,默认的控制台日志级别。
# echo '7 7 1 7' > /proc/sys/kernel/printk
#echo '7 7' > /proc/sys/kernel/printk
注:第二项是“默认消息日志级别”,当printk()中不设置日志级别时才采用默认消息日志级别。
----------------------------------------------------------------------------
为了解决一个问题临时加调试信息可以有两种做法:
一种选择是保持终端的默认记录等级不变,给所有调试信息KERN CRIT或更低的等级以保证信息一定会被输出。另一种方法则相反,给所有调试信息KERN DEBUG等级,而调整终端的默认记录等级为7,也可以输出所有调试信息。两种方法各有利弊。
示例1:
static int __init mm_init(void)
{
printk(KERN_INFO "Hi module!\n");
return 0;
}
static void __exit mm_exit(void)
{
printk(KERN_WARNING "Bye module!\n");
}
模块测试:
/mnt # insmod main.ko
[ 2332.295166] Hi module!
/mnt # cat /proc/sys/kernel/printk
8 7 1 8
/mnt # rmmod main
[ 2585.805572] Bye module!
/mnt # echo 4 > /proc/sys/kernel/printk
/mnt # cat /proc/sys/kernel/printk
4 7 1 8
/mnt # insmod main.ko
/mnt # rmmod main
/mnt # echo 5 > /proc/sys/kernel/printk
/mnt # insmod main.ko
/mnt # rmmod main
[ 3444.786712] Bye module!
示例2:
static int __init mm_init(void)
{
printk(KERN_ERR "Hi module!\n");
return 0;
}
static void __exit mm_exit(void)
{
printk("Bye module!\n");
}
模块测试:
/mnt # insmod main.ko
[ 3606.503204] Hi module!
/mnt # rmmod main.ko
/mnt # cat /proc/sys/kernel/printk
5 7 1 8
/mnt # echo 5 4 > /proc/sys/kernel/printk
/mnt # insmod main.ko
[ 3679.207916] Hi module!
/mnt # rmmod main
[ 3684.487152] Bye module!
/mnt # echo 3 4 > /proc/sys/kernel/printk
/mnt # insmod main.ko
/mnt # rmmod main
-----------------------------------------------------------------------------
采用日志级别的printk()在include/linux/printk.h中有其简便应用方法:
#ifndef pr_fmt
#define pr_fmt(fmt) fmt
#endif

#define pr_emerg(fmt, ...) \
printk(KERN_EMERG pr_fmt(fmt), ##__VA_ARGS__)
#define pr_alert(fmt, ...) \
printk(KERN_ALERT pr_fmt(fmt), ##__VA_ARGS__)
#define pr_crit(fmt, ...) \
printk(KERN_CRIT pr_fmt(fmt), ##__VA_ARGS__)
#define pr_err(fmt, ...) \
printk(KERN_ERR pr_fmt(fmt), ##__VA_ARGS__)
#define pr_warning(fmt, ...) \
printk(KERN_WARNING pr_fmt(fmt), ##__VA_ARGS__)
#define pr_warn pr_warning
#define pr_notice(fmt, ...) \
printk(KERN_NOTICE pr_fmt(fmt), ##__VA_ARGS__)
#define pr_info(fmt, ...) \
printk(KERN_INFO pr_fmt(fmt), ##__VA_ARGS__)
#define pr_cont(fmt, ...) \
printk(KERN_CONT fmt, ##__VA_ARGS__)
此外还有单独的debug应用,此应用必须在此文件中定义DEBUG,否则不能打印信息,其与日志级别和控制台日志级别无关(当然,其调用printk()的KERN_DEBUG级别,若要打印信息,还要满足此日志级别)。
int no_printk(const char *fmt, ...)
{
return 0;
}

/* pr_devel() should produce zero code unless DEBUG is defined */
#ifdef DEBUG
#define pr_devel(fmt, ...) \
printk(KERN_DEBUG pr_fmt(fmt), ##__VA_ARGS__)
#else
#define pr_devel(fmt, ...) \
no_printk(KERN_DEBUG pr_fmt(fmt), ##__VA_ARGS__)
#endif

/* If you are writing a driver, please use dev_dbg instead */
#if defined(DEBUG)
#define pr_debug(fmt, ...) \
printk(KERN_DEBUG pr_fmt(fmt), ##__VA_ARGS__)
#elif defined(CONFIG_DYNAMIC_DEBUG)
/* dynamic_pr_debug() uses pr_fmt() internally so we don't need it here */
#define pr_debug(fmt, ...) \
dynamic_pr_debug(fmt, ##__VA_ARGS__)
#else
#define pr_debug(fmt, ...) \
no_printk(KERN_DEBUG pr_fmt(fmt), ##__VA_ARGS__)
#endif

参考:debug宏起作用应用

参考:http://blog.chinaunix.net/uid-20543672-id-3211832.html

kernel printk信息显示级别的更多相关文章

  1. kernel/printk.c

    /* *  linux/kernel/printk.c * *  Copyright (C) 1991, 1992  Linus Torvalds * * Modified to make sys_s ...

  2. 更改printk打印级别

    1.查看当前控制台的打印级别 cat /proc/sys/kernel/printk 4    4    1    7 其中第一个"4"表示内核打印函数printk的打印级别,只有 ...

  3. 二分查找方法和printk打印级别

    人生就是一个茶几,上面摆满了杯具.内核也是一个大茶几,不过它上面的杯具是一个个的bug.确定bug什么时候被引入是一个很关键的步骤,在这个定位bug的过程中,不论有意或无意,都会很自然地用到二分查找的 ...

  4. 更改printk打印级别【转】

    本文转载自:http://blog.csdn.net/weed_hz/article/details/8949140 1.查看当前控制台的打印级别 cat /proc/sys/kernel/print ...

  5. 终端下更改printk打印级别

    如何去更改printk的打印级别? 1.查看当前控制台的打印级别 # cat /proc/sys/kernel/printk 该文件有4个数字值,它们根据日志记录消息的重要性,定义将其发送到何处,上面 ...

  6. printk打印级别

    默认级别 # cat /proc/sys/kernel/printk 4 4 1 7 分别是:控制台日志级别.默认的消息日志级别.最低的控制台日志级别和默认的控制台日志级别 举例 # echo 0 & ...

  7. debug宏起作用应用

    在linux内核中重新定义了printk,如pr_debug,dev_dbg等.要使用这些宏函数就需要定义DEBUG. 详见:kernel printk信息显示级别 那么DEBUG该定义在什么地方呢? ...

  8. printk函数日志级别的设置【转】

    本文转载自: 下面执行cat /proc/sys/kernel/printk 打印出的四个数字分别代表: 控制台日志级别.默认的消息日志级别.最低的控制台日志级别和默认的控制台日志级别 只有当prin ...

  9. [kernel]内核日志及printk结构分析

    一直都知道内核printk分级机制,但是没有去了解过,前段时间和一个同事聊到开机启动打印太多,只需要设置一下等级即可:另外今天看驱动源码,也看到类似于Printk(KERN_ERR "... ...

随机推荐

  1. hduoj----(1033)Edge

    Edge                         Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K ( ...

  2. Tomact8部署在linux下启动很慢详解

    omcat 8启动很慢,且日志上无任何错误,在日志中查看到如下信息: Log4j:[2015-10-29 15:47:11] INFO ReadProperty:172 - Loading prope ...

  3. python学习笔记011——函数式编程

    1 函数式编程 面向对象 ,面向过程 ,函数式编程 侧重函数的作用,注重函数结果的传递 函数可以被赋值,也可以接受其他的值 2 函数式编程特点 1.函数是一等公民 与其他变量一样,可以赋值和被赋值,可 ...

  4. Android手机在不同分辨率情况下字体自适应大小

    两种解决方法: 一. 1.首先根据不同分辨率获取不同字体大小. 在RES里创建values-480x320/strings.xml 里面设置<dimen name="Text_size ...

  5. java中如何设置下载文件

    如果想要设置某一url为下载文件的方法如下 需要设置文件响应类型,使用response.setContentType,比如jpeg格式的图片.如果想要访问该页面时出现下载保存的窗口,使用respons ...

  6. windows live writer 2012 0x80070643

        折腾了两天,windows live writer 安装不成功,最后放弃了,发现一个叫做菊子曰的软件,但是免费版本的,发图片有限制,感觉非常不爽.windows live writer报错如下 ...

  7. C 指针使用误区

    /** *错误给指针赋常量 *知识点:指针存储内存地址 **/ #include <stdio.h>void main(){ //int *p_int = 123; //错误,不能直接给指 ...

  8. 了不起的 “filter(NULL IS NOT NULL)”

    经常会在执行计划中看到很奇怪的"FILTER"操作,然后看对应的执行信息是"filter(NULL IS NOT NULL)".  其实这是优化器非常聪明的“短 ...

  9. c# 实现查找mysql安装路径

    1.c#能够调用msyql的导入导出命令,可是须要先推断客户机是否安装了mysql.及其安装mysql的路径问题. 2.查询mysql安装路径的函数 private string GetMysqlPa ...

  10. GIS(一)——在js版搜索地图上加入Marker标记

    因为我们做的是有关于旅游方面的项目,所以涉及到了地图功能.我接到的当中一个任务就是,在地图上显示指定的几个景点,并在地图上加上标记. 我们项目用的是搜狗地图.使用的是js版本号.大家有兴趣的话,能够參 ...