383 lines
12 KiB
Text
383 lines
12 KiB
Text
/* ARM assembly AARCH64 Raspberry PI 3B */
|
|
/* program sha1_64.s */
|
|
|
|
/*******************************************/
|
|
/* Constantes file */
|
|
/*******************************************/
|
|
/* for this file see task include a file in language AArch64 assembly*/
|
|
.include "../includeConstantesARM64.inc"
|
|
|
|
.equ SHA_DIGEST_LENGTH, 20
|
|
|
|
//.include "../../ficmacros64.s"
|
|
|
|
/*********************************/
|
|
/* Initialized data */
|
|
/*********************************/
|
|
.data
|
|
szMessRosetta: .asciz "Rosetta Code"
|
|
szMessTest1: .asciz "abc"
|
|
szMessSup64: .ascii "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
|
|
.ascii "abcdefghijklmnopqrstuvwxyz"
|
|
.asciz "1234567890AZERTYUIOP"
|
|
szMessTest2: .asciz "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"
|
|
szMessFinPgm: .asciz "Program End ok.\n"
|
|
szMessResult: .asciz "Rosetta Code => "
|
|
szCarriageReturn: .asciz "\n"
|
|
|
|
/* array constantes Hi */
|
|
tbConstHi: .int 0x67452301 // H0
|
|
.int 0xEFCDAB89 // H1
|
|
.int 0x98BADCFE // H2
|
|
.int 0x10325476 // H3
|
|
.int 0xC3D2E1F0 // H4
|
|
/* array constantes Kt */
|
|
tbConstKt: .int 0x5A827999
|
|
.int 0x6ED9EBA1
|
|
.int 0x8F1BBCDC
|
|
.int 0xCA62C1D6
|
|
|
|
|
|
/*********************************/
|
|
/* UnInitialized data */
|
|
/*********************************/
|
|
.bss
|
|
.align 4
|
|
iNbBlocs: .skip 8
|
|
sZoneConv: .skip 24
|
|
sZoneResult: .skip 24
|
|
sZoneTrav: .skip 1000
|
|
tbH: .skip 4 * 5 // 5 variables H
|
|
tbW: .skip 4 * 80 // 80 words W
|
|
/*********************************/
|
|
/* code section */
|
|
/*********************************/
|
|
.text
|
|
.global main
|
|
main: // entry of program
|
|
|
|
ldr x0,qAdrszMessRosetta
|
|
//ldr x0,qAdrszMessTest1
|
|
//ldr x0,qAdrszMessTest2
|
|
//ldr x0,qAdrszMessSup64
|
|
bl computeSHA1 // call routine SHA1
|
|
|
|
ldr x0,qAdrszMessResult
|
|
bl affichageMess // display message
|
|
|
|
ldr x0, qAdrsZoneResult
|
|
bl displaySHA1
|
|
|
|
ldr x0,qAdrszMessFinPgm
|
|
bl affichageMess // display message
|
|
|
|
|
|
100: // standard end of the program
|
|
mov x0,0 // return code
|
|
mov x8,EXIT // request to exit program
|
|
svc 0 // perform the system call
|
|
|
|
qAdrszCarriageReturn: .quad szCarriageReturn
|
|
qAdrszMessResult: .quad szMessResult
|
|
qAdrszMessRosetta: .quad szMessRosetta
|
|
qAdrszMessTest1: .quad szMessTest1
|
|
qAdrszMessTest2: .quad szMessTest2
|
|
qAdrsZoneTrav: .quad sZoneTrav
|
|
qAdrsZoneConv: .quad sZoneConv
|
|
qAdrszMessFinPgm: .quad szMessFinPgm
|
|
qAdrszMessSup64: .quad szMessSup64
|
|
/******************************************************************/
|
|
/* compute SHA1 */
|
|
/******************************************************************/
|
|
/* x0 contains the address of the message */
|
|
computeSHA1:
|
|
stp x1,lr,[sp,-16]! // save registers
|
|
ldr x1,qAdrsZoneTrav
|
|
mov x2,#0 // counter length
|
|
debCopy: // copy string in work area
|
|
ldrb w3,[x0,x2]
|
|
strb w3,[x1,x2]
|
|
cmp x3,#0
|
|
add x4,x2,1
|
|
csel x2,x4,x2,ne
|
|
bne debCopy
|
|
lsl x6,x2,#3 // initial message length in bits
|
|
mov x3,#0b10000000 // add bit 1 at end of string
|
|
strb w3,[x1,x2]
|
|
add x2,x2,#1 // length in bytes
|
|
lsl x4,x2,#3 // length in bits
|
|
mov x3,#0
|
|
addZeroes:
|
|
lsr x5,x2,#6
|
|
lsl x5,x5,#6
|
|
sub x5,x2,x5
|
|
cmp x5,#56
|
|
beq storeLength // yes -> end add
|
|
strb w3,[x1,x2] // add zero at message end
|
|
add x2,x2,#1 // increment lenght bytes
|
|
add x4,x4,#8 // increment length in bits
|
|
b addZeroes
|
|
storeLength:
|
|
add x2,x2,#4 // add four bytes
|
|
rev w6,w6 // inversion bits initials message length
|
|
str w6,[x1,x2] // and store at end
|
|
|
|
ldr x7,qAdrtbConstHi // constantes H address
|
|
ldr x4,qAdrtbH // start area H
|
|
mov x5,#0
|
|
loopConst: // init array H with start constantes
|
|
ldr w6,[x7,x5,lsl #2] // load constante
|
|
str w6,[x4,x5,lsl #2] // and store
|
|
add x5,x5,#1
|
|
cmp x5,#5
|
|
blt loopConst
|
|
// split into block of 64 bytes
|
|
add x2,x2,#4 // TODO : à revoir
|
|
lsr x4,x2,#6 // blocks number
|
|
ldr x0,qAdriNbBlocs
|
|
str x4,[x0] // save block maxi
|
|
mov x7,#0 // n° de block et x1 contient l'adresse zone de travail
|
|
loopBlock: // begin loop of each block of 64 bytes
|
|
mov x0,x7
|
|
bl inversion // inversion each word because little indian
|
|
ldr x3,qAdrtbW // working area W address
|
|
mov x6,#0 // indice t
|
|
/* x2 address begin each block */
|
|
ldr x1,qAdrsZoneTrav
|
|
add x2,x1,x7,lsl #6 // compute block begin indice * 4 * 16
|
|
|
|
loopPrep: // loop for expand 80 words
|
|
cmp x6,#15 //
|
|
bgt expand1
|
|
ldr w0,[x2,x6,lsl #2] // load four byte message
|
|
str w0,[x3,x6,lsl #2] // store in first 16 block
|
|
b expandEnd
|
|
expand1:
|
|
sub x8,x6,#3
|
|
ldr w9,[x3,x8,lsl #2]
|
|
sub x8,x6,#8
|
|
ldr w10,[x3,x8,lsl #2]
|
|
eor x9,x9,x10
|
|
sub x8,x6,#14
|
|
ldr w10,[x3,x8,lsl #2]
|
|
eor x9,x9,x10
|
|
sub x8,x6,#16
|
|
ldr w10,[x3,x8,lsl #2]
|
|
eor x9,x9,x10
|
|
ror w9,w9,#31
|
|
|
|
str w9,[x3,x6,lsl #2]
|
|
expandEnd:
|
|
add x6,x6,#1
|
|
cmp x6,#80 // 80 words ?
|
|
blt loopPrep // and loop
|
|
/* COMPUTING THE MESSAGE DIGEST */
|
|
/* x1 area H constantes address */
|
|
/* x3 working area W address */
|
|
/* x5 address constantes K */
|
|
/* x6 counter t */
|
|
/* x7 block counter */
|
|
/* x8 a, x9 b, x10 c, x11 d, x12 e */
|
|
|
|
// init variable a b c d e
|
|
ldr x0,qAdrtbH
|
|
ldr w8,[x0]
|
|
ldr w9,[x0,#4]
|
|
ldr w10,[x0,#8]
|
|
ldr w11,[x0,#12]
|
|
ldr w12,[x0,#16]
|
|
|
|
ldr x1,qAdrtbConstHi
|
|
ldr x5,qAdrtbConstKt
|
|
mov x6,#0
|
|
loop80T: // begin loop 80 t
|
|
cmp x6,#19
|
|
bgt T2
|
|
ldr w0,[x5] // load constantes k0
|
|
and x2,x9,x10 // b and c
|
|
mvn w4,w9 // not b
|
|
and x4,x4,x11 // and d
|
|
orr x2,x2,x4
|
|
b T_fin
|
|
T2:
|
|
cmp x6,#39
|
|
bgt T3
|
|
ldr w0,[x5,#4] // load constantes k1
|
|
eor x2,x9,x10
|
|
eor x2,x2,x11
|
|
b T_fin
|
|
T3:
|
|
cmp x6,#59
|
|
bgt T4
|
|
ldr w0,[x5,#8] // load constantes k2
|
|
and x2,x9,x10
|
|
and x4,x9,x11
|
|
orr x2,x2,x4
|
|
and x4,x10,x11
|
|
orr x2,x2,x4
|
|
b T_fin
|
|
T4:
|
|
ldr w0,[x5,#12] // load constantes k3
|
|
eor x2,x9,x10
|
|
eor x2,x2,x11
|
|
b T_fin
|
|
T_fin:
|
|
ror w4,w8,#27 // left rotate a to 5
|
|
add w2,w2,w4
|
|
//affregtit Tfin 0
|
|
//affregtit Tfin 8
|
|
add w2,w2,w12
|
|
ldr w4,[x3,x6,lsl #2] // Wt
|
|
add w2,w2,w4
|
|
add w2,w2,w0 // Kt
|
|
mov x12,x11 // e = d
|
|
mov x11,x10 // d = c
|
|
ror w10,w9,#2 // c
|
|
mov x9,x8 // b = a
|
|
mov x8,x2 // nouveau a
|
|
|
|
add x6,x6,#1 // increment t
|
|
cmp x6,#80
|
|
blt loop80T
|
|
// other bloc
|
|
add x7,x7,1 // increment block
|
|
ldr x0,qAdriNbBlocs
|
|
ldr w4,[x0] // restaur maxi block
|
|
cmp x7,x4 // maxi ?
|
|
bge End
|
|
// End block
|
|
ldr x0,qAdrtbH // start area H
|
|
ldr w3,[x0]
|
|
add w3,w3,w8
|
|
str w3,[x0] // store a in H0
|
|
ldr w3,[x0,#4]
|
|
add w3,w3,w9
|
|
str w3,[x0,#4] // store b in H1
|
|
ldr w3,[x0,#8]
|
|
add w3,w3,w10
|
|
str w3,[x0,#8] // store c in H2
|
|
ldr w3,[x0,#12]
|
|
add w3,w3,w11
|
|
str w3,[x0,#12] // store d in H3
|
|
ldr w3,[x0,#16]
|
|
add w3,w3,w12
|
|
str w3,[x0,#16] // store e in H4
|
|
b loopBlock // loop
|
|
|
|
End:
|
|
// compute final result
|
|
ldr x0,qAdrtbH // start area H
|
|
ldr x2,qAdrsZoneResult
|
|
ldr w1,[x0]
|
|
add x1,x1,x8
|
|
rev w1,w1
|
|
str w1,[x2]
|
|
ldr w1,[x0,#4]
|
|
add x1,x1,x9
|
|
rev w1,w1
|
|
str w1,[x2,#4]
|
|
ldr w1,[x0,#8]
|
|
add x1,x1,x10
|
|
rev w1,w1
|
|
str w1,[x2,#8]
|
|
ldr w1,[x0,#12]
|
|
add x1,x1,x11
|
|
rev w1,w1
|
|
str w1,[x2,#12]
|
|
ldr w1,[x0,#16]
|
|
add x1,x1,x12
|
|
rev w1,w1
|
|
str w1,[x2,#16]
|
|
mov x0,#0 // routine OK
|
|
100:
|
|
|
|
ldp x1,lr,[sp],16 // restaur 2 registers
|
|
ret // return to address lr x30
|
|
qAdrtbConstHi: .quad tbConstHi
|
|
qAdrtbConstKt: .quad tbConstKt
|
|
qAdrtbH: .quad tbH
|
|
qAdrtbW: .quad tbW
|
|
qAdrsZoneResult: .quad sZoneResult
|
|
qAdriNbBlocs: .quad iNbBlocs
|
|
/******************************************************************/
|
|
/* inversion des mots de 32 bits d'un bloc */
|
|
/******************************************************************/
|
|
/* x0 contains N° block */
|
|
inversion:
|
|
stp x1,lr,[sp,-16]! // save registers
|
|
stp x2,x3,[sp,-16]! // save registers
|
|
ldr x1,qAdrsZoneTrav
|
|
add x1,x1,x0,lsl 6 // debut du bloc
|
|
mov x2,#0
|
|
1: // start loop
|
|
ldr w3,[x1,x2,lsl #2]
|
|
rev w3,w3
|
|
str w3,[x1,x2,lsl #2]
|
|
add x2,x2,#1
|
|
cmp x2,#16
|
|
blt 1b
|
|
100:
|
|
ldp x2,x3,[sp],16 // restaur 2 registers
|
|
ldp x1,lr,[sp],16 // restaur 2 registers
|
|
ret // return to address lr x30
|
|
/******************************************************************/
|
|
/* display hash SHA1 */
|
|
/******************************************************************/
|
|
/* x0 contains the address of hash */
|
|
displaySHA1:
|
|
stp x1,lr,[sp,-16]! // save registers
|
|
stp x2,x3,[sp,-16]! // save registers
|
|
mov x3,x0
|
|
mov x2,#0
|
|
1:
|
|
ldr w0,[x3,x2,lsl #2] // load 4 bytes
|
|
rev w0,w0 // reverse bytes
|
|
ldr x1,qAdrsZoneConv
|
|
bl conversion16_4W // conversion hexa
|
|
ldr x0,qAdrsZoneConv
|
|
bl affichageMess
|
|
add x2,x2,#1
|
|
cmp x2,#SHA_DIGEST_LENGTH / 4
|
|
blt 1b // and loop
|
|
ldr x0,qAdrszCarriageReturn
|
|
bl affichageMess // display message
|
|
100:
|
|
ldp x2,x3,[sp],16 // restaur 2 registers
|
|
ldp x1,lr,[sp],16 // restaur 2 registers
|
|
ret // return to address lr x30
|
|
/******************************************************************/
|
|
/* conversion hexadecimal register 32 bits */
|
|
/******************************************************************/
|
|
/* x0 contains value and x1 address zone receptrice */
|
|
conversion16_4W:
|
|
stp x0,lr,[sp,-48]! // save registres
|
|
stp x1,x2,[sp,32] // save registres
|
|
stp x3,x4,[sp,16] // save registres
|
|
mov x2,#28 // start bit position
|
|
mov x4,#0xF0000000 // mask
|
|
mov x3,x0 // save entry value
|
|
1: // start loop
|
|
and x0,x3,x4 // value register and mask
|
|
lsr x0,x0,x2 // right shift
|
|
cmp x0,#10 // >= 10 ?
|
|
bge 2f // yes
|
|
add x0,x0,#48 // no is digit
|
|
b 3f
|
|
2:
|
|
add x0,x0,#55 // else is a letter A-F
|
|
3:
|
|
strb w0,[x1],#1 // load result and + 1 in address
|
|
lsr x4,x4,#4 // shift mask 4 bits left
|
|
subs x2,x2,#4 // decrement counter 4 bits <= zero ?
|
|
bge 1b // no -> loop
|
|
|
|
100: // fin standard de la fonction
|
|
ldp x3,x4,[sp,16] // restaur des 2 registres
|
|
ldp x1,x2,[sp,32] // restaur des 2 registres
|
|
ldp x0,lr,[sp],48 // restaur des 2 registres
|
|
ret
|
|
/********************************************************/
|
|
/* File Include fonctions */
|
|
/********************************************************/
|
|
/* for this file see task include a file in language AArch64 assembly */
|
|
.include "../includeARM64.inc"
|