2011-08-04 27 views
7

這是接近Using GCC to produce readable assembly?,但我在這裏的上下文是avr-gcc(和相應地,爲avr-objdump)爲愛特梅爾(雖然,我想它會適用於整個海灣合作委員會董事會)。GCC/objdump:生成可編譯/可構建的程序集(散佈在C/C++中)源代碼?

事情是,我有一個多個.c和.cpp文件的項目;最終被編譯成可執行文件,其名稱與'master'.cpp文件相同。在這個過程中,我可以以兩種方式獲得組件列表:

  • 我可以指示gcc發射組件列表源使用-S開關(參見Linux Assembly and Disassembly an Introduction);在這種情況下,我得到一個文件,用類似的內容:
     
    ... 
    loop: 
        push r14 
        push r15 
        push r16 
        push r17 
        push r28 
        push r29 
    /* prologue: function / 
    / frame size = 0 */ 
        ldi r24,lo8(13) 
        ldi r22,lo8(1) 
        call digitalWrite 
        rjmp .L2 
    .L3: 
        ldi r24,lo8(MyObj) 
        ldi r25,hi8(MyObj) 
        call _ZN16MYOBJ7connectEv 
    .L2: 
        ldi r24,lo8(MyObj) 
        ldi r25,hi8(MyObj) 
        call _ZN16MYOBJ11isConnectedEv 
    ... 
    

有沒有嘗試過,但我想這個代碼編譯/可建....

  • 我可以檢查最終的可執行文件並指示objdump使用-S開關發出彙編列表源代碼;在這種情況下,我得到一個文件,用類似的內容:
     
    ... 
    0000066a <init>: 
    void init() 
    { 
         // this needs to be called before setup() or some functions won't 
         // work there 
         sei(); 
        66a:  78 94   sei 
        66c:  83 b7   in  r24, 0x33  ; 51 
        66e:  84 60   ori  r24, 0x04  ; 4 
        670:  83 bf   out  0x33, r24  ; 51 
    ... 
    000006be <loop>: 
        6be:  ef 92   push r14 
        6c0:  ff 92   push r15 
        6c2:  0f 93   push r16 
        6c4:  1f 93   push r17 
        6c6:  cf 93   push r28 
        6c8:  df 93   push r29 
        6ca:  8d e0   ldi  r24, 0x0D  ; 13 
        6cc:  61 e0   ldi  r22, 0x01  ; 1 
        6ce:  0e 94 23 02  call 0x446 ; 0x446 
        6d2:  04 c0   rjmp .+8    ; 0x6dc 
        6d4:  8d ef   ldi  r24, 0xFD  ; 253 
        6d6:  94 e0   ldi  r25, 0x04  ; 4 
        6d8:  0e 94 25 06  call 0xc4a ; 0xc4a <_ZN16MYOBJ7connectEv> 
        6dc:  8d ef   ldi  r24, 0xFD  ; 253 
        6de:  94 e0   ldi  r25, 0x04  ; 4 
        6e0:  0e 94 21 06  call 0xc42 ; 0xc42 <_ZN16MYOBJ11isConnectedEv> 
    ... 
    

我曾嘗試建立這個代碼,它沒有失敗 - 它讀取「行號」爲標籤

顯然,這兩個列表(至少對於loop函數來說)表示相同的彙編代碼;除了:

  • gcc酮(應)編譯 - 在objdump一個確實
  • objdump一個包含所有的目錄稱爲功能,這可能在除了「主」其他文件中定義(例如,digitalWrite) - 的gcc一個確實
  • objdump一個含有原來的C/C++源極線與裝配「穿插」(但只是偶爾,並且似乎只對C文件) - 的gcc一個確實

因此,有一種方法來獲得的組件列表,這將是「編譯」,但是與所有在連接的功能,並且其中源C/C++代碼是(可能,其中適當)散佈爲註釋(所以它們不會干擾彙編文件的彙編)? (短編寫解析器爲objdump輸出,即:)

回答

1

添加選項-fverbose-asm到您的gcc命令行那裏。 (這是在gcc手冊中,但它在「代碼Gen選項」中有記錄)

+0

非常感謝你,@ Spudd86 - 剛剛嘗試過'-fverbose-asm'選項;然而,它並沒有「包含依賴關係」,也沒有將C/C++源代碼行逐字保存......它確實生成了「_options passed_」列表,並且它將開始記錄一些變量:'lds r24,MyObj \t; MyObj._isConnected,MyObj._isConnected' - 但我想我更感興趣的功能開始以某種方式分隔...再次感謝 - 歡呼! – sdaau

1

您所說的「依賴性」通常來自庫或單獨的目標文件,因此它們沒有源代碼 - 只是作爲二進制代碼鏈接到最終的可執行文件中。由於這樣的代碼沒有通過彙編器傳遞,所以你必須用其他方式來提取它 - 例如,使用objdump。

也許你應該告訴我們你真的想達到的目標,因爲我沒有看到這樣一個練習本身很多點。

+0

嗨@Igor Skochinsky,感謝您的評論!你是對的 - 但在AVR代碼的情況下,通常很多對象文件實際上都來自源文件。我所希望的是最終生成一個「合併」的程序集文件,我可以使用它生成與項目相同的ELF可執行文件 - 然後我打算在avr-gdb中使用此彙編列表進行調試(如目前,我似乎無法設置gdb,因此它在調試過程中捕獲了正確的源代碼行)。再次感謝 - 歡呼! – sdaau

+0

我想說用gdb修復調試應該更容易(希望),並且最終更正確的方法。 –

1

我已經能夠得到的最好的是使用-Wa,-ahl=outfile.s而不是-S。它不是可編譯的代碼,但是用於診斷目的的列表文件;編譯後的目標文件照常發出。

+0

非常感謝那@匿名懦夫 - 很高興知道這個選項!乾杯! – sdaau

相關問題