当前位置: 首页 > news >正文

Linux 内核动态打印调试(dev_info、 dev_dbg )

目录

前言

1 printk消息级别

2 调整内核printk打印级别 

3 dev_xxx函数简介

4 配置内核使用动态打印

5 动态调试使用方法

6 动态打印调试的基本原理


  •  🎈个人主页🎈:linux_嵌入式大师之路的博客-CSDN博客
  • 🎉🎉🎉欢迎 👍点赞✍评论⭐收藏
  • 🤝希望本文能对你有所帮助,欢迎在评论区交流讨论!🤝

前言

在 kernel 驱动代码中,使用动态输出是系统内核调试的重要手段之一,printk打印是全局的,只能设置输出等级。而动态输出可以动态选择打开某个内核子系统的输出,可以有选择性地打开某些模块的输出,printk被dev_info,dev_dbg,dev_err之类的函数代替,dev_xxx函数的本质还是使用printk打印的,只是对printk进行了一层包装。

1 printk消息级别

Linux 内核共提供了八种不同的消息级别,分为级别 0~7。数值越大,表示级别越低,对应的消息越不重要。相应的宏定义在 include/linux/kern_levels.h 文件中。

#define KERN_SOH   "\001"      /* ASCII Start Of Header */
#define KERN_SOH_ASCII '\001'#define KERN_EMERG      KERN_SOH "0"   /* system is unusable */
#define KERN_ALERT      KERN_SOH "1"   /* action must be taken immediately */
#define KERN_CRIT       KERN_SOH "2"   /* critical conditions */
#define KERN_ERR        KERN_SOH "3"   /* error conditions */
#define KERN_WARNING    KERN_SOH "4"   /* warning conditions */
#define KERN_NOTICE     KERN_SOH "5"   /* normal but significant condition */
#define KERN_INFO       KERN_SOH "6"   /* informational */
#define KERN_DEBUG      KERN_SOH "7"   /* debug-level messages */
  • KERN_ALERT 表示必须立即采取行动的消息;
  • KERN_CRIT 表示临界状态,通常涉及严重的硬件或软件操作失败;
  • KERN_ERR 用于报告错误状态,设备驱动程序会经常使用该级别来报告来自硬件的问题;
  • KERN_WARNING 对可能出现问题的情况进行警告,这类情况通常不会对系统造成严重的问题;
  • KERN_NOTICE 表示有必要进行提示的正常情形,许多与安全相关的状况用这个级别进行汇报;
  • KERN_INFO 表示内核提示信息,很多驱动程序在启动的时候,用这个级别打印出它们找到的硬件信息;
  • KERN_DEBUG 用于调试信息。
  • KERN_EMERG 表示紧急事件,一般是系统崩溃之前提示的消息;

2 调整内核printk打印级别 

通过 /proc/sys/kernel/printk 文件可以调节 printk 的输出等级,该文件有 4 个数字值。例如,在 Ubuntu 上的值如下:

​​

 四个数值的含义如下:

控制台日志级别:优先级高于该值的消息将被打印至控制台;

默认的消息日志级别:将用该优先级来打印没有优先级的消息(即 printk 没有指定消息级别);

最低的控制台日志级别:控制台日志级别可被设置的最小值(最高优先级);

默认的控制台日志级别:控制台日志级别的缺省值。

通过修改 /proc/sys/kernel/printk 中的值来改变内核打印效果。例如,屏蔽掉所有的内核 printk 打印,只需要把第一个数值调到最小值1或者0,指令如下:

echo 1 4 1 7 > /proc/sys/kernel/printk

3 dev_xxx函数简介

下面简述下这几个dev_xxx函数的基本使用规则,以及动态调试使用方式。

  • dev_info(): 启动过程、或者模块加载过程等 “通知类的” 信息等,一般只会通知一次,例如 probe 函数;
  • dev_dbg(): 一般使用在普通错误,如-EINVAL、-ENOMEM 等 errno 发生处,用于调试;
  • dev_err(): 一般使用在严重错误,尤其是用户无法得到 errno 的地方,或者程序员不容易猜测系统哪里出了问题的地方;

4 配置内核使用动态打印

  • 打开内核动态调试开关,打开内核配置选项CONFIG_DEBUG_FS=y,CONFIG_DYNAMIC_DEBUG=y
  • debugfs默认会挂载到/sys/kernel/debug,如果没有挂载,可以执行以下命令挂载: 

        mount -t debugfs none /sys/kernel/debug

5 动态调试使用方法

  • 使用下面方式控制你想输出 dev_dbg() 信息
控制某个文件所有 dev_dbg():
echo -n "file xxx.c +p" > /mnt/dbg/dynamic_debug/control控制某个函数所有 dev_dbg():
echo -n "func xxx +p" > /mnt/dbg/dynamic_debug/control
  • 运行程序,使用 dmesg 则可以看到相应 dev_dbg() 的输出信息
  • 当调试结束,不再想输出 dev_dbg() 信息了,使用下面命令关闭即可
echo -n "file xxx.c -p" > /sys/kernel/debug/dynamic_debug/controlecho -n "func xxx -p" > /sys/kernel/debug/dynamic_debug/control

例子:

echo -n "file ca_dsc_core.c +p" > /sys/kernel/debug/dynamic_debug/control 则打印ca_dsc_core.c所有的 dev_dbg() 信息
echo -n "func ca_dsc_read +p" > /sys/kernel/debug/dynamic_debug/control 则打印ca_dsc_read()函数所有 dev_dbg() 

上面是打开动态输出语句的例子,除了能输出pr_debug()/dev_dbg()函数中定义的输出信息外,还能输出一些额外信息,如函数名、行号、模块名字以及线程ID等

  • p:打开动态输出语句(可以是某个文件,某个模块,某个函数,或者文件路径包含某个关键字的文件里所有的动态打印语句)
  • f:输出函数名
  • l:输出行号
  • m:输出模块名字
  • t:输出线程ID

另外,还可以在各个子系统的Makefile中添加ccflags来打开动态输出语句

Makefile:
ccflags-y += -DDEBUG
ccflags-y += -DVERBOSE_DEBUG

6 动态打印调试的基本原理

当编译选项CONFIG_DYNAMIC_DEBUG打开的时候,在编译阶段,kernel 会把所有使用 dev_dbg() 的信息记录在一个 table 中,这些信息我们可以从/sys/kernel/debug/dynamic_debug/control解析出来:

# cat /sys/kernel/debug/dynamic_debug/control

相关文章:

Linux 内核动态打印调试(dev_info、 dev_dbg )

目录 前言 1 printk消息级别 2 调整内核printk打印级别 3 dev_xxx函数简介 4 配置内核使用动态打印 5 动态调试使用方法 6 动态打印调试的基本原理 🎈个人主页🎈:linux_嵌入式大师之路的博客-CSDN博客🎉🎉&…...

深入浅出AXI协议(3)——握手过程

一、前言 在之前的文章中我们快速地浏览了一下AXI4协议中的接口信号,对此我们建议先有一个简单的认知,接下来在使用到的时候我们还会对各种信号进行一个详细的讲解,在这篇文章中我们将讲述AXI协议的握手协议。 二、握手协议概述 在前面的文章…...

Ansible学习笔记5

copy模块:(重点) copy模块用于对文件的远程拷贝(如把本地的文件拷贝到远程主机上。) 在master的主机上准备一个文件,拷贝文件到group1的所有主机上。 这个用的频率非常高,非常有用的一个模块…...

LeetCode 面试题 02.06. 回文链表

文章目录 一、题目二、C# 题解 一、题目 编写一个函数,检查输入的链表是否是回文的。 点击此处跳转题目。 示例 1: 输入: 1->2 输出: false 示例 2: 输入: 1->2->2->1 输出: true …...

linux环境没有curl或者telnet命令解决方法与区分linux环境类型

如何区分你当前使用的 Linux 系统是 Ubuntu、CentOS 还是 Alpine,查看 /etc/os-release 文件 [rootlocalhost ~]# cat /etc/os-release NAME"CentOS Linux" VERSION"7 (Core)" ID"centos" ID_LIKE"rhel fedora" VERSION_I…...

golang channel

channel是不同协程之间异步通信的数据结构。 基本用法 1 构造 ch:make(chan int)//无缓冲 ch:make(chan int,10)//有缓冲2 读操作 val:<-ch <-ch val,ok:<-ch3 写 var data int ch<-data4 关闭 close(ch)5 多路复用 select{ case <-parent.Done():child.…...

高等职业学校物联网实训室建设方案

一、概述 1.1专业背景 物联网&#xff08;Internet of Things&#xff09;被称为继计算机、互联网之后世界信息产业第三次浪潮&#xff0c;它并非一个全新的技术领域&#xff0c;而是现代信息技术发展到一定阶段后出现的一种聚合性应用与技术提升&#xff0c;是随着传感网、通…...

Python基础学习第四天:Python注释

创建注释 注释以 &#xff03; 开头&#xff0c;Python 将忽略它们&#xff1a; 实例 #This is a comment print("Hello, World!")运行实例 注释可以放在一行的末尾&#xff0c;Python 将忽略该行的其余部分&#xff1a; 实例 print("Hello, World!")…...

Puppeteer中使用Stealth.min.js库

这里需要安装npm install puppeteer-extra puppeteer-extra-plugin-stealth&#xff0c;然后&#xff0c;在启动浏览器时&#xff0c;Puppeteer 会自动应用 Stealth.min.js 插件的功能。 const puppeteer require(puppeteer-extra); const StealthPlugin require(puppeteer-…...

JVM ZGC垃圾收集器

ZGC垃圾收集器 ZGC&#xff08;“Z”并非什么专业名词的缩写&#xff0c;这款收集器的名字就叫作Z Garbage Collector&#xff09;是一款在JDK 11中新加入的具有实验性质[1]的低延迟垃圾收集器&#xff0c;是由Oracle公司研发的。 ZGC收集器是一款基于Region内存布局的&#…...

事务管理-事务进阶-propagation属性

目录 事务属性-传播行为 propagation 案例 需求 步骤 具体代码 小结 事务属性-传播行为 propagation 事务传播行为&#xff1a;指的就是当一个事务方法被另一个事务方法调用时&#xff0c;这个事务方法应该如何进行事务控制。即如果事务方法A中调用了事务方法B&#xff0c…...

树多选搜索查询,搜索后选中状态仍保留

<template><div class"half-transfer"><div class"el-transfer-panel"><div><el-checkbox v-model"selectAll" change"handleSelectAll">全部</el-checkbox></div><el-input v-model&qu…...

数据结构--字典树(trie)

概念&#xff1a; Trie 是一种能够快速插入和查询字符串的多叉树结构。、 节点的编号各不相同&#xff0c;根节点编号为0&#xff0c;其他节点用来标识路径&#xff0c;还可以标记单词的插入次数&#xff0c;边表示字符。 tire 维护字符串的集合&#xff0c;支持两种操作&…...

iframe通过postMessage进行跨域通信以及在Angular中使用

写在前面 在前端开发过程中&#xff0c;会遇到一些需要使用iframe的场景&#xff0c;使用iframe关键的一个点是数据之间的传输&#xff0c;基于同源的要求十分苛刻&#xff0c;大家基本上是都是跨域的&#xff0c;如果跨域进行数据传输呢&#xff1f; 大家使用的比较多的就是p…...

rust学习-引用C库

link和extern #[link(name = "...")] 是一个用于链接外部库的属性宏。 可以在 Rust 代码中引入其他语言编写的动态链接库(.so、.dll 等文件),从而实现 Rust 和其他语言的互操作。 #[link(name = "...")] 属性宏用于在 Rust 模块中引入标准 C 库(如 m…...

WebAssembly 在云原生中的实践指南

1 WebAssembly 介绍 WebAssembly&#xff08;Wasm&#xff09;是一种通用字节码技术&#xff0c;它可以将其他编程语言&#xff08;如 Go、Rust、C/C 等&#xff09;的程序代码编译为可在浏览器环境直接执行的字节码程序。 WebAssembly 的初衷之一是解决 JavaScript 的性能问…...

Azure sqlserver 更改字符集

前言 我们的Azure SQL Server是在2018年建的&#xff0c;当时还不支持汉字的字符集。然后最近发现因为字符集的缘故&#xff0c;出了bug&#xff0c;要调整字符集。然后就照着sqlserver 排序规则&#xff08;字符集&#xff09;查看与修改 一通修改。 然后神奇的事情来了&…...

git push时,由于commit了大文件无法成功push的解决办法

2句命令解决&#xff01; 如图可以看见大文件的md5值&#xff0c;复制下来&#xff0c;以下命令会使用到 命令1&#xff1a; git rev-list --objects --all | grep b8d13387c0dfd7a8cec9ff0f6c8ded06eb21556f执行上面命令将得到&#xff0c;如下的输出&#xff0c;可以得知是…...

2023_Spark_实验一:Windows中基础环境安装

Ⅰ、WINDOWS中安装JDK1.8 一、下载安装包 链接&#xff1a;百度网盘 请输入提取码 所在文件夹&#xff1a;根目录或者大数据必备工具--》开发工具(前端后端)--》后端 下载文件名称&#xff1a;jdk-8u191-windows-x64.exe 二、安装JDK 1.现在转到下载的exe文件可用的文件夹&…...

如何在Windows / Mac / iPhone / Android / Online上将MP4转换为MP3

如果只想保留MP4视频的音频轨道&#xff0c;则可以将MP4转换为MP3格式。 MP3是几乎所有设备&#xff0c;播放器和编辑器都支持的数字音频格式。无论您将MP4视频转换为MP3音频以进行脱机播放或进一步编辑&#xff0c;都可以提取音轨并保存为MP3格式。这是在不损失质量的情况下将…...

【App端】uni-app使用百度地图api和echarts省市地图下钻

目录 前言方案一&#xff1a;echarts百度地图获取百度地图AK安装echarts和引入百度地图api完整使用代码 方案二&#xff1a;echarts地图和柱状图变形动画实现思路完整使用代码 方案三&#xff1a;中国地图和各省市地图下钻实现思路完整使用代码 前言 近期的app项目中想加一个功…...

深度学习(十)--- cv2.pointPolygonTest() 判断一点是否在指定区域内

今天发现了opencv一个好用的函数 cv2.pointPolygonTest() &#xff0c;它可以判断一个点是否在指定区域内。 1. cv2.pointPolygonTest() 函数解析 dist cv2.pointPolygonTest(contour,point,Boolean)contour: 多边形轮廓 point: 坐标点 Boolean:True或False &#xff0c;Tru…...

后端面试话术集锦第 八 篇:redis面试话术

这是后端面试集锦第八篇博文——redis面试话术❗❗❗ 1. 介绍一下redis Redis是一个非关系数据库,我们项目中主要用它来存储热点数据的,减轻数据库的压力,单线程纯内存操作,采用了非阻塞IO多路复用机制,就是单线程监听,我们项目中使用springdata-redis来操作redis。 我…...

LiteOS qemu realview-pbx-a9 环境搭建与运行

前言 最近打算移植搭建 一些常见的 RTOS 的 qemu 开发学习环境&#xff0c;当前 RT-Thread、FreeRTOS 已经成功运行 qemu&#xff0c;LiteOS 初步验证可以正常 运行 qemu realview-pbx-a9&#xff0c;这里做个记录 首先学习或者研究 RTOS&#xff0c;只是看内核源码&#xff0…...

Kubernetes技术--Kubernetes架构组件以及核心概念

1.Kubernetes集群架构组件 搭建一个Kubernetes环境集群,其架构如下所示: 内容详解: Master:控制节点,指派任务、决策 Node:工作节点,实际干活的。 Master组件内容:...

拿来即用修改密码功能

<template><div><!-- 重置密码 --><el-dialogtitle"修改密码"v-model"state.resetPwdDialogVisible":showClose"state.firstLogin ! 1"width"550px"close"onCancel":close-on-click-modal"false&…...

违背原则才能写好代码(一)

如果我说&#xff0c;要写好代码&#xff0c;必须违背这些原则&#xff0c;我想所有人都会骂&#xff1a;疯子、胡说八道、哗众取宠&#xff0c;找打&#xff01; 以前我也会骂那个疯子&#xff0c;但现在不会&#xff0c;而且我会肯定地、负责任地说&#xff1a;这是真的&…...

面试官眼中的理想候选人:如何成为他们的首选

&#x1f337;&#x1f341; 博主猫头虎 带您 Go to New World.✨&#x1f341; &#x1f984; 博客首页——猫头虎的博客&#x1f390; &#x1f433;《面试题大全专栏》 文章图文并茂&#x1f995;生动形象&#x1f996;简单易学&#xff01;欢迎大家来踩踩~&#x1f33a; &a…...

ES6中的扩展运算符你真的会用吗?

本文不会具体介绍扩展运算符的基本用法。 只是分享在项目中踩坑的点。 你以为的扩展运算符只是复制的功能&#xff0c;其实会偷偷修改你的原数组 案例&#xff1a; 假如arr [...arr2] &#xff0c;修改arr的值会改变arr2的值吗? 解决方案&#xff1a; case1 使用 arr […...

利用逻辑回归判断病人肺部是否发生病变

大家好&#xff0c;我是带我去滑雪&#xff01; 判断肺部是否发生病变可以及早发现疾病、指导治疗和监测疾病进展&#xff0c;以及预防和促进肺部健康&#xff0c;定期进行肺部评估和检查对于保护肺健康、预防疾病和提高生活质量至关重要。本期将利用相关医学临床数据结合逻辑回…...