2013-12-11 61 views
14

我在編寫內核時試圖調試我有的鏈接器問題。鏈接器腳本:調試策略?

的問題是,我有一個變量SCAN_CODE_MAPPING,我是無法使用 - 它顯示爲空或東西。我可以通過更改鏈接我的程序的方式來解決此問題,但我不知道爲什麼。

當我使用objdump查看生成的二進制文件時,變量的數據肯定存在,因此只有一些參考文件被破壞。

Here's a gist同時與連接器腳本和符號表的這兩個文件之間不同的部分。

什麼讓我困惑的是,這兩個符號表中都相同的符號,它們都是相同的長度,而且他們似乎包含正確的數據。我可以看到的唯一區別是它們的順序不同。

到目前爲止,我已經試過

  • 檢查SCAN_CODE_MAPPING存儲位置,以確保它擁有我希望的數據並沒有被置零
  • 檢查所有的符號同
  • 檢查所有符號的內容是相同的長度
  • 看着.data.rel.ro.local,以確保它具有數據的地址

一個可能的線索是這樣的警告:

warning: uninitialized space declared in non-BSS section `.text': zeroing

,我在這兩個破碎的和正確的情況下得到的。

接下來我應該嘗試什麼?

+0

投票關閉的調試幫助。 –

回答

3

您可以使用「readelf」得到一噸多的信息。

特別是,看看該程序標題:

readelf -l程序

你BSS部分比標準之一,這可能引起報警很大的不同。下面是默認的樣子我的系統上:

.bss   : 
    { 
    *(.dynbss) 
    *(.bss .bss.* .gnu.linkonce.b.*) 
    *(COMMON) 
    /* Align here to ensure that the .bss section occupies space up to 
     _end. Align after .bss to ensure correct alignment even if the 
     .bss section disappears because there are no input sections. 
     FIXME: Why do we need it? When there is no .bss section, we don't 
     pad the .data section. */ 
    . = ALIGN(. != 0 ? 64/8 : 1); 
    } 

如果輸入部分不會在你的鏈接腳本匹配任何鏈接器仍然有地方放置。確保你覆蓋了所有的輸入部分。

注意,有節和段之間的差。段由鏈接器使用,但程序加載器唯一看到的是段。文本段包含文本部分,但也包含其他部分。進入同一網段的部分必須相鄰。所以訂單確實很重要。

的RODATA部分通常是文本段後進入。這些文件在執行過程中都是隻讀的,並且在程序頭文件中會顯示一次,作爲讀取&執行權限的LOAD條目。該LOAD條目是文本段。

bss部分通常在數據部分之後。這些在執行過程中都是可寫的,並且會在程序頭文件中顯示一次,作爲LOAD條目,具有讀取&寫入權限。 LOAD條目是數據段。

如果更改順序,它會影響鏈接器生成程序標題的方式。在執行程序之前加載程序時使用程序頭文件,而不是段頭文件。確保在使用自定義鏈接腳本時檢查程序標題。

如果您可以提供關於您的實際症狀的更多細節,那麼它會更容易幫助。

+0

這不是我遇到的問題(我正在編寫內核,所以最終可執行文件的結構並不重要)。無論如何,有用的信息。 – jvns

5

這裏的問題原來是我正在編寫一個操作系統,只有12k的被加載,而不是整個事情。所以鏈接器腳本實際上工作正常。

我以前理解的二進制文件的主要工具是:

  • 納米
  • objdump的
  • readelf