1/* SPDX-License-Identifier: GPL-2.0-only */ 2/* 3 * Bit sliced AES using NEON instructions 4 * 5 * Copyright (C) 2017 Linaro Ltd. 6 * Author: Ard Biesheuvel <ard.biesheuvel@linaro.org> 7 */ 8 9/* 10 * The algorithm implemented here is described in detail by the paper 11 * 'Faster and Timing-Attack Resistant AES-GCM' by Emilia Kaesper and 12 * Peter Schwabe (https://eprint.iacr.org/2009/129.pdf) 13 * 14 * This implementation is based primarily on the OpenSSL implementation 15 * for 32-bit ARM written by Andy Polyakov <appro@openssl.org> 16 */ 17 18#include <linux/linkage.h> 19#include <asm/assembler.h> 20 21 .text 22 .fpu neon 23 24 rounds .req ip 25 bskey .req r4 26 27 q0l .req d0 28 q0h .req d1 29 q1l .req d2 30 q1h .req d3 31 q2l .req d4 32 q2h .req d5 33 q3l .req d6 34 q3h .req d7 35 q4l .req d8 36 q4h .req d9 37 q5l .req d10 38 q5h .req d11 39 q6l .req d12 40 q6h .req d13 41 q7l .req d14 42 q7h .req d15 43 q8l .req d16 44 q8h .req d17 45 q9l .req d18 46 q9h .req d19 47 q10l .req d20 48 q10h .req d21 49 q11l .req d22 50 q11h .req d23 51 q12l .req d24 52 q12h .req d25 53 q13l .req d26 54 q13h .req d27 55 q14l .req d28 56 q14h .req d29 57 q15l .req d30 58 q15h .req d31 59 60 .macro __tbl, out, tbl, in, tmp 61 .ifc \out, \tbl 62 .ifb \tmp 63 .error __tbl needs temp register if out == tbl 64 .endif 65 vmov \tmp, \out 66 .endif 67 vtbl.8 \out\()l, {\tbl}, \in\()l 68 .ifc \out, \tbl 69 vtbl.8 \out\()h, {\tmp}, \in\()h 70 .else 71 vtbl.8 \out\()h, {\tbl}, \in\()h 72 .endif 73 .endm 74 75 .macro __ldr, out, sym 76 vldr \out\()l, \sym 77 vldr \out\()h, \sym + 8 78 .endm 79 80 .macro __adr, reg, lbl 81 adr \reg, \lbl 82THUMB( orr \reg, \reg, #1 ) 83 .endm 84 85 .macro in_bs_ch, b0, b1, b2, b3, b4, b5, b6, b7 86 veor \b2, \b2, \b1 87 veor \b5, \b5, \b6 88 veor \b3, \b3, \b0 89 veor \b6, \b6, \b2 90 veor \b5, \b5, \b0 91 veor \b6, \b6, \b3 92 veor \b3, \b3, \b7 93 veor \b7, \b7, \b5 94 veor \b3, \b3, \b4 95 veor \b4, \b4, \b5 96 veor \b2, \b2, \b7 97 veor \b3, \b3, \b1 98 veor \b1, \b1, \b5 99 .endm 100 101 .macro out_bs_ch, b0, b1, b2, b3, b4, b5, b6, b7 102 veor \b0, \b0, \b6 103 veor \b1, \b1, \b4 104 veor \b4, \b4, \b6 105 veor \b2, \b2, \b0 106 veor \b6, \b6, \b1 107 veor \b1, \b1, \b5 108 veor \b5, \b5, \b3 109 veor \b3, \b3, \b7 110 veor \b7, \b7, \b5 111 veor \b2, \b2, \b5 112 veor \b4, \b4, \b7 113 .endm 114 115 .macro inv_in_bs_ch, b6, b1, b2, b4, b7, b0, b3, b5 116 veor \b1, \b1, \b7 117 veor \b4, \b4, \b7 118 veor \b7, \b7, \b5 119 veor \b1, \b1, \b3 120 veor \b2, \b2, \b5 121 veor \b3, \b3, \b7 122 veor \b6, \b6, \b1 123 veor \b2, \b2, \b0 124 veor \b5, \b5, \b3 125 veor \b4, \b4, \b6 126 veor \b0, \b0, \b6 127 veor \b1, \b1, \b4 128 .endm 129 130 .macro inv_out_bs_ch, b6, b5, b0, b3, b7, b1, b4, b2 131 veor \b1, \b1, \b5 132 veor \b2, \b2, \b7 133 veor \b3, \b3, \b1 134 veor \b4, \b4, \b5 135 veor \b7, \b7, \b5 136 veor \b3, \b3, \b4 137 veor \b5, \b5, \b0 138 veor \b3, \b3, \b7 139 veor \b6, \b6, \b2 140 veor \b2, \b2, \b1 141 veor \b6, \b6, \b3 142 veor \b3, \b3, \b0 143 veor \b5, \b5, \b6 144 .endm 145 146 .macro mul_gf4, x0, x1, y0, y1, t0, t1 147 veor \t0, \y0, \y1 148 vand \t0, \t0, \x0 149 veor \x0, \x0, \x1 150 vand \t1, \x1, \y0 151 vand \x0, \x0, \y1 152 veor \x1, \t1, \t0 153 veor \x0, \x0, \t1 154 .endm 155 156 .macro mul_gf4_n_gf4, x0, x1, y0, y1, t0, x2, x3, y2, y3, t1 157 veor \t0, \y0, \y1 158 veor \t1, \y2, \y3 159 vand \t0, \t0, \x0 160 vand \t1, \t1, \x2 161 veor \x0, \x0, \x1 162 veor \x2, \x2, \x3 163 vand \x1, \x1, \y0 164 vand \x3, \x3, \y2 165 vand \x0, \x0, \y1 166 vand \x2, \x2, \y3 167 veor \x1, \x1, \x0 168 veor \x2, \x2, \x3 169 veor \x0, \x0, \t0 170 veor \x3, \x3, \t1 171 .endm 172 173 .macro mul_gf16_2, x0, x1, x2, x3, x4, x5, x6, x7, \ 174 y0, y1, y2, y3, t0, t1, t2, t3 175 veor \t0, \x0, \x2 176 veor \t1, \x1, \x3 177 mul_gf4 \x0, \x1, \y0, \y1, \t2, \t3 178 veor \y0, \y0, \y2 179 veor \y1, \y1, \y3 180 mul_gf4_n_gf4 \t0, \t1, \y0, \y1, \t3, \x2, \x3, \y2, \y3, \t2 181 veor \x0, \x0, \t0 182 veor \x2, \x2, \t0 183 veor \x1, \x1, \t1 184 veor \x3, \x3, \t1 185 veor \t0, \x4, \x6 186 veor \t1, \x5, \x7 187 mul_gf4_n_gf4 \t0, \t1, \y0, \y1, \t3, \x6, \x7, \y2, \y3, \t2 188 veor \y0, \y0, \y2 189 veor \y1, \y1, \y3 190 mul_gf4 \x4, \x5, \y0, \y1, \t2, \t3 191 veor \x4, \x4, \t0 192 veor \x6, \x6, \t0 193 veor \x5, \x5, \t1 194 veor \x7, \x7, \t1 195 .endm 196 197 .macro inv_gf256, x0, x1, x2, x3, x4, x5, x6, x7, \ 198 t0, t1, t2, t3, s0, s1, s2, s3 199 veor \t3, \x4, \x6 200 veor \t0, \x5, \x7 201 veor \t1, \x1, \x3 202 veor \s1, \x7, \x6 203 veor \s0, \x0, \x2 204 veor \s3, \t3, \t0 205 vorr \t2, \t0, \t1 206 vand \s2, \t3, \s0 207 vorr \t3, \t3, \s0 208 veor \s0, \s0, \t1 209 vand \t0, \t0, \t1 210 veor \t1, \x3, \x2 211 vand \s3, \s3, \s0 212 vand \s1, \s1, \t1 213 veor \t1, \x4, \x5 214 veor \s0, \x1, \x0 215 veor \t3, \t3, \s1 216 veor \t2, \t2, \s1 217 vand \s1, \t1, \s0 218 vorr \t1, \t1, \s0 219 veor \t3, \t3, \s3 220 veor \t0, \t0, \s1 221 veor \t2, \t2, \s2 222 veor \t1, \t1, \s3 223 veor \t0, \t0, \s2 224 vand \s0, \x7, \x3 225 veor \t1, \t1, \s2 226 vand \s1, \x6, \x2 227 vand \s2, \x5, \x1 228 vorr \s3, \x4, \x0 229 veor \t3, \t3, \s0 230 veor \t1, \t1, \s2 231 veor \s0, \t0, \s3 232 veor \t2, \t2, \s1 233 vand \s2, \t3, \t1 234 veor \s1, \t2, \s2 235 veor \s3, \s0, \s2 236 vbsl \s1, \t1, \s0 237 vmvn \t0, \s0 238 vbsl \s0, \s1, \s3 239 vbsl \t0, \s1, \s3 240 vbsl \s3, \t3, \t2 241 veor \t3, \t3, \t2 242 vand \s2, \s0, \s3 243 veor \t1, \t1, \t0 244 veor \s2, \s2, \t3 245 mul_gf16_2 \x0, \x1, \x2, \x3, \x4, \x5, \x6, \x7, \ 246 \s3, \s2, \s1, \t1, \s0, \t0, \t2, \t3 247 .endm 248 249 .macro sbox, b0, b1, b2, b3, b4, b5, b6, b7, \ 250 t0, t1, t2, t3, s0, s1, s2, s3 251 in_bs_ch \b0, \b1, \b2, \b3, \b4, \b5, \b6, \b7 252 inv_gf256 \b6, \b5, \b0, \b3, \b7, \b1, \b4, \b2, \ 253 \t0, \t1, \t2, \t3, \s0, \s1, \s2, \s3 254 out_bs_ch \b7, \b1, \b4, \b2, \b6, \b5, \b0, \b3 255 .endm 256 257 .macro inv_sbox, b0, b1, b2, b3, b4, b5, b6, b7, \ 258 t0, t1, t2, t3, s0, s1, s2, s3 259 inv_in_bs_ch \b0, \b1, \b2, \b3, \b4, \b5, \b6, \b7 260 inv_gf256 \b5, \b1, \b2, \b6, \b3, \b7, \b0, \b4, \ 261 \t0, \t1, \t2, \t3, \s0, \s1, \s2, \s3 262 inv_out_bs_ch \b3, \b7, \b0, \b4, \b5, \b1, \b2, \b6 263 .endm 264 265 .macro shift_rows, x0, x1, x2, x3, x4, x5, x6, x7, \ 266 t0, t1, t2, t3, mask 267 vld1.8 {\t0-\t1}, [bskey, :256]! 268 veor \t0, \t0, \x0 269 vld1.8 {\t2-\t3}, [bskey, :256]! 270 veor \t1, \t1, \x1 271 __tbl \x0, \t0, \mask 272 veor \t2, \t2, \x2 273 __tbl \x1, \t1, \mask 274 vld1.8 {\t0-\t1}, [bskey, :256]! 275 veor \t3, \t3, \x3 276 __tbl \x2, \t2, \mask 277 __tbl \x3, \t3, \mask 278 vld1.8 {\t2-\t3}, [bskey, :256]! 279 veor \t0, \t0, \x4 280 veor \t1, \t1, \x5 281 __tbl \x4, \t0, \mask 282 veor \t2, \t2, \x6 283 __tbl \x5, \t1, \mask 284 veor \t3, \t3, \x7 285 __tbl \x6, \t2, \mask 286 __tbl \x7, \t3, \mask 287 .endm 288 289 .macro inv_shift_rows, x0, x1, x2, x3, x4, x5, x6, x7, \ 290 t0, t1, t2, t3, mask 291 __tbl \x0, \x0, \mask, \t0 292 __tbl \x1, \x1, \mask, \t1 293 __tbl \x2, \x2, \mask, \t2 294 __tbl \x3, \x3, \mask, \t3 295 __tbl \x4, \x4, \mask, \t0 296 __tbl \x5, \x5, \mask, \t1 297 __tbl \x6, \x6, \mask, \t2 298 __tbl \x7, \x7, \mask, \t3 299 .endm 300 301 .macro mix_cols, x0, x1, x2, x3, x4, x5, x6, x7, \ 302 t0, t1, t2, t3, t4, t5, t6, t7, inv 303 vext.8 \t0, \x0, \x0, #12 304 vext.8 \t1, \x1, \x1, #12 305 veor \x0, \x0, \t0 306 vext.8 \t2, \x2, \x2, #12 307 veor \x1, \x1, \t1 308 vext.8 \t3, \x3, \x3, #12 309 veor \x2, \x2, \t2 310 vext.8 \t4, \x4, \x4, #12 311 veor \x3, \x3, \t3 312 vext.8 \t5, \x5, \x5, #12 313 veor \x4, \x4, \t4 314 vext.8 \t6, \x6, \x6, #12 315 veor \x5, \x5, \t5 316 vext.8 \t7, \x7, \x7, #12 317 veor \x6, \x6, \t6 318 veor \t1, \t1, \x0 319 veor.8 \x7, \x7, \t7 320 vext.8 \x0, \x0, \x0, #8 321 veor \t2, \t2, \x1 322 veor \t0, \t0, \x7 323 veor \t1, \t1, \x7 324 vext.8 \x1, \x1, \x1, #8 325 veor \t5, \t5, \x4 326 veor \x0, \x0, \t0 327 veor \t6, \t6, \x5 328 veor \x1, \x1, \t1 329 vext.8 \t0, \x4, \x4, #8 330 veor \t4, \t4, \x3 331 vext.8 \t1, \x5, \x5, #8 332 veor \t7, \t7, \x6 333 vext.8 \x4, \x3, \x3, #8 334 veor \t3, \t3, \x2 335 vext.8 \x5, \x7, \x7, #8 336 veor \t4, \t4, \x7 337 vext.8 \x3, \x6, \x6, #8 338 veor \t3, \t3, \x7 339 vext.8 \x6, \x2, \x2, #8 340 veor \x7, \t1, \t5 341 .ifb \inv 342 veor \x2, \t0, \t4 343 veor \x4, \x4, \t3 344 veor \x5, \x5, \t7 345 veor \x3, \x3, \t6 346 veor \x6, \x6, \t2 347 .else 348 veor \t3, \t3, \x4 349 veor \x5, \x5, \t7 350 veor \x2, \x3, \t6 351 veor \x3, \t0, \t4 352 veor \x4, \x6, \t2 353 vmov \x6, \t3 354 .endif 355 .endm 356 357 .macro inv_mix_cols, x0, x1, x2, x3, x4, x5, x6, x7, \ 358 t0, t1, t2, t3, t4, t5, t6, t7 359 vld1.8 {\t0-\t1}, [bskey, :256]! 360 veor \x0, \x0, \t0 361 vld1.8 {\t2-\t3}, [bskey, :256]! 362 veor \x1, \x1, \t1 363 vld1.8 {\t4-\t5}, [bskey, :256]! 364 veor \x2, \x2, \t2 365 vld1.8 {\t6-\t7}, [bskey, :256] 366 sub bskey, bskey, #224 367 veor \x3, \x3, \t3 368 veor \x4, \x4, \t4 369 veor \x5, \x5, \t5 370 veor \x6, \x6, \t6 371 veor \x7, \x7, \t7 372 vext.8 \t0, \x0, \x0, #8 373 vext.8 \t6, \x6, \x6, #8 374 vext.8 \t7, \x7, \x7, #8 375 veor \t0, \t0, \x0 376 vext.8 \t1, \x1, \x1, #8 377 veor \t6, \t6, \x6 378 vext.8 \t2, \x2, \x2, #8 379 veor \t7, \t7, \x7 380 vext.8 \t3, \x3, \x3, #8 381 veor \t1, \t1, \x1 382 vext.8 \t4, \x4, \x4, #8 383 veor \t2, \t2, \x2 384 vext.8 \t5, \x5, \x5, #8 385 veor \t3, \t3, \x3 386 veor \t4, \t4, \x4 387 veor \t5, \t5, \x5 388 veor \x0, \x0, \t6 389 veor \x1, \x1, \t6 390 veor \x2, \x2, \t0 391 veor \x4, \x4, \t2 392 veor \x3, \x3, \t1 393 veor \x1, \x1, \t7 394 veor \x2, \x2, \t7 395 veor \x4, \x4, \t6 396 veor \x5, \x5, \t3 397 veor \x3, \x3, \t6 398 veor \x6, \x6, \t4 399 veor \x4, \x4, \t7 400 veor \x5, \x5, \t7 401 veor \x7, \x7, \t5 402 mix_cols \x0, \x1, \x2, \x3, \x4, \x5, \x6, \x7, \ 403 \t0, \t1, \t2, \t3, \t4, \t5, \t6, \t7, 1 404 .endm 405 406 .macro swapmove_2x, a0, b0, a1, b1, n, mask, t0, t1 407 vshr.u64 \t0, \b0, #\n 408 vshr.u64 \t1, \b1, #\n 409 veor \t0, \t0, \a0 410 veor \t1, \t1, \a1 411 vand \t0, \t0, \mask 412 vand \t1, \t1, \mask 413 veor \a0, \a0, \t0 414 vshl.s64 \t0, \t0, #\n 415 veor \a1, \a1, \t1 416 vshl.s64 \t1, \t1, #\n 417 veor \b0, \b0, \t0 418 veor \b1, \b1, \t1 419 .endm 420 421 .macro bitslice, x7, x6, x5, x4, x3, x2, x1, x0, t0, t1, t2, t3 422 vmov.i8 \t0, #0x55 423 vmov.i8 \t1, #0x33 424 swapmove_2x \x0, \x1, \x2, \x3, 1, \t0, \t2, \t3 425 swapmove_2x \x4, \x5, \x6, \x7, 1, \t0, \t2, \t3 426 vmov.i8 \t0, #0x0f 427 swapmove_2x \x0, \x2, \x1, \x3, 2, \t1, \t2, \t3 428 swapmove_2x \x4, \x6, \x5, \x7, 2, \t1, \t2, \t3 429 swapmove_2x \x0, \x4, \x1, \x5, 4, \t0, \t2, \t3 430 swapmove_2x \x2, \x6, \x3, \x7, 4, \t0, \t2, \t3 431 .endm 432 433 .align 4 434M0: .quad 0x02060a0e03070b0f, 0x0004080c0105090d 435 436 /* 437 * void aesbs_convert_key(u8 out[], u32 const rk[], int rounds) 438 */ 439ENTRY(aesbs_convert_key) 440 vld1.32 {q7}, [r1]! // load round 0 key 441 vld1.32 {q15}, [r1]! // load round 1 key 442 443 vmov.i8 q8, #0x01 // bit masks 444 vmov.i8 q9, #0x02 445 vmov.i8 q10, #0x04 446 vmov.i8 q11, #0x08 447 vmov.i8 q12, #0x10 448 vmov.i8 q13, #0x20 449 __ldr q14, M0 450 451 sub r2, r2, #1 452 vst1.8 {q7}, [r0, :128]! // save round 0 key 453 454.Lkey_loop: 455 __tbl q7, q15, q14 456 vmov.i8 q6, #0x40 457 vmov.i8 q15, #0x80 458 459 vtst.8 q0, q7, q8 460 vtst.8 q1, q7, q9 461 vtst.8 q2, q7, q10 462 vtst.8 q3, q7, q11 463 vtst.8 q4, q7, q12 464 vtst.8 q5, q7, q13 465 vtst.8 q6, q7, q6 466 vtst.8 q7, q7, q15 467 vld1.32 {q15}, [r1]! // load next round key 468 vmvn q0, q0 469 vmvn q1, q1 470 vmvn q5, q5 471 vmvn q6, q6 472 473 subs r2, r2, #1 474 vst1.8 {q0-q1}, [r0, :256]! 475 vst1.8 {q2-q3}, [r0, :256]! 476 vst1.8 {q4-q5}, [r0, :256]! 477 vst1.8 {q6-q7}, [r0, :256]! 478 bne .Lkey_loop 479 480 vmov.i8 q7, #0x63 // compose .L63 481 veor q15, q15, q7 482 vst1.8 {q15}, [r0, :128] 483 bx lr 484ENDPROC(aesbs_convert_key) 485 486 .align 4 487M0SR: .quad 0x0a0e02060f03070b, 0x0004080c05090d01 488 489aesbs_encrypt8: 490 vld1.8 {q9}, [bskey, :128]! // round 0 key 491 __ldr q8, M0SR 492 493 veor q10, q0, q9 // xor with round0 key 494 veor q11, q1, q9 495 __tbl q0, q10, q8 496 veor q12, q2, q9 497 __tbl q1, q11, q8 498 veor q13, q3, q9 499 __tbl q2, q12, q8 500 veor q14, q4, q9 501 __tbl q3, q13, q8 502 veor q15, q5, q9 503 __tbl q4, q14, q8 504 veor q10, q6, q9 505 __tbl q5, q15, q8 506 veor q11, q7, q9 507 __tbl q6, q10, q8 508 __tbl q7, q11, q8 509 510 bitslice q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11 511 512 sub rounds, rounds, #1 513 b .Lenc_sbox 514 515 .align 5 516SR: .quad 0x0504070600030201, 0x0f0e0d0c0a09080b 517SRM0: .quad 0x0304090e00050a0f, 0x01060b0c0207080d 518 519.Lenc_last: 520 __ldr q12, SRM0 521.Lenc_loop: 522 shift_rows q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11, q12 523.Lenc_sbox: 524 sbox q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11, q12, \ 525 q13, q14, q15 526 subs rounds, rounds, #1 527 bcc .Lenc_done 528 529 mix_cols q0, q1, q4, q6, q3, q7, q2, q5, q8, q9, q10, q11, q12, \ 530 q13, q14, q15 531 532 beq .Lenc_last 533 __ldr q12, SR 534 b .Lenc_loop 535 536.Lenc_done: 537 vld1.8 {q12}, [bskey, :128] // last round key 538 539 bitslice q0, q1, q4, q6, q3, q7, q2, q5, q8, q9, q10, q11 540 541 veor q0, q0, q12 542 veor q1, q1, q12 543 veor q4, q4, q12 544 veor q6, q6, q12 545 veor q3, q3, q12 546 veor q7, q7, q12 547 veor q2, q2, q12 548 veor q5, q5, q12 549 bx lr 550ENDPROC(aesbs_encrypt8) 551 552 .align 4 553M0ISR: .quad 0x0a0e0206070b0f03, 0x0004080c0d010509 554 555aesbs_decrypt8: 556 add bskey, bskey, rounds, lsl #7 557 sub bskey, bskey, #112 558 vld1.8 {q9}, [bskey, :128] // round 0 key 559 sub bskey, bskey, #128 560 __ldr q8, M0ISR 561 562 veor q10, q0, q9 // xor with round0 key 563 veor q11, q1, q9 564 __tbl q0, q10, q8 565 veor q12, q2, q9 566 __tbl q1, q11, q8 567 veor q13, q3, q9 568 __tbl q2, q12, q8 569 veor q14, q4, q9 570 __tbl q3, q13, q8 571 veor q15, q5, q9 572 __tbl q4, q14, q8 573 veor q10, q6, q9 574 __tbl q5, q15, q8 575 veor q11, q7, q9 576 __tbl q6, q10, q8 577 __tbl q7, q11, q8 578 579 bitslice q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11 580 581 sub rounds, rounds, #1 582 b .Ldec_sbox 583 584 .align 5 585ISR: .quad 0x0504070602010003, 0x0f0e0d0c080b0a09 586ISRM0: .quad 0x01040b0e0205080f, 0x0306090c00070a0d 587 588.Ldec_last: 589 __ldr q12, ISRM0 590.Ldec_loop: 591 inv_shift_rows q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11, q12 592.Ldec_sbox: 593 inv_sbox q0, q1, q2, q3, q4, q5, q6, q7, q8, q9, q10, q11, q12, \ 594 q13, q14, q15 595 subs rounds, rounds, #1 596 bcc .Ldec_done 597 598 inv_mix_cols q0, q1, q6, q4, q2, q7, q3, q5, q8, q9, q10, q11, q12, \ 599 q13, q14, q15 600 601 beq .Ldec_last 602 __ldr q12, ISR 603 b .Ldec_loop 604 605.Ldec_done: 606 add bskey, bskey, #112 607 vld1.8 {q12}, [bskey, :128] // last round key 608 609 bitslice q0, q1, q6, q4, q2, q7, q3, q5, q8, q9, q10, q11 610 611 veor q0, q0, q12 612 veor q1, q1, q12 613 veor q6, q6, q12 614 veor q4, q4, q12 615 veor q2, q2, q12 616 veor q7, q7, q12 617 veor q3, q3, q12 618 veor q5, q5, q12 619 bx lr 620ENDPROC(aesbs_decrypt8) 621 622 /* 623 * aesbs_ecb_encrypt(u8 out[], u8 const in[], u8 const rk[], int rounds, 624 * int blocks) 625 * aesbs_ecb_decrypt(u8 out[], u8 const in[], u8 const rk[], int rounds, 626 * int blocks) 627 */ 628 .macro __ecb_crypt, do8, o0, o1, o2, o3, o4, o5, o6, o7 629 push {r4-r6, lr} 630 ldr r5, [sp, #16] // number of blocks 631 63299: __adr ip, 0f 633 and lr, r5, #7 634 cmp r5, #8 635 sub ip, ip, lr, lsl #2 636 bxlt ip // computed goto if blocks < 8 637 638 vld1.8 {q0}, [r1]! 639 vld1.8 {q1}, [r1]! 640 vld1.8 {q2}, [r1]! 641 vld1.8 {q3}, [r1]! 642 vld1.8 {q4}, [r1]! 643 vld1.8 {q5}, [r1]! 644 vld1.8 {q6}, [r1]! 645 vld1.8 {q7}, [r1]! 646 6470: mov bskey, r2 648 mov rounds, r3 649 bl \do8 650 651 __adr ip, 1f 652 and lr, r5, #7 653 cmp r5, #8 654 sub ip, ip, lr, lsl #2 655 bxlt ip // computed goto if blocks < 8 656 657 vst1.8 {\o0}, [r0]! 658 vst1.8 {\o1}, [r0]! 659 vst1.8 {\o2}, [r0]! 660 vst1.8 {\o3}, [r0]! 661 vst1.8 {\o4}, [r0]! 662 vst1.8 {\o5}, [r0]! 663 vst1.8 {\o6}, [r0]! 664 vst1.8 {\o7}, [r0]! 665 6661: subs r5, r5, #8 667 bgt 99b 668 669 pop {r4-r6, pc} 670 .endm 671 672 .align 4 673ENTRY(aesbs_ecb_encrypt) 674 __ecb_crypt aesbs_encrypt8, q0, q1, q4, q6, q3, q7, q2, q5 675ENDPROC(aesbs_ecb_encrypt) 676 677 .align 4 678ENTRY(aesbs_ecb_decrypt) 679 __ecb_crypt aesbs_decrypt8, q0, q1, q6, q4, q2, q7, q3, q5 680ENDPROC(aesbs_ecb_decrypt) 681 682 /* 683 * aesbs_cbc_decrypt(u8 out[], u8 const in[], u8 const rk[], 684 * int rounds, int blocks, u8 iv[]) 685 */ 686 .align 4 687ENTRY(aesbs_cbc_decrypt) 688 mov ip, sp 689 push {r4-r6, lr} 690 ldm ip, {r5-r6} // load args 4-5 691 69299: __adr ip, 0f 693 and lr, r5, #7 694 cmp r5, #8 695 sub ip, ip, lr, lsl #2 696 mov lr, r1 697 bxlt ip // computed goto if blocks < 8 698 699 vld1.8 {q0}, [lr]! 700 vld1.8 {q1}, [lr]! 701 vld1.8 {q2}, [lr]! 702 vld1.8 {q3}, [lr]! 703 vld1.8 {q4}, [lr]! 704 vld1.8 {q5}, [lr]! 705 vld1.8 {q6}, [lr]! 706 vld1.8 {q7}, [lr] 707 7080: mov bskey, r2 709 mov rounds, r3 710 bl aesbs_decrypt8 711 712 vld1.8 {q8}, [r6] 713 vmov q9, q8 714 vmov q10, q8 715 vmov q11, q8 716 vmov q12, q8 717 vmov q13, q8 718 vmov q14, q8 719 vmov q15, q8 720 721 __adr ip, 1f 722 and lr, r5, #7 723 cmp r5, #8 724 sub ip, ip, lr, lsl #2 725 bxlt ip // computed goto if blocks < 8 726 727 vld1.8 {q9}, [r1]! 728 vld1.8 {q10}, [r1]! 729 vld1.8 {q11}, [r1]! 730 vld1.8 {q12}, [r1]! 731 vld1.8 {q13}, [r1]! 732 vld1.8 {q14}, [r1]! 733 vld1.8 {q15}, [r1]! 734 W(nop) 735 7361: __adr ip, 2f 737 sub ip, ip, lr, lsl #3 738 bxlt ip // computed goto if blocks < 8 739 740 veor q0, q0, q8 741 vst1.8 {q0}, [r0]! 742 veor q1, q1, q9 743 vst1.8 {q1}, [r0]! 744 veor q6, q6, q10 745 vst1.8 {q6}, [r0]! 746 veor q4, q4, q11 747 vst1.8 {q4}, [r0]! 748 veor q2, q2, q12 749 vst1.8 {q2}, [r0]! 750 veor q7, q7, q13 751 vst1.8 {q7}, [r0]! 752 veor q3, q3, q14 753 vst1.8 {q3}, [r0]! 754 veor q5, q5, q15 755 vld1.8 {q8}, [r1]! // load next round's iv 7562: vst1.8 {q5}, [r0]! 757 758 subs r5, r5, #8 759 vst1.8 {q8}, [r6] // store next round's iv 760 bgt 99b 761 762 pop {r4-r6, pc} 763ENDPROC(aesbs_cbc_decrypt) 764 765 .macro next_ctr, q 766 vmov.32 \q\()h[1], r10 767 adds r10, r10, #1 768 vmov.32 \q\()h[0], r9 769 adcs r9, r9, #0 770 vmov.32 \q\()l[1], r8 771 adcs r8, r8, #0 772 vmov.32 \q\()l[0], r7 773 adc r7, r7, #0 774 vrev32.8 \q, \q 775 .endm 776 777 /* 778 * aesbs_ctr_encrypt(u8 out[], u8 const in[], u8 const rk[], 779 * int rounds, int blocks, u8 ctr[], u8 final[]) 780 */ 781ENTRY(aesbs_ctr_encrypt) 782 mov ip, sp 783 push {r4-r10, lr} 784 785 ldm ip, {r5-r7} // load args 4-6 786 teq r7, #0 787 addne r5, r5, #1 // one extra block if final != 0 788 789 vld1.8 {q0}, [r6] // load counter 790 vrev32.8 q1, q0 791 vmov r9, r10, d3 792 vmov r7, r8, d2 793 794 adds r10, r10, #1 795 adcs r9, r9, #0 796 adcs r8, r8, #0 797 adc r7, r7, #0 798 79999: vmov q1, q0 800 vmov q2, q0 801 vmov q3, q0 802 vmov q4, q0 803 vmov q5, q0 804 vmov q6, q0 805 vmov q7, q0 806 807 __adr ip, 0f 808 sub lr, r5, #1 809 and lr, lr, #7 810 cmp r5, #8 811 sub ip, ip, lr, lsl #5 812 sub ip, ip, lr, lsl #2 813 bxlt ip // computed goto if blocks < 8 814 815 next_ctr q1 816 next_ctr q2 817 next_ctr q3 818 next_ctr q4 819 next_ctr q5 820 next_ctr q6 821 next_ctr q7 822 8230: mov bskey, r2 824 mov rounds, r3 825 bl aesbs_encrypt8 826 827 __adr ip, 1f 828 and lr, r5, #7 829 cmp r5, #8 830 movgt r4, #0 831 ldrle r4, [sp, #40] // load final in the last round 832 sub ip, ip, lr, lsl #2 833 bxlt ip // computed goto if blocks < 8 834 835 vld1.8 {q8}, [r1]! 836 vld1.8 {q9}, [r1]! 837 vld1.8 {q10}, [r1]! 838 vld1.8 {q11}, [r1]! 839 vld1.8 {q12}, [r1]! 840 vld1.8 {q13}, [r1]! 841 vld1.8 {q14}, [r1]! 842 teq r4, #0 // skip last block if 'final' 8431: bne 2f 844 vld1.8 {q15}, [r1]! 845 8462: __adr ip, 3f 847 cmp r5, #8 848 sub ip, ip, lr, lsl #3 849 bxlt ip // computed goto if blocks < 8 850 851 veor q0, q0, q8 852 vst1.8 {q0}, [r0]! 853 veor q1, q1, q9 854 vst1.8 {q1}, [r0]! 855 veor q4, q4, q10 856 vst1.8 {q4}, [r0]! 857 veor q6, q6, q11 858 vst1.8 {q6}, [r0]! 859 veor q3, q3, q12 860 vst1.8 {q3}, [r0]! 861 veor q7, q7, q13 862 vst1.8 {q7}, [r0]! 863 veor q2, q2, q14 864 vst1.8 {q2}, [r0]! 865 teq r4, #0 // skip last block if 'final' 866 W(bne) 5f 8673: veor q5, q5, q15 868 vst1.8 {q5}, [r0]! 869 8704: next_ctr q0 871 872 subs r5, r5, #8 873 bgt 99b 874 875 vst1.8 {q0}, [r6] 876 pop {r4-r10, pc} 877 8785: vst1.8 {q5}, [r4] 879 b 4b 880ENDPROC(aesbs_ctr_encrypt) 881 882 .macro next_tweak, out, in, const, tmp 883 vshr.s64 \tmp, \in, #63 884 vand \tmp, \tmp, \const 885 vadd.u64 \out, \in, \in 886 vext.8 \tmp, \tmp, \tmp, #8 887 veor \out, \out, \tmp 888 .endm 889 890 .align 4 891.Lxts_mul_x: 892 .quad 1, 0x87 893 894 /* 895 * aesbs_xts_encrypt(u8 out[], u8 const in[], u8 const rk[], int rounds, 896 * int blocks, u8 iv[]) 897 * aesbs_xts_decrypt(u8 out[], u8 const in[], u8 const rk[], int rounds, 898 * int blocks, u8 iv[]) 899 */ 900__xts_prepare8: 901 vld1.8 {q14}, [r7] // load iv 902 __ldr q15, .Lxts_mul_x // load tweak mask 903 vmov q12, q14 904 905 __adr ip, 0f 906 and r4, r6, #7 907 cmp r6, #8 908 sub ip, ip, r4, lsl #5 909 mov r4, sp 910 bxlt ip // computed goto if blocks < 8 911 912 vld1.8 {q0}, [r1]! 913 next_tweak q12, q14, q15, q13 914 veor q0, q0, q14 915 vst1.8 {q14}, [r4, :128]! 916 917 vld1.8 {q1}, [r1]! 918 next_tweak q14, q12, q15, q13 919 veor q1, q1, q12 920 vst1.8 {q12}, [r4, :128]! 921 922 vld1.8 {q2}, [r1]! 923 next_tweak q12, q14, q15, q13 924 veor q2, q2, q14 925 vst1.8 {q14}, [r4, :128]! 926 927 vld1.8 {q3}, [r1]! 928 next_tweak q14, q12, q15, q13 929 veor q3, q3, q12 930 vst1.8 {q12}, [r4, :128]! 931 932 vld1.8 {q4}, [r1]! 933 next_tweak q12, q14, q15, q13 934 veor q4, q4, q14 935 vst1.8 {q14}, [r4, :128]! 936 937 vld1.8 {q5}, [r1]! 938 next_tweak q14, q12, q15, q13 939 veor q5, q5, q12 940 vst1.8 {q12}, [r4, :128]! 941 942 vld1.8 {q6}, [r1]! 943 next_tweak q12, q14, q15, q13 944 veor q6, q6, q14 945 vst1.8 {q14}, [r4, :128]! 946 947 vld1.8 {q7}, [r1]! 948 next_tweak q14, q12, q15, q13 949 veor q7, q7, q12 950 vst1.8 {q12}, [r4, :128] 951 9520: vst1.8 {q14}, [r7] // store next iv 953 bx lr 954ENDPROC(__xts_prepare8) 955 956 .macro __xts_crypt, do8, o0, o1, o2, o3, o4, o5, o6, o7 957 push {r4-r8, lr} 958 mov r5, sp // preserve sp 959 ldrd r6, r7, [sp, #24] // get blocks and iv args 960 sub ip, sp, #128 // make room for 8x tweak 961 bic ip, ip, #0xf // align sp to 16 bytes 962 mov sp, ip 963 96499: bl __xts_prepare8 965 966 mov bskey, r2 967 mov rounds, r3 968 bl \do8 969 970 __adr ip, 0f 971 and lr, r6, #7 972 cmp r6, #8 973 sub ip, ip, lr, lsl #2 974 mov r4, sp 975 bxlt ip // computed goto if blocks < 8 976 977 vld1.8 {q8}, [r4, :128]! 978 vld1.8 {q9}, [r4, :128]! 979 vld1.8 {q10}, [r4, :128]! 980 vld1.8 {q11}, [r4, :128]! 981 vld1.8 {q12}, [r4, :128]! 982 vld1.8 {q13}, [r4, :128]! 983 vld1.8 {q14}, [r4, :128]! 984 vld1.8 {q15}, [r4, :128] 985 9860: __adr ip, 1f 987 sub ip, ip, lr, lsl #3 988 bxlt ip // computed goto if blocks < 8 989 990 veor \o0, \o0, q8 991 vst1.8 {\o0}, [r0]! 992 veor \o1, \o1, q9 993 vst1.8 {\o1}, [r0]! 994 veor \o2, \o2, q10 995 vst1.8 {\o2}, [r0]! 996 veor \o3, \o3, q11 997 vst1.8 {\o3}, [r0]! 998 veor \o4, \o4, q12 999 vst1.8 {\o4}, [r0]! 1000 veor \o5, \o5, q13 1001 vst1.8 {\o5}, [r0]! 1002 veor \o6, \o6, q14 1003 vst1.8 {\o6}, [r0]! 1004 veor \o7, \o7, q15 1005 vst1.8 {\o7}, [r0]! 1006 10071: subs r6, r6, #8 1008 bgt 99b 1009 1010 mov sp, r5 1011 pop {r4-r8, pc} 1012 .endm 1013 1014ENTRY(aesbs_xts_encrypt) 1015 __xts_crypt aesbs_encrypt8, q0, q1, q4, q6, q3, q7, q2, q5 1016ENDPROC(aesbs_xts_encrypt) 1017 1018ENTRY(aesbs_xts_decrypt) 1019 __xts_crypt aesbs_decrypt8, q0, q1, q6, q4, q2, q7, q3, q5 1020ENDPROC(aesbs_xts_decrypt) 1021