簡體   English   中英

使用gdb訪問命令行參數

[英]accessing command-line arguments with gdb

我在linux上使用gdb版本6.8-debian。 我一直很好奇c程序中的主要功能是如何被執行和在不同的地方玩耍,我了解到函數__libc_start_main對此負責。 __libc_start_main的參數包括:main的地址(就像我們從c中知道的那樣,路徑總是以argv [0]給出),next argc應該駐留在寄存器ESI中,而argv的下一個地址應該是在ECX。

為了解決這個問題,我制作了以下簡單程序cmdargs.c,它只是輸出start時給出的第一個命令行參數:

#include <stdio.h>
#include <stdlib.h>

int main (int argc, char *argv[])
{
    printf("%s: %s\n", "argv[1]", *++argv);
    return EXIT_SUCCESS;
}

現在我開始調試cmdargs並在main和__libc_start_main上設置斷點(從啟動gdb刪除的信息):

gdb cmdargs

(gdb) b main
Breakpoint 1 at 0x80483d2
(gdb) b __libc_start_main
Breakpoint 2 at 0xb7f3f5a8
(gdb) r qwerty

在這里我點擊了__libc_start_main中的斷點2,可以查看argc和argv [0]

(gdb) p $esi

(gdb) x/s *($ecx)

這按預期工作,但如何訪問第一個非隱式命令行參數“qwerty”? 我已經嘗試繼續在main處斷點並踩到,但argc和argv無法識別(為什么?)。 誰能告訴我發生了什么事?

Breakpoint 1, 0x080483d2 in main ()
(gdb) stepi
0x080483d5 in main () 
(gdb) p argc
No symbol "argc" in current context.
(gdb) p argv
No symbol "argv" in current context.
(gdb) 

是的,你的問題是缺少符號,不包括在編譯時。

要使用調試信息進行編譯:

$ gcc -g3 cmdargs.c -o cmdargs

然后:

$ gdb ./cmdargs
...
Reading symbols from ./cmdargs...done.
(gdb) b main
Breakpoint 1 at 0x400545: file cmdargs.c, line 6.
(gdb) r
Starting program: cmdargs 

Breakpoint 1, main (argc=1, argv=0x7fffffffdc28) at cmdargs.c:6
6       printf("%s: %s\n", "argv[1]", *++argv);
(gdb) p argc
$1 = 1
(gdb) p argv
$2 = (char **) 0x7fffffffdc28
(gdb) p *argv
$3 = 0x7fffffffe00c "/home/jcgonzalez/cmdargs"

看,現在您可以訪問符號(它們被識別)以及行號。 Let_Me_Be所示,您可以使用array [n]表示法訪問單個數組元素,但您也可以使用* array @ times表示法一次顯示所有命令行參數(包括[0] -ed)。 請注意,以下示例中的第一個參數是帶引號的字符串:

(gdb) set args "this is an argument" these are four more 
(gdb) r
Starting program: cmdargs "this is an argument" these are four more

Breakpoint 1, main (argc=6, argv=0x7fffffffdbd8) at cmdargs.c:6
6       printf("%s: %s\n", "argv[1]", *++argv);
(gdb) p argc
$4 = 6
(gdb) p *argv@argc                                    
$5 = {0x7fffffffdfe6 "/home/jcgonzalez/cmdargs", 0x7fffffffdfff "this is an argument", 0x7fffffffe012 "these", 0x7fffffffe017 "are", 0x7fffffffe01b "four", 
  0x7fffffffe020 "more"}
(gdb) p argv[1]
$6 = 0x7fffffffdfff "this is an argument"
(gdb) p argv[2]
$7 = 0x7fffffffe012 "these"

輸出看起來好像沒有足夠的debuging信息。 GDB不應該只打印地址而是打印行號。

(gdb) b main
Breakpoint 1 at 0x400543: file test.c, line 3.
(gdb) r test1 test2
Starting program: /home/simon/a.out test1 test2

Breakpoint 1, main (argc=3, argv=0x7fffffffdca8) at test.c:3
3               puts("blabla");
(gdb) print argc
$1 = 3
(gdb) print argv
$2 = (char **) 0x7fffffffdca8
(gdb) print argv[0]
$3 = 0x7fffffffe120 "/home/simon/a.out"
(gdb) print argv[1]
$4 = 0x7fffffffe132 "test1"
(gdb) print argv[2]
$5 = 0x7fffffffe138 "test2"
(gdb)

你應該將-g選項添加到gcc,這告訴它也要構建調試信息..

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM