2019-06-04 10:11:33 +02:00
/* SPDX-License-Identifier: GPL-2.0-only */
2015-03-10 09:47:47 +01:00
/ *
* aes- c e - c o r e . S - A E S i n C B C / C T R / X T S m o d e u s i n g A R M v8 C r y p t o E x t e n s i o n s
*
* Copyright ( C ) 2 0 1 5 L i n a r o L t d < a r d . b i e s h e u v e l @linaro.org>
* /
# include < l i n u x / l i n k a g e . h >
# include < a s m / a s s e m b l e r . h >
.text
2019-09-17 09:50:00 +01:00
.arch armv8 - a
2015-03-10 09:47:47 +01:00
.fpu crypto- n e o n - f p - a r m v8
.align 3
.macro enc_ r o u n d , s t a t e , k e y
aese. 8 \ s t a t e , \ k e y
aesmc. 8 \ s t a t e , \ s t a t e
.endm
.macro dec_ r o u n d , s t a t e , k e y
aesd. 8 \ s t a t e , \ k e y
aesimc. 8 \ s t a t e , \ s t a t e
.endm
.macro enc_ d r o u n d , k e y 1 , k e y 2
enc_ r o u n d q0 , \ k e y 1
enc_ r o u n d q0 , \ k e y 2
.endm
.macro dec_ d r o u n d , k e y 1 , k e y 2
dec_ r o u n d q0 , \ k e y 1
dec_ r o u n d q0 , \ k e y 2
.endm
.macro enc_ f r o u n d , k e y 1 , k e y 2 , k e y 3
enc_ r o u n d q0 , \ k e y 1
aese. 8 q0 , \ k e y 2
veor q0 , q0 , \ k e y 3
.endm
.macro dec_ f r o u n d , k e y 1 , k e y 2 , k e y 3
dec_ r o u n d q0 , \ k e y 1
aesd. 8 q0 , \ k e y 2
veor q0 , q0 , \ k e y 3
.endm
2019-09-03 09:43:25 -07:00
.macro enc_ d r o u n d _ 4 x , k e y 1 , k e y 2
2015-03-10 09:47:47 +01:00
enc_ r o u n d q0 , \ k e y 1
enc_ r o u n d q1 , \ k e y 1
enc_ r o u n d q2 , \ k e y 1
2019-09-03 09:43:25 -07:00
enc_ r o u n d q3 , \ k e y 1
2015-03-10 09:47:47 +01:00
enc_ r o u n d q0 , \ k e y 2
enc_ r o u n d q1 , \ k e y 2
enc_ r o u n d q2 , \ k e y 2
2019-09-03 09:43:25 -07:00
enc_ r o u n d q3 , \ k e y 2
2015-03-10 09:47:47 +01:00
.endm
2019-09-03 09:43:25 -07:00
.macro dec_ d r o u n d _ 4 x , k e y 1 , k e y 2
2015-03-10 09:47:47 +01:00
dec_ r o u n d q0 , \ k e y 1
dec_ r o u n d q1 , \ k e y 1
dec_ r o u n d q2 , \ k e y 1
2019-09-03 09:43:25 -07:00
dec_ r o u n d q3 , \ k e y 1
2015-03-10 09:47:47 +01:00
dec_ r o u n d q0 , \ k e y 2
dec_ r o u n d q1 , \ k e y 2
dec_ r o u n d q2 , \ k e y 2
2019-09-03 09:43:25 -07:00
dec_ r o u n d q3 , \ k e y 2
2015-03-10 09:47:47 +01:00
.endm
2019-09-03 09:43:25 -07:00
.macro enc_ f r o u n d _ 4 x , k e y 1 , k e y 2 , k e y 3
2015-03-10 09:47:47 +01:00
enc_ r o u n d q0 , \ k e y 1
enc_ r o u n d q1 , \ k e y 1
enc_ r o u n d q2 , \ k e y 1
2019-09-03 09:43:25 -07:00
enc_ r o u n d q3 , \ k e y 1
2015-03-10 09:47:47 +01:00
aese. 8 q0 , \ k e y 2
aese. 8 q1 , \ k e y 2
aese. 8 q2 , \ k e y 2
2019-09-03 09:43:25 -07:00
aese. 8 q3 , \ k e y 2
2015-03-10 09:47:47 +01:00
veor q0 , q0 , \ k e y 3
veor q1 , q1 , \ k e y 3
veor q2 , q2 , \ k e y 3
2019-09-03 09:43:25 -07:00
veor q3 , q3 , \ k e y 3
2015-03-10 09:47:47 +01:00
.endm
2019-09-03 09:43:25 -07:00
.macro dec_ f r o u n d _ 4 x , k e y 1 , k e y 2 , k e y 3
2015-03-10 09:47:47 +01:00
dec_ r o u n d q0 , \ k e y 1
dec_ r o u n d q1 , \ k e y 1
dec_ r o u n d q2 , \ k e y 1
2019-09-03 09:43:25 -07:00
dec_ r o u n d q3 , \ k e y 1
2015-03-10 09:47:47 +01:00
aesd. 8 q0 , \ k e y 2
aesd. 8 q1 , \ k e y 2
aesd. 8 q2 , \ k e y 2
2019-09-03 09:43:25 -07:00
aesd. 8 q3 , \ k e y 2
2015-03-10 09:47:47 +01:00
veor q0 , q0 , \ k e y 3
veor q1 , q1 , \ k e y 3
veor q2 , q2 , \ k e y 3
2019-09-03 09:43:25 -07:00
veor q3 , q3 , \ k e y 3
2015-03-10 09:47:47 +01:00
.endm
.macro do_ b l o c k , d r o u n d , f r o u n d
cmp r3 , #12 @ which key size?
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q10 - q11 } , [ i p ] !
2015-03-10 09:47:47 +01:00
\ dround q8 , q9
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q12 - q13 } , [ i p ] !
2015-03-10 09:47:47 +01:00
\ dround q10 , q11
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q10 - q11 } , [ i p ] !
2015-03-10 09:47:47 +01:00
\ dround q12 , q13
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q12 - q13 } , [ i p ] !
2015-03-10 09:47:47 +01:00
\ dround q10 , q11
blo 0 f @ AES-128: 10 rounds
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q10 - q11 } , [ i p ] !
2015-03-10 09:47:47 +01:00
\ dround q12 , q13
2015-05-08 10:46:22 +02:00
beq 1 f @ AES-192: 12 rounds
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q12 - q13 } , [ i p ]
2015-03-10 09:47:47 +01:00
\ dround q10 , q11
0 : \ fround q12 , q13 , q14
bx l r
2015-05-08 10:46:22 +02:00
1 : \ fround q10 , q11 , q14
2015-03-10 09:47:47 +01:00
bx l r
.endm
/ *
* Internal, n o n - A A P C S c o m p l i a n t f u n c t i o n s t h a t i m p l e m e n t t h e c o r e A E S
* transforms. T h e s e s h o u l d p r e s e r v e a l l r e g i s t e r s e x c e p t q0 - q2 a n d i p
* Arguments :
* q0 : f i r s t i n / o u t p u t b l o c k
2019-09-03 09:43:25 -07:00
* q1 : s e c o n d i n / o u t p u t b l o c k ( _ 4 x v e r s i o n o n l y )
* q2 : t h i r d i n / o u t p u t b l o c k ( _ 4 x v e r s i o n o n l y )
* q3 : f o u r t h i n / o u t p u t b l o c k ( _ 4 x v e r s i o n o n l y )
2015-03-10 09:47:47 +01:00
* q8 : f i r s t r o u n d k e y
* q9 : s e c o u n d r o u n d k e y
* q1 4 : f i n a l r o u n d k e y
2015-05-08 10:46:22 +02:00
* r2 : a d d r e s s o f r o u n d k e y a r r a y
2015-03-10 09:47:47 +01:00
* r3 : n u m b e r o f r o u n d s
* /
.align 6
aes_encrypt :
add i p , r2 , #32 @ 3rd round key
.Laes_encrypt_tweak :
do_ b l o c k e n c _ d r o u n d , e n c _ f r o u n d
ENDPROC( a e s _ e n c r y p t )
.align 6
aes_decrypt :
add i p , r2 , #32 @ 3rd round key
do_ b l o c k d e c _ d r o u n d , d e c _ f r o u n d
ENDPROC( a e s _ d e c r y p t )
.align 6
2019-09-03 09:43:25 -07:00
aes_encrypt_4x :
2015-03-10 09:47:47 +01:00
add i p , r2 , #32 @ 3rd round key
2019-09-03 09:43:25 -07:00
do_ b l o c k e n c _ d r o u n d _ 4 x , e n c _ f r o u n d _ 4 x
ENDPROC( a e s _ e n c r y p t _ 4 x )
2015-03-10 09:47:47 +01:00
.align 6
2019-09-03 09:43:25 -07:00
aes_decrypt_4x :
2015-03-10 09:47:47 +01:00
add i p , r2 , #32 @ 3rd round key
2019-09-03 09:43:25 -07:00
do_ b l o c k d e c _ d r o u n d _ 4 x , d e c _ f r o u n d _ 4 x
ENDPROC( a e s _ d e c r y p t _ 4 x )
2015-03-10 09:47:47 +01:00
.macro prepare_ k e y , r k , r o u n d s
add i p , \ r k , \ r o u n d s , l s l #4
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q8 - q9 } , [ \ r k ] @ load first 2 round keys
vld1 . 3 2 { q14 } , [ i p ] @ load last round key
2015-03-10 09:47:47 +01:00
.endm
/ *
2019-09-03 09:43:23 -07:00
* aes_ e c b _ e n c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] , i n t r o u n d s ,
2015-03-10 09:47:47 +01:00
* int b l o c k s )
2019-09-03 09:43:23 -07:00
* aes_ e c b _ d e c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] , i n t r o u n d s ,
2015-03-10 09:47:47 +01:00
* int b l o c k s )
* /
ENTRY( c e _ a e s _ e c b _ e n c r y p t )
push { r4 , l r }
ldr r4 , [ s p , #8 ]
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
.Lecbencloop4x :
subs r4 , r4 , #4
2015-03-10 09:47:47 +01:00
bmi . L e c b e n c1 x
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 - q1 } , [ r1 ] !
2019-09-03 09:43:25 -07:00
vld1 . 8 { q2 - q3 } , [ r1 ] !
bl a e s _ e n c r y p t _ 4 x
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 - q1 } , [ r0 ] !
2019-09-03 09:43:25 -07:00
vst1 . 8 { q2 - q3 } , [ r0 ] !
b . L e c b e n c l o o p4 x
2015-03-10 09:47:47 +01:00
.Lecbenc1x :
2019-09-03 09:43:25 -07:00
adds r4 , r4 , #4
2015-03-10 09:47:47 +01:00
beq . L e c b e n c o u t
.Lecbencloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 } , [ r1 ] !
2015-03-10 09:47:47 +01:00
bl a e s _ e n c r y p t
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
subs r4 , r4 , #1
bne . L e c b e n c l o o p
.Lecbencout :
pop { r4 , p c }
ENDPROC( c e _ a e s _ e c b _ e n c r y p t )
ENTRY( c e _ a e s _ e c b _ d e c r y p t )
push { r4 , l r }
ldr r4 , [ s p , #8 ]
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
.Lecbdecloop4x :
subs r4 , r4 , #4
2015-03-10 09:47:47 +01:00
bmi . L e c b d e c1 x
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 - q1 } , [ r1 ] !
2019-09-03 09:43:25 -07:00
vld1 . 8 { q2 - q3 } , [ r1 ] !
bl a e s _ d e c r y p t _ 4 x
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 - q1 } , [ r0 ] !
2019-09-03 09:43:25 -07:00
vst1 . 8 { q2 - q3 } , [ r0 ] !
b . L e c b d e c l o o p4 x
2015-03-10 09:47:47 +01:00
.Lecbdec1x :
2019-09-03 09:43:25 -07:00
adds r4 , r4 , #4
2015-03-10 09:47:47 +01:00
beq . L e c b d e c o u t
.Lecbdecloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 } , [ r1 ] !
2015-03-10 09:47:47 +01:00
bl a e s _ d e c r y p t
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
subs r4 , r4 , #1
bne . L e c b d e c l o o p
.Lecbdecout :
pop { r4 , p c }
ENDPROC( c e _ a e s _ e c b _ d e c r y p t )
/ *
2019-09-03 09:43:23 -07:00
* aes_ c b c _ e n c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] , i n t r o u n d s ,
2015-03-10 09:47:47 +01:00
* int b l o c k s , u 8 i v [ ] )
2019-09-03 09:43:23 -07:00
* aes_ c b c _ d e c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] , i n t r o u n d s ,
2015-03-10 09:47:47 +01:00
* int b l o c k s , u 8 i v [ ] )
* /
ENTRY( c e _ a e s _ c b c _ e n c r y p t )
push { r4 - r6 , l r }
ldrd r4 , r5 , [ s p , #16 ]
vld1 . 8 { q0 } , [ r5 ]
prepare_ k e y r2 , r3
.Lcbcencloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q1 } , [ r1 ] ! @ get next pt block
2015-03-10 09:47:47 +01:00
veor q0 , q0 , q1 @ ..and xor with iv
bl a e s _ e n c r y p t
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
subs r4 , r4 , #1
bne . L c b c e n c l o o p
vst1 . 8 { q0 } , [ r5 ]
pop { r4 - r6 , p c }
ENDPROC( c e _ a e s _ c b c _ e n c r y p t )
ENTRY( c e _ a e s _ c b c _ d e c r y p t )
push { r4 - r6 , l r }
ldrd r4 , r5 , [ s p , #16 ]
2019-09-03 09:43:25 -07:00
vld1 . 8 { q15 } , [ r5 ] @ keep iv in q15
2015-03-10 09:47:47 +01:00
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
.Lcbcdecloop4x :
subs r4 , r4 , #4
2015-03-10 09:47:47 +01:00
bmi . L c b c d e c1 x
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 - q1 } , [ r1 ] !
2019-09-03 09:43:25 -07:00
vld1 . 8 { q2 - q3 } , [ r1 ] !
vmov q4 , q0
vmov q5 , q1
vmov q6 , q2
vmov q7 , q3
bl a e s _ d e c r y p t _ 4 x
veor q0 , q0 , q15
veor q1 , q1 , q4
veor q2 , q2 , q5
veor q3 , q3 , q6
vmov q15 , q7
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 - q1 } , [ r0 ] !
2019-09-03 09:43:25 -07:00
vst1 . 8 { q2 - q3 } , [ r0 ] !
b . L c b c d e c l o o p4 x
2015-03-10 09:47:47 +01:00
.Lcbcdec1x :
2019-09-03 09:43:25 -07:00
adds r4 , r4 , #4
2015-03-10 09:47:47 +01:00
beq . L c b c d e c o u t
2019-09-03 09:43:25 -07:00
vmov q6 , q14 @ preserve last round key
2015-03-10 09:47:47 +01:00
.Lcbcdecloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 } , [ r1 ] ! @ get next ct block
2015-03-10 09:47:47 +01:00
veor q14 , q15 , q6 @ combine prev ct with last key
2019-09-03 09:43:25 -07:00
vmov q15 , q0
2015-03-10 09:47:47 +01:00
bl a e s _ d e c r y p t
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
subs r4 , r4 , #1
bne . L c b c d e c l o o p
.Lcbcdecout :
2019-09-03 09:43:25 -07:00
vst1 . 8 { q15 } , [ r5 ] @ keep iv in q15
2015-03-10 09:47:47 +01:00
pop { r4 - r6 , p c }
ENDPROC( c e _ a e s _ c b c _ d e c r y p t )
2019-09-03 09:43:37 -07:00
/ *
* ce_ a e s _ c b c _ c t s _ e n c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] ,
* int r o u n d s , i n t b y t e s , u 8 c o n s t i v [ ] )
* ce_ a e s _ c b c _ c t s _ d e c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] ,
* int r o u n d s , i n t b y t e s , u 8 c o n s t i v [ ] )
* /
ENTRY( c e _ a e s _ c b c _ c t s _ e n c r y p t )
push { r4 - r6 , l r }
ldrd r4 , r5 , [ s p , #16 ]
movw i p , : l o w e r16 : . L c t s _ p e r m u t e _ t a b l e
movt i p , : u p p e r16 : . L c t s _ p e r m u t e _ t a b l e
sub r4 , r4 , #16
add l r , i p , #32
add i p , i p , r4
sub l r , l r , r4
vld1 . 8 { q5 } , [ i p ]
vld1 . 8 { q6 } , [ l r ]
add i p , r1 , r4
vld1 . 8 { q0 } , [ r1 ] @ overlapping loads
vld1 . 8 { q3 } , [ i p ]
vld1 . 8 { q1 } , [ r5 ] @ get iv
prepare_ k e y r2 , r3
veor q0 , q0 , q1 @ xor with iv
bl a e s _ e n c r y p t
vtbl. 8 d4 , { d0 - d1 } , d10
vtbl. 8 d5 , { d0 - d1 } , d11
vtbl. 8 d2 , { d6 - d7 } , d12
vtbl. 8 d3 , { d6 - d7 } , d13
veor q0 , q0 , q1
bl a e s _ e n c r y p t
add r4 , r0 , r4
vst1 . 8 { q2 } , [ r4 ] @ overlapping stores
vst1 . 8 { q0 } , [ r0 ]
pop { r4 - r6 , p c }
ENDPROC( c e _ a e s _ c b c _ c t s _ e n c r y p t )
ENTRY( c e _ a e s _ c b c _ c t s _ d e c r y p t )
push { r4 - r6 , l r }
ldrd r4 , r5 , [ s p , #16 ]
movw i p , : l o w e r16 : . L c t s _ p e r m u t e _ t a b l e
movt i p , : u p p e r16 : . L c t s _ p e r m u t e _ t a b l e
sub r4 , r4 , #16
add l r , i p , #32
add i p , i p , r4
sub l r , l r , r4
vld1 . 8 { q5 } , [ i p ]
vld1 . 8 { q6 } , [ l r ]
add i p , r1 , r4
vld1 . 8 { q0 } , [ r1 ] @ overlapping loads
vld1 . 8 { q1 } , [ i p ]
vld1 . 8 { q3 } , [ r5 ] @ get iv
prepare_ k e y r2 , r3
bl a e s _ d e c r y p t
vtbl. 8 d4 , { d0 - d1 } , d10
vtbl. 8 d5 , { d0 - d1 } , d11
vtbx. 8 d0 , { d2 - d3 } , d12
vtbx. 8 d1 , { d2 - d3 } , d13
veor q1 , q1 , q2
bl a e s _ d e c r y p t
veor q0 , q0 , q3 @ xor with iv
add r4 , r0 , r4
vst1 . 8 { q1 } , [ r4 ] @ overlapping stores
vst1 . 8 { q0 } , [ r0 ]
pop { r4 - r6 , p c }
ENDPROC( c e _ a e s _ c b c _ c t s _ d e c r y p t )
2015-03-10 09:47:47 +01:00
/ *
2019-09-03 09:43:23 -07:00
* aes_ c t r _ e n c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k [ ] , i n t r o u n d s ,
2015-03-10 09:47:47 +01:00
* int b l o c k s , u 8 c t r [ ] )
* /
ENTRY( c e _ a e s _ c t r _ e n c r y p t )
push { r4 - r6 , l r }
ldrd r4 , r5 , [ s p , #16 ]
2019-09-03 09:43:25 -07:00
vld1 . 8 { q7 } , [ r5 ] @ load ctr
2015-03-10 09:47:47 +01:00
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
vmov r6 , s31 @ keep swabbed ctr in r6
2015-03-10 09:47:47 +01:00
rev r6 , r6
cmn r6 , r4 @ 32 bit overflow?
bcs . L c t r l o o p
2019-09-03 09:43:25 -07:00
.Lctrloop4x :
subs r4 , r4 , #4
2015-03-10 09:47:47 +01:00
bmi . L c t r1 x
add r6 , r6 , #1
2019-09-03 09:43:25 -07:00
vmov q0 , q7
vmov q1 , q7
2015-03-10 09:47:47 +01:00
rev i p , r6
add r6 , r6 , #1
2019-09-03 09:43:25 -07:00
vmov q2 , q7
2015-03-10 09:47:47 +01:00
vmov s7 , i p
rev i p , r6
add r6 , r6 , #1
2019-09-03 09:43:25 -07:00
vmov q3 , q7
2015-03-10 09:47:47 +01:00
vmov s11 , i p
2019-09-03 09:43:25 -07:00
rev i p , r6
add r6 , r6 , #1
vmov s15 , i p
vld1 . 8 { q4 - q5 } , [ r1 ] !
vld1 . 8 { q6 } , [ r1 ] !
vld1 . 8 { q15 } , [ r1 ] !
bl a e s _ e n c r y p t _ 4 x
veor q0 , q0 , q4
veor q1 , q1 , q5
veor q2 , q2 , q6
veor q3 , q3 , q15
2015-03-10 09:47:47 +01:00
rev i p , r6
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 - q1 } , [ r0 ] !
2019-09-03 09:43:25 -07:00
vst1 . 8 { q2 - q3 } , [ r0 ] !
vmov s31 , i p
b . L c t r l o o p4 x
2015-03-10 09:47:47 +01:00
.Lctr1x :
2019-09-03 09:43:25 -07:00
adds r4 , r4 , #4
2015-03-10 09:47:47 +01:00
beq . L c t r o u t
.Lctrloop :
2019-09-03 09:43:25 -07:00
vmov q0 , q7
2015-03-10 09:47:47 +01:00
bl a e s _ e n c r y p t
adds r6 , r6 , #1 @ increment BE ctr
rev i p , r6
2019-09-03 09:43:25 -07:00
vmov s31 , i p
2015-03-10 09:47:47 +01:00
bcs . L c t r c a r r y
2019-02-14 00:03:55 -08:00
.Lctrcarrydone :
subs r4 , r4 , #1
bmi . L c t r t a i l b l o c k @ blocks < 0 means tail block
vld1 . 8 { q3 } , [ r1 ] !
veor q3 , q0 , q3
vst1 . 8 { q3 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
bne . L c t r l o o p
2019-02-14 00:03:55 -08:00
2015-03-10 09:47:47 +01:00
.Lctrout :
2019-09-03 09:43:25 -07:00
vst1 . 8 { q7 } , [ r5 ] @ return next CTR value
2015-03-10 09:47:47 +01:00
pop { r4 - r6 , p c }
2017-01-28 23:25:31 +00:00
.Lctrtailblock :
2019-02-14 00:03:55 -08:00
vst1 . 8 { q0 } , [ r0 , : 6 4 ] @ return the key stream
b . L c t r o u t
2015-03-10 09:47:47 +01:00
.Lctrcarry :
2019-09-03 09:43:25 -07:00
.irp sreg, s30 , s29 , s28
2015-03-10 09:47:47 +01:00
vmov i p , \ s r e g @ load next word of ctr
rev i p , i p @ ... to handle the carry
adds i p , i p , #1
rev i p , i p
vmov \ s r e g , i p
2019-02-14 00:03:55 -08:00
bcc . L c t r c a r r y d o n e
2015-03-10 09:47:47 +01:00
.endr
2019-02-14 00:03:55 -08:00
b . L c t r c a r r y d o n e
2015-03-10 09:47:47 +01:00
ENDPROC( c e _ a e s _ c t r _ e n c r y p t )
/ *
2019-09-03 09:43:23 -07:00
* aes_ x t s _ e n c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k 1 [ ] , i n t r o u n d s ,
2019-09-03 09:43:35 -07:00
* int b y t e s , u 8 i v [ ] , u 3 2 c o n s t r k 2 [ ] , i n t f i r s t )
2019-09-03 09:43:23 -07:00
* aes_ x t s _ d e c r y p t ( u 8 o u t [ ] , u 8 c o n s t i n [ ] , u 3 2 c o n s t r k 1 [ ] , i n t r o u n d s ,
2019-09-03 09:43:35 -07:00
* int b y t e s , u 8 i v [ ] , u 3 2 c o n s t r k 2 [ ] , i n t f i r s t )
2015-03-10 09:47:47 +01:00
* /
.macro next_ t w e a k , o u t , i n , c o n s t , t m p
vshr. s64 \ t m p , \ i n , #63
vand \ t m p , \ t m p , \ c o n s t
vadd. u 6 4 \ o u t , \ i n , \ i n
vext. 8 \ t m p , \ t m p , \ t m p , #8
veor \ o u t , \ o u t , \ t m p
.endm
ce_aes_xts_init :
2019-09-03 09:43:26 -07:00
vmov. i 3 2 d30 , #0x87 @ compose tweak mask vector
vmovl. u 3 2 q15 , d30
vshr. u 6 4 d30 , d31 , #7
2015-03-10 09:47:47 +01:00
ldrd r4 , r5 , [ s p , #16 ] @ load args
ldr r6 , [ s p , #28 ]
vld1 . 8 { q0 } , [ r5 ] @ load iv
teq r6 , #1 @ start of a block?
bxne l r
@ Encrypt the IV in q0 with the second AES key. This should only
@ be done at the start of a block.
ldr r6 , [ s p , #24 ] @ load AES key 2
prepare_ k e y r6 , r3
add i p , r6 , #32 @ 3rd round key of key 2
b . L a e s _ e n c r y p t _ t w e a k @ tail call
ENDPROC( c e _ a e s _ x t s _ i n i t )
ENTRY( c e _ a e s _ x t s _ e n c r y p t )
push { r4 - r6 , l r }
bl c e _ a e s _ x t s _ i n i t @ run shared prologue
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
vmov q4 , q0
2015-03-10 09:47:47 +01:00
teq r6 , #0 @ start of a block?
2019-09-03 09:43:25 -07:00
bne . L x t s e n c4 x
2015-03-10 09:47:47 +01:00
2019-09-03 09:43:25 -07:00
.Lxtsencloop4x :
next_ t w e a k q4 , q4 , q15 , q10
.Lxtsenc4x :
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #64
2015-03-10 09:47:47 +01:00
bmi . L x t s e n c1 x
2019-09-03 09:43:25 -07:00
vld1 . 8 { q0 - q1 } , [ r1 ] ! @ get 4 pt blocks
vld1 . 8 { q2 - q3 } , [ r1 ] !
next_ t w e a k q5 , q4 , q15 , q10
veor q0 , q0 , q4
next_ t w e a k q6 , q5 , q15 , q10
veor q1 , q1 , q5
next_ t w e a k q7 , q6 , q15 , q10
veor q2 , q2 , q6
veor q3 , q3 , q7
bl a e s _ e n c r y p t _ 4 x
veor q0 , q0 , q4
veor q1 , q1 , q5
veor q2 , q2 , q6
veor q3 , q3 , q7
vst1 . 8 { q0 - q1 } , [ r0 ] ! @ write 4 ct blocks
vst1 . 8 { q2 - q3 } , [ r0 ] !
vmov q4 , q7
2015-03-10 09:47:47 +01:00
teq r4 , #0
2019-09-03 09:43:35 -07:00
beq . L x t s e n c r e t
2019-09-03 09:43:25 -07:00
b . L x t s e n c l o o p4 x
2015-03-10 09:47:47 +01:00
.Lxtsenc1x :
2019-09-03 09:43:35 -07:00
adds r4 , r4 , #64
2015-03-10 09:47:47 +01:00
beq . L x t s e n c o u t
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #16
bmi . L x t s e n c c t s N x
2015-03-10 09:47:47 +01:00
.Lxtsencloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 } , [ r1 ] !
2019-09-03 09:43:35 -07:00
.Lxtsencctsout :
2019-09-03 09:43:25 -07:00
veor q0 , q0 , q4
2015-03-10 09:47:47 +01:00
bl a e s _ e n c r y p t
2019-09-03 09:43:25 -07:00
veor q0 , q0 , q4
2019-09-03 09:43:35 -07:00
teq r4 , #0
2015-03-10 09:47:47 +01:00
beq . L x t s e n c o u t
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #16
2019-09-03 09:43:25 -07:00
next_ t w e a k q4 , q4 , q15 , q6
2019-09-03 09:43:35 -07:00
bmi . L x t s e n c c t s
vst1 . 8 { q0 } , [ r0 ] !
2015-03-10 09:47:47 +01:00
b . L x t s e n c l o o p
.Lxtsencout :
2019-09-03 09:43:35 -07:00
vst1 . 8 { q0 } , [ r0 ]
.Lxtsencret :
2019-09-03 09:43:25 -07:00
vst1 . 8 { q4 } , [ r5 ]
2015-03-10 09:47:47 +01:00
pop { r4 - r6 , p c }
2019-09-03 09:43:35 -07:00
.LxtsencctsNx :
vmov q0 , q3
sub r0 , r0 , #16
.Lxtsenccts :
movw i p , : l o w e r16 : . L c t s _ p e r m u t e _ t a b l e
movt i p , : u p p e r16 : . L c t s _ p e r m u t e _ t a b l e
add r1 , r1 , r4 @ rewind input pointer
add r4 , r4 , #16 @ # bytes in final block
add l r , i p , #32
add i p , i p , r4
sub l r , l r , r4
add r4 , r0 , r4 @ output address of final block
vld1 . 8 { q1 } , [ r1 ] @ load final partial block
vld1 . 8 { q2 } , [ i p ]
vld1 . 8 { q3 } , [ l r ]
vtbl. 8 d4 , { d0 - d1 } , d4
vtbl. 8 d5 , { d0 - d1 } , d5
vtbx. 8 d0 , { d2 - d3 } , d6
vtbx. 8 d1 , { d2 - d3 } , d7
vst1 . 8 { q2 } , [ r4 ] @ overlapping stores
mov r4 , #0
b . L x t s e n c c t s o u t
2015-03-10 09:47:47 +01:00
ENDPROC( c e _ a e s _ x t s _ e n c r y p t )
ENTRY( c e _ a e s _ x t s _ d e c r y p t )
push { r4 - r6 , l r }
bl c e _ a e s _ x t s _ i n i t @ run shared prologue
prepare_ k e y r2 , r3
2019-09-03 09:43:25 -07:00
vmov q4 , q0
2015-03-10 09:47:47 +01:00
2019-09-03 09:43:35 -07:00
/* subtract 16 bytes if we are doing CTS */
tst r4 , #0xf
subne r4 , r4 , #0x10
2015-03-10 09:47:47 +01:00
teq r6 , #0 @ start of a block?
2019-09-03 09:43:25 -07:00
bne . L x t s d e c4 x
2015-03-10 09:47:47 +01:00
2019-09-03 09:43:25 -07:00
.Lxtsdecloop4x :
next_ t w e a k q4 , q4 , q15 , q10
.Lxtsdec4x :
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #64
2015-03-10 09:47:47 +01:00
bmi . L x t s d e c1 x
2019-09-03 09:43:25 -07:00
vld1 . 8 { q0 - q1 } , [ r1 ] ! @ get 4 ct blocks
vld1 . 8 { q2 - q3 } , [ r1 ] !
next_ t w e a k q5 , q4 , q15 , q10
veor q0 , q0 , q4
next_ t w e a k q6 , q5 , q15 , q10
veor q1 , q1 , q5
next_ t w e a k q7 , q6 , q15 , q10
veor q2 , q2 , q6
veor q3 , q3 , q7
bl a e s _ d e c r y p t _ 4 x
veor q0 , q0 , q4
veor q1 , q1 , q5
veor q2 , q2 , q6
veor q3 , q3 , q7
vst1 . 8 { q0 - q1 } , [ r0 ] ! @ write 4 pt blocks
vst1 . 8 { q2 - q3 } , [ r0 ] !
vmov q4 , q7
2015-03-10 09:47:47 +01:00
teq r4 , #0
beq . L x t s d e c o u t
2019-09-03 09:43:25 -07:00
b . L x t s d e c l o o p4 x
2015-03-10 09:47:47 +01:00
.Lxtsdec1x :
2019-09-03 09:43:35 -07:00
adds r4 , r4 , #64
2015-03-10 09:47:47 +01:00
beq . L x t s d e c o u t
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #16
2015-03-10 09:47:47 +01:00
.Lxtsdecloop :
2017-01-28 23:25:31 +00:00
vld1 . 8 { q0 } , [ r1 ] !
2019-09-03 09:43:35 -07:00
bmi . L x t s d e c c t s
.Lxtsdecctsout :
2019-09-03 09:43:25 -07:00
veor q0 , q0 , q4
2015-03-10 09:47:47 +01:00
bl a e s _ d e c r y p t
2019-09-03 09:43:25 -07:00
veor q0 , q0 , q4
2017-01-28 23:25:31 +00:00
vst1 . 8 { q0 } , [ r0 ] !
2019-09-03 09:43:35 -07:00
teq r4 , #0
2015-03-10 09:47:47 +01:00
beq . L x t s d e c o u t
2019-09-03 09:43:35 -07:00
subs r4 , r4 , #16
2019-09-03 09:43:25 -07:00
next_ t w e a k q4 , q4 , q15 , q6
2015-03-10 09:47:47 +01:00
b . L x t s d e c l o o p
.Lxtsdecout :
2019-09-03 09:43:25 -07:00
vst1 . 8 { q4 } , [ r5 ]
2015-03-10 09:47:47 +01:00
pop { r4 - r6 , p c }
2019-09-03 09:43:35 -07:00
.Lxtsdeccts :
movw i p , : l o w e r16 : . L c t s _ p e r m u t e _ t a b l e
movt i p , : u p p e r16 : . L c t s _ p e r m u t e _ t a b l e
add r1 , r1 , r4 @ rewind input pointer
add r4 , r4 , #16 @ # bytes in final block
add l r , i p , #32
add i p , i p , r4
sub l r , l r , r4
add r4 , r0 , r4 @ output address of final block
next_ t w e a k q5 , q4 , q15 , q6
vld1 . 8 { q1 } , [ r1 ] @ load final partial block
vld1 . 8 { q2 } , [ i p ]
vld1 . 8 { q3 } , [ l r ]
veor q0 , q0 , q5
bl a e s _ d e c r y p t
veor q0 , q0 , q5
vtbl. 8 d4 , { d0 - d1 } , d4
vtbl. 8 d5 , { d0 - d1 } , d5
vtbx. 8 d0 , { d2 - d3 } , d6
vtbx. 8 d1 , { d2 - d3 } , d7
vst1 . 8 { q2 } , [ r4 ] @ overlapping stores
mov r4 , #0
b . L x t s d e c c t s o u t
2015-03-10 09:47:47 +01:00
ENDPROC( c e _ a e s _ x t s _ d e c r y p t )
/ *
* u3 2 c e _ a e s _ s u b ( u 3 2 i n p u t ) - u s e t h e a e s e i n s t r u c t i o n t o p e r f o r m t h e
* AES s b o x s u b s t i t u t i o n o n e a c h b y t e i n
* ' input'
* /
ENTRY( c e _ a e s _ s u b )
vdup. 3 2 q1 , r0
veor q0 , q0 , q0
aese. 8 q0 , q1
vmov r0 , s0
bx l r
ENDPROC( c e _ a e s _ s u b )
/ *
* void c e _ a e s _ i n v e r t ( u 8 * d s t , u 8 * s r c ) - p e r f o r m t h e I n v e r s e M i x C o l u m n s
* operation o n r o u n d k e y * s r c
* /
ENTRY( c e _ a e s _ i n v e r t )
2019-07-02 21:41:37 +02:00
vld1 . 3 2 { q0 } , [ r1 ]
2015-03-10 09:47:47 +01:00
aesimc. 8 q0 , q0
2019-07-02 21:41:37 +02:00
vst1 . 3 2 { q0 } , [ r0 ]
2015-03-10 09:47:47 +01:00
bx l r
ENDPROC( c e _ a e s _ i n v e r t )
2019-09-03 09:43:35 -07:00
.section " .rodata " , " a"
.align 6
.Lcts_permute_table :
.byte 0 xff, 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f
.byte 0 xff, 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f
.byte 0 x0 , 0 x1 , 0 x2 , 0 x3 , 0 x4 , 0 x5 , 0 x6 , 0 x7
.byte 0 x8 , 0 x9 , 0 x a , 0 x b , 0 x c , 0 x d , 0 x e , 0 x f
.byte 0 xff, 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f
.byte 0 xff, 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f , 0 x f f