2012-03-12 380 views
0

我優化OpenRISC C代碼,我想手動prereserve在寄存器中的一些計算值,僞代碼看起來像這樣:的內聯彙編使用寄存器

external loop 
    compute eight values (heavy calculations) 
    internal loop 
     use values computed above 

當我看着GCC ABI爲OpenRISC我看到兩組寄存器:被保存的和臨時的?我應該使用哪些寄存器來存儲這八個值?我的意思是,哪些寄存器可以放入內聯asm中的clobbered列表?

我需要努力註冊,因爲我們在自定義的OpenRISC上運行可執行文件。

回答

1

答案是:無論你喜歡什麼。

如果你使用callee-save寄存器,那麼編譯器會爲你保存它們(只要你標記它們被破壞)。

如果您使用臨時寄存器(a.k.a. caller-save),那麼編譯器將被強制保存它們,如果您進行函數調用。請注意,編譯器也傾向於將這些用於其他變量,所以如果你使用了保存調用者的函數,它將不得不使用callee-save來處理其他事情,所以它最終可能會產生同樣的變化。

在一天結束時,如果您正在進行繁重的計算,那麼在您開始之前保存一些寄存器堆棧並不會有什麼大不了的。

有些寄存器包含重要值(如堆棧指針),您不能覆蓋它們。其他的,比如GOT表格指針不那麼重要,編譯器會在你完成時恢復它的值(只要確保在這個過程中你不需要它)。

真的,雖然你不需要去解決它自己:編譯器可以爲您選擇寄存器:

int a, b, c; 

asm volatile ("whatever" : "=&w" (a), "=&w" (b), "=&w" (c)); 

不需要的變量,但他們必須分配寄存器,所以他們有效地保留任何你想要一個寄存器中的&表示「early-clobber」,這意味着它們不能像輸入寄存器那樣共享相同的寄存器(不是我的示例顯示了任何內容)。