Domanda

Sono nuovo di assemblatore e programmazione NEON. Il mio compito è quello di convertire parte di un algoritmo da C a ARM Assembler utilizzando le istruzioni NEON. L'algoritmo prende un array int32, carica i valori diversi da questo array, fa alcune bitshifting e XOR e scrive il risultato in un altro array. In seguito userò un array con valori a 64 bit, ma per ora ho solo cercare di riscrivere il codice.

C Pseudo code:

out_array[index] = shiftSome( in_array[index] ) ^ shiftSome( in_array[index] );

Così qui sono le mie domande riguardanti istruzioni NEON:

1) se carico di un registro come questo:.

vld1.32 d0, [r1]

intende caricare solo 32 bit dalla memoria o 2x32Bit per riempire il 64Bit Neon D-Register?

2.) Come posso accedere alle parti 2/4/8 (i32, i16, i8) del D-Register?

3.) Sto cercando di caricare valori diversi dalla matrice con un offset, ma non è così sembra funzionare ... quello che sto facendo male ... Ecco il mio codice: (È una matrice intera quindi sono cercando di carico per esempio il 3-elemento, che dovrebbe avere un offset di 64 bit = 8 byte)

asm volatile(
"vld1.32 d0, [%0], #8 \n"     
"vst1.32 d0, [%1]" : : "r" (a), "r" (out): "d0", "r5");

dove "a" è la matrice e "out" è un puntatore a un intero (per il debug).

4) Quando si carica un valore dalla matrice ho bisogno di spostare verso destra ma non sembra funzionare:.

vshr.u32 d0, d0, #24     // C code:   x >> 24;

5.) E 'possibile caricare solo 1 byte in un Neon registrare in modo che io non devo spostamento / maschera qualcosa per ottenere solo quella Byte ho bisogno?

6) ho bisogno di usare Inline assembler, ma non sono sicuro di quello che l'ultima riga è per:.

input list : output list : what is this for?

7). Sapete tutti i riferimenti buono al neon con esempi di codice?

Il programma dovrebbe funzionare su un Galaxy S2 di Samsung, Cortex-A9 processore se questo fa alcuna differenza. Grazie per l'aiuto.

---------------- Modifica -------------------

Questo è quello che ho scoperto:

  1. Sarà sempre caricare il pieno Register (64 bit)
  2. È possibile utilizzare l'istruzione "vmov" a parte il trasferimento di un registro al neon ad un registro braccio.
  3. L'offset dovrebbe essere in un registro braccio e verrà aggiunto alla indirizzo di base dopo l'accesso alla memoria.
  4. E 'la "lista reg rovinati". Ogni registro che viene utilizzato e né nella lista di ingresso o di uscita, dovrebbe essere scritto qui.
È stato utile?

Soluzione

posso rispondere alla maggior parte delle vostre domande: (aggiornamento: chiarito problema "corsia")

1) istruzioni neon, può solo caricare e memorizzare interi registri (64-bit, 128 bit) alla volta da e per la memoria. Esiste una variante istruzione MOV che permette "corsie" single di essere spostati o dai registri ARM.

2) È possibile utilizzare l'istruzione MOV NEON di influenzare singole corsie. Prestazioni soffrirà quando si fa troppe operazioni singolo elemento. istruzioni NEON beneficiano delle prestazioni delle applicazioni facendo operazioni parallele su vettori (gruppi di carri / int).

3) Gli offset valore immediato in linguaggio assembly ARM sono byte, non elementi / registri. istruzioni NEON permettono incremento post con un registro, non valore immediato. Per le normali istruzioni ARM, il tuo post-incremento di 8 aggiungerà 8 (byte) per il puntatore sorgente.

4) Variazioni nella NEON influenzano tutti gli elementi di un vettore. Un diritto spostamento di 24 bit utilizzando vshr.u32 si sposterà entrambi anela senza segno a 32 bit da 24 bit e buttare via i bit che vengono spostati fuori.

5) istruzioni NEON permettono lo spostamento elementi singoli in e fuori di normali registri ARM, ma non consentono carichi o esercizi di memoria direttamente in "corsie".

6)?

7) Inizia da qui: http: / /blogs.arm.com/software-enablement/161-coding-for-neon-part-1-load-and-stores/ Il sito ARM ha un buon tutorial su NEON.

Altri suggerimenti

6) registri rovinati.

asm(code : output operand list : input operand list : clobber list);

Se si utilizza registri, che non erano state passate come operandi, è necessario informare il compilatore su questo. Il seguente codice si regola un valore ad un multiplo di quattro. esso usa r3 come un registro zero e lascia il know compilatore su questo specificando r3 nel Lista clobber. Inoltre i flag di stato della CPU vengono modificate dall'istruzione ands. L'aggiunta del cc pseudo registro alla lista clobber manterrà il compilatore informato su questa modifica pure.

asm (
"ands R3, %1, #3"
"eor %0, %0, r3"
: "=r"(len)
: "0"(len)
: "cc", "r3"
);
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top