2012-03-16 145 views
1

我在使用某些內聯彙編代碼時遇到了問題。我試圖從本地靜態數組中將項目加載到ARM平臺上的寄存器中。不幸的是,我不知道如何告訴GCC它應該傳遞數組上的指針來註冊。該寄存器將用於間接訪問數組。在gcc內聯彙編程序(ARM)中使用數組

// should return argv[1] 
int test() { 
    int argv[4] = {4, 3, 2, 1}; 
    int out; 

    __asm__ volatile (
     "ldr r0, %[ARGV]" "\n\t" 
     "mov r1, #4" "\n\t" 
     "ldr r2, [r0, r1]" "\n\t" 
     "mov %[OUT], r2" 
     : [OUT] "=r" (out) 
     : [ARGV] "m" (argv) // <==== i don't know which constraint put here :/ 
     : "r0", "r1", "r2" 
    ); 

    return out; 
} 

現在GCC拋出錯誤,我不知道如何解決它:

Assembler messages: 
Error: invalid offset, value too big (0xFFFFFFFC) 

THX

編輯:我已經與Android NDK(ARM-Linux的androideabi-編譯它G ++)

+0

這個組裝,鏈接和運行良好使用鏗鏘。不知道發生了什麼事。你確定它在這個代碼中,它是錯誤的? – mattjgalloway 2012-03-16 10:21:06

+0

我忘了告訴我用Android NDK編譯它(arm-linux-androideabi-g ++) – zdenek 2012-03-16 10:28:34

+0

如果你將'argv'的約束設置爲'「rm」',它是否適合你? – mattjgalloway 2012-03-16 10:35:00

回答

1

我認爲它應該像這樣工作:

[ARGV] "r" (argv) 

這就是說「將數組的地址加載到寄存器中」。

+0

是的,你是對的。我用'MOV'替換'LDR'指令並使用'r'約束,現在它工作正常。謝謝。 – zdenek 2012-03-16 14:40:57

1

您不需要將ARGV或OUT移入/移出寄存器,這就是寄存器約束爲您處理的內容。

"mov r1, #4\n\t" 
"ldr %[OUT], [%[ARGV], r1]\n\t" 
: [OUT] "=r" (out) 
: [ARGV] "r" (argv) 
: "r1" 

注:這段代碼時過高的優化設置編譯有問題。 (我不知道如何解決這個問題,除了:使用-O0)