引言
在一些常見的嵌入式系統(tǒng)的開發(fā)當中,硬件的調(diào)試接口是極其重要的,但是一些傳統(tǒng)的調(diào)試方法往往存在一些可能致命的問題。比如串口調(diào)試雖然簡單容易使用,但是實時性較差,不夠精確。單步執(zhí)行的話,雖然精確度高,但是又存在操作復雜的問題。傳統(tǒng)的調(diào)試方法往往受到速度、準確性和調(diào)試精度的限制。
為了解決這些問題,JTAG(聯(lián)合測試行動組,Joint Test Action Group)和SWD(Serial Wire Debug)作為兩種主要的調(diào)試協(xié)議,廣泛應(yīng)用于嵌入式開發(fā)中。它們提供了高效的硬件調(diào)試手段,不僅能夠?qū)崿F(xiàn)單步執(zhí)行、斷點設(shè)置、變量監(jiān)控等常規(guī)調(diào)試功能,還能夠深入底層硬件,進行更復雜的系統(tǒng)級調(diào)試。
JTAG 和 SWD
JTAG(聯(lián)合測試行動組)
大多說人可能聽過JTAG,并且用它給MCU或者FPGA燒錄過程序,或者對開發(fā)板進行過調(diào)試,JTAG 最初是為了解決硬件板級測試問題而提出的,它是一種標準化的調(diào)試接口,那什么是標準化的調(diào)試接口呢?比如說在PCB板上存在三種廠家的芯片,那如果想對三個芯片都進行測試的話就需要一個適應(yīng)所有芯片的代碼,會非常的龐大且單一性較強,所以才有了像JTAG這些標準化的調(diào)試接口。
JTAG 協(xié)議基于一個串行通信接口,由四個主要的信號線(上圖中的實線部分)和一個復位引腳組成(虛線部分)主要通過四個信號引腳進行數(shù)據(jù)傳輸:
· TDI(Test Data In):測試數(shù)據(jù)輸入,用于接收數(shù)據(jù)到目標設(shè)備。
· TDO(Test Data Out):測試數(shù)據(jù)輸出,用于輸出從目標設(shè)備獲取的數(shù)據(jù)。
· TMS(Test Mode Select):測試模式選擇,通過該信號來選擇不同的工作模式。
· TCK(Test Clock):測試時鐘,提供時鐘信號以驅(qū)動數(shù)據(jù)傳輸。
通過這四個信號,JTAG 能夠控制和訪問目標設(shè)備的各個寄存器、內(nèi)存以及執(zhí)行控制流程。
我們在使用JTAG進行調(diào)試時,一般不會在我們寫好的代碼當中去調(diào)用JTAG的接口,而是通過JTAG調(diào)試器來與硬件進行交互。一般會與我們的開發(fā)環(huán)境進行配合,比如我們常見的GDB調(diào)試工具。下面我舉了一個簡單的例子來使用JTAG進行調(diào)試。
下面我將對上面的C語言程序使用GDB和JTAG進行調(diào)試
1. 編譯程序,為了使用 GDB 和 JTAG 進行調(diào)試,我們需要編譯程序并生成調(diào)試信息。使用 -g 參數(shù)編譯程序,這樣 GDB 才能讀取符號信息
2. 假設(shè)已經(jīng)連接了一個 JTAG 調(diào)試器(如 ST-Link 或 J-Link),可以使用 OpenOCD 啟動調(diào)試服務(wù)器。這個服務(wù)器會通過 JTAG 接口與目標硬件通信。在 OpenOCD 啟動命令行中指定調(diào)試器接口和目標設(shè)備
執(zhí)行結(jié)束后會啟動OpenOCD,對GDB調(diào)試命令進行監(jiān)聽。
3. 啟動GDB并且加載好編譯的文件
4. 連接GDB到OpenOCD在 GDB 中,連接到運行 OpenOCD 的調(diào)試服務(wù)器
GDB 會連接到 OpenOCD,后者通過 JTAG 連接到目標設(shè)備。
1. 設(shè)置斷點并且調(diào)試
l 設(shè)置斷點:可以設(shè)置斷點在 main 函數(shù)或任何其他地方(例如,剛剛插入的 __asm("bkpt #0"))。
l break main:會在main函數(shù)的開頭設(shè)置一個斷點
l 運行程序:使用 continue 命令運行程序,GDB 會在斷點處暫停。
l 單步執(zhí)行:當程序在斷點處暫停時,可以單步執(zhí)行代碼:(step 進入函數(shù) next 執(zhí)行下一行,不進入函數(shù))
l 查看寄存器:可以查看 CPU 寄存器的內(nèi)容,例如查看程序計數(shù)器 PC(info registers)
l 查看變量值:還可以查看某個變量的值,例如查看 i(print i)
l 退出 GDB:調(diào)試結(jié)束后,你可以退出 GDB。
2. 調(diào)試器和JTAG的交互
l 當程序運行到 __asm("bkpt #0") 斷點時,JTAG 調(diào)試器會暫停程序的執(zhí)行,GDB 會接管控制。
l 你可以通過 GDB 調(diào)試命令來執(zhí)行單步調(diào)試、查看寄存器和內(nèi)存內(nèi)容、設(shè)置更多斷點等。
l TAG 在這個過程中負責與硬件進行交互,GDB 通過 JTAG 通道控制程序執(zhí)行。
以上就是JATG的基本使用方法。那下面我們再來說一下SWD
SWD(Serial Wire Debug)調(diào)試技術(shù)
SWD是我們在學習STM32過程中最常見的燒錄接口SWD是由ARM公司為其處理器(特別是Cortex系列)開發(fā)的一種串行調(diào)試接口。它的設(shè)計目的是為了在有限的引腳資源下提供高效、低功耗的調(diào)試解決方案,尤其適用于嵌入式應(yīng)用和資源受限的系統(tǒng)。
SWD是一個2線(或4線)接口,相比JTAG節(jié)省了許多硬件資源,典型的接口信號有:
l SWDIO(Serial Wire Debug Input/Output):串行數(shù)據(jù)輸入/輸出
l SWCLK(Serial Wire Clock):時鐘信號
l NRST(可選,復位信號):目標設(shè)備的復位信號
SWD提供了與JTAG類似的調(diào)試功能,但采用串行方式進行數(shù)據(jù)傳輸,相對占用更少的引腳。
如果想進行SWD的實際調(diào)試,只需要將上面示例中的JTAG更換成SWD即可
JTAG和SWD在系統(tǒng)調(diào)試中的應(yīng)用
以上示例就是JTAG和SWD的簡單使用,那在實際的應(yīng)用開發(fā)當中,這兩種調(diào)試方法我們應(yīng)該如何去選擇呢?這就需要了解一下兩種技術(shù)的優(yōu)缺點
首先,JTAG技術(shù)具有廣泛的硬件支持,很多嵌入式的芯片和處理器都提供了JTAG接口,JATG接口通常提供了豐富的調(diào)試功能,包括讀取和寫入寄存器、訪問內(nèi)存、硬件斷點等。因為JTAG提供了更多的控制和功能,所以更適用于比較復雜的嵌入式操作系統(tǒng)。但是由于它的并行性和較多的控制線,硬件實現(xiàn)會更加復雜。
SWD的硬件設(shè)計更為簡化,只需要少量的引腳,所以在資源受限的系統(tǒng)中更加容易執(zhí)行,但是提供的功能不如JTAG豐富。
那JTAG vs. SWD:如何選擇?
在選擇JTAG還是SWD時,應(yīng)考慮以下因素:
1、硬件支持
首先,檢查目標芯片是否支持所需的調(diào)試接口。如果芯片只支持其中一種接口,選擇已支持的接口是明智的。
2、性能需求
如果你需要更高的通信速度和較低的功耗,那么SWD可能是更好的選擇。但如果你需要豐富的調(diào)試功能,可能需要使用JTAG。
3、系統(tǒng)復雜性
對于較復雜的系統(tǒng),特別是涉及多個處理器核心或FPGA的系統(tǒng),JTAG通常更適用,因為它提供了更多的控制和功能。
4、成本考慮
考慮硬件成本和復雜性。SWD通常更簡單,因此在資源有限的系統(tǒng)中可能更經(jīng)濟實惠。
5、開發(fā)工具
確保你的開發(fā)工具和調(diào)試器支持你選擇的接口。大多數(shù)現(xiàn)代調(diào)試工具都同時支持JTAG和SWD。
結(jié)論
JTAG和SWD都是重要的嵌入式系統(tǒng)調(diào)試接口,各自具有優(yōu)勢和劣勢。選擇哪種接口取決于項目需求、硬件支持和性能要求。對于復雜的系統(tǒng),可能需要使用JTAG以獲得更多的控制和功能,而對于資源有限的系統(tǒng),SWD可能更適合。綜合考慮這些因素,可以幫助你做出明智的選擇,以便更有效地進行嵌入式系統(tǒng)開發(fā)和調(diào)試。