2013-03-22 10 views
14

Jaki jest najlepszy/najszybszy sposób załadowania 64-bitowej wartości całkowitej w rejestrze SSE2 xmm w trybie 32-bitowym?Najlepszy sposób na załadowanie 64-bitowej liczby całkowitej do rejestru podwójnej precyzji SSE2?

W trybie 64-bitowym można używać cvtsi2sd, ale w trybie 32-bitowym obsługuje tylko 32-bitowe liczby całkowite.

tej pory nie znalazłem znacznie poza:

  • użytku fild, fstp stos następnie movsd do xmm rejestr
  • obciążenie część wysoki 32-bitowy, należy pomnożyć przez 2^32, dodaj niski 32-bitowy

pierwsze rozwiązanie jest powolny, drugie rozwiązanie może wprowadzić utraty precyzji (edit: i jest powolny i tak, ponieważ niska 3 2-bitowe muszą zostać przekonwertowane jako unsigned ...)

Lepsze podejście?

+0

Pomnożenie 32 górnych bitów przez 2 ** 32 w zmiennoprzecinkowej nie spowoduje ich obcięcia/zaokrąglenia. Dopiero gdy dodasz do nich 32 bity, suma zostanie zaokrąglona/obcięta i tak właśnie otrzymasz pierwszą metodę. O ile czegoś mi nie brakuje, te dwie metody są równoważne (z wyjątkiem wydajności). –

+3

FWIW gcc wydaje się korzystać z pierwszego podejścia (fild, fst, movsd). –

+0

Druga opcja jest rzeczywiście powolna, przez pomyłkę użyłem cvtsi2sd dla niskiego 32-bitowego, ale to było niepoprawne, musi zostać przekonwertowane jako unsigned, dla którego nie ma instrukcji CPU, więc jest wolne ... –

Odpowiedz

9

Twoja druga opcja, , może, zadziałać, chociaż jest trochę nieporęczna. Zakładam, że twój 64-bitowy numer jest początkowo w edx: eax.

cvtsi2sd xmm0, edx    // high part * 2**-32 
mulsd xmm0, [2**32 from mem] // high part 
movsd xmm2, [2**52 from mem] 
movd  xmm1, eax 
orpd  xmm1, xmm2    // (double)(2*52 + low part as unsigned) 
subsd xmm1, xmm2    // (double)(low part as unsigned) 
addsd xmm0, xmm1    // (double)(high part + low part as unsigned) 

Wszystkie operacje, z wyjątkiem prawdopodobnie ostatecznego, są dokładne, więc jest poprawnie zaokrąglone. Należy zauważyć, że ta konwersja generuje -0.0, gdy wejście to 0, a mxcsr jest ustawione na wartość od rundy do-minus-nieskończoności. Musiałoby to zostać rozwiązane, gdyby było używane w bibliotece środowiska wykonawczego dla kompilatora mającego na celu zapewnienie zgodności z IEEE-754, ale nie stanowi problemu w przypadku większości zastosowań.

Powiązane problemy