2010-12-14 56 views
2

我想得到一個變量的地址並由4096(它對應於它的內存頁面的地址)來代替。由於這一點是可以離線我做了一件看起來像這樣(v是可變的,v第應當包含其頁面的地址)來計算:不能在Gnu AS表達式中使用'&'運算符

.data 
    v:  .zero 0x100 
    vpage: .long v & 0xfffff000 

試圖編譯與x86彙編結果在這個文件出現以下錯誤:

test.S: Assembler messages: 
test.S:3: Error: invalid sections for operation on `v' and `L0' 

GAS爲什麼拒絕計算這個值?現在奇怪的部分:用「+」代替'&',代碼將被編譯,地址甚至可以在鏈接後正確計算。任何暗示這種行爲的原因或如何解決這個問題都是非常受歡迎的。

+0

氣體通常用作後端彙編程序。編譯器已經評估過所有常量表達式 – 2010-12-14 21:14:25

+0

@Marco在這種情況下,我想我能做的最好的辦法是切換到NASM或YASM ... – Gnurou 2010-12-16 03:07:19

+0

對於非平凡的數量:是的。或者使用編譯器內聯彙編器,並讓你的編譯器修復它。 – 2010-12-17 13:07:06

回答

6

問題在於,GAS生成將由鏈接器處理的目標文件。雖然GAS支持按位與運算,但絕對地址無法實現。它們可能會被鏈接器更改,因此GAS必須生成只支持有限操作的重定位條目(主要是抵消)。如果您可以將您的絕對地址轉換爲(本地)相對地址,則GAS可在裝配時間內對其進行計算。否則,你將不得不在運行時從代碼中完成。

+0

很好的答案。這個問題很容易通過調用gcc而不是as來使用C預處理器來解決,但是你讓我明白了這種行爲的原因。謝謝! – Gnurou 2011-02-22 04:10:55

0

在Intel語法,您可以使用_AND_OR_NOT_SHL_SHR或者其他人做到這一點。這也可能在GNU的彙編程序中起作用。

+0

不幸的是GAS不認識這些。 – Gnurou 2010-12-16 03:06:28