Home | History | Annotate | Download | only in fipsmodule
      1 @ Copyright 2012-2016 The OpenSSL Project Authors. All Rights Reserved.
      2 @
      3 @ Licensed under the OpenSSL license (the "License").  You may not use
      4 @ this file except in compliance with the License.  You can obtain a copy
      5 @ in the file LICENSE in the source distribution or at
      6 @ https://www.openssl.org/source/license.html
      7 
      8 
      9 @ ====================================================================
     10 @ Written by Andy Polyakov <appro@openssl.org> for the OpenSSL
     11 @ project. The module is, however, dual licensed under OpenSSL and
     12 @ CRYPTOGAMS licenses depending on where you obtain it. For further
     13 @ details see http://www.openssl.org/~appro/cryptogams/.
     14 @
     15 @ Specific modes and adaptation for Linux kernel by Ard Biesheuvel
     16 @ <ard.biesheuvel@linaro.org>. Permission to use under GPL terms is
     17 @ granted.
     18 @ ====================================================================
     19 
     20 @ Bit-sliced AES for ARM NEON
     21 @
     22 @ February 2012.
     23 @
     24 @ This implementation is direct adaptation of bsaes-x86_64 module for
     25 @ ARM NEON. Except that this module is endian-neutral [in sense that
     26 @ it can be compiled for either endianness] by courtesy of vld1.8's
     27 @ neutrality. Initial version doesn't implement interface to OpenSSL,
     28 @ only low-level primitives and unsupported entry points, just enough
     29 @ to collect performance results, which for Cortex-A8 core are:
     30 @
     31 @ encrypt	19.5 cycles per byte processed with 128-bit key
     32 @ decrypt	22.1 cycles per byte processed with 128-bit key
     33 @ key conv.	440  cycles per 128-bit key/0.18 of 8x block
     34 @
     35 @ Snapdragon S4 encrypts byte in 17.6 cycles and decrypts in 19.7,
     36 @ which is [much] worse than anticipated (for further details see
     37 @ http://www.openssl.org/~appro/Snapdragon-S4.html).
     38 @
     39 @ Cortex-A15 manages in 14.2/16.1 cycles [when integer-only code
     40 @ manages in 20.0 cycles].
     41 @
     42 @ When comparing to x86_64 results keep in mind that NEON unit is
     43 @ [mostly] single-issue and thus can't [fully] benefit from
     44 @ instruction-level parallelism. And when comparing to aes-armv4
     45 @ results keep in mind key schedule conversion overhead (see
     46 @ bsaes-x86_64.pl for further details)...
     47 @
     48 @						<appro (at) openssl.org>
     49 
     50 @ April-August 2013
     51 @
     52 @ Add CBC, CTR and XTS subroutines, adapt for kernel use.
     53 @
     54 @					<ard.biesheuvel (at) linaro.org>
     55 
     56 #ifndef __KERNEL__
     57 # include <openssl/arm_arch.h>
     58 
     59 # define VFP_ABI_PUSH	vstmdb	sp!,{d8-d15}
     60 # define VFP_ABI_POP	vldmia	sp!,{d8-d15}
     61 # define VFP_ABI_FRAME	0x40
     62 #else
     63 # define VFP_ABI_PUSH
     64 # define VFP_ABI_POP
     65 # define VFP_ABI_FRAME	0
     66 # define BSAES_ASM_EXTENDED_KEY
     67 # define XTS_CHAIN_TWEAK
     68 # define __ARM_ARCH__ __LINUX_ARM_ARCH__
     69 # define __ARM_MAX_ARCH__ 7
     70 #endif
     71 
     72 #ifdef __thumb__
     73 # define adrl adr
     74 #endif
     75 
     76 #if __ARM_MAX_ARCH__>=7
     77 
     78 
     79 
     80 .text
     81 .syntax	unified 	@ ARMv7-capable assembler is expected to handle this
     82 #if defined(__thumb2__) && !defined(__APPLE__)
     83 .thumb
     84 #else
     85 .code	32
     86 # undef __thumb2__
     87 #endif
     88 
     89 #ifdef __thumb2__
     90 .thumb_func	_bsaes_decrypt8
     91 #endif
     92 .align	4
     93 _bsaes_decrypt8:
     94 	adr	r6,.
     95 	vldmia	r4!, {q9}		@ round 0 key
     96 #ifdef	__APPLE__
     97 	adr	r6,LM0ISR
     98 #else
     99 	add	r6,r6,#LM0ISR-_bsaes_decrypt8
    100 #endif
    101 
    102 	vldmia	r6!, {q8}		@ LM0ISR
    103 	veor	q10, q0, q9	@ xor with round0 key
    104 	veor	q11, q1, q9
    105 	vtbl.8	d0, {q10}, d16
    106 	vtbl.8	d1, {q10}, d17
    107 	veor	q12, q2, q9
    108 	vtbl.8	d2, {q11}, d16
    109 	vtbl.8	d3, {q11}, d17
    110 	veor	q13, q3, q9
    111 	vtbl.8	d4, {q12}, d16
    112 	vtbl.8	d5, {q12}, d17
    113 	veor	q14, q4, q9
    114 	vtbl.8	d6, {q13}, d16
    115 	vtbl.8	d7, {q13}, d17
    116 	veor	q15, q5, q9
    117 	vtbl.8	d8, {q14}, d16
    118 	vtbl.8	d9, {q14}, d17
    119 	veor	q10, q6, q9
    120 	vtbl.8	d10, {q15}, d16
    121 	vtbl.8	d11, {q15}, d17
    122 	veor	q11, q7, q9
    123 	vtbl.8	d12, {q10}, d16
    124 	vtbl.8	d13, {q10}, d17
    125 	vtbl.8	d14, {q11}, d16
    126 	vtbl.8	d15, {q11}, d17
    127 	vmov.i8	q8,#0x55			@ compose LBS0
    128 	vmov.i8	q9,#0x33			@ compose LBS1
    129 	vshr.u64	q10, q6, #1
    130 	vshr.u64	q11, q4, #1
    131 	veor	q10, q10, q7
    132 	veor	q11, q11, q5
    133 	vand	q10, q10, q8
    134 	vand	q11, q11, q8
    135 	veor	q7, q7, q10
    136 	vshl.u64	q10, q10, #1
    137 	veor	q5, q5, q11
    138 	vshl.u64	q11, q11, #1
    139 	veor	q6, q6, q10
    140 	veor	q4, q4, q11
    141 	vshr.u64	q10, q2, #1
    142 	vshr.u64	q11, q0, #1
    143 	veor	q10, q10, q3
    144 	veor	q11, q11, q1
    145 	vand	q10, q10, q8
    146 	vand	q11, q11, q8
    147 	veor	q3, q3, q10
    148 	vshl.u64	q10, q10, #1
    149 	veor	q1, q1, q11
    150 	vshl.u64	q11, q11, #1
    151 	veor	q2, q2, q10
    152 	veor	q0, q0, q11
    153 	vmov.i8	q8,#0x0f			@ compose LBS2
    154 	vshr.u64	q10, q5, #2
    155 	vshr.u64	q11, q4, #2
    156 	veor	q10, q10, q7
    157 	veor	q11, q11, q6
    158 	vand	q10, q10, q9
    159 	vand	q11, q11, q9
    160 	veor	q7, q7, q10
    161 	vshl.u64	q10, q10, #2
    162 	veor	q6, q6, q11
    163 	vshl.u64	q11, q11, #2
    164 	veor	q5, q5, q10
    165 	veor	q4, q4, q11
    166 	vshr.u64	q10, q1, #2
    167 	vshr.u64	q11, q0, #2
    168 	veor	q10, q10, q3
    169 	veor	q11, q11, q2
    170 	vand	q10, q10, q9
    171 	vand	q11, q11, q9
    172 	veor	q3, q3, q10
    173 	vshl.u64	q10, q10, #2
    174 	veor	q2, q2, q11
    175 	vshl.u64	q11, q11, #2
    176 	veor	q1, q1, q10
    177 	veor	q0, q0, q11
    178 	vshr.u64	q10, q3, #4
    179 	vshr.u64	q11, q2, #4
    180 	veor	q10, q10, q7
    181 	veor	q11, q11, q6
    182 	vand	q10, q10, q8
    183 	vand	q11, q11, q8
    184 	veor	q7, q7, q10
    185 	vshl.u64	q10, q10, #4
    186 	veor	q6, q6, q11
    187 	vshl.u64	q11, q11, #4
    188 	veor	q3, q3, q10
    189 	veor	q2, q2, q11
    190 	vshr.u64	q10, q1, #4
    191 	vshr.u64	q11, q0, #4
    192 	veor	q10, q10, q5
    193 	veor	q11, q11, q4
    194 	vand	q10, q10, q8
    195 	vand	q11, q11, q8
    196 	veor	q5, q5, q10
    197 	vshl.u64	q10, q10, #4
    198 	veor	q4, q4, q11
    199 	vshl.u64	q11, q11, #4
    200 	veor	q1, q1, q10
    201 	veor	q0, q0, q11
    202 	sub	r5,r5,#1
    203 	b	Ldec_sbox
    204 .align	4
    205 Ldec_loop:
    206 	vldmia	r4!, {q8,q9,q10,q11}
    207 	veor	q8, q8, q0
    208 	veor	q9, q9, q1
    209 	vtbl.8	d0, {q8}, d24
    210 	vtbl.8	d1, {q8}, d25
    211 	vldmia	r4!, {q8}
    212 	veor	q10, q10, q2
    213 	vtbl.8	d2, {q9}, d24
    214 	vtbl.8	d3, {q9}, d25
    215 	vldmia	r4!, {q9}
    216 	veor	q11, q11, q3
    217 	vtbl.8	d4, {q10}, d24
    218 	vtbl.8	d5, {q10}, d25
    219 	vldmia	r4!, {q10}
    220 	vtbl.8	d6, {q11}, d24
    221 	vtbl.8	d7, {q11}, d25
    222 	vldmia	r4!, {q11}
    223 	veor	q8, q8, q4
    224 	veor	q9, q9, q5
    225 	vtbl.8	d8, {q8}, d24
    226 	vtbl.8	d9, {q8}, d25
    227 	veor	q10, q10, q6
    228 	vtbl.8	d10, {q9}, d24
    229 	vtbl.8	d11, {q9}, d25
    230 	veor	q11, q11, q7
    231 	vtbl.8	d12, {q10}, d24
    232 	vtbl.8	d13, {q10}, d25
    233 	vtbl.8	d14, {q11}, d24
    234 	vtbl.8	d15, {q11}, d25
    235 Ldec_sbox:
    236 	veor	q1, q1, q4
    237 	veor	q3, q3, q4
    238 
    239 	veor	q4, q4, q7
    240 	veor	q1, q1, q6
    241 	veor	q2, q2, q7
    242 	veor	q6, q6, q4
    243 
    244 	veor	q0, q0, q1
    245 	veor	q2, q2, q5
    246 	veor	q7, q7, q6
    247 	veor	q3, q3, q0
    248 	veor	q5, q5, q0
    249 	veor	q1, q1, q3
    250 	veor	q11, q3, q0
    251 	veor	q10, q7, q4
    252 	veor	q9, q1, q6
    253 	veor	q13, q4, q0
    254 	vmov	q8, q10
    255 	veor	q12, q5, q2
    256 
    257 	vorr	q10, q10, q9
    258 	veor	q15, q11, q8
    259 	vand	q14, q11, q12
    260 	vorr	q11, q11, q12
    261 	veor	q12, q12, q9
    262 	vand	q8, q8, q9
    263 	veor	q9, q6, q2
    264 	vand	q15, q15, q12
    265 	vand	q13, q13, q9
    266 	veor	q9, q3, q7
    267 	veor	q12, q1, q5
    268 	veor	q11, q11, q13
    269 	veor	q10, q10, q13
    270 	vand	q13, q9, q12
    271 	vorr	q9, q9, q12
    272 	veor	q11, q11, q15
    273 	veor	q8, q8, q13
    274 	veor	q10, q10, q14
    275 	veor	q9, q9, q15
    276 	veor	q8, q8, q14
    277 	vand	q12, q4, q6
    278 	veor	q9, q9, q14
    279 	vand	q13, q0, q2
    280 	vand	q14, q7, q1
    281 	vorr	q15, q3, q5
    282 	veor	q11, q11, q12
    283 	veor	q9, q9, q14
    284 	veor	q8, q8, q15
    285 	veor	q10, q10, q13
    286 
    287 	@ Inv_GF16 	0, 	1, 	2, 	3, s0, s1, s2, s3
    288 
    289 	@ new smaller inversion
    290 
    291 	vand	q14, q11, q9
    292 	vmov	q12, q8
    293 
    294 	veor	q13, q10, q14
    295 	veor	q15, q8, q14
    296 	veor	q14, q8, q14	@ q14=q15
    297 
    298 	vbsl	q13, q9, q8
    299 	vbsl	q15, q11, q10
    300 	veor	q11, q11, q10
    301 
    302 	vbsl	q12, q13, q14
    303 	vbsl	q8, q14, q13
    304 
    305 	vand	q14, q12, q15
    306 	veor	q9, q9, q8
    307 
    308 	veor	q14, q14, q11
    309 	veor	q12, q5, q2
    310 	veor	q8, q1, q6
    311 	veor	q10, q15, q14
    312 	vand	q10, q10, q5
    313 	veor	q5, q5, q1
    314 	vand	q11, q1, q15
    315 	vand	q5, q5, q14
    316 	veor	q1, q11, q10
    317 	veor	q5, q5, q11
    318 	veor	q15, q15, q13
    319 	veor	q14, q14, q9
    320 	veor	q11, q15, q14
    321 	veor	q10, q13, q9
    322 	vand	q11, q11, q12
    323 	vand	q10, q10, q2
    324 	veor	q12, q12, q8
    325 	veor	q2, q2, q6
    326 	vand	q8, q8, q15
    327 	vand	q6, q6, q13
    328 	vand	q12, q12, q14
    329 	vand	q2, q2, q9
    330 	veor	q8, q8, q12
    331 	veor	q2, q2, q6
    332 	veor	q12, q12, q11
    333 	veor	q6, q6, q10
    334 	veor	q5, q5, q12
    335 	veor	q2, q2, q12
    336 	veor	q1, q1, q8
    337 	veor	q6, q6, q8
    338 
    339 	veor	q12, q3, q0
    340 	veor	q8, q7, q4
    341 	veor	q11, q15, q14
    342 	veor	q10, q13, q9
    343 	vand	q11, q11, q12
    344 	vand	q10, q10, q0
    345 	veor	q12, q12, q8
    346 	veor	q0, q0, q4
    347 	vand	q8, q8, q15
    348 	vand	q4, q4, q13
    349 	vand	q12, q12, q14
    350 	vand	q0, q0, q9
    351 	veor	q8, q8, q12
    352 	veor	q0, q0, q4
    353 	veor	q12, q12, q11
    354 	veor	q4, q4, q10
    355 	veor	q15, q15, q13
    356 	veor	q14, q14, q9
    357 	veor	q10, q15, q14
    358 	vand	q10, q10, q3
    359 	veor	q3, q3, q7
    360 	vand	q11, q7, q15
    361 	vand	q3, q3, q14
    362 	veor	q7, q11, q10
    363 	veor	q3, q3, q11
    364 	veor	q3, q3, q12
    365 	veor	q0, q0, q12
    366 	veor	q7, q7, q8
    367 	veor	q4, q4, q8
    368 	veor	q1, q1, q7
    369 	veor	q6, q6, q5
    370 
    371 	veor	q4, q4, q1
    372 	veor	q2, q2, q7
    373 	veor	q5, q5, q7
    374 	veor	q4, q4, q2
    375 	veor	q7, q7, q0
    376 	veor	q4, q4, q5
    377 	veor	q3, q3, q6
    378 	veor	q6, q6, q1
    379 	veor	q3, q3, q4
    380 
    381 	veor	q4, q4, q0
    382 	veor	q7, q7, q3
    383 	subs	r5,r5,#1
    384 	bcc	Ldec_done
    385 	@ multiplication by 0x05-0x00-0x04-0x00
    386 	vext.8	q8, q0, q0, #8
    387 	vext.8	q14, q3, q3, #8
    388 	vext.8	q15, q5, q5, #8
    389 	veor	q8, q8, q0
    390 	vext.8	q9, q1, q1, #8
    391 	veor	q14, q14, q3
    392 	vext.8	q10, q6, q6, #8
    393 	veor	q15, q15, q5
    394 	vext.8	q11, q4, q4, #8
    395 	veor	q9, q9, q1
    396 	vext.8	q12, q2, q2, #8
    397 	veor	q10, q10, q6
    398 	vext.8	q13, q7, q7, #8
    399 	veor	q11, q11, q4
    400 	veor	q12, q12, q2
    401 	veor	q13, q13, q7
    402 
    403 	veor	q0, q0, q14
    404 	veor	q1, q1, q14
    405 	veor	q6, q6, q8
    406 	veor	q2, q2, q10
    407 	veor	q4, q4, q9
    408 	veor	q1, q1, q15
    409 	veor	q6, q6, q15
    410 	veor	q2, q2, q14
    411 	veor	q7, q7, q11
    412 	veor	q4, q4, q14
    413 	veor	q3, q3, q12
    414 	veor	q2, q2, q15
    415 	veor	q7, q7, q15
    416 	veor	q5, q5, q13
    417 	vext.8	q8, q0, q0, #12	@ x0 <<< 32
    418 	vext.8	q9, q1, q1, #12
    419 	veor	q0, q0, q8		@ x0 ^ (x0 <<< 32)
    420 	vext.8	q10, q6, q6, #12
    421 	veor	q1, q1, q9
    422 	vext.8	q11, q4, q4, #12
    423 	veor	q6, q6, q10
    424 	vext.8	q12, q2, q2, #12
    425 	veor	q4, q4, q11
    426 	vext.8	q13, q7, q7, #12
    427 	veor	q2, q2, q12
    428 	vext.8	q14, q3, q3, #12
    429 	veor	q7, q7, q13
    430 	vext.8	q15, q5, q5, #12
    431 	veor	q3, q3, q14
    432 
    433 	veor	q9, q9, q0
    434 	veor	q5, q5, q15
    435 	vext.8	q0, q0, q0, #8		@ (x0 ^ (x0 <<< 32)) <<< 64)
    436 	veor	q10, q10, q1
    437 	veor	q8, q8, q5
    438 	veor	q9, q9, q5
    439 	vext.8	q1, q1, q1, #8
    440 	veor	q13, q13, q2
    441 	veor	q0, q0, q8
    442 	veor	q14, q14, q7
    443 	veor	q1, q1, q9
    444 	vext.8	q8, q2, q2, #8
    445 	veor	q12, q12, q4
    446 	vext.8	q9, q7, q7, #8
    447 	veor	q15, q15, q3
    448 	vext.8	q2, q4, q4, #8
    449 	veor	q11, q11, q6
    450 	vext.8	q7, q5, q5, #8
    451 	veor	q12, q12, q5
    452 	vext.8	q4, q3, q3, #8
    453 	veor	q11, q11, q5
    454 	vext.8	q3, q6, q6, #8
    455 	veor	q5, q9, q13
    456 	veor	q11, q11, q2
    457 	veor	q7, q7, q15
    458 	veor	q6, q4, q14
    459 	veor	q4, q8, q12
    460 	veor	q2, q3, q10
    461 	vmov	q3, q11
    462 	 @ vmov	q5, q9
    463 	vldmia	r6, {q12}		@ LISR
    464 	ite	eq				@ Thumb2 thing, sanity check in ARM
    465 	addeq	r6,r6,#0x10
    466 	bne	Ldec_loop
    467 	vldmia	r6, {q12}		@ LISRM0
    468 	b	Ldec_loop
    469 .align	4
    470 Ldec_done:
    471 	vmov.i8	q8,#0x55			@ compose LBS0
    472 	vmov.i8	q9,#0x33			@ compose LBS1
    473 	vshr.u64	q10, q3, #1
    474 	vshr.u64	q11, q2, #1
    475 	veor	q10, q10, q5
    476 	veor	q11, q11, q7
    477 	vand	q10, q10, q8
    478 	vand	q11, q11, q8
    479 	veor	q5, q5, q10
    480 	vshl.u64	q10, q10, #1
    481 	veor	q7, q7, q11
    482 	vshl.u64	q11, q11, #1
    483 	veor	q3, q3, q10
    484 	veor	q2, q2, q11
    485 	vshr.u64	q10, q6, #1
    486 	vshr.u64	q11, q0, #1
    487 	veor	q10, q10, q4
    488 	veor	q11, q11, q1
    489 	vand	q10, q10, q8
    490 	vand	q11, q11, q8
    491 	veor	q4, q4, q10
    492 	vshl.u64	q10, q10, #1
    493 	veor	q1, q1, q11
    494 	vshl.u64	q11, q11, #1
    495 	veor	q6, q6, q10
    496 	veor	q0, q0, q11
    497 	vmov.i8	q8,#0x0f			@ compose LBS2
    498 	vshr.u64	q10, q7, #2
    499 	vshr.u64	q11, q2, #2
    500 	veor	q10, q10, q5
    501 	veor	q11, q11, q3
    502 	vand	q10, q10, q9
    503 	vand	q11, q11, q9
    504 	veor	q5, q5, q10
    505 	vshl.u64	q10, q10, #2
    506 	veor	q3, q3, q11
    507 	vshl.u64	q11, q11, #2
    508 	veor	q7, q7, q10
    509 	veor	q2, q2, q11
    510 	vshr.u64	q10, q1, #2
    511 	vshr.u64	q11, q0, #2
    512 	veor	q10, q10, q4
    513 	veor	q11, q11, q6
    514 	vand	q10, q10, q9
    515 	vand	q11, q11, q9
    516 	veor	q4, q4, q10
    517 	vshl.u64	q10, q10, #2
    518 	veor	q6, q6, q11
    519 	vshl.u64	q11, q11, #2
    520 	veor	q1, q1, q10
    521 	veor	q0, q0, q11
    522 	vshr.u64	q10, q4, #4
    523 	vshr.u64	q11, q6, #4
    524 	veor	q10, q10, q5
    525 	veor	q11, q11, q3
    526 	vand	q10, q10, q8
    527 	vand	q11, q11, q8
    528 	veor	q5, q5, q10
    529 	vshl.u64	q10, q10, #4
    530 	veor	q3, q3, q11
    531 	vshl.u64	q11, q11, #4
    532 	veor	q4, q4, q10
    533 	veor	q6, q6, q11
    534 	vshr.u64	q10, q1, #4
    535 	vshr.u64	q11, q0, #4
    536 	veor	q10, q10, q7
    537 	veor	q11, q11, q2
    538 	vand	q10, q10, q8
    539 	vand	q11, q11, q8
    540 	veor	q7, q7, q10
    541 	vshl.u64	q10, q10, #4
    542 	veor	q2, q2, q11
    543 	vshl.u64	q11, q11, #4
    544 	veor	q1, q1, q10
    545 	veor	q0, q0, q11
    546 	vldmia	r4, {q8}			@ last round key
    547 	veor	q6, q6, q8
    548 	veor	q4, q4, q8
    549 	veor	q2, q2, q8
    550 	veor	q7, q7, q8
    551 	veor	q3, q3, q8
    552 	veor	q5, q5, q8
    553 	veor	q0, q0, q8
    554 	veor	q1, q1, q8
    555 	bx	lr
    556 
    557 
    558 
    559 .align	6
    560 _bsaes_const:
    561 LM0ISR:@ InvShiftRows constants
    562 .quad	0x0a0e0206070b0f03, 0x0004080c0d010509
    563 LISR:
    564 .quad	0x0504070602010003, 0x0f0e0d0c080b0a09
    565 LISRM0:
    566 .quad	0x01040b0e0205080f, 0x0306090c00070a0d
    567 LM0SR:@ ShiftRows constants
    568 .quad	0x0a0e02060f03070b, 0x0004080c05090d01
    569 LSR:
    570 .quad	0x0504070600030201, 0x0f0e0d0c0a09080b
    571 LSRM0:
    572 .quad	0x0304090e00050a0f, 0x01060b0c0207080d
    573 LM0:
    574 .quad	0x02060a0e03070b0f, 0x0004080c0105090d
    575 LREVM0SR:
    576 .quad	0x090d01050c000408, 0x03070b0f060a0e02
    577 .byte	66,105,116,45,115,108,105,99,101,100,32,65,69,83,32,102,111,114,32,78,69,79,78,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0
    578 .align	2
    579 .align	6
    580 
    581 
    582 #ifdef __thumb2__
    583 .thumb_func	_bsaes_encrypt8
    584 #endif
    585 .align	4
    586 _bsaes_encrypt8:
    587 	adr	r6,.
    588 	vldmia	r4!, {q9}		@ round 0 key
    589 #ifdef	__APPLE__
    590 	adr	r6,LM0SR
    591 #else
    592 	sub	r6,r6,#_bsaes_encrypt8-LM0SR
    593 #endif
    594 
    595 	vldmia	r6!, {q8}		@ LM0SR
    596 _bsaes_encrypt8_alt:
    597 	veor	q10, q0, q9	@ xor with round0 key
    598 	veor	q11, q1, q9
    599 	vtbl.8	d0, {q10}, d16
    600 	vtbl.8	d1, {q10}, d17
    601 	veor	q12, q2, q9
    602 	vtbl.8	d2, {q11}, d16
    603 	vtbl.8	d3, {q11}, d17
    604 	veor	q13, q3, q9
    605 	vtbl.8	d4, {q12}, d16
    606 	vtbl.8	d5, {q12}, d17
    607 	veor	q14, q4, q9
    608 	vtbl.8	d6, {q13}, d16
    609 	vtbl.8	d7, {q13}, d17
    610 	veor	q15, q5, q9
    611 	vtbl.8	d8, {q14}, d16
    612 	vtbl.8	d9, {q14}, d17
    613 	veor	q10, q6, q9
    614 	vtbl.8	d10, {q15}, d16
    615 	vtbl.8	d11, {q15}, d17
    616 	veor	q11, q7, q9
    617 	vtbl.8	d12, {q10}, d16
    618 	vtbl.8	d13, {q10}, d17
    619 	vtbl.8	d14, {q11}, d16
    620 	vtbl.8	d15, {q11}, d17
    621 _bsaes_encrypt8_bitslice:
    622 	vmov.i8	q8,#0x55			@ compose LBS0
    623 	vmov.i8	q9,#0x33			@ compose LBS1
    624 	vshr.u64	q10, q6, #1
    625 	vshr.u64	q11, q4, #1
    626 	veor	q10, q10, q7
    627 	veor	q11, q11, q5
    628 	vand	q10, q10, q8
    629 	vand	q11, q11, q8
    630 	veor	q7, q7, q10
    631 	vshl.u64	q10, q10, #1
    632 	veor	q5, q5, q11
    633 	vshl.u64	q11, q11, #1
    634 	veor	q6, q6, q10
    635 	veor	q4, q4, q11
    636 	vshr.u64	q10, q2, #1
    637 	vshr.u64	q11, q0, #1
    638 	veor	q10, q10, q3
    639 	veor	q11, q11, q1
    640 	vand	q10, q10, q8
    641 	vand	q11, q11, q8
    642 	veor	q3, q3, q10
    643 	vshl.u64	q10, q10, #1
    644 	veor	q1, q1, q11
    645 	vshl.u64	q11, q11, #1
    646 	veor	q2, q2, q10
    647 	veor	q0, q0, q11
    648 	vmov.i8	q8,#0x0f			@ compose LBS2
    649 	vshr.u64	q10, q5, #2
    650 	vshr.u64	q11, q4, #2
    651 	veor	q10, q10, q7
    652 	veor	q11, q11, q6
    653 	vand	q10, q10, q9
    654 	vand	q11, q11, q9
    655 	veor	q7, q7, q10
    656 	vshl.u64	q10, q10, #2
    657 	veor	q6, q6, q11
    658 	vshl.u64	q11, q11, #2
    659 	veor	q5, q5, q10
    660 	veor	q4, q4, q11
    661 	vshr.u64	q10, q1, #2
    662 	vshr.u64	q11, q0, #2
    663 	veor	q10, q10, q3
    664 	veor	q11, q11, q2
    665 	vand	q10, q10, q9
    666 	vand	q11, q11, q9
    667 	veor	q3, q3, q10
    668 	vshl.u64	q10, q10, #2
    669 	veor	q2, q2, q11
    670 	vshl.u64	q11, q11, #2
    671 	veor	q1, q1, q10
    672 	veor	q0, q0, q11
    673 	vshr.u64	q10, q3, #4
    674 	vshr.u64	q11, q2, #4
    675 	veor	q10, q10, q7
    676 	veor	q11, q11, q6
    677 	vand	q10, q10, q8
    678 	vand	q11, q11, q8
    679 	veor	q7, q7, q10
    680 	vshl.u64	q10, q10, #4
    681 	veor	q6, q6, q11
    682 	vshl.u64	q11, q11, #4
    683 	veor	q3, q3, q10
    684 	veor	q2, q2, q11
    685 	vshr.u64	q10, q1, #4
    686 	vshr.u64	q11, q0, #4
    687 	veor	q10, q10, q5
    688 	veor	q11, q11, q4
    689 	vand	q10, q10, q8
    690 	vand	q11, q11, q8
    691 	veor	q5, q5, q10
    692 	vshl.u64	q10, q10, #4
    693 	veor	q4, q4, q11
    694 	vshl.u64	q11, q11, #4
    695 	veor	q1, q1, q10
    696 	veor	q0, q0, q11
    697 	sub	r5,r5,#1
    698 	b	Lenc_sbox
    699 .align	4
    700 Lenc_loop:
    701 	vldmia	r4!, {q8,q9,q10,q11}
    702 	veor	q8, q8, q0
    703 	veor	q9, q9, q1
    704 	vtbl.8	d0, {q8}, d24
    705 	vtbl.8	d1, {q8}, d25
    706 	vldmia	r4!, {q8}
    707 	veor	q10, q10, q2
    708 	vtbl.8	d2, {q9}, d24
    709 	vtbl.8	d3, {q9}, d25
    710 	vldmia	r4!, {q9}
    711 	veor	q11, q11, q3
    712 	vtbl.8	d4, {q10}, d24
    713 	vtbl.8	d5, {q10}, d25
    714 	vldmia	r4!, {q10}
    715 	vtbl.8	d6, {q11}, d24
    716 	vtbl.8	d7, {q11}, d25
    717 	vldmia	r4!, {q11}
    718 	veor	q8, q8, q4
    719 	veor	q9, q9, q5
    720 	vtbl.8	d8, {q8}, d24
    721 	vtbl.8	d9, {q8}, d25
    722 	veor	q10, q10, q6
    723 	vtbl.8	d10, {q9}, d24
    724 	vtbl.8	d11, {q9}, d25
    725 	veor	q11, q11, q7
    726 	vtbl.8	d12, {q10}, d24
    727 	vtbl.8	d13, {q10}, d25
    728 	vtbl.8	d14, {q11}, d24
    729 	vtbl.8	d15, {q11}, d25
    730 Lenc_sbox:
    731 	veor	q2, q2, q1
    732 	veor	q5, q5, q6
    733 	veor	q3, q3, q0
    734 	veor	q6, q6, q2
    735 	veor	q5, q5, q0
    736 
    737 	veor	q6, q6, q3
    738 	veor	q3, q3, q7
    739 	veor	q7, q7, q5
    740 	veor	q3, q3, q4
    741 	veor	q4, q4, q5
    742 
    743 	veor	q2, q2, q7
    744 	veor	q3, q3, q1
    745 	veor	q1, q1, q5
    746 	veor	q11, q7, q4
    747 	veor	q10, q1, q2
    748 	veor	q9, q5, q3
    749 	veor	q13, q2, q4
    750 	vmov	q8, q10
    751 	veor	q12, q6, q0
    752 
    753 	vorr	q10, q10, q9
    754 	veor	q15, q11, q8
    755 	vand	q14, q11, q12
    756 	vorr	q11, q11, q12
    757 	veor	q12, q12, q9
    758 	vand	q8, q8, q9
    759 	veor	q9, q3, q0
    760 	vand	q15, q15, q12
    761 	vand	q13, q13, q9
    762 	veor	q9, q7, q1
    763 	veor	q12, q5, q6
    764 	veor	q11, q11, q13
    765 	veor	q10, q10, q13
    766 	vand	q13, q9, q12
    767 	vorr	q9, q9, q12
    768 	veor	q11, q11, q15
    769 	veor	q8, q8, q13
    770 	veor	q10, q10, q14
    771 	veor	q9, q9, q15
    772 	veor	q8, q8, q14
    773 	vand	q12, q2, q3
    774 	veor	q9, q9, q14
    775 	vand	q13, q4, q0
    776 	vand	q14, q1, q5
    777 	vorr	q15, q7, q6
    778 	veor	q11, q11, q12
    779 	veor	q9, q9, q14
    780 	veor	q8, q8, q15
    781 	veor	q10, q10, q13
    782 
    783 	@ Inv_GF16 	0, 	1, 	2, 	3, s0, s1, s2, s3
    784 
    785 	@ new smaller inversion
    786 
    787 	vand	q14, q11, q9
    788 	vmov	q12, q8
    789 
    790 	veor	q13, q10, q14
    791 	veor	q15, q8, q14
    792 	veor	q14, q8, q14	@ q14=q15
    793 
    794 	vbsl	q13, q9, q8
    795 	vbsl	q15, q11, q10
    796 	veor	q11, q11, q10
    797 
    798 	vbsl	q12, q13, q14
    799 	vbsl	q8, q14, q13
    800 
    801 	vand	q14, q12, q15
    802 	veor	q9, q9, q8
    803 
    804 	veor	q14, q14, q11
    805 	veor	q12, q6, q0
    806 	veor	q8, q5, q3
    807 	veor	q10, q15, q14
    808 	vand	q10, q10, q6
    809 	veor	q6, q6, q5
    810 	vand	q11, q5, q15
    811 	vand	q6, q6, q14
    812 	veor	q5, q11, q10
    813 	veor	q6, q6, q11
    814 	veor	q15, q15, q13
    815 	veor	q14, q14, q9
    816 	veor	q11, q15, q14
    817 	veor	q10, q13, q9
    818 	vand	q11, q11, q12
    819 	vand	q10, q10, q0
    820 	veor	q12, q12, q8
    821 	veor	q0, q0, q3
    822 	vand	q8, q8, q15
    823 	vand	q3, q3, q13
    824 	vand	q12, q12, q14
    825 	vand	q0, q0, q9
    826 	veor	q8, q8, q12
    827 	veor	q0, q0, q3
    828 	veor	q12, q12, q11
    829 	veor	q3, q3, q10
    830 	veor	q6, q6, q12
    831 	veor	q0, q0, q12
    832 	veor	q5, q5, q8
    833 	veor	q3, q3, q8
    834 
    835 	veor	q12, q7, q4
    836 	veor	q8, q1, q2
    837 	veor	q11, q15, q14
    838 	veor	q10, q13, q9
    839 	vand	q11, q11, q12
    840 	vand	q10, q10, q4
    841 	veor	q12, q12, q8
    842 	veor	q4, q4, q2
    843 	vand	q8, q8, q15
    844 	vand	q2, q2, q13
    845 	vand	q12, q12, q14
    846 	vand	q4, q4, q9
    847 	veor	q8, q8, q12
    848 	veor	q4, q4, q2
    849 	veor	q12, q12, q11
    850 	veor	q2, q2, q10
    851 	veor	q15, q15, q13
    852 	veor	q14, q14, q9
    853 	veor	q10, q15, q14
    854 	vand	q10, q10, q7
    855 	veor	q7, q7, q1
    856 	vand	q11, q1, q15
    857 	vand	q7, q7, q14
    858 	veor	q1, q11, q10
    859 	veor	q7, q7, q11
    860 	veor	q7, q7, q12
    861 	veor	q4, q4, q12
    862 	veor	q1, q1, q8
    863 	veor	q2, q2, q8
    864 	veor	q7, q7, q0
    865 	veor	q1, q1, q6
    866 	veor	q6, q6, q0
    867 	veor	q4, q4, q7
    868 	veor	q0, q0, q1
    869 
    870 	veor	q1, q1, q5
    871 	veor	q5, q5, q2
    872 	veor	q2, q2, q3
    873 	veor	q3, q3, q5
    874 	veor	q4, q4, q5
    875 
    876 	veor	q6, q6, q3
    877 	subs	r5,r5,#1
    878 	bcc	Lenc_done
    879 	vext.8	q8, q0, q0, #12	@ x0 <<< 32
    880 	vext.8	q9, q1, q1, #12
    881 	veor	q0, q0, q8		@ x0 ^ (x0 <<< 32)
    882 	vext.8	q10, q4, q4, #12
    883 	veor	q1, q1, q9
    884 	vext.8	q11, q6, q6, #12
    885 	veor	q4, q4, q10
    886 	vext.8	q12, q3, q3, #12
    887 	veor	q6, q6, q11
    888 	vext.8	q13, q7, q7, #12
    889 	veor	q3, q3, q12
    890 	vext.8	q14, q2, q2, #12
    891 	veor	q7, q7, q13
    892 	vext.8	q15, q5, q5, #12
    893 	veor	q2, q2, q14
    894 
    895 	veor	q9, q9, q0
    896 	veor	q5, q5, q15
    897 	vext.8	q0, q0, q0, #8		@ (x0 ^ (x0 <<< 32)) <<< 64)
    898 	veor	q10, q10, q1
    899 	veor	q8, q8, q5
    900 	veor	q9, q9, q5
    901 	vext.8	q1, q1, q1, #8
    902 	veor	q13, q13, q3
    903 	veor	q0, q0, q8
    904 	veor	q14, q14, q7
    905 	veor	q1, q1, q9
    906 	vext.8	q8, q3, q3, #8
    907 	veor	q12, q12, q6
    908 	vext.8	q9, q7, q7, #8
    909 	veor	q15, q15, q2
    910 	vext.8	q3, q6, q6, #8
    911 	veor	q11, q11, q4
    912 	vext.8	q7, q5, q5, #8
    913 	veor	q12, q12, q5
    914 	vext.8	q6, q2, q2, #8
    915 	veor	q11, q11, q5
    916 	vext.8	q2, q4, q4, #8
    917 	veor	q5, q9, q13
    918 	veor	q4, q8, q12
    919 	veor	q3, q3, q11
    920 	veor	q7, q7, q15
    921 	veor	q6, q6, q14
    922 	 @ vmov	q4, q8
    923 	veor	q2, q2, q10
    924 	 @ vmov	q5, q9
    925 	vldmia	r6, {q12}		@ LSR
    926 	ite	eq				@ Thumb2 thing, samity check in ARM
    927 	addeq	r6,r6,#0x10
    928 	bne	Lenc_loop
    929 	vldmia	r6, {q12}		@ LSRM0
    930 	b	Lenc_loop
    931 .align	4
    932 Lenc_done:
    933 	vmov.i8	q8,#0x55			@ compose LBS0
    934 	vmov.i8	q9,#0x33			@ compose LBS1
    935 	vshr.u64	q10, q2, #1
    936 	vshr.u64	q11, q3, #1
    937 	veor	q10, q10, q5
    938 	veor	q11, q11, q7
    939 	vand	q10, q10, q8
    940 	vand	q11, q11, q8
    941 	veor	q5, q5, q10
    942 	vshl.u64	q10, q10, #1
    943 	veor	q7, q7, q11
    944 	vshl.u64	q11, q11, #1
    945 	veor	q2, q2, q10
    946 	veor	q3, q3, q11
    947 	vshr.u64	q10, q4, #1
    948 	vshr.u64	q11, q0, #1
    949 	veor	q10, q10, q6
    950 	veor	q11, q11, q1
    951 	vand	q10, q10, q8
    952 	vand	q11, q11, q8
    953 	veor	q6, q6, q10
    954 	vshl.u64	q10, q10, #1
    955 	veor	q1, q1, q11
    956 	vshl.u64	q11, q11, #1
    957 	veor	q4, q4, q10
    958 	veor	q0, q0, q11
    959 	vmov.i8	q8,#0x0f			@ compose LBS2
    960 	vshr.u64	q10, q7, #2
    961 	vshr.u64	q11, q3, #2
    962 	veor	q10, q10, q5
    963 	veor	q11, q11, q2
    964 	vand	q10, q10, q9
    965 	vand	q11, q11, q9
    966 	veor	q5, q5, q10
    967 	vshl.u64	q10, q10, #2
    968 	veor	q2, q2, q11
    969 	vshl.u64	q11, q11, #2
    970 	veor	q7, q7, q10
    971 	veor	q3, q3, q11
    972 	vshr.u64	q10, q1, #2
    973 	vshr.u64	q11, q0, #2
    974 	veor	q10, q10, q6
    975 	veor	q11, q11, q4
    976 	vand	q10, q10, q9
    977 	vand	q11, q11, q9
    978 	veor	q6, q6, q10
    979 	vshl.u64	q10, q10, #2
    980 	veor	q4, q4, q11
    981 	vshl.u64	q11, q11, #2
    982 	veor	q1, q1, q10
    983 	veor	q0, q0, q11
    984 	vshr.u64	q10, q6, #4
    985 	vshr.u64	q11, q4, #4
    986 	veor	q10, q10, q5
    987 	veor	q11, q11, q2
    988 	vand	q10, q10, q8
    989 	vand	q11, q11, q8
    990 	veor	q5, q5, q10
    991 	vshl.u64	q10, q10, #4
    992 	veor	q2, q2, q11
    993 	vshl.u64	q11, q11, #4
    994 	veor	q6, q6, q10
    995 	veor	q4, q4, q11
    996 	vshr.u64	q10, q1, #4
    997 	vshr.u64	q11, q0, #4
    998 	veor	q10, q10, q7
    999 	veor	q11, q11, q3
   1000 	vand	q10, q10, q8
   1001 	vand	q11, q11, q8
   1002 	veor	q7, q7, q10
   1003 	vshl.u64	q10, q10, #4
   1004 	veor	q3, q3, q11
   1005 	vshl.u64	q11, q11, #4
   1006 	veor	q1, q1, q10
   1007 	veor	q0, q0, q11
   1008 	vldmia	r4, {q8}			@ last round key
   1009 	veor	q4, q4, q8
   1010 	veor	q6, q6, q8
   1011 	veor	q3, q3, q8
   1012 	veor	q7, q7, q8
   1013 	veor	q2, q2, q8
   1014 	veor	q5, q5, q8
   1015 	veor	q0, q0, q8
   1016 	veor	q1, q1, q8
   1017 	bx	lr
   1018 
   1019 #ifdef __thumb2__
   1020 .thumb_func	_bsaes_key_convert
   1021 #endif
   1022 .align	4
   1023 _bsaes_key_convert:
   1024 	adr	r6,.
   1025 	vld1.8	{q7},  [r4]!		@ load round 0 key
   1026 #ifdef	__APPLE__
   1027 	adr	r6,LM0
   1028 #else
   1029 	sub	r6,r6,#_bsaes_key_convert-LM0
   1030 #endif
   1031 	vld1.8	{q15}, [r4]!		@ load round 1 key
   1032 
   1033 	vmov.i8	q8,  #0x01			@ bit masks
   1034 	vmov.i8	q9,  #0x02
   1035 	vmov.i8	q10, #0x04
   1036 	vmov.i8	q11, #0x08
   1037 	vmov.i8	q12, #0x10
   1038 	vmov.i8	q13, #0x20
   1039 	vldmia	r6, {q14}		@ LM0
   1040 
   1041 #ifdef __ARMEL__
   1042 	vrev32.8	q7,  q7
   1043 	vrev32.8	q15, q15
   1044 #endif
   1045 	sub	r5,r5,#1
   1046 	vstmia	r12!, {q7}		@ save round 0 key
   1047 	b	Lkey_loop
   1048 
   1049 .align	4
   1050 Lkey_loop:
   1051 	vtbl.8	d14,{q15},d28
   1052 	vtbl.8	d15,{q15},d29
   1053 	vmov.i8	q6,  #0x40
   1054 	vmov.i8	q15, #0x80
   1055 
   1056 	vtst.8	q0, q7, q8
   1057 	vtst.8	q1, q7, q9
   1058 	vtst.8	q2, q7, q10
   1059 	vtst.8	q3, q7, q11
   1060 	vtst.8	q4, q7, q12
   1061 	vtst.8	q5, q7, q13
   1062 	vtst.8	q6, q7, q6
   1063 	vtst.8	q7, q7, q15
   1064 	vld1.8	{q15}, [r4]!		@ load next round key
   1065 	vmvn	q0, q0		@ "pnot"
   1066 	vmvn	q1, q1
   1067 	vmvn	q5, q5
   1068 	vmvn	q6, q6
   1069 #ifdef __ARMEL__
   1070 	vrev32.8	q15, q15
   1071 #endif
   1072 	subs	r5,r5,#1
   1073 	vstmia	r12!,{q0,q1,q2,q3,q4,q5,q6,q7}		@ write bit-sliced round key
   1074 	bne	Lkey_loop
   1075 
   1076 	vmov.i8	q7,#0x63			@ compose L63
   1077 	@ don't save last round key
   1078 	bx	lr
   1079 
   1080 
   1081 
   1082 
   1083 .globl	_bsaes_cbc_encrypt
   1084 .private_extern	_bsaes_cbc_encrypt
   1085 #ifdef __thumb2__
   1086 .thumb_func	_bsaes_cbc_encrypt
   1087 #endif
   1088 .align	5
   1089 _bsaes_cbc_encrypt:
   1090 #ifndef	__KERNEL__
   1091 	cmp	r2, #128
   1092 #ifndef	__thumb__
   1093 	blo	_AES_cbc_encrypt
   1094 #else
   1095 	bhs	1f
   1096 	b	_AES_cbc_encrypt
   1097 1:
   1098 #endif
   1099 #endif
   1100 
   1101 	@ it is up to the caller to make sure we are called with enc == 0
   1102 
   1103 	mov	ip, sp
   1104 	stmdb	sp!, {r4,r5,r6,r7,r8,r9,r10, lr}
   1105 	VFP_ABI_PUSH
   1106 	ldr	r8, [ip]			@ IV is 1st arg on the stack
   1107 	mov	r2, r2, lsr#4		@ len in 16 byte blocks
   1108 	sub	sp, #0x10			@ scratch space to carry over the IV
   1109 	mov	r9, sp				@ save sp
   1110 
   1111 	ldr	r10, [r3, #240]		@ get # of rounds
   1112 #ifndef	BSAES_ASM_EXTENDED_KEY
   1113 	@ allocate the key schedule on the stack
   1114 	sub	r12, sp, r10, lsl#7		@ 128 bytes per inner round key
   1115 	add	r12, #96			@ sifze of bit-slices key schedule
   1116 
   1117 	@ populate the key schedule
   1118 	mov	r4, r3			@ pass key
   1119 	mov	r5, r10			@ pass # of rounds
   1120 	mov	sp, r12				@ sp is sp
   1121 	bl	_bsaes_key_convert
   1122 	vldmia	sp, {q6}
   1123 	vstmia	r12,  {q15}		@ save last round key
   1124 	veor	q7, q7, q6	@ fix up round 0 key
   1125 	vstmia	sp, {q7}
   1126 #else
   1127 	ldr	r12, [r3, #244]
   1128 	eors	r12, #1
   1129 	beq	0f
   1130 
   1131 	@ populate the key schedule
   1132 	str	r12, [r3, #244]
   1133 	mov	r4, r3			@ pass key
   1134 	mov	r5, r10			@ pass # of rounds
   1135 	add	r12, r3, #248			@ pass key schedule
   1136 	bl	_bsaes_key_convert
   1137 	add	r4, r3, #248
   1138 	vldmia	r4, {q6}
   1139 	vstmia	r12, {q15}			@ save last round key
   1140 	veor	q7, q7, q6	@ fix up round 0 key
   1141 	vstmia	r4, {q7}
   1142 
   1143 .align	2
   1144 
   1145 #endif
   1146 
   1147 	vld1.8	{q15}, [r8]		@ load IV
   1148 	b	Lcbc_dec_loop
   1149 
   1150 .align	4
   1151 Lcbc_dec_loop:
   1152 	subs	r2, r2, #0x8
   1153 	bmi	Lcbc_dec_loop_finish
   1154 
   1155 	vld1.8	{q0,q1}, [r0]!	@ load input
   1156 	vld1.8	{q2,q3}, [r0]!
   1157 #ifndef	BSAES_ASM_EXTENDED_KEY
   1158 	mov	r4, sp			@ pass the key
   1159 #else
   1160 	add	r4, r3, #248
   1161 #endif
   1162 	vld1.8	{q4,q5}, [r0]!
   1163 	mov	r5, r10
   1164 	vld1.8	{q6,q7}, [r0]
   1165 	sub	r0, r0, #0x60
   1166 	vstmia	r9, {q15}			@ put aside IV
   1167 
   1168 	bl	_bsaes_decrypt8
   1169 
   1170 	vldmia	r9, {q14}			@ reload IV
   1171 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1172 	veor	q0, q0, q14	@ ^= IV
   1173 	vld1.8	{q10,q11}, [r0]!
   1174 	veor	q1, q1, q8
   1175 	veor	q6, q6, q9
   1176 	vld1.8	{q12,q13}, [r0]!
   1177 	veor	q4, q4, q10
   1178 	veor	q2, q2, q11
   1179 	vld1.8	{q14,q15}, [r0]!
   1180 	veor	q7, q7, q12
   1181 	vst1.8	{q0,q1}, [r1]!	@ write output
   1182 	veor	q3, q3, q13
   1183 	vst1.8	{q6}, [r1]!
   1184 	veor	q5, q5, q14
   1185 	vst1.8	{q4}, [r1]!
   1186 	vst1.8	{q2}, [r1]!
   1187 	vst1.8	{q7}, [r1]!
   1188 	vst1.8	{q3}, [r1]!
   1189 	vst1.8	{q5}, [r1]!
   1190 
   1191 	b	Lcbc_dec_loop
   1192 
   1193 Lcbc_dec_loop_finish:
   1194 	adds	r2, r2, #8
   1195 	beq	Lcbc_dec_done
   1196 
   1197 	vld1.8	{q0}, [r0]!		@ load input
   1198 	cmp	r2, #2
   1199 	blo	Lcbc_dec_one
   1200 	vld1.8	{q1}, [r0]!
   1201 #ifndef	BSAES_ASM_EXTENDED_KEY
   1202 	mov	r4, sp			@ pass the key
   1203 #else
   1204 	add	r4, r3, #248
   1205 #endif
   1206 	mov	r5, r10
   1207 	vstmia	r9, {q15}			@ put aside IV
   1208 	beq	Lcbc_dec_two
   1209 	vld1.8	{q2}, [r0]!
   1210 	cmp	r2, #4
   1211 	blo	Lcbc_dec_three
   1212 	vld1.8	{q3}, [r0]!
   1213 	beq	Lcbc_dec_four
   1214 	vld1.8	{q4}, [r0]!
   1215 	cmp	r2, #6
   1216 	blo	Lcbc_dec_five
   1217 	vld1.8	{q5}, [r0]!
   1218 	beq	Lcbc_dec_six
   1219 	vld1.8	{q6}, [r0]!
   1220 	sub	r0, r0, #0x70
   1221 
   1222 	bl	_bsaes_decrypt8
   1223 
   1224 	vldmia	r9, {q14}			@ reload IV
   1225 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1226 	veor	q0, q0, q14	@ ^= IV
   1227 	vld1.8	{q10,q11}, [r0]!
   1228 	veor	q1, q1, q8
   1229 	veor	q6, q6, q9
   1230 	vld1.8	{q12,q13}, [r0]!
   1231 	veor	q4, q4, q10
   1232 	veor	q2, q2, q11
   1233 	vld1.8	{q15}, [r0]!
   1234 	veor	q7, q7, q12
   1235 	vst1.8	{q0,q1}, [r1]!	@ write output
   1236 	veor	q3, q3, q13
   1237 	vst1.8	{q6}, [r1]!
   1238 	vst1.8	{q4}, [r1]!
   1239 	vst1.8	{q2}, [r1]!
   1240 	vst1.8	{q7}, [r1]!
   1241 	vst1.8	{q3}, [r1]!
   1242 	b	Lcbc_dec_done
   1243 .align	4
   1244 Lcbc_dec_six:
   1245 	sub	r0, r0, #0x60
   1246 	bl	_bsaes_decrypt8
   1247 	vldmia	r9,{q14}			@ reload IV
   1248 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1249 	veor	q0, q0, q14	@ ^= IV
   1250 	vld1.8	{q10,q11}, [r0]!
   1251 	veor	q1, q1, q8
   1252 	veor	q6, q6, q9
   1253 	vld1.8	{q12}, [r0]!
   1254 	veor	q4, q4, q10
   1255 	veor	q2, q2, q11
   1256 	vld1.8	{q15}, [r0]!
   1257 	veor	q7, q7, q12
   1258 	vst1.8	{q0,q1}, [r1]!	@ write output
   1259 	vst1.8	{q6}, [r1]!
   1260 	vst1.8	{q4}, [r1]!
   1261 	vst1.8	{q2}, [r1]!
   1262 	vst1.8	{q7}, [r1]!
   1263 	b	Lcbc_dec_done
   1264 .align	4
   1265 Lcbc_dec_five:
   1266 	sub	r0, r0, #0x50
   1267 	bl	_bsaes_decrypt8
   1268 	vldmia	r9, {q14}			@ reload IV
   1269 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1270 	veor	q0, q0, q14	@ ^= IV
   1271 	vld1.8	{q10,q11}, [r0]!
   1272 	veor	q1, q1, q8
   1273 	veor	q6, q6, q9
   1274 	vld1.8	{q15}, [r0]!
   1275 	veor	q4, q4, q10
   1276 	vst1.8	{q0,q1}, [r1]!	@ write output
   1277 	veor	q2, q2, q11
   1278 	vst1.8	{q6}, [r1]!
   1279 	vst1.8	{q4}, [r1]!
   1280 	vst1.8	{q2}, [r1]!
   1281 	b	Lcbc_dec_done
   1282 .align	4
   1283 Lcbc_dec_four:
   1284 	sub	r0, r0, #0x40
   1285 	bl	_bsaes_decrypt8
   1286 	vldmia	r9, {q14}			@ reload IV
   1287 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1288 	veor	q0, q0, q14	@ ^= IV
   1289 	vld1.8	{q10}, [r0]!
   1290 	veor	q1, q1, q8
   1291 	veor	q6, q6, q9
   1292 	vld1.8	{q15}, [r0]!
   1293 	veor	q4, q4, q10
   1294 	vst1.8	{q0,q1}, [r1]!	@ write output
   1295 	vst1.8	{q6}, [r1]!
   1296 	vst1.8	{q4}, [r1]!
   1297 	b	Lcbc_dec_done
   1298 .align	4
   1299 Lcbc_dec_three:
   1300 	sub	r0, r0, #0x30
   1301 	bl	_bsaes_decrypt8
   1302 	vldmia	r9, {q14}			@ reload IV
   1303 	vld1.8	{q8,q9}, [r0]!	@ reload input
   1304 	veor	q0, q0, q14	@ ^= IV
   1305 	vld1.8	{q15}, [r0]!
   1306 	veor	q1, q1, q8
   1307 	veor	q6, q6, q9
   1308 	vst1.8	{q0,q1}, [r1]!	@ write output
   1309 	vst1.8	{q6}, [r1]!
   1310 	b	Lcbc_dec_done
   1311 .align	4
   1312 Lcbc_dec_two:
   1313 	sub	r0, r0, #0x20
   1314 	bl	_bsaes_decrypt8
   1315 	vldmia	r9, {q14}			@ reload IV
   1316 	vld1.8	{q8}, [r0]!		@ reload input
   1317 	veor	q0, q0, q14	@ ^= IV
   1318 	vld1.8	{q15}, [r0]!		@ reload input
   1319 	veor	q1, q1, q8
   1320 	vst1.8	{q0,q1}, [r1]!	@ write output
   1321 	b	Lcbc_dec_done
   1322 .align	4
   1323 Lcbc_dec_one:
   1324 	sub	r0, r0, #0x10
   1325 	mov	r10, r1			@ save original out pointer
   1326 	mov	r1, r9			@ use the iv scratch space as out buffer
   1327 	mov	r2, r3
   1328 	vmov	q4,q15		@ just in case ensure that IV
   1329 	vmov	q5,q0			@ and input are preserved
   1330 	bl	_AES_decrypt
   1331 	vld1.8	{q0}, [r9]		@ load result
   1332 	veor	q0, q0, q4	@ ^= IV
   1333 	vmov	q15, q5		@ q5 holds input
   1334 	vst1.8	{q0}, [r10]		@ write output
   1335 
   1336 Lcbc_dec_done:
   1337 #ifndef	BSAES_ASM_EXTENDED_KEY
   1338 	vmov.i32	q0, #0
   1339 	vmov.i32	q1, #0
   1340 Lcbc_dec_bzero:@ wipe key schedule [if any]
   1341 	vstmia	sp!, {q0,q1}
   1342 	cmp	sp, r9
   1343 	bne	Lcbc_dec_bzero
   1344 #endif
   1345 
   1346 	mov	sp, r9
   1347 	add	sp, #0x10			@ add sp,r9,#0x10 is no good for thumb
   1348 	vst1.8	{q15}, [r8]		@ return IV
   1349 	VFP_ABI_POP
   1350 	ldmia	sp!, {r4,r5,r6,r7,r8,r9,r10, pc}
   1351 
   1352 
   1353 .globl	_bsaes_ctr32_encrypt_blocks
   1354 .private_extern	_bsaes_ctr32_encrypt_blocks
   1355 #ifdef __thumb2__
   1356 .thumb_func	_bsaes_ctr32_encrypt_blocks
   1357 #endif
   1358 .align	5
   1359 _bsaes_ctr32_encrypt_blocks:
   1360 	cmp	r2, #8			@ use plain AES for
   1361 	blo	Lctr_enc_short			@ small sizes
   1362 
   1363 	mov	ip, sp
   1364 	stmdb	sp!, {r4,r5,r6,r7,r8,r9,r10, lr}
   1365 	VFP_ABI_PUSH
   1366 	ldr	r8, [ip]			@ ctr is 1st arg on the stack
   1367 	sub	sp, sp, #0x10			@ scratch space to carry over the ctr
   1368 	mov	r9, sp				@ save sp
   1369 
   1370 	ldr	r10, [r3, #240]		@ get # of rounds
   1371 #ifndef	BSAES_ASM_EXTENDED_KEY
   1372 	@ allocate the key schedule on the stack
   1373 	sub	r12, sp, r10, lsl#7		@ 128 bytes per inner round key
   1374 	add	r12, #96			@ size of bit-sliced key schedule
   1375 
   1376 	@ populate the key schedule
   1377 	mov	r4, r3			@ pass key
   1378 	mov	r5, r10			@ pass # of rounds
   1379 	mov	sp, r12				@ sp is sp
   1380 	bl	_bsaes_key_convert
   1381 	veor	q7,q7,q15	@ fix up last round key
   1382 	vstmia	r12, {q7}			@ save last round key
   1383 
   1384 	vld1.8	{q0}, [r8]		@ load counter
   1385 #ifdef	__APPLE__
   1386 	mov	r8, #:lower16:(LREVM0SR-LM0)
   1387 	add	r8, r6, r8
   1388 #else
   1389 	add	r8, r6, #LREVM0SR-LM0	@ borrow r8
   1390 #endif
   1391 	vldmia	sp, {q4}		@ load round0 key
   1392 #else
   1393 	ldr	r12, [r3, #244]
   1394 	eors	r12, #1
   1395 	beq	0f
   1396 
   1397 	@ populate the key schedule
   1398 	str	r12, [r3, #244]
   1399 	mov	r4, r3			@ pass key
   1400 	mov	r5, r10			@ pass # of rounds
   1401 	add	r12, r3, #248			@ pass key schedule
   1402 	bl	_bsaes_key_convert
   1403 	veor	q7,q7,q15	@ fix up last round key
   1404 	vstmia	r12, {q7}			@ save last round key
   1405 
   1406 .align	2
   1407 	add	r12, r3, #248
   1408 	vld1.8	{q0}, [r8]		@ load counter
   1409 	adrl	r8, LREVM0SR			@ borrow r8
   1410 	vldmia	r12, {q4}			@ load round0 key
   1411 	sub	sp, #0x10			@ place for adjusted round0 key
   1412 #endif
   1413 
   1414 	vmov.i32	q8,#1		@ compose 1<<96
   1415 	veor	q9,q9,q9
   1416 	vrev32.8	q0,q0
   1417 	vext.8	q8,q9,q8,#4
   1418 	vrev32.8	q4,q4
   1419 	vadd.u32	q9,q8,q8	@ compose 2<<96
   1420 	vstmia	sp, {q4}		@ save adjusted round0 key
   1421 	b	Lctr_enc_loop
   1422 
   1423 .align	4
   1424 Lctr_enc_loop:
   1425 	vadd.u32	q10, q8, q9	@ compose 3<<96
   1426 	vadd.u32	q1, q0, q8	@ +1
   1427 	vadd.u32	q2, q0, q9	@ +2
   1428 	vadd.u32	q3, q0, q10	@ +3
   1429 	vadd.u32	q4, q1, q10
   1430 	vadd.u32	q5, q2, q10
   1431 	vadd.u32	q6, q3, q10
   1432 	vadd.u32	q7, q4, q10
   1433 	vadd.u32	q10, q5, q10	@ next counter
   1434 
   1435 	@ Borrow prologue from _bsaes_encrypt8 to use the opportunity
   1436 	@ to flip byte order in 32-bit counter
   1437 
   1438 	vldmia	sp, {q9}		@ load round0 key
   1439 #ifndef	BSAES_ASM_EXTENDED_KEY
   1440 	add	r4, sp, #0x10		@ pass next round key
   1441 #else
   1442 	add	r4, r3, #264
   1443 #endif
   1444 	vldmia	r8, {q8}			@ LREVM0SR
   1445 	mov	r5, r10			@ pass rounds
   1446 	vstmia	r9, {q10}			@ save next counter
   1447 #ifdef	__APPLE__
   1448 	mov	r6, #:lower16:(LREVM0SR-LSR)
   1449 	sub	r6, r8, r6
   1450 #else
   1451 	sub	r6, r8, #LREVM0SR-LSR	@ pass constants
   1452 #endif
   1453 
   1454 	bl	_bsaes_encrypt8_alt
   1455 
   1456 	subs	r2, r2, #8
   1457 	blo	Lctr_enc_loop_done
   1458 
   1459 	vld1.8	{q8,q9}, [r0]!	@ load input
   1460 	vld1.8	{q10,q11}, [r0]!
   1461 	veor	q0, q8
   1462 	veor	q1, q9
   1463 	vld1.8	{q12,q13}, [r0]!
   1464 	veor	q4, q10
   1465 	veor	q6, q11
   1466 	vld1.8	{q14,q15}, [r0]!
   1467 	veor	q3, q12
   1468 	vst1.8	{q0,q1}, [r1]!	@ write output
   1469 	veor	q7, q13
   1470 	veor	q2, q14
   1471 	vst1.8	{q4}, [r1]!
   1472 	veor	q5, q15
   1473 	vst1.8	{q6}, [r1]!
   1474 	vmov.i32	q8, #1			@ compose 1<<96
   1475 	vst1.8	{q3}, [r1]!
   1476 	veor	q9, q9, q9
   1477 	vst1.8	{q7}, [r1]!
   1478 	vext.8	q8, q9, q8, #4
   1479 	vst1.8	{q2}, [r1]!
   1480 	vadd.u32	q9,q8,q8		@ compose 2<<96
   1481 	vst1.8	{q5}, [r1]!
   1482 	vldmia	r9, {q0}			@ load counter
   1483 
   1484 	bne	Lctr_enc_loop
   1485 	b	Lctr_enc_done
   1486 
   1487 .align	4
   1488 Lctr_enc_loop_done:
   1489 	add	r2, r2, #8
   1490 	vld1.8	{q8}, [r0]!	@ load input
   1491 	veor	q0, q8
   1492 	vst1.8	{q0}, [r1]!	@ write output
   1493 	cmp	r2, #2
   1494 	blo	Lctr_enc_done
   1495 	vld1.8	{q9}, [r0]!
   1496 	veor	q1, q9
   1497 	vst1.8	{q1}, [r1]!
   1498 	beq	Lctr_enc_done
   1499 	vld1.8	{q10}, [r0]!
   1500 	veor	q4, q10
   1501 	vst1.8	{q4}, [r1]!
   1502 	cmp	r2, #4
   1503 	blo	Lctr_enc_done
   1504 	vld1.8	{q11}, [r0]!
   1505 	veor	q6, q11
   1506 	vst1.8	{q6}, [r1]!
   1507 	beq	Lctr_enc_done
   1508 	vld1.8	{q12}, [r0]!
   1509 	veor	q3, q12
   1510 	vst1.8	{q3}, [r1]!
   1511 	cmp	r2, #6
   1512 	blo	Lctr_enc_done
   1513 	vld1.8	{q13}, [r0]!
   1514 	veor	q7, q13
   1515 	vst1.8	{q7}, [r1]!
   1516 	beq	Lctr_enc_done
   1517 	vld1.8	{q14}, [r0]
   1518 	veor	q2, q14
   1519 	vst1.8	{q2}, [r1]!
   1520 
   1521 Lctr_enc_done:
   1522 	vmov.i32	q0, #0
   1523 	vmov.i32	q1, #0
   1524 #ifndef	BSAES_ASM_EXTENDED_KEY
   1525 Lctr_enc_bzero:@ wipe key schedule [if any]
   1526 	vstmia	sp!, {q0,q1}
   1527 	cmp	sp, r9
   1528 	bne	Lctr_enc_bzero
   1529 #else
   1530 	vstmia	sp, {q0,q1}
   1531 #endif
   1532 
   1533 	mov	sp, r9
   1534 	add	sp, #0x10		@ add sp,r9,#0x10 is no good for thumb
   1535 	VFP_ABI_POP
   1536 	ldmia	sp!, {r4,r5,r6,r7,r8,r9,r10, pc}	@ return
   1537 
   1538 .align	4
   1539 Lctr_enc_short:
   1540 	ldr	ip, [sp]		@ ctr pointer is passed on stack
   1541 	stmdb	sp!, {r4,r5,r6,r7,r8, lr}
   1542 
   1543 	mov	r4, r0		@ copy arguments
   1544 	mov	r5, r1
   1545 	mov	r6, r2
   1546 	mov	r7, r3
   1547 	ldr	r8, [ip, #12]		@ load counter LSW
   1548 	vld1.8	{q1}, [ip]		@ load whole counter value
   1549 #ifdef __ARMEL__
   1550 	rev	r8, r8
   1551 #endif
   1552 	sub	sp, sp, #0x10
   1553 	vst1.8	{q1}, [sp]		@ copy counter value
   1554 	sub	sp, sp, #0x10
   1555 
   1556 Lctr_enc_short_loop:
   1557 	add	r0, sp, #0x10		@ input counter value
   1558 	mov	r1, sp			@ output on the stack
   1559 	mov	r2, r7			@ key
   1560 
   1561 	bl	_AES_encrypt
   1562 
   1563 	vld1.8	{q0}, [r4]!	@ load input
   1564 	vld1.8	{q1}, [sp]		@ load encrypted counter
   1565 	add	r8, r8, #1
   1566 #ifdef __ARMEL__
   1567 	rev	r0, r8
   1568 	str	r0, [sp, #0x1c]		@ next counter value
   1569 #else
   1570 	str	r8, [sp, #0x1c]		@ next counter value
   1571 #endif
   1572 	veor	q0,q0,q1
   1573 	vst1.8	{q0}, [r5]!	@ store output
   1574 	subs	r6, r6, #1
   1575 	bne	Lctr_enc_short_loop
   1576 
   1577 	vmov.i32	q0, #0
   1578 	vmov.i32	q1, #0
   1579 	vstmia	sp!, {q0,q1}
   1580 
   1581 	ldmia	sp!, {r4,r5,r6,r7,r8, pc}
   1582 
   1583 .globl	_bsaes_xts_encrypt
   1584 .private_extern	_bsaes_xts_encrypt
   1585 #ifdef __thumb2__
   1586 .thumb_func	_bsaes_xts_encrypt
   1587 #endif
   1588 .align	4
   1589 _bsaes_xts_encrypt:
   1590 	mov	ip, sp
   1591 	stmdb	sp!, {r4,r5,r6,r7,r8,r9,r10, lr}		@ 0x20
   1592 	VFP_ABI_PUSH
   1593 	mov	r6, sp				@ future r3
   1594 
   1595 	mov	r7, r0
   1596 	mov	r8, r1
   1597 	mov	r9, r2
   1598 	mov	r10, r3
   1599 
   1600 	sub	r0, sp, #0x10			@ 0x10
   1601 	bic	r0, #0xf			@ align at 16 bytes
   1602 	mov	sp, r0
   1603 
   1604 #ifdef	XTS_CHAIN_TWEAK
   1605 	ldr	r0, [ip]			@ pointer to input tweak
   1606 #else
   1607 	@ generate initial tweak
   1608 	ldr	r0, [ip, #4]			@ iv[]
   1609 	mov	r1, sp
   1610 	ldr	r2, [ip, #0]			@ key2
   1611 	bl	_AES_encrypt
   1612 	mov	r0,sp				@ pointer to initial tweak
   1613 #endif
   1614 
   1615 	ldr	r1, [r10, #240]		@ get # of rounds
   1616 	mov	r3, r6
   1617 #ifndef	BSAES_ASM_EXTENDED_KEY
   1618 	@ allocate the key schedule on the stack
   1619 	sub	r12, sp, r1, lsl#7		@ 128 bytes per inner round key
   1620 	@ add	r12, #96			@ size of bit-sliced key schedule
   1621 	sub	r12, #48			@ place for tweak[9]
   1622 
   1623 	@ populate the key schedule
   1624 	mov	r4, r10			@ pass key
   1625 	mov	r5, r1			@ pass # of rounds
   1626 	mov	sp, r12
   1627 	add	r12, #0x90			@ pass key schedule
   1628 	bl	_bsaes_key_convert
   1629 	veor	q7, q7, q15	@ fix up last round key
   1630 	vstmia	r12, {q7}			@ save last round key
   1631 #else
   1632 	ldr	r12, [r10, #244]
   1633 	eors	r12, #1
   1634 	beq	0f
   1635 
   1636 	str	r12, [r10, #244]
   1637 	mov	r4, r10			@ pass key
   1638 	mov	r5, r1			@ pass # of rounds
   1639 	add	r12, r10, #248			@ pass key schedule
   1640 	bl	_bsaes_key_convert
   1641 	veor	q7, q7, q15	@ fix up last round key
   1642 	vstmia	r12, {q7}
   1643 
   1644 .align	2
   1645 	sub	sp, #0x90			@ place for tweak[9]
   1646 #endif
   1647 
   1648 	vld1.8	{q8}, [r0]			@ initial tweak
   1649 	adr	r2, Lxts_magic
   1650 
   1651 	subs	r9, #0x80
   1652 	blo	Lxts_enc_short
   1653 	b	Lxts_enc_loop
   1654 
   1655 .align	4
   1656 Lxts_enc_loop:
   1657 	vldmia	r2, {q5}	@ load XTS magic
   1658 	vshr.s64	q6, q8, #63
   1659 	mov	r0, sp
   1660 	vand	q6, q6, q5
   1661 	vadd.u64	q9, q8, q8
   1662 	vst1.64	{q8}, [r0,:128]!
   1663 	vswp	d13,d12
   1664 	vshr.s64	q7, q9, #63
   1665 	veor	q9, q9, q6
   1666 	vand	q7, q7, q5
   1667 	vadd.u64	q10, q9, q9
   1668 	vst1.64	{q9}, [r0,:128]!
   1669 	vswp	d15,d14
   1670 	vshr.s64	q6, q10, #63
   1671 	veor	q10, q10, q7
   1672 	vand	q6, q6, q5
   1673 	vld1.8	{q0}, [r7]!
   1674 	vadd.u64	q11, q10, q10
   1675 	vst1.64	{q10}, [r0,:128]!
   1676 	vswp	d13,d12
   1677 	vshr.s64	q7, q11, #63
   1678 	veor	q11, q11, q6
   1679 	vand	q7, q7, q5
   1680 	vld1.8	{q1}, [r7]!
   1681 	veor	q0, q0, q8
   1682 	vadd.u64	q12, q11, q11
   1683 	vst1.64	{q11}, [r0,:128]!
   1684 	vswp	d15,d14
   1685 	vshr.s64	q6, q12, #63
   1686 	veor	q12, q12, q7
   1687 	vand	q6, q6, q5
   1688 	vld1.8	{q2}, [r7]!
   1689 	veor	q1, q1, q9
   1690 	vadd.u64	q13, q12, q12
   1691 	vst1.64	{q12}, [r0,:128]!
   1692 	vswp	d13,d12
   1693 	vshr.s64	q7, q13, #63
   1694 	veor	q13, q13, q6
   1695 	vand	q7, q7, q5
   1696 	vld1.8	{q3}, [r7]!
   1697 	veor	q2, q2, q10
   1698 	vadd.u64	q14, q13, q13
   1699 	vst1.64	{q13}, [r0,:128]!
   1700 	vswp	d15,d14
   1701 	vshr.s64	q6, q14, #63
   1702 	veor	q14, q14, q7
   1703 	vand	q6, q6, q5
   1704 	vld1.8	{q4}, [r7]!
   1705 	veor	q3, q3, q11
   1706 	vadd.u64	q15, q14, q14
   1707 	vst1.64	{q14}, [r0,:128]!
   1708 	vswp	d13,d12
   1709 	vshr.s64	q7, q15, #63
   1710 	veor	q15, q15, q6
   1711 	vand	q7, q7, q5
   1712 	vld1.8	{q5}, [r7]!
   1713 	veor	q4, q4, q12
   1714 	vadd.u64	q8, q15, q15
   1715 	vst1.64	{q15}, [r0,:128]!
   1716 	vswp	d15,d14
   1717 	veor	q8, q8, q7
   1718 	vst1.64	{q8}, [r0,:128]		@ next round tweak
   1719 
   1720 	vld1.8	{q6,q7}, [r7]!
   1721 	veor	q5, q5, q13
   1722 #ifndef	BSAES_ASM_EXTENDED_KEY
   1723 	add	r4, sp, #0x90			@ pass key schedule
   1724 #else
   1725 	add	r4, r10, #248			@ pass key schedule
   1726 #endif
   1727 	veor	q6, q6, q14
   1728 	mov	r5, r1			@ pass rounds
   1729 	veor	q7, q7, q15
   1730 	mov	r0, sp
   1731 
   1732 	bl	_bsaes_encrypt8
   1733 
   1734 	vld1.64	{q8,q9}, [r0,:128]!
   1735 	vld1.64	{q10,q11}, [r0,:128]!
   1736 	veor	q0, q0, q8
   1737 	vld1.64	{q12,q13}, [r0,:128]!
   1738 	veor	q1, q1, q9
   1739 	veor	q8, q4, q10
   1740 	vst1.8	{q0,q1}, [r8]!
   1741 	veor	q9, q6, q11
   1742 	vld1.64	{q14,q15}, [r0,:128]!
   1743 	veor	q10, q3, q12
   1744 	vst1.8	{q8,q9}, [r8]!
   1745 	veor	q11, q7, q13
   1746 	veor	q12, q2, q14
   1747 	vst1.8	{q10,q11}, [r8]!
   1748 	veor	q13, q5, q15
   1749 	vst1.8	{q12,q13}, [r8]!
   1750 
   1751 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1752 
   1753 	subs	r9, #0x80
   1754 	bpl	Lxts_enc_loop
   1755 
   1756 Lxts_enc_short:
   1757 	adds	r9, #0x70
   1758 	bmi	Lxts_enc_done
   1759 
   1760 	vldmia	r2, {q5}	@ load XTS magic
   1761 	vshr.s64	q7, q8, #63
   1762 	mov	r0, sp
   1763 	vand	q7, q7, q5
   1764 	vadd.u64	q9, q8, q8
   1765 	vst1.64	{q8}, [r0,:128]!
   1766 	vswp	d15,d14
   1767 	vshr.s64	q6, q9, #63
   1768 	veor	q9, q9, q7
   1769 	vand	q6, q6, q5
   1770 	vadd.u64	q10, q9, q9
   1771 	vst1.64	{q9}, [r0,:128]!
   1772 	vswp	d13,d12
   1773 	vshr.s64	q7, q10, #63
   1774 	veor	q10, q10, q6
   1775 	vand	q7, q7, q5
   1776 	vld1.8	{q0}, [r7]!
   1777 	subs	r9, #0x10
   1778 	bmi	Lxts_enc_1
   1779 	vadd.u64	q11, q10, q10
   1780 	vst1.64	{q10}, [r0,:128]!
   1781 	vswp	d15,d14
   1782 	vshr.s64	q6, q11, #63
   1783 	veor	q11, q11, q7
   1784 	vand	q6, q6, q5
   1785 	vld1.8	{q1}, [r7]!
   1786 	subs	r9, #0x10
   1787 	bmi	Lxts_enc_2
   1788 	veor	q0, q0, q8
   1789 	vadd.u64	q12, q11, q11
   1790 	vst1.64	{q11}, [r0,:128]!
   1791 	vswp	d13,d12
   1792 	vshr.s64	q7, q12, #63
   1793 	veor	q12, q12, q6
   1794 	vand	q7, q7, q5
   1795 	vld1.8	{q2}, [r7]!
   1796 	subs	r9, #0x10
   1797 	bmi	Lxts_enc_3
   1798 	veor	q1, q1, q9
   1799 	vadd.u64	q13, q12, q12
   1800 	vst1.64	{q12}, [r0,:128]!
   1801 	vswp	d15,d14
   1802 	vshr.s64	q6, q13, #63
   1803 	veor	q13, q13, q7
   1804 	vand	q6, q6, q5
   1805 	vld1.8	{q3}, [r7]!
   1806 	subs	r9, #0x10
   1807 	bmi	Lxts_enc_4
   1808 	veor	q2, q2, q10
   1809 	vadd.u64	q14, q13, q13
   1810 	vst1.64	{q13}, [r0,:128]!
   1811 	vswp	d13,d12
   1812 	vshr.s64	q7, q14, #63
   1813 	veor	q14, q14, q6
   1814 	vand	q7, q7, q5
   1815 	vld1.8	{q4}, [r7]!
   1816 	subs	r9, #0x10
   1817 	bmi	Lxts_enc_5
   1818 	veor	q3, q3, q11
   1819 	vadd.u64	q15, q14, q14
   1820 	vst1.64	{q14}, [r0,:128]!
   1821 	vswp	d15,d14
   1822 	vshr.s64	q6, q15, #63
   1823 	veor	q15, q15, q7
   1824 	vand	q6, q6, q5
   1825 	vld1.8	{q5}, [r7]!
   1826 	subs	r9, #0x10
   1827 	bmi	Lxts_enc_6
   1828 	veor	q4, q4, q12
   1829 	sub	r9, #0x10
   1830 	vst1.64	{q15}, [r0,:128]		@ next round tweak
   1831 
   1832 	vld1.8	{q6}, [r7]!
   1833 	veor	q5, q5, q13
   1834 #ifndef	BSAES_ASM_EXTENDED_KEY
   1835 	add	r4, sp, #0x90			@ pass key schedule
   1836 #else
   1837 	add	r4, r10, #248			@ pass key schedule
   1838 #endif
   1839 	veor	q6, q6, q14
   1840 	mov	r5, r1			@ pass rounds
   1841 	mov	r0, sp
   1842 
   1843 	bl	_bsaes_encrypt8
   1844 
   1845 	vld1.64	{q8,q9}, [r0,:128]!
   1846 	vld1.64	{q10,q11}, [r0,:128]!
   1847 	veor	q0, q0, q8
   1848 	vld1.64	{q12,q13}, [r0,:128]!
   1849 	veor	q1, q1, q9
   1850 	veor	q8, q4, q10
   1851 	vst1.8	{q0,q1}, [r8]!
   1852 	veor	q9, q6, q11
   1853 	vld1.64	{q14}, [r0,:128]!
   1854 	veor	q10, q3, q12
   1855 	vst1.8	{q8,q9}, [r8]!
   1856 	veor	q11, q7, q13
   1857 	veor	q12, q2, q14
   1858 	vst1.8	{q10,q11}, [r8]!
   1859 	vst1.8	{q12}, [r8]!
   1860 
   1861 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1862 	b	Lxts_enc_done
   1863 .align	4
   1864 Lxts_enc_6:
   1865 	veor	q4, q4, q12
   1866 #ifndef	BSAES_ASM_EXTENDED_KEY
   1867 	add	r4, sp, #0x90			@ pass key schedule
   1868 #else
   1869 	add	r4, r10, #248			@ pass key schedule
   1870 #endif
   1871 	veor	q5, q5, q13
   1872 	mov	r5, r1			@ pass rounds
   1873 	mov	r0, sp
   1874 
   1875 	bl	_bsaes_encrypt8
   1876 
   1877 	vld1.64	{q8,q9}, [r0,:128]!
   1878 	vld1.64	{q10,q11}, [r0,:128]!
   1879 	veor	q0, q0, q8
   1880 	vld1.64	{q12,q13}, [r0,:128]!
   1881 	veor	q1, q1, q9
   1882 	veor	q8, q4, q10
   1883 	vst1.8	{q0,q1}, [r8]!
   1884 	veor	q9, q6, q11
   1885 	veor	q10, q3, q12
   1886 	vst1.8	{q8,q9}, [r8]!
   1887 	veor	q11, q7, q13
   1888 	vst1.8	{q10,q11}, [r8]!
   1889 
   1890 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1891 	b	Lxts_enc_done
   1892 
   1893 @ put this in range for both ARM and Thumb mode adr instructions
   1894 .align	5
   1895 Lxts_magic:
   1896 .quad	1, 0x87
   1897 
   1898 .align	5
   1899 Lxts_enc_5:
   1900 	veor	q3, q3, q11
   1901 #ifndef	BSAES_ASM_EXTENDED_KEY
   1902 	add	r4, sp, #0x90			@ pass key schedule
   1903 #else
   1904 	add	r4, r10, #248			@ pass key schedule
   1905 #endif
   1906 	veor	q4, q4, q12
   1907 	mov	r5, r1			@ pass rounds
   1908 	mov	r0, sp
   1909 
   1910 	bl	_bsaes_encrypt8
   1911 
   1912 	vld1.64	{q8,q9}, [r0,:128]!
   1913 	vld1.64	{q10,q11}, [r0,:128]!
   1914 	veor	q0, q0, q8
   1915 	vld1.64	{q12}, [r0,:128]!
   1916 	veor	q1, q1, q9
   1917 	veor	q8, q4, q10
   1918 	vst1.8	{q0,q1}, [r8]!
   1919 	veor	q9, q6, q11
   1920 	veor	q10, q3, q12
   1921 	vst1.8	{q8,q9}, [r8]!
   1922 	vst1.8	{q10}, [r8]!
   1923 
   1924 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1925 	b	Lxts_enc_done
   1926 .align	4
   1927 Lxts_enc_4:
   1928 	veor	q2, q2, q10
   1929 #ifndef	BSAES_ASM_EXTENDED_KEY
   1930 	add	r4, sp, #0x90			@ pass key schedule
   1931 #else
   1932 	add	r4, r10, #248			@ pass key schedule
   1933 #endif
   1934 	veor	q3, q3, q11
   1935 	mov	r5, r1			@ pass rounds
   1936 	mov	r0, sp
   1937 
   1938 	bl	_bsaes_encrypt8
   1939 
   1940 	vld1.64	{q8,q9}, [r0,:128]!
   1941 	vld1.64	{q10,q11}, [r0,:128]!
   1942 	veor	q0, q0, q8
   1943 	veor	q1, q1, q9
   1944 	veor	q8, q4, q10
   1945 	vst1.8	{q0,q1}, [r8]!
   1946 	veor	q9, q6, q11
   1947 	vst1.8	{q8,q9}, [r8]!
   1948 
   1949 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1950 	b	Lxts_enc_done
   1951 .align	4
   1952 Lxts_enc_3:
   1953 	veor	q1, q1, q9
   1954 #ifndef	BSAES_ASM_EXTENDED_KEY
   1955 	add	r4, sp, #0x90			@ pass key schedule
   1956 #else
   1957 	add	r4, r10, #248			@ pass key schedule
   1958 #endif
   1959 	veor	q2, q2, q10
   1960 	mov	r5, r1			@ pass rounds
   1961 	mov	r0, sp
   1962 
   1963 	bl	_bsaes_encrypt8
   1964 
   1965 	vld1.64	{q8,q9}, [r0,:128]!
   1966 	vld1.64	{q10}, [r0,:128]!
   1967 	veor	q0, q0, q8
   1968 	veor	q1, q1, q9
   1969 	veor	q8, q4, q10
   1970 	vst1.8	{q0,q1}, [r8]!
   1971 	vst1.8	{q8}, [r8]!
   1972 
   1973 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1974 	b	Lxts_enc_done
   1975 .align	4
   1976 Lxts_enc_2:
   1977 	veor	q0, q0, q8
   1978 #ifndef	BSAES_ASM_EXTENDED_KEY
   1979 	add	r4, sp, #0x90			@ pass key schedule
   1980 #else
   1981 	add	r4, r10, #248			@ pass key schedule
   1982 #endif
   1983 	veor	q1, q1, q9
   1984 	mov	r5, r1			@ pass rounds
   1985 	mov	r0, sp
   1986 
   1987 	bl	_bsaes_encrypt8
   1988 
   1989 	vld1.64	{q8,q9}, [r0,:128]!
   1990 	veor	q0, q0, q8
   1991 	veor	q1, q1, q9
   1992 	vst1.8	{q0,q1}, [r8]!
   1993 
   1994 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   1995 	b	Lxts_enc_done
   1996 .align	4
   1997 Lxts_enc_1:
   1998 	mov	r0, sp
   1999 	veor	q0, q0, q8
   2000 	mov	r1, sp
   2001 	vst1.8	{q0}, [sp,:128]
   2002 	mov	r2, r10
   2003 	mov	r4, r3				@ preserve fp
   2004 
   2005 	bl	_AES_encrypt
   2006 
   2007 	vld1.8	{q0}, [sp,:128]
   2008 	veor	q0, q0, q8
   2009 	vst1.8	{q0}, [r8]!
   2010 	mov	r3, r4
   2011 
   2012 	vmov	q8, q9		@ next round tweak
   2013 
   2014 Lxts_enc_done:
   2015 #ifndef	XTS_CHAIN_TWEAK
   2016 	adds	r9, #0x10
   2017 	beq	Lxts_enc_ret
   2018 	sub	r6, r8, #0x10
   2019 
   2020 Lxts_enc_steal:
   2021 	ldrb	r0, [r7], #1
   2022 	ldrb	r1, [r8, #-0x10]
   2023 	strb	r0, [r8, #-0x10]
   2024 	strb	r1, [r8], #1
   2025 
   2026 	subs	r9, #1
   2027 	bhi	Lxts_enc_steal
   2028 
   2029 	vld1.8	{q0}, [r6]
   2030 	mov	r0, sp
   2031 	veor	q0, q0, q8
   2032 	mov	r1, sp
   2033 	vst1.8	{q0}, [sp,:128]
   2034 	mov	r2, r10
   2035 	mov	r4, r3			@ preserve fp
   2036 
   2037 	bl	_AES_encrypt
   2038 
   2039 	vld1.8	{q0}, [sp,:128]
   2040 	veor	q0, q0, q8
   2041 	vst1.8	{q0}, [r6]
   2042 	mov	r3, r4
   2043 #endif
   2044 
   2045 Lxts_enc_ret:
   2046 	bic	r0, r3, #0xf
   2047 	vmov.i32	q0, #0
   2048 	vmov.i32	q1, #0
   2049 #ifdef	XTS_CHAIN_TWEAK
   2050 	ldr	r1, [r3, #0x20+VFP_ABI_FRAME]	@ chain tweak
   2051 #endif
   2052 Lxts_enc_bzero:@ wipe key schedule [if any]
   2053 	vstmia	sp!, {q0,q1}
   2054 	cmp	sp, r0
   2055 	bne	Lxts_enc_bzero
   2056 
   2057 	mov	sp, r3
   2058 #ifdef	XTS_CHAIN_TWEAK
   2059 	vst1.8	{q8}, [r1]
   2060 #endif
   2061 	VFP_ABI_POP
   2062 	ldmia	sp!, {r4,r5,r6,r7,r8,r9,r10, pc}	@ return
   2063 
   2064 
   2065 
   2066 .globl	_bsaes_xts_decrypt
   2067 .private_extern	_bsaes_xts_decrypt
   2068 #ifdef __thumb2__
   2069 .thumb_func	_bsaes_xts_decrypt
   2070 #endif
   2071 .align	4
   2072 _bsaes_xts_decrypt:
   2073 	mov	ip, sp
   2074 	stmdb	sp!, {r4,r5,r6,r7,r8,r9,r10, lr}		@ 0x20
   2075 	VFP_ABI_PUSH
   2076 	mov	r6, sp				@ future r3
   2077 
   2078 	mov	r7, r0
   2079 	mov	r8, r1
   2080 	mov	r9, r2
   2081 	mov	r10, r3
   2082 
   2083 	sub	r0, sp, #0x10			@ 0x10
   2084 	bic	r0, #0xf			@ align at 16 bytes
   2085 	mov	sp, r0
   2086 
   2087 #ifdef	XTS_CHAIN_TWEAK
   2088 	ldr	r0, [ip]			@ pointer to input tweak
   2089 #else
   2090 	@ generate initial tweak
   2091 	ldr	r0, [ip, #4]			@ iv[]
   2092 	mov	r1, sp
   2093 	ldr	r2, [ip, #0]			@ key2
   2094 	bl	_AES_encrypt
   2095 	mov	r0, sp				@ pointer to initial tweak
   2096 #endif
   2097 
   2098 	ldr	r1, [r10, #240]		@ get # of rounds
   2099 	mov	r3, r6
   2100 #ifndef	BSAES_ASM_EXTENDED_KEY
   2101 	@ allocate the key schedule on the stack
   2102 	sub	r12, sp, r1, lsl#7		@ 128 bytes per inner round key
   2103 	@ add	r12, #96			@ size of bit-sliced key schedule
   2104 	sub	r12, #48			@ place for tweak[9]
   2105 
   2106 	@ populate the key schedule
   2107 	mov	r4, r10			@ pass key
   2108 	mov	r5, r1			@ pass # of rounds
   2109 	mov	sp, r12
   2110 	add	r12, #0x90			@ pass key schedule
   2111 	bl	_bsaes_key_convert
   2112 	add	r4, sp, #0x90
   2113 	vldmia	r4, {q6}
   2114 	vstmia	r12,  {q15}		@ save last round key
   2115 	veor	q7, q7, q6	@ fix up round 0 key
   2116 	vstmia	r4, {q7}
   2117 #else
   2118 	ldr	r12, [r10, #244]
   2119 	eors	r12, #1
   2120 	beq	0f
   2121 
   2122 	str	r12, [r10, #244]
   2123 	mov	r4, r10			@ pass key
   2124 	mov	r5, r1			@ pass # of rounds
   2125 	add	r12, r10, #248			@ pass key schedule
   2126 	bl	_bsaes_key_convert
   2127 	add	r4, r10, #248
   2128 	vldmia	r4, {q6}
   2129 	vstmia	r12,  {q15}		@ save last round key
   2130 	veor	q7, q7, q6	@ fix up round 0 key
   2131 	vstmia	r4, {q7}
   2132 
   2133 .align	2
   2134 	sub	sp, #0x90			@ place for tweak[9]
   2135 #endif
   2136 	vld1.8	{q8}, [r0]			@ initial tweak
   2137 	adr	r2, Lxts_magic
   2138 
   2139 #ifndef	XTS_CHAIN_TWEAK
   2140 	tst	r9, #0xf			@ if not multiple of 16
   2141 	it	ne				@ Thumb2 thing, sanity check in ARM
   2142 	subne	r9, #0x10			@ subtract another 16 bytes
   2143 #endif
   2144 	subs	r9, #0x80
   2145 
   2146 	blo	Lxts_dec_short
   2147 	b	Lxts_dec_loop
   2148 
   2149 .align	4
   2150 Lxts_dec_loop:
   2151 	vldmia	r2, {q5}	@ load XTS magic
   2152 	vshr.s64	q6, q8, #63
   2153 	mov	r0, sp
   2154 	vand	q6, q6, q5
   2155 	vadd.u64	q9, q8, q8
   2156 	vst1.64	{q8}, [r0,:128]!
   2157 	vswp	d13,d12
   2158 	vshr.s64	q7, q9, #63
   2159 	veor	q9, q9, q6
   2160 	vand	q7, q7, q5
   2161 	vadd.u64	q10, q9, q9
   2162 	vst1.64	{q9}, [r0,:128]!
   2163 	vswp	d15,d14
   2164 	vshr.s64	q6, q10, #63
   2165 	veor	q10, q10, q7
   2166 	vand	q6, q6, q5
   2167 	vld1.8	{q0}, [r7]!
   2168 	vadd.u64	q11, q10, q10
   2169 	vst1.64	{q10}, [r0,:128]!
   2170 	vswp	d13,d12
   2171 	vshr.s64	q7, q11, #63
   2172 	veor	q11, q11, q6
   2173 	vand	q7, q7, q5
   2174 	vld1.8	{q1}, [r7]!
   2175 	veor	q0, q0, q8
   2176 	vadd.u64	q12, q11, q11
   2177 	vst1.64	{q11}, [r0,:128]!
   2178 	vswp	d15,d14
   2179 	vshr.s64	q6, q12, #63
   2180 	veor	q12, q12, q7
   2181 	vand	q6, q6, q5
   2182 	vld1.8	{q2}, [r7]!
   2183 	veor	q1, q1, q9
   2184 	vadd.u64	q13, q12, q12
   2185 	vst1.64	{q12}, [r0,:128]!
   2186 	vswp	d13,d12
   2187 	vshr.s64	q7, q13, #63
   2188 	veor	q13, q13, q6
   2189 	vand	q7, q7, q5
   2190 	vld1.8	{q3}, [r7]!
   2191 	veor	q2, q2, q10
   2192 	vadd.u64	q14, q13, q13
   2193 	vst1.64	{q13}, [r0,:128]!
   2194 	vswp	d15,d14
   2195 	vshr.s64	q6, q14, #63
   2196 	veor	q14, q14, q7
   2197 	vand	q6, q6, q5
   2198 	vld1.8	{q4}, [r7]!
   2199 	veor	q3, q3, q11
   2200 	vadd.u64	q15, q14, q14
   2201 	vst1.64	{q14}, [r0,:128]!
   2202 	vswp	d13,d12
   2203 	vshr.s64	q7, q15, #63
   2204 	veor	q15, q15, q6
   2205 	vand	q7, q7, q5
   2206 	vld1.8	{q5}, [r7]!
   2207 	veor	q4, q4, q12
   2208 	vadd.u64	q8, q15, q15
   2209 	vst1.64	{q15}, [r0,:128]!
   2210 	vswp	d15,d14
   2211 	veor	q8, q8, q7
   2212 	vst1.64	{q8}, [r0,:128]		@ next round tweak
   2213 
   2214 	vld1.8	{q6,q7}, [r7]!
   2215 	veor	q5, q5, q13
   2216 #ifndef	BSAES_ASM_EXTENDED_KEY
   2217 	add	r4, sp, #0x90			@ pass key schedule
   2218 #else
   2219 	add	r4, r10, #248			@ pass key schedule
   2220 #endif
   2221 	veor	q6, q6, q14
   2222 	mov	r5, r1			@ pass rounds
   2223 	veor	q7, q7, q15
   2224 	mov	r0, sp
   2225 
   2226 	bl	_bsaes_decrypt8
   2227 
   2228 	vld1.64	{q8,q9}, [r0,:128]!
   2229 	vld1.64	{q10,q11}, [r0,:128]!
   2230 	veor	q0, q0, q8
   2231 	vld1.64	{q12,q13}, [r0,:128]!
   2232 	veor	q1, q1, q9
   2233 	veor	q8, q6, q10
   2234 	vst1.8	{q0,q1}, [r8]!
   2235 	veor	q9, q4, q11
   2236 	vld1.64	{q14,q15}, [r0,:128]!
   2237 	veor	q10, q2, q12
   2238 	vst1.8	{q8,q9}, [r8]!
   2239 	veor	q11, q7, q13
   2240 	veor	q12, q3, q14
   2241 	vst1.8	{q10,q11}, [r8]!
   2242 	veor	q13, q5, q15
   2243 	vst1.8	{q12,q13}, [r8]!
   2244 
   2245 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2246 
   2247 	subs	r9, #0x80
   2248 	bpl	Lxts_dec_loop
   2249 
   2250 Lxts_dec_short:
   2251 	adds	r9, #0x70
   2252 	bmi	Lxts_dec_done
   2253 
   2254 	vldmia	r2, {q5}	@ load XTS magic
   2255 	vshr.s64	q7, q8, #63
   2256 	mov	r0, sp
   2257 	vand	q7, q7, q5
   2258 	vadd.u64	q9, q8, q8
   2259 	vst1.64	{q8}, [r0,:128]!
   2260 	vswp	d15,d14
   2261 	vshr.s64	q6, q9, #63
   2262 	veor	q9, q9, q7
   2263 	vand	q6, q6, q5
   2264 	vadd.u64	q10, q9, q9
   2265 	vst1.64	{q9}, [r0,:128]!
   2266 	vswp	d13,d12
   2267 	vshr.s64	q7, q10, #63
   2268 	veor	q10, q10, q6
   2269 	vand	q7, q7, q5
   2270 	vld1.8	{q0}, [r7]!
   2271 	subs	r9, #0x10
   2272 	bmi	Lxts_dec_1
   2273 	vadd.u64	q11, q10, q10
   2274 	vst1.64	{q10}, [r0,:128]!
   2275 	vswp	d15,d14
   2276 	vshr.s64	q6, q11, #63
   2277 	veor	q11, q11, q7
   2278 	vand	q6, q6, q5
   2279 	vld1.8	{q1}, [r7]!
   2280 	subs	r9, #0x10
   2281 	bmi	Lxts_dec_2
   2282 	veor	q0, q0, q8
   2283 	vadd.u64	q12, q11, q11
   2284 	vst1.64	{q11}, [r0,:128]!
   2285 	vswp	d13,d12
   2286 	vshr.s64	q7, q12, #63
   2287 	veor	q12, q12, q6
   2288 	vand	q7, q7, q5
   2289 	vld1.8	{q2}, [r7]!
   2290 	subs	r9, #0x10
   2291 	bmi	Lxts_dec_3
   2292 	veor	q1, q1, q9
   2293 	vadd.u64	q13, q12, q12
   2294 	vst1.64	{q12}, [r0,:128]!
   2295 	vswp	d15,d14
   2296 	vshr.s64	q6, q13, #63
   2297 	veor	q13, q13, q7
   2298 	vand	q6, q6, q5
   2299 	vld1.8	{q3}, [r7]!
   2300 	subs	r9, #0x10
   2301 	bmi	Lxts_dec_4
   2302 	veor	q2, q2, q10
   2303 	vadd.u64	q14, q13, q13
   2304 	vst1.64	{q13}, [r0,:128]!
   2305 	vswp	d13,d12
   2306 	vshr.s64	q7, q14, #63
   2307 	veor	q14, q14, q6
   2308 	vand	q7, q7, q5
   2309 	vld1.8	{q4}, [r7]!
   2310 	subs	r9, #0x10
   2311 	bmi	Lxts_dec_5
   2312 	veor	q3, q3, q11
   2313 	vadd.u64	q15, q14, q14
   2314 	vst1.64	{q14}, [r0,:128]!
   2315 	vswp	d15,d14
   2316 	vshr.s64	q6, q15, #63
   2317 	veor	q15, q15, q7
   2318 	vand	q6, q6, q5
   2319 	vld1.8	{q5}, [r7]!
   2320 	subs	r9, #0x10
   2321 	bmi	Lxts_dec_6
   2322 	veor	q4, q4, q12
   2323 	sub	r9, #0x10
   2324 	vst1.64	{q15}, [r0,:128]		@ next round tweak
   2325 
   2326 	vld1.8	{q6}, [r7]!
   2327 	veor	q5, q5, q13
   2328 #ifndef	BSAES_ASM_EXTENDED_KEY
   2329 	add	r4, sp, #0x90			@ pass key schedule
   2330 #else
   2331 	add	r4, r10, #248			@ pass key schedule
   2332 #endif
   2333 	veor	q6, q6, q14
   2334 	mov	r5, r1			@ pass rounds
   2335 	mov	r0, sp
   2336 
   2337 	bl	_bsaes_decrypt8
   2338 
   2339 	vld1.64	{q8,q9}, [r0,:128]!
   2340 	vld1.64	{q10,q11}, [r0,:128]!
   2341 	veor	q0, q0, q8
   2342 	vld1.64	{q12,q13}, [r0,:128]!
   2343 	veor	q1, q1, q9
   2344 	veor	q8, q6, q10
   2345 	vst1.8	{q0,q1}, [r8]!
   2346 	veor	q9, q4, q11
   2347 	vld1.64	{q14}, [r0,:128]!
   2348 	veor	q10, q2, q12
   2349 	vst1.8	{q8,q9}, [r8]!
   2350 	veor	q11, q7, q13
   2351 	veor	q12, q3, q14
   2352 	vst1.8	{q10,q11}, [r8]!
   2353 	vst1.8	{q12}, [r8]!
   2354 
   2355 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2356 	b	Lxts_dec_done
   2357 .align	4
   2358 Lxts_dec_6:
   2359 	vst1.64	{q14}, [r0,:128]		@ next round tweak
   2360 
   2361 	veor	q4, q4, q12
   2362 #ifndef	BSAES_ASM_EXTENDED_KEY
   2363 	add	r4, sp, #0x90			@ pass key schedule
   2364 #else
   2365 	add	r4, r10, #248			@ pass key schedule
   2366 #endif
   2367 	veor	q5, q5, q13
   2368 	mov	r5, r1			@ pass rounds
   2369 	mov	r0, sp
   2370 
   2371 	bl	_bsaes_decrypt8
   2372 
   2373 	vld1.64	{q8,q9}, [r0,:128]!
   2374 	vld1.64	{q10,q11}, [r0,:128]!
   2375 	veor	q0, q0, q8
   2376 	vld1.64	{q12,q13}, [r0,:128]!
   2377 	veor	q1, q1, q9
   2378 	veor	q8, q6, q10
   2379 	vst1.8	{q0,q1}, [r8]!
   2380 	veor	q9, q4, q11
   2381 	veor	q10, q2, q12
   2382 	vst1.8	{q8,q9}, [r8]!
   2383 	veor	q11, q7, q13
   2384 	vst1.8	{q10,q11}, [r8]!
   2385 
   2386 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2387 	b	Lxts_dec_done
   2388 .align	4
   2389 Lxts_dec_5:
   2390 	veor	q3, q3, q11
   2391 #ifndef	BSAES_ASM_EXTENDED_KEY
   2392 	add	r4, sp, #0x90			@ pass key schedule
   2393 #else
   2394 	add	r4, r10, #248			@ pass key schedule
   2395 #endif
   2396 	veor	q4, q4, q12
   2397 	mov	r5, r1			@ pass rounds
   2398 	mov	r0, sp
   2399 
   2400 	bl	_bsaes_decrypt8
   2401 
   2402 	vld1.64	{q8,q9}, [r0,:128]!
   2403 	vld1.64	{q10,q11}, [r0,:128]!
   2404 	veor	q0, q0, q8
   2405 	vld1.64	{q12}, [r0,:128]!
   2406 	veor	q1, q1, q9
   2407 	veor	q8, q6, q10
   2408 	vst1.8	{q0,q1}, [r8]!
   2409 	veor	q9, q4, q11
   2410 	veor	q10, q2, q12
   2411 	vst1.8	{q8,q9}, [r8]!
   2412 	vst1.8	{q10}, [r8]!
   2413 
   2414 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2415 	b	Lxts_dec_done
   2416 .align	4
   2417 Lxts_dec_4:
   2418 	veor	q2, q2, q10
   2419 #ifndef	BSAES_ASM_EXTENDED_KEY
   2420 	add	r4, sp, #0x90			@ pass key schedule
   2421 #else
   2422 	add	r4, r10, #248			@ pass key schedule
   2423 #endif
   2424 	veor	q3, q3, q11
   2425 	mov	r5, r1			@ pass rounds
   2426 	mov	r0, sp
   2427 
   2428 	bl	_bsaes_decrypt8
   2429 
   2430 	vld1.64	{q8,q9}, [r0,:128]!
   2431 	vld1.64	{q10,q11}, [r0,:128]!
   2432 	veor	q0, q0, q8
   2433 	veor	q1, q1, q9
   2434 	veor	q8, q6, q10
   2435 	vst1.8	{q0,q1}, [r8]!
   2436 	veor	q9, q4, q11
   2437 	vst1.8	{q8,q9}, [r8]!
   2438 
   2439 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2440 	b	Lxts_dec_done
   2441 .align	4
   2442 Lxts_dec_3:
   2443 	veor	q1, q1, q9
   2444 #ifndef	BSAES_ASM_EXTENDED_KEY
   2445 	add	r4, sp, #0x90			@ pass key schedule
   2446 #else
   2447 	add	r4, r10, #248			@ pass key schedule
   2448 #endif
   2449 	veor	q2, q2, q10
   2450 	mov	r5, r1			@ pass rounds
   2451 	mov	r0, sp
   2452 
   2453 	bl	_bsaes_decrypt8
   2454 
   2455 	vld1.64	{q8,q9}, [r0,:128]!
   2456 	vld1.64	{q10}, [r0,:128]!
   2457 	veor	q0, q0, q8
   2458 	veor	q1, q1, q9
   2459 	veor	q8, q6, q10
   2460 	vst1.8	{q0,q1}, [r8]!
   2461 	vst1.8	{q8}, [r8]!
   2462 
   2463 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2464 	b	Lxts_dec_done
   2465 .align	4
   2466 Lxts_dec_2:
   2467 	veor	q0, q0, q8
   2468 #ifndef	BSAES_ASM_EXTENDED_KEY
   2469 	add	r4, sp, #0x90			@ pass key schedule
   2470 #else
   2471 	add	r4, r10, #248			@ pass key schedule
   2472 #endif
   2473 	veor	q1, q1, q9
   2474 	mov	r5, r1			@ pass rounds
   2475 	mov	r0, sp
   2476 
   2477 	bl	_bsaes_decrypt8
   2478 
   2479 	vld1.64	{q8,q9}, [r0,:128]!
   2480 	veor	q0, q0, q8
   2481 	veor	q1, q1, q9
   2482 	vst1.8	{q0,q1}, [r8]!
   2483 
   2484 	vld1.64	{q8}, [r0,:128]		@ next round tweak
   2485 	b	Lxts_dec_done
   2486 .align	4
   2487 Lxts_dec_1:
   2488 	mov	r0, sp
   2489 	veor	q0, q0, q8
   2490 	mov	r1, sp
   2491 	vst1.8	{q0}, [sp,:128]
   2492 	mov	r5, r2			@ preserve magic
   2493 	mov	r2, r10
   2494 	mov	r4, r3				@ preserve fp
   2495 
   2496 	bl	_AES_decrypt
   2497 
   2498 	vld1.8	{q0}, [sp,:128]
   2499 	veor	q0, q0, q8
   2500 	vst1.8	{q0}, [r8]!
   2501 	mov	r3, r4
   2502 	mov	r2, r5
   2503 
   2504 	vmov	q8, q9		@ next round tweak
   2505 
   2506 Lxts_dec_done:
   2507 #ifndef	XTS_CHAIN_TWEAK
   2508 	adds	r9, #0x10
   2509 	beq	Lxts_dec_ret
   2510 
   2511 	@ calculate one round of extra tweak for the stolen ciphertext
   2512 	vldmia	r2, {q5}
   2513 	vshr.s64	q6, q8, #63
   2514 	vand	q6, q6, q5
   2515 	vadd.u64	q9, q8, q8
   2516 	vswp	d13,d12
   2517 	veor	q9, q9, q6
   2518 
   2519 	@ perform the final decryption with the last tweak value
   2520 	vld1.8	{q0}, [r7]!
   2521 	mov	r0, sp
   2522 	veor	q0, q0, q9
   2523 	mov	r1, sp
   2524 	vst1.8	{q0}, [sp,:128]
   2525 	mov	r2, r10
   2526 	mov	r4, r3			@ preserve fp
   2527 
   2528 	bl	_AES_decrypt
   2529 
   2530 	vld1.8	{q0}, [sp,:128]
   2531 	veor	q0, q0, q9
   2532 	vst1.8	{q0}, [r8]
   2533 
   2534 	mov	r6, r8
   2535 Lxts_dec_steal:
   2536 	ldrb	r1, [r8]
   2537 	ldrb	r0, [r7], #1
   2538 	strb	r1, [r8, #0x10]
   2539 	strb	r0, [r8], #1
   2540 
   2541 	subs	r9, #1
   2542 	bhi	Lxts_dec_steal
   2543 
   2544 	vld1.8	{q0}, [r6]
   2545 	mov	r0, sp
   2546 	veor	q0, q8
   2547 	mov	r1, sp
   2548 	vst1.8	{q0}, [sp,:128]
   2549 	mov	r2, r10
   2550 
   2551 	bl	_AES_decrypt
   2552 
   2553 	vld1.8	{q0}, [sp,:128]
   2554 	veor	q0, q0, q8
   2555 	vst1.8	{q0}, [r6]
   2556 	mov	r3, r4
   2557 #endif
   2558 
   2559 Lxts_dec_ret:
   2560 	bic	r0, r3, #0xf
   2561 	vmov.i32	q0, #0
   2562 	vmov.i32	q1, #0
   2563 #ifdef	XTS_CHAIN_TWEAK
   2564 	ldr	r1, [r3, #0x20+VFP_ABI_FRAME]	@ chain tweak
   2565 #endif
   2566 Lxts_dec_bzero:@ wipe key schedule [if any]
   2567 	vstmia	sp!, {q0,q1}
   2568 	cmp	sp, r0
   2569 	bne	Lxts_dec_bzero
   2570 
   2571 	mov	sp, r3
   2572 #ifdef	XTS_CHAIN_TWEAK
   2573 	vst1.8	{q8}, [r1]
   2574 #endif
   2575 	VFP_ABI_POP
   2576 	ldmia	sp!, {r4,r5,r6,r7,r8,r9,r10, pc}	@ return
   2577 
   2578 
   2579 #endif
   2580