Linux 內(nèi)核日志級(jí)別與 dmesg 用法實(shí)戰(zhàn)指南
1. 內(nèi)核日志級(jí)別(Log Level)
Linux 內(nèi)核定義了 8 個(gè)日志級(jí)別(定義在 include/linux/kern_levels.h):
| 級(jí)別 | 宏定義 | 含義 | 說(shuō)明 |
|---|---|---|---|
| 0 | KERN_EMERG | 系統(tǒng)不可用 | 系統(tǒng)即將崩潰 |
| 1 | KERN_ALERT | 需要立即處理 | 必須立即采取行動(dòng) |
| 2 | KERN_CRIT | 嚴(yán)重錯(cuò)誤 | 硬件/軟件嚴(yán)重故障 |
| 3 | KERN_ERR | 錯(cuò)誤 | 一般錯(cuò)誤條件 |
| 4 | KERN_WARNING | 警告 | 可能出問(wèn)題的情況 |
| 5 | KERN_NOTICE | 正常但重要 | 正常但值得注意的信息 |
| 6 | KERN_INFO | 信息 | 一般性信息 |
| 7 | KERN_DEBUG | 調(diào)試 | 調(diào)試級(jí)別的信息 |
數(shù)字越小,優(yōu)先級(jí)越高。
2. 控制臺(tái)日志級(jí)別
內(nèi)核通過(guò) /proc/sys/kernel/printk 控制哪些消息輸出到控制臺(tái)。該文件包含 4 個(gè)值:
cat /proc/sys/kernel/printk # 輸出示例: 4 4 1 7 # | | | | # | | | +-- default_console_loglevel(新打開(kāi)控制臺(tái)的默認(rèn)級(jí)別) # | | +------- minimum_console_loglevel(控制臺(tái)最小允許級(jí)別) # | +------------ default_message_loglevel(printk 默認(rèn)消息級(jí)別) # +----------------- console_loglevel(當(dāng)前控制臺(tái)日志級(jí)別閾值)
只有級(jí)別值 < console_loglevel 的消息才會(huì)輸出到控制臺(tái)。
3. dmesg -n 命令
dmesg(display message)是用戶空間讀取內(nèi)核 ring buffer 的工具。其 -n 選項(xiàng)可以在運(yùn)行時(shí)動(dòng)態(tài)修改上述 console_loglevel 的值,從而控制哪些級(jí)別的內(nèi)核消息會(huì)輸出到控制臺(tái),而無(wú)需重啟系統(tǒng)或修改配置文件。
3.1 語(yǔ)法
sudo dmesg -n <level>
設(shè)置控制臺(tái)日志級(jí)別閾值。只有嚴(yán)格小于 level 的消息才會(huì)打印到控制臺(tái)。
3.2 常用場(chǎng)景
# 只顯示 KERN_EMERG (級(jí)別0) 的消息,幾乎屏蔽所有輸出 sudo dmesg -n 1 # 顯示 ERR 及以上 (級(jí)別 0-2) sudo dmesg -n 3 # 顯示 WARNING 及以上 (級(jí)別 0-3) sudo dmesg -n 4 # 顯示所有消息(包括 DEBUG) sudo dmesg -n 8 # 恢復(fù)系統(tǒng)默認(rèn)(通常是 4 或 7) sudo dmesg -n 7
3.3 等效方法
# 方法1: 通過(guò) /proc 接口 echo 1 | sudo tee /proc/sys/kernel/printk # 方法2: 通過(guò) sysctl sudo sysctl -w kernel.printk="1 4 1 7"
4. 實(shí)際應(yīng)用場(chǎng)景
場(chǎng)景1:內(nèi)核死循環(huán)打印
當(dāng)內(nèi)核驅(qū)動(dòng)(如 amdgpu)因 bug 持續(xù)打印日志刷屏?xí)r:
# 1. 立即止住控制臺(tái)輸出 sudo dmesg -n 1 # 2. 將日志重定向到文件分析 sudo dmesg > /tmp/kern_dump.log # 3. 嘗試恢復(fù)驅(qū)動(dòng)狀態(tài) sudo modprobe -r amdgpu && sudo modprobe amdgpu # 4. 如果模塊卸載失敗 sudo fuser -k /dev/kfd sudo fuser -k /dev/dri/* sudo modprobe -r amdgpu # 5. 恢復(fù)日志級(jí)別 sudo dmesg -n 7
場(chǎng)景2:調(diào)試時(shí)開(kāi)啟詳細(xì)日志
# 開(kāi)啟 amdgpu 驅(qū)動(dòng)動(dòng)態(tài)調(diào)試 echo 'module amdgpu +p' | sudo tee /sys/kernel/debug/dynamic_debug/control # 同時(shí)確??刂婆_(tái)能看到 DEBUG 消息 sudo dmesg -n 8
場(chǎng)景3:只關(guān)注錯(cuò)誤信息
# 只看 ERR 及以上級(jí)別 sudo dmesg -n 4 # 過(guò)濾 dmesg 中的錯(cuò)誤 dmesg --level=err,crit,alert,emerg
dmesg 其他常用選項(xiàng)
# 持續(xù)監(jiān)聽(tīng)內(nèi)核消息(類(lèi)似 tail -f) sudo dmesg -w # 帶時(shí)間戳顯示 dmesg -T # 帶級(jí)別標(biāo)記顯示 dmesg --decode # 清空 ring buffer sudo dmesg -C # 只顯示特定級(jí)別 dmesg --level=err dmesg --level=warn,err # 顯示最后 N 行 dmesg | tail -50
5. Ring Buffer 機(jī)制與溢出處理
5.1 Ring Buffer 基本概念
內(nèi)核日志存儲(chǔ)在一個(gè)固定大小的環(huán)形緩沖區(qū)(ring buffer)中。當(dāng) buffer 滿時(shí),內(nèi)核自動(dòng)覆蓋最舊的消息(FIFO 循環(huán)寫(xiě)入),這是設(shè)計(jì)行為,不需要手動(dòng)干預(yù)。
5.2 查看 Ring Buffer 大小
# 查看當(dāng)前 ring buffer 大小 dmesg | grep "log_buf_len" # 或通過(guò) sysfs(如果可用) cat /sys/kernel/debug/tracing/buffer_size_kb
5.3 增大 Ring Buffer(防止日志丟失)
# 啟動(dòng)時(shí)通過(guò) grub 參數(shù)設(shè)置(永久生效) # 編輯 /etc/default/grub,在 GRUB_CMDLINE_LINUX 中添加: log_buf_len=4M # 然后更新 grub sudo update-grub
5.4 日志持久化方案
Ring buffer 中的日志重啟后丟失,且可能被覆蓋。以下方法可持久化保存:
# 方法1: 通過(guò) journald 持久化(systemd 系統(tǒng)) # 確認(rèn)配置: /etc/systemd/journald.conf # Storage=persistent # 查看歷史內(nèi)核日志(包括之前的啟動(dòng)) journalctl -k journalctl -k -b -1 # 上一次啟動(dòng)的內(nèi)核日志 # 方法2: 持續(xù)寫(xiě)入文件(實(shí)時(shí)捕獲,不受 ring buffer 覆蓋影響) sudo cat /dev/kmsg > /tmp/kmsg_full.log & # 方法3: 使用 dmesg -w 持續(xù)監(jiān)聽(tīng)并保存 sudo dmesg -wT > /tmp/kern_continuous.log &
5.5dmesg與/dev/kmsg的區(qū)別
| dmesg | /dev/kmsg | |
|---|---|---|
| 數(shù)據(jù)來(lái)源 | ring buffer 快照 | 實(shí)時(shí)流式讀取 |
| 讀取方式 | 一次性輸出當(dāng)前所有內(nèi)容 | 持續(xù)讀取新消息 |
| 舊消息 | 包含 ring buffer 中所有現(xiàn)存消息 | 只讀取打開(kāi)后的新消息 |
| 典型用法 | dmesg > log.txt | cat /dev/kmsg > log.txt & |
5.6 關(guān)鍵結(jié)論
- Ring buffer 溢出是正常行為,不需要也無(wú)法阻止
- 關(guān)鍵調(diào)試日志應(yīng)通過(guò)
/dev/kmsg或dmesg -w實(shí)時(shí)持久化捕獲 - 不要依賴 ring buffer 保留完整歷史,大量日志輸出(如死循環(huán)打?。?huì)快速覆蓋有用信息
6. 注意事項(xiàng)
dmesg -n只影響控制臺(tái)輸出,不影響內(nèi)核 ring buffer 中的日志記錄- 消息始終可通過(guò)
dmesg命令或/dev/kmsg讀取 - systemd 系統(tǒng)中,
journalctl -k也可查看內(nèi)核日志 - 重啟后日志級(jí)別恢復(fù)默認(rèn),如需持久化可修改
/etc/sysctl.conf:kernel.printk = 4 4 1 7
- Ring buffer 滿時(shí)自動(dòng)覆蓋舊消息,調(diào)試時(shí)應(yīng)提前用
/dev/kmsg或dmesg -w持久化捕獲
到此這篇關(guān)于Linux 內(nèi)核日志級(jí)別與 dmesg 用法實(shí)戰(zhàn)指南的文章就介紹到這了,更多相關(guān)Linux 內(nèi)核日志級(jí)別內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
開(kāi)發(fā)者常用及實(shí)用Linux Shell命令備忘錄(小結(jié))
這篇文章主要介紹了開(kāi)發(fā)者常用及實(shí)用Linux Shell命令備忘錄(小結(jié)),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-11-11
shell腳本declare命令的用法詳解(聲明變量的屬性和類(lèi)型)
這篇文章主要介紹了shell腳本declare命令用法(聲明變量的屬性和類(lèi)型,declare?命令在一般的腳本編寫(xiě)中并不常用,大多數(shù)情況下直接使用簡(jiǎn)單的變量賦值語(yǔ)句即可滿足需求,需要的朋友可以參考下2023-06-06
nginx 下安裝配置 phpadmin報(bào)錯(cuò)的解決方法
下面小編就為大家?guī)?lái)一篇nginx 下安裝配置 phpadmin報(bào)錯(cuò)的解決方法。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-02-02
很實(shí)用的Linux 系統(tǒng)運(yùn)維常用命令及常識(shí)(超實(shí)用)
作為L(zhǎng)inux運(yùn)維,需要了解Linux操作系統(tǒng)的基本使用和管理知識(shí),下面腳本之家小編給大家介紹下Linux運(yùn)維需要掌握的命令,想成為L(zhǎng)inux運(yùn)維的朋友可以來(lái)學(xué)習(xí)一下2016-10-10
jenkins?pipeline中獲取shell命令的標(biāo)準(zhǔn)輸出或者狀態(tài)的方法小結(jié)
這篇文章主要介紹了jenkins?pipeline中獲取shell命令的標(biāo)準(zhǔn)輸出或者狀態(tài),工作中需要獲取shell?命令的執(zhí)行狀態(tài),返回0或者非0,本文給大家介紹的非常詳細(xì),需要的朋友可以參考下2024-02-02
shell參數(shù)換行與shell輸出換行的方法實(shí)例
這篇文章主要給大家介紹了關(guān)于shell參數(shù)換行與shell輸出換行的方法實(shí)例,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2023-02-02

