目錄
#1、簡介(基於s3c2440 linux)" >#1、簡介(基於s3c2440 linux)
2、透過指令cat /proc/sys/kernel/printk查看等級設定:" >2、透過指令cat /proc/sys/kernel/printk查看等級設定:
3、修改等級配置:" >3、修改等級配置:
4、printk函數記錄的名稱及使用" >4、printk函數記錄的名稱及使用
5、串列埠與printk函數的關係:" >5、串列埠與printk函數的關係:
首頁 系統教程 Linux Linux核心中的偵錯輸出函數:printk詳解

Linux核心中的偵錯輸出函數:printk詳解

Feb 14, 2024 pm 08:33 PM
linux linux教程 linux系統 linux指令 shell腳本 嵌入式linux linux入門 linux學習

printk是Linux核心中最常用的偵錯函數之一,它用來向內核緩衝區或控制台輸出偵錯訊息,如變數的值,函數的執行流程,錯誤的原因等。 printk的優點是簡單易用,不需要額外的設備或驅動。 printk的實作涉及到核心緩衝區,日誌等級,格式化字串等概念。在本文中,我們將介紹Linux核心調試技術之printk的原理和方法,並舉例說明它們的使用方法和注意事項。

Linux核心中的偵錯輸出函數:printk詳解

#1、簡介(基於s3c2440 linux)

在內核偵錯技術之中,最簡單的就是printk的使用了,它的用法和C語言應用程式中的printf使用類似,在應用程式中依賴的是stdio.h中的函式庫,而在linux核心中沒有這個函式庫,所以在linux核心中,使用這個printk就要對核心的實作有一定的了解。

printf和printk的差別:printk會在開頭處加上””樣式的字符,N的範圍是0~7,表示這個資訊的等級。

當printk(“”…);中的n

在核心檔案中Printk.c (kernel) 初始化這個console_loglevel 的等級為7.

/* printk's without a loglevel use this.. */
#define DEFAULT_MESSAGE_LOGLEVEL 4 /* KERN_WARNING */

/* 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
 */int console_printk[4] = {
    DEFAULT_CONSOLE_LOGLEVEL,    /* console_loglevel */
    DEFAULT_MESSAGE_LOGLEVEL,    /* default_message_loglevel */
    MINIMUM_CONSOLE_LOGLEVEL,    /* minimum_console_loglevel */
    DEFAULT_CONSOLE_LOGLEVEL,    /* default_console_loglevel */
};
登入後複製

2、透過指令cat /proc/sys/kernel/printk查看等級設定:

## cat /proc/sys/kernel/printk
7 4 1 7

其中的 7 4 1 7,分別對應與:console_loglevel、default_message_loglevel、minimum_console_loglevel、default_console_loglevel

3、修改等級配置:

#echo “1 4 1 7”>/proc/sys/kernel/printk 改變這四個值,當被console_loglevel設定為1的時候,所有的偵錯資訊都會被印出來。

4、printk函數記錄的名稱及使用

在核心檔案:Kernel.h (include\linux) 定義了0~7這8個等級的名稱

#define   KERN_EMERG   ""    /* system is unusable */
#define    KERN_ALERT    ""  
  /* action must be taken immediately */
#define    KERN_CRIT     ""    /* critical
 conditions */
#define    KERN_ERR      ""    /* error conditions */
#define   
 KERN_WARNING  ""    /* warning conditions */
#define    KERN_NOTICE   ""  
  /* normal but significant condition*/
#define    KERN_INFO     ""   
 /* informational*/
#define    KERN_DEBUG    ""    /* debug-level messages 
*/
#define console_loglevel      (console_printk[0])
#define 
default_message_loglevel (console_printk[1])
#define minimum_console_loglevel 
(console_printk[2])
#define default_console_loglevel (console_printk[3])
登入後複製

使用printk:

① printk(KERN_WARNING"there is a warning here!\n");//注意,中间没有逗号间隔。

② printk(KERN_DEBUG"%s %s %d\n", __FILE__, __FUNCTION__, __LINE__);
登入後複製

在①和②中,我們需要查看緩衝區log_buf中的數據,才能看到列印出來的資訊。需要使用指令 #dmesg

#``# dmesg``Linux version 2.6.22.6 (book@book-desktop) (gcc version 3.4.5) #19 Thu
 Dec 8 14:06:03 CST 2016``CPU: ARM920T
 [41129200] revision 0 (ARMv4T), cr=c0007177``Machine: SMDK2440``Memory policy: 
ECC disabled, Data cache writeback``On node 0 totalpages: 16384`` ``DMA zone: 128 
pages used ``for` `memmap`` ``DMA zone: 0 pages reserved`` ``DMA zone: 16256 pages,
 LIFO batch:3`` ``Normal zone: 0 pages used ``for` `memmap``CPU S3C2440A (id 0x32440001)................................
登入後複製

也可以使用 cat /proc/kmsg& 後台運行,即時列印出偵錯資訊。在②中,__FILE__, FUNCTION, __LINE__分別對應的是那個文件,那個函數,第幾行。非常實用。

# cat /proc/kmsg&``# ./firstdrvtest on``/work/LinuxDrives/20.printk_debug/first_drv.c
 first_drv_open 23``/work/LinuxDrives/20.printk_debug/first_drv.c first_drv_open 25``
/work/LinuxDrives/20.printk_debug/first_drv.c first_drv_open 27``# ./firstdrvtest off`
`/work/LinuxDrives/20.printk_debug/first_drv.c first_drv_open 23``/work/LinuxDrives/
20.printk_debug/first_drv.c first_drv_open 25``/work/LinuxDrives/20.printk_debug
/first_drv.c first_drv_open 27
登入後複製

5、串列埠與printk函數的關係:

#
printk
    vprintk
        vscnprintf //先把输出信息放入临时BUFFER
                // Copy the output into log_buf.
                // 把临时BUFFER里的数据稍作处理,再写入log_buf
                // 比如printk("abc")会得到"abc", 再写入log_buf
                // 可以用dmesg命令把log_buf里的数据打印出来重现内核的输出信息

        // 调用硬件的write函数输出
        release_console_sem    
            call_console_drivers
          //从log_buf得到数据,算出打印级别
                _call_console_drivers
                    if ((msg_log_level write //con是console_drivers链表中的项,对用具体的输出函

数 在drives/serial/s3c2410.c中查看

在该函数中注册一个console结构体
static void s3c24xx_serial_console_write(struct console *co, const char *s,
unsigned int count)
{
uart_console_write(cons_uart, s, count, s3c24xx_serial_console_putchar);
}
登入後複製

串口輸出函數,會呼叫s3c24xx_serial_console_putchar函數

static int s3c24xx_serial_initconsole(void)
{
    ...........................
    register_console(&s3c24xx_serial_console);
    return 0;
}
static struct console s3c24xx_serial_console =
{
.name = S3C24XX_SERIAL_NAME,//这个宏被定义为:TTYSAC
.device = uart_console_device, //init进程,用户程序打开/dev/console的时候会调用
.flags = CON_PRINTBUFFER,//打印还没有初始化化console前保存在log_buf里面的数据
.index = -1,//选择那个串口,由uboot中的命令决定
.write = s3c24xx_serial_console_write,//控制台输出函数
.setup = s3c24xx_serial_console_setup //串口设置函数
}; 
登入後複製

這個函數和硬體相關,讀取暫存器,看資料是否被傳送完成,最後將資料一個位元組一個位元組的寫入暫存器,s3c2440的串列控制器會自動把資料送出去

static void s3c24xx_serial_console_putchar(struct uart_port *port, int ch)

{
unsigned int ufcon = rd_regl(cons_uart, S3C2410_UFCON);
while (!s3c24xx_serial_console_txrdy(port, ufcon))
barrier();
wr_regb(cons_uart, S3C2410_UTXH, ch);
}
登入後複製

uboot的console=ttySAC0如果在linux中被辨識出來是串口0的,在/kernel/printk.c中有一下程式碼,

__setup("console=", console_setup);

static int __init console_setup(char *str)
{
........
  add_preferred_console(name, idx, options);
} 
登入後複製

核心開始執行時,會發現「console=…」的命令列參數時候,就會呼叫console_setup函數進行資料解析,對於命令列參數」console=ttySAC0″,會解析出:裝置名稱(name)為ttySAC,索引index為0,這些資訊被保存在類型為console_cmdline、名稱為console_cmdline的全域數組中(注意:數組名稱和數組的類型相同)

在後面的register_console(&s3c24xx_serial_console);的時候,會將s3c24xx_serial_console結構和console_cmdline數組中的設備進行比較。

①解析出來的name為S3C24XX_SERIAL_NAME 既“ttySAC”,而console_cmdline中的指令中的name也為“ttySAC”

②s3c24xx_serial_console結構體中的索引index為-1,表示使用命令列參數「console=ttySAC0」中的索引,index = 0

Through this article, we have learned about the principles and methods of printk, the Linux kernel debugging technology, which can be used to debug and output the kernel. We should choose the appropriate method based on actual needs and follow some basic principles, such as using the correct log level, using the correct format string, using the correct output function, etc. Printk is one of the simplest and most effective debugging functions in the Linux kernel. It can realize feedback and monitoring of the kernel, and can also improve the maintainability and scalability of the kernel. I hope this article can be helpful and inspiring to you.

以上是Linux核心中的偵錯輸出函數:printk詳解的詳細內容。更多資訊請關注PHP中文網其他相關文章!

本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

Video Face Swap

Video Face Swap

使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

<🎜>:泡泡膠模擬器無窮大 - 如何獲取和使用皇家鑰匙
3 週前 By 尊渡假赌尊渡假赌尊渡假赌
北端:融合系統,解釋
3 週前 By 尊渡假赌尊渡假赌尊渡假赌
Mandragora:巫婆樹的耳語 - 如何解鎖抓鉤
3 週前 By 尊渡假赌尊渡假赌尊渡假赌

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發環境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

熱門話題

Java教學
1664
14
CakePHP 教程
1423
52
Laravel 教程
1321
25
PHP教程
1269
29
C# 教程
1249
24
Linux體系結構:揭示5個基本組件 Linux體系結構:揭示5個基本組件 Apr 20, 2025 am 12:04 AM

Linux系統的五個基本組件是:1.內核,2.系統庫,3.系統實用程序,4.圖形用戶界面,5.應用程序。內核管理硬件資源,系統庫提供預編譯函數,系統實用程序用於系統管理,GUI提供可視化交互,應用程序利用這些組件實現功能。

git怎麼查看倉庫地址 git怎麼查看倉庫地址 Apr 17, 2025 pm 01:54 PM

要查看 Git 倉庫地址,請執行以下步驟:1. 打開命令行並導航到倉庫目錄;2. 運行 "git remote -v" 命令;3. 查看輸出中的倉庫名稱及其相應的地址。

notepad怎麼運行java代碼 notepad怎麼運行java代碼 Apr 16, 2025 pm 07:39 PM

雖然 Notepad 無法直接運行 Java 代碼,但可以通過借助其他工具實現:使用命令行編譯器 (javac) 編譯代碼,生成字節碼文件 (filename.class)。使用 Java 解釋器 (java) 解釋字節碼,執行代碼並輸出結果。

sublime寫好代碼後如何運行 sublime寫好代碼後如何運行 Apr 16, 2025 am 08:51 AM

在 Sublime 中運行代碼的方法有六種:通過熱鍵、菜單、構建系統、命令行、設置默認構建系統和自定義構建命令,並可通過右鍵單擊項目/文件運行單個文件/項目,構建系統可用性取決於 Sublime Text 的安裝情況。

laravel安裝代碼 laravel安裝代碼 Apr 18, 2025 pm 12:30 PM

要安裝 Laravel,需依序進行以下步驟:安裝 Composer(適用於 macOS/Linux 和 Windows)安裝 Laravel 安裝器創建新項目啟動服務訪問應用程序(網址:http://127.0.0.1:8000)設置數據庫連接(如果需要)

Linux的主要目的是什麼? Linux的主要目的是什麼? Apr 16, 2025 am 12:19 AM

Linux的主要用途包括:1.服務器操作系統,2.嵌入式系統,3.桌面操作系統,4.開發和測試環境。 Linux在這些領域表現出色,提供了穩定性、安全性和高效的開發工具。

git軟件安裝 git軟件安裝 Apr 17, 2025 am 11:57 AM

安裝 Git 軟件包括以下步驟:下載安裝包運行安裝包驗證安裝配置 Git安裝 Git Bash(僅限 Windows)

VSCode怎麼用 VSCode怎麼用 Apr 15, 2025 pm 11:21 PM

Visual Studio Code (VSCode) 是一款跨平台、開源且免費的代碼編輯器,由微軟開發。它以輕量、可擴展性和對眾多編程語言的支持而著稱。要安裝 VSCode,請訪問官方網站下載並運行安裝程序。使用 VSCode 時,可以創建新項目、編輯代碼、調試代碼、導航項目、擴展 VSCode 和管理設置。 VSCode 適用於 Windows、macOS 和 Linux,支持多種編程語言,並通過 Marketplace 提供各種擴展。它的優勢包括輕量、可擴展性、廣泛的語言支持、豐富的功能和版

See all articles