2010-02-12 56 views
0

我在寫一個名爲absD的函數,它返回它的參數的絕對值。 我不想使用任何預定義的功能。現在,當我嘗試編譯它時,我得到一個解析錯誤。double的絕對值

我想要所有我必須做的事情來獲得雙倍的絕對值是改變符號位?這是我所

#include <stdio.h> 
#include <stdlib.h> 

#define PRECISION 3 

double absD (double n) 
{ 

asm(" fld  %eax \n" 
    " movl $0x7FFFFFFFFFFFFFFF, %eax \n"  
    " pop  %eax  \n" 

    ); 

return n; 


} 

int main (int argc, char **argv) 
{ 
double n = 0.0; 

printf("Absolute value\n"); 
if (argc > 1) 
    n = atof(argv[1]); 

printf("abs(%.*f) = %.*f\n", PRECISION, n, PRECISION, absD(n)); 

return 0; 
} 

我固定的花括號.. 我得到的錯誤是

~ $ gc a02 
gcc -Wall -g a02.c -o a02 
/tmp/ccl2H7rf.s: Assembler messages: 
/tmp/ccl2H7rf.s:228: Error: suffix or operands invalid for `fld' 
/tmp/ccl2H7rf.s:229: Error: missing or invalid immediate expression `0x7FFFFFFFF 
FFFFFFF' 
~ $ 
+1

什麼是編譯錯誤? – 2010-02-12 01:34:50

+0

而錯誤是...? – GManNickG 2010-02-12 01:35:05

+4

科裏希望*你*編譯它,並將錯誤報告給他,並在完成後打嗝。 – 2010-02-12 01:40:43

回答

1

你需要做的是在組裝?這是一項家庭作業要求,還是你在尋找非常高的性能?

這不使用任何預定義的功能:

double absD(double n) 
{ 
    if (n < 0.0) 
     n = -n; 

    return n; 
} 
+2

return(n <0.0)? -n:n; – pm100 2010-02-12 02:06:10

+1

這是一項家庭作業。我需要在裝配中這樣做。我不想讓別人爲我做。我只需要一些指導 – Steller 2010-02-12 02:21:33

+2

' #define absD fabs' – kennytm 2010-02-12 19:56:01

1

我不是專家,但它看起來像你使用(打開的裝配體塊和}結束它。你可能應該使用一個或另一個,而不是不一致。

1
asm(" fld  %eax \n" 
" movl $0x7FFFFFFFFFFFFFFF, %eax \n"  
" pop  %eax  \n" 

}; 

注意分號前的曲線支架。

+0

嘿,我修復了大括號併發布了新的錯誤信息 – Steller 2010-02-12 02:08:40

1

取決於你想如何治療-0.0,你可以使用C99/POSIX(2004)的signbit()函數。

#include <math.h> 

double absD (double x) 
{ 
    if (signbit(x)) { 
#ifdef NAIVE 
     return 0.0 - x; 
#else 
     return x &= 0x7FFFFFFFFFFFFFFF; 
#endif 
    } else { 
     return x; 
    } 
} 

但坦率地說,如果你使用標準C庫(libc)ATOF和printf,我不明白爲什麼不使用fabs()是可取的。因爲你也可以在C中進行正常的位操作。

當然,如果你正在使用程序集,爲什麼不使用fchs op呢?

+1

這是一項家庭作業。我需要在裝配中這樣做。我不想讓別人爲我做。我只需要一些指導就可以做什麼。 – Steller 2010-02-12 02:22:18

+0

然後它應該被標記爲HOMEWORK。 – mctylr 2010-02-12 02:43:17

1

你的彙編代碼有錯誤,彙編代碼給你完全合理的錯誤信息。

  • 您不能加載從%eax中浮點值直接 - 操作數必須是一個地址,從

  • 加載你不能有不適合在常量文本32位。

+0

那麼我如何加載浮點? – Steller 2010-02-12 02:49:58

1

浮點數的符號只是高位,所以您只需清除最高位。

如果你必須在彙編中做到這一點,那麼在我看來,你會更好地使用整數而不是浮點指令。您無法對浮點寄存器執行按位操作。如果處理器沒有8字節的整型寄存器,那麼不需要將整個8字節值加載到任何寄存器中,只需要在高字節(或整型)上操作即可。

0

/tmp/ccl2H7rf.s:228: Error: suffix or operands invalid for `fld'

fld需要操作數在內存中。把它放在內存中,即堆棧,並提供地址。

/tmp/ccl2H7rf.s:229: Error: missing or invalid immediate expression `0x7FFFFFFFF FFFFFFF'

EAX不能保存多於32位。如果你的意思是這是一個浮點數,用一條加載指令(即fld)將它放在浮點堆棧上。