Domanda

Sto usando SIMD per calcolare risultato elevamento a potenza veloce. Io paragono la sincronizzazione con il codice non-SIMD. L'elevamento a potenza è implementato utilizzando l'algoritmo di piazza e si moltiplicano.

ordinario (non-SIMD) versione del codice:

b = 1;  
for (i=WPE-1; i>=0; --i){  
    ew = e[i];  
    for(j=0; j<BPW; ++j){  
        b = (b * b) % p;  
        if (ew & 0x80000000U)  b = (b * a) % p;  
        ew <<= 1;  
    }  
}  

Versione SIMD:

   B.data[0] = B.data[1] = B.data[2] = B.data[3] = 1U;  
   P.data[0] = P.data[1] = P.data[2] = P.data[3] = p;  
   for (i=WPE-1; i>=0; --i) {  
      EW.data[0] = e1[i]; EW.data[1] = e2[i]; EW.data[2] = e3[i]; EW.data[3] = e4[i];  
      for (j=0; j<BPW;++j){  
         B.v *= B.v; B.v -= (B.v / P.v) * P.v;  
         EWV.v = _mm_srli_epi32(EW.v,31);  
         M.data[0] = (EWV.data[0]) ? a1 : 1U;  
         M.data[1] = (EWV.data[1]) ? a2 : 1U; 
         M.data[2] = (EWV.data[2]) ? a3 : 1U; 
         M.data[3] = (EWV.data[3]) ? a4 : 1U;  
         B.v *= M.v; B.v -= (B.v / P.v) * P.v;  
         EW.v = _mm_slli_epi32(EW.v,1);  
      }  
   } 

Il problema è se si sta calcolando correttamente, la versione SIMD sta prendendo più tempo di quanto versione non-SIMD.

Si prega di aiutare me il debug le ragioni. Qualche suggerimento su codifica SIMD è inoltre benvenuto.

Grazie e saluti, Anup.

È stato utile?

Soluzione

Tutte le funzioni del per cicli dovrebbe essere funzioni SIMD, non solo due. Tempo di prendere per impostare gli argomenti per le 2 funzioni è meno ottimale, allora il tuo esempio originale (che è più probabile ottimizzato dal compilatore)

Altri suggerimenti

Un SIMD ciclo per i dati int a 32 bit sembra tipicamente qualcosa di simile:

for (i = 0; i < N; i += 4)
{
    // load input vector(s) with data at array index i..i+3
    __m128 va = _mm_load_si128(&A[i]);
    __m128 vb = _mm_load_si128(&B[i]);

    // process vectors using SIMD instructions (i.e. no scalar code)
    __m128 vc = _mm_add_epi32(va, vb);

    // store result vector(s) at array index i..i+3
    _mm_store_si128(&C[i], vc);
}

Se si scopre che è necessario spostare tra il codice scalare e il codice SIMD all'interno del ciclo, allora probabilmente non otterrà nulla dalla ottimizzazione SIMD.

La maggior parte delle abilità nella programmazione SIMD viene dalla ricerca di modi per rendere il vostro lavoro algoritmo con il numero limitato di istruzioni supportate ei tipi di dati che una data architettura SIMD fornisce. Avrete spesso bisogno di sfruttare a priori la conoscenza del vostro set di dati per ottenere le migliori prestazioni possibili, per esempio se si sa per certo che i valori interi a 32 bit in realtà hanno una gamma che si inserisce all'interno di 16 bit allora che renderebbe la parte moltiplicazione del vostro algoritmo molto più facile da implementare.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top