當我們調試一個較複雜問題時,比較難以定位問題,需要嘗試多次設定斷點,多次 continue,多次查看變 量值等,有時,需要設定一些特殊的調試變數等等。這個過程,往往需要多次重啟調試器,也重新開始這些調 試命令。如果調試不支援反向調試,或是反向調試效能較差時,記錄與調試指令碼的配合使用將簡化這樣的 過程,下面以 zOS USS DBX 為例,我們一起來看看如何使用。同時,這樣的調試指令碼將有會成為自己或其他 初次使用 dbx 使用者的參考。
當我們在調試一個較為複雜的問 題時,可能會比較難以定位,需要嘗試多次的設定斷點,多次的continue,多次的查看變數值等操作。有時, 還需要設定一些特殊的調試變數。這個過程往往需要多次重啟調試器,一遍又一遍的執行這些調試命令。這時 ,如果調試器不支援反向調試,或是反向調試效能較差時,上面的過程就淪落為一系列繁瑣,重複性的操作。 手酸了吧,敲累了吧,蒙圈了吧,下面給大家介紹一種利用記錄與調試指令碼相互配合的方法來解放我們可 憐的雙手和大腦。以 zOS USS DBX 為例,我們一起來看看我們的操作將怎樣得以簡化。同時,這種方法對於 未來類似的調試工作或者初次使用 dbx 的使用者也具有參考價值。
1. 我們以用dbx調試main程式為例進 行說明,下面列出的是調試過程,在此期間我們設定了斷點和調試變數。在調試的最後,我們用 history 命 令得到所有執行的 dbx subcommands。注意咯,黃色的部分是我敲入的用於偵錯工具的dbx subcommand,其它 部分是dbx的輸出。
dbx main
/u/chenxl/example-dbx >> dbx main # 啟動dbx調試main
(dbx64) stop in main # 在main()處設定斷點
[1] stop in 'int main(int argc, unsigned char **argv)'
(dbx64) set $listwindow=20 # 將預設顯示行數10改為20
(dbx64) set $repeat # 設定repeat,enter後,將重複上次的 dbx subcommand
(dbx64) set $catchbp=1 # 執行next/step過程,如果遇到斷點,將觸發斷點,並停下來
(dbx64) run # 設定好調試變數後,let’s go
[1] stopped in main at line 16 in file "main.c" ($t2)
16 int main(int argc, char *argv[])
(dbx64) list # 顯示20行源碼
17 {
18 volatile int ti = 0;
19
20 if (argc > 2) {
21 x = atoi(argv[1]);
22 if (argc > 3) {
23 y= atoi(argv [2]);
24 }
25 }
26
27 ti = bbb();
28 for( ti = 0; ti < 50; ti++) {
29 aaa();
30 }
31 if (x == 4) {
32 y = bbb();
33 }
34 else {
35 y = ccc(x,y);
36 }