2015-06-07 56 views
0

我有具有下述組成的結構:加載128位混合float + int數據?

static constexpr uint64_t emptyStructValue { 0 }; 

union MyStruct { 
    explicit MyStruct(uint64_t comp) : composite(comp){} 

    struct{ 
     int16_t a;  
     bool b; 
     bool c; 
     float d; 
    }; 

    uint64_t composite = 0; 

    bool hasValue(){ 
     return composite != emptyStructValue; 
    } 
}; 

和我有兩個這些結構的另一個目的:

class B{ 
    Struct s1; 
    Struct s2; 
}; 

和我想知道,B型的給定對象,我怎麼能把所有的128位加載到一個SSE寄存器並檢查是否設置了一位?我發現了_mm_loadu_si128(),但我的數據有ints和float的混合?

+0

你只是想檢查是否至少設置了一個位?只是爲了確保,在浮標上做這件事時你期望什麼?對於整數(和二進制補碼),它與檢查它是否不是0相同,但浮點數更復雜=>目的是什麼? – deviantfan

+0

如果結構中沒有任何東西,我希望所有的64位都是0.我只想看看一個結構是否包含一個條目,很快,因此我只想看看是否設置了任何位。該結構有一個聯合,它將64位設置爲零,如果它爲空。 – user997112

+2

你的結構的實例總是包含所有4個變量的一些值?它不能是虛擬的。編輯:工會的東西不會讓它變得空虛。 – deviantfan

回答

3

實際上,如果(sizeof(B) == 2*sizeof(uint64_t),那麼我認爲沒有理由不去做你的建議。但是,如果速度很重要(看起來像這樣),則應該將B對象與128位邊界對齊,以便可以使用_mm_load_si128而不是_mm_loadu_si128

編輯爲:實際上,在64位模式下,使用常規操作碼可能會更快。例如:

mov rax,[rsi] 
or rax,[rsi+8] 
jnz BitSet 

即使在32位模式下,它可能會變得更快。你將不得不嘗試。

+0

在堆棧上創建B,對齊到128位。然後做了__declspec(align(128))B b; B * bptr =&b; __m128i intrinreg = _mm_load_si128(reinterpret_cast <__m128i*>(bptr)); 但不確定如何比較__m128i和數字零? – user997112

+0

@ user997112:嗯,好問題。我看不出有辦法做到這一點。也許最好的辦法就是'if(s1.composite == 0 && s2.composite == 0)'。 – TonyK

+0

@ user997112 [有一個關於這個的問題](http://stackoverflow.com/questions/10175711/check-xmm-register-for-all-zeroes),如果'pcmpeqq'對你來說不夠好。 –