dev_dbg 将日志写入哪里?
Where does dev_dbg writes log to?
在 Linux 树中的设备驱动程序源中,我看到了 dev_dbg(...)
和 dev_err(...)
,我在哪里可以找到记录的消息?
一个参考建议添加 #define DEBUG
。另一个reference涉及到dynamic debug和debugfs,我迷路了
dev_dbg()
扩展为 dynamic_dev_dbg()
、dev_printk()
或空操作,具体取决于编译标志。
#if defined(CONFIG_DYNAMIC_DEBUG)
#define dev_dbg(dev, format, ...) \
do { \
dynamic_dev_dbg(dev, format, ##__VA_ARGS__); \
} while (0)
#elif defined(DEBUG)
#define dev_dbg(dev, format, arg...) \
dev_printk(KERN_DEBUG, dev, format, ##arg)
#else
#define dev_dbg(dev, format, arg...) \
({ \
if (0) \
dev_printk(KERN_DEBUG, dev, format, ##arg); \
})
#endif
dynamic_dev_dbg()
和 dev_printk()
调用 dev_printk_emit()
调用 vprintk_emit()
.
当您只执行 printk()
时,在正常模式下会调用这个完全相同的函数。请注意,其余函数如 dev_err()
将以相同的函数结束。
因此,很明显,缓冲区都是一样的,即内核内部缓冲区。
最后记录的消息被打印到
- 当前控制台如果内核 loglevel 值(可以通过内核命令行或通过 procfs 更改)对于某些消息来说足够高,这里 KERN_DEBUG.
- 可以通过运行
dmesg
命令读取的内部缓冲区。
注意,只要缓冲区中还有空间,就会保留 2 中的数据。由于它是有限的和循环的,所以新数据会优先于旧数据。
有关如何启用动态调试的更多信息。
首先,请确保您的内核配置中有CONFIG_DYNAMIC_DEBUG=y
。
假设我们想要在名称为 8250 的 built-in 模块中启用所有调试打印。为了实现这一点,我们简单地向内核命令行添加以下 8250.dyndbg=+p
.
如果相同的驱动程序被编译为可加载模块,我们可以将 options 8250 dyndbg
添加到 modprobe 配置或添加到 shell 命令行。手动,例如 modprobe 8250 dyndbg
.
Dynamic Debug 文档中描述了更多详细信息。
您可以在内核消息中找到 dev_err(...)
。顾名思义,dev_err(...)
消息是错误消息,所以如果执行到那个点,肯定会打印出来。 dev_dbg(...)
是在内核驱动程序代码中更广泛使用的调试消息,默认情况下不打印它们。所以你读到的关于 dynamic_debugging 的所有内容都适用于 dev_dbg(...)
。
动态调试工作有几个先决条件,下面的 1. 和 2. 是动态调试的一般先决条件。 3. 及以后是针对您的特定 driver/module/subsystem 并且可以是 .
- 动态调试支持必须在您的内核配置中
CONFIG_DYNAMIC_DEBUG=y
。你可以看看是不是这样 zgrep DYNAMIC_DEBUG /proc/config.gz
- 必须安装 debugfs。您可以使用
sudo mount | grep debugfs
检查,如果不存在,您可以使用 sudo mount -t debugfs /sys/kernel/debug
安装
- 参考dynamic_debugging并启用您感兴趣的特定file/function/line
在 Linux 树中的设备驱动程序源中,我看到了 dev_dbg(...)
和 dev_err(...)
,我在哪里可以找到记录的消息?
一个参考建议添加 #define DEBUG
。另一个reference涉及到dynamic debug和debugfs,我迷路了
dev_dbg()
扩展为 dynamic_dev_dbg()
、dev_printk()
或空操作,具体取决于编译标志。
#if defined(CONFIG_DYNAMIC_DEBUG)
#define dev_dbg(dev, format, ...) \
do { \
dynamic_dev_dbg(dev, format, ##__VA_ARGS__); \
} while (0)
#elif defined(DEBUG)
#define dev_dbg(dev, format, arg...) \
dev_printk(KERN_DEBUG, dev, format, ##arg)
#else
#define dev_dbg(dev, format, arg...) \
({ \
if (0) \
dev_printk(KERN_DEBUG, dev, format, ##arg); \
})
#endif
dynamic_dev_dbg()
和 dev_printk()
调用 dev_printk_emit()
调用 vprintk_emit()
.
当您只执行 printk()
时,在正常模式下会调用这个完全相同的函数。请注意,其余函数如 dev_err()
将以相同的函数结束。
因此,很明显,缓冲区都是一样的,即内核内部缓冲区。
最后记录的消息被打印到
- 当前控制台如果内核 loglevel 值(可以通过内核命令行或通过 procfs 更改)对于某些消息来说足够高,这里 KERN_DEBUG.
- 可以通过运行
dmesg
命令读取的内部缓冲区。
注意,只要缓冲区中还有空间,就会保留 2 中的数据。由于它是有限的和循环的,所以新数据会优先于旧数据。
有关如何启用动态调试的更多信息。
首先,请确保您的内核配置中有CONFIG_DYNAMIC_DEBUG=y
。
假设我们想要在名称为 8250 的 built-in 模块中启用所有调试打印。为了实现这一点,我们简单地向内核命令行添加以下 8250.dyndbg=+p
.
如果相同的驱动程序被编译为可加载模块,我们可以将 options 8250 dyndbg
添加到 modprobe 配置或添加到 shell 命令行。手动,例如 modprobe 8250 dyndbg
.
Dynamic Debug 文档中描述了更多详细信息。
您可以在内核消息中找到 dev_err(...)
。顾名思义,dev_err(...)
消息是错误消息,所以如果执行到那个点,肯定会打印出来。 dev_dbg(...)
是在内核驱动程序代码中更广泛使用的调试消息,默认情况下不打印它们。所以你读到的关于 dynamic_debugging 的所有内容都适用于 dev_dbg(...)
。
动态调试工作有几个先决条件,下面的 1. 和 2. 是动态调试的一般先决条件。 3. 及以后是针对您的特定 driver/module/subsystem 并且可以是 .
- 动态调试支持必须在您的内核配置中
CONFIG_DYNAMIC_DEBUG=y
。你可以看看是不是这样zgrep DYNAMIC_DEBUG /proc/config.gz
- 必须安装 debugfs。您可以使用
sudo mount | grep debugfs
检查,如果不存在,您可以使用sudo mount -t debugfs /sys/kernel/debug
安装
- 参考dynamic_debugging并启用您感兴趣的特定file/function/line