1######################################################################## 2# Copyright (c) 2013, Intel Corporation 3# 4# This software is available to you under a choice of one of two 5# licenses. You may choose to be licensed under the terms of the GNU 6# General Public License (GPL) Version 2, available from the file 7# COPYING in the main directory of this source tree, or the 8# OpenIB.org BSD license below: 9# 10# Redistribution and use in source and binary forms, with or without 11# modification, are permitted provided that the following conditions are 12# met: 13# 14# * Redistributions of source code must retain the above copyright 15# notice, this list of conditions and the following disclaimer. 16# 17# * Redistributions in binary form must reproduce the above copyright 18# notice, this list of conditions and the following disclaimer in the 19# documentation and/or other materials provided with the 20# distribution. 21# 22# * Neither the name of the Intel Corporation nor the names of its 23# contributors may be used to endorse or promote products derived from 24# this software without specific prior written permission. 25# 26# 27# THIS SOFTWARE IS PROVIDED BY INTEL CORPORATION ""AS IS"" AND ANY 28# EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 29# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 30# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL CORPORATION OR 31# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 32# EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 33# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES# LOSS OF USE, DATA, OR 34# PROFITS# OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 35# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 36# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 37# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 38######################################################################## 39## 40## Authors: 41## Erdinc Ozturk <erdinc.ozturk@intel.com> 42## Vinodh Gopal <vinodh.gopal@intel.com> 43## James Guilford <james.guilford@intel.com> 44## Tim Chen <tim.c.chen@linux.intel.com> 45## 46## References: 47## This code was derived and highly optimized from the code described in paper: 48## Vinodh Gopal et. al. Optimized Galois-Counter-Mode Implementation 49## on Intel Architecture Processors. August, 2010 50## The details of the implementation is explained in: 51## Erdinc Ozturk et. al. Enabling High-Performance Galois-Counter-Mode 52## on Intel Architecture Processors. October, 2012. 53## 54## Assumptions: 55## 56## 57## 58## iv: 59## 0 1 2 3 60## 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 61## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 62## | Salt (From the SA) | 63## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 64## | Initialization Vector | 65## | (This is the sequence number from IPSec header) | 66## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 67## | 0x1 | 68## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 69## 70## 71## 72## AAD: 73## AAD padded to 128 bits with 0 74## for example, assume AAD is a u32 vector 75## 76## if AAD is 8 bytes: 77## AAD[3] = {A0, A1}# 78## padded AAD in xmm register = {A1 A0 0 0} 79## 80## 0 1 2 3 81## 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 82## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 83## | SPI (A1) | 84## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 85## | 32-bit Sequence Number (A0) | 86## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 87## | 0x0 | 88## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 89## 90## AAD Format with 32-bit Sequence Number 91## 92## if AAD is 12 bytes: 93## AAD[3] = {A0, A1, A2}# 94## padded AAD in xmm register = {A2 A1 A0 0} 95## 96## 0 1 2 3 97## 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 98## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 99## | SPI (A2) | 100## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 101## | 64-bit Extended Sequence Number {A1,A0} | 102## | | 103## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 104## | 0x0 | 105## +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 106## 107## AAD Format with 64-bit Extended Sequence Number 108## 109## 110## aadLen: 111## from the definition of the spec, aadLen can only be 8 or 12 bytes. 112## The code additionally supports aadLen of length 16 bytes. 113## 114## TLen: 115## from the definition of the spec, TLen can only be 8, 12 or 16 bytes. 116## 117## poly = x^128 + x^127 + x^126 + x^121 + 1 118## throughout the code, one tab and two tab indentations are used. one tab is 119## for GHASH part, two tabs is for AES part. 120## 121 122#include <linux/linkage.h> 123#include <asm/inst.h> 124 125# constants in mergeable sections, linker can reorder and merge 126.section .rodata.cst16.POLY, "aM", @progbits, 16 127.align 16 128POLY: .octa 0xC2000000000000000000000000000001 129 130.section .rodata.cst16.POLY2, "aM", @progbits, 16 131.align 16 132POLY2: .octa 0xC20000000000000000000001C2000000 133 134.section .rodata.cst16.TWOONE, "aM", @progbits, 16 135.align 16 136TWOONE: .octa 0x00000001000000000000000000000001 137 138.section .rodata.cst16.SHUF_MASK, "aM", @progbits, 16 139.align 16 140SHUF_MASK: .octa 0x000102030405060708090A0B0C0D0E0F 141 142.section .rodata.cst16.ONE, "aM", @progbits, 16 143.align 16 144ONE: .octa 0x00000000000000000000000000000001 145 146.section .rodata.cst16.ONEf, "aM", @progbits, 16 147.align 16 148ONEf: .octa 0x01000000000000000000000000000000 149 150# order of these constants should not change. 151# more specifically, ALL_F should follow SHIFT_MASK, and zero should follow ALL_F 152.section .rodata, "a", @progbits 153.align 16 154SHIFT_MASK: .octa 0x0f0e0d0c0b0a09080706050403020100 155ALL_F: .octa 0xffffffffffffffffffffffffffffffff 156 .octa 0x00000000000000000000000000000000 157 158.section .rodata 159.align 16 160.type aad_shift_arr, @object 161.size aad_shift_arr, 272 162aad_shift_arr: 163 .octa 0xffffffffffffffffffffffffffffffff 164 .octa 0xffffffffffffffffffffffffffffff0C 165 .octa 0xffffffffffffffffffffffffffff0D0C 166 .octa 0xffffffffffffffffffffffffff0E0D0C 167 .octa 0xffffffffffffffffffffffff0F0E0D0C 168 .octa 0xffffffffffffffffffffff0C0B0A0908 169 .octa 0xffffffffffffffffffff0D0C0B0A0908 170 .octa 0xffffffffffffffffff0E0D0C0B0A0908 171 .octa 0xffffffffffffffff0F0E0D0C0B0A0908 172 .octa 0xffffffffffffff0C0B0A090807060504 173 .octa 0xffffffffffff0D0C0B0A090807060504 174 .octa 0xffffffffff0E0D0C0B0A090807060504 175 .octa 0xffffffff0F0E0D0C0B0A090807060504 176 .octa 0xffffff0C0B0A09080706050403020100 177 .octa 0xffff0D0C0B0A09080706050403020100 178 .octa 0xff0E0D0C0B0A09080706050403020100 179 .octa 0x0F0E0D0C0B0A09080706050403020100 180 181 182.text 183 184 185##define the fields of the gcm aes context 186#{ 187# u8 expanded_keys[16*11] store expanded keys 188# u8 shifted_hkey_1[16] store HashKey <<1 mod poly here 189# u8 shifted_hkey_2[16] store HashKey^2 <<1 mod poly here 190# u8 shifted_hkey_3[16] store HashKey^3 <<1 mod poly here 191# u8 shifted_hkey_4[16] store HashKey^4 <<1 mod poly here 192# u8 shifted_hkey_5[16] store HashKey^5 <<1 mod poly here 193# u8 shifted_hkey_6[16] store HashKey^6 <<1 mod poly here 194# u8 shifted_hkey_7[16] store HashKey^7 <<1 mod poly here 195# u8 shifted_hkey_8[16] store HashKey^8 <<1 mod poly here 196# u8 shifted_hkey_1_k[16] store XOR HashKey <<1 mod poly here (for Karatsuba purposes) 197# u8 shifted_hkey_2_k[16] store XOR HashKey^2 <<1 mod poly here (for Karatsuba purposes) 198# u8 shifted_hkey_3_k[16] store XOR HashKey^3 <<1 mod poly here (for Karatsuba purposes) 199# u8 shifted_hkey_4_k[16] store XOR HashKey^4 <<1 mod poly here (for Karatsuba purposes) 200# u8 shifted_hkey_5_k[16] store XOR HashKey^5 <<1 mod poly here (for Karatsuba purposes) 201# u8 shifted_hkey_6_k[16] store XOR HashKey^6 <<1 mod poly here (for Karatsuba purposes) 202# u8 shifted_hkey_7_k[16] store XOR HashKey^7 <<1 mod poly here (for Karatsuba purposes) 203# u8 shifted_hkey_8_k[16] store XOR HashKey^8 <<1 mod poly here (for Karatsuba purposes) 204#} gcm_ctx# 205 206HashKey = 16*11 # store HashKey <<1 mod poly here 207HashKey_2 = 16*12 # store HashKey^2 <<1 mod poly here 208HashKey_3 = 16*13 # store HashKey^3 <<1 mod poly here 209HashKey_4 = 16*14 # store HashKey^4 <<1 mod poly here 210HashKey_5 = 16*15 # store HashKey^5 <<1 mod poly here 211HashKey_6 = 16*16 # store HashKey^6 <<1 mod poly here 212HashKey_7 = 16*17 # store HashKey^7 <<1 mod poly here 213HashKey_8 = 16*18 # store HashKey^8 <<1 mod poly here 214HashKey_k = 16*19 # store XOR of HashKey <<1 mod poly here (for Karatsuba purposes) 215HashKey_2_k = 16*20 # store XOR of HashKey^2 <<1 mod poly here (for Karatsuba purposes) 216HashKey_3_k = 16*21 # store XOR of HashKey^3 <<1 mod poly here (for Karatsuba purposes) 217HashKey_4_k = 16*22 # store XOR of HashKey^4 <<1 mod poly here (for Karatsuba purposes) 218HashKey_5_k = 16*23 # store XOR of HashKey^5 <<1 mod poly here (for Karatsuba purposes) 219HashKey_6_k = 16*24 # store XOR of HashKey^6 <<1 mod poly here (for Karatsuba purposes) 220HashKey_7_k = 16*25 # store XOR of HashKey^7 <<1 mod poly here (for Karatsuba purposes) 221HashKey_8_k = 16*26 # store XOR of HashKey^8 <<1 mod poly here (for Karatsuba purposes) 222 223#define arg1 %rdi 224#define arg2 %rsi 225#define arg3 %rdx 226#define arg4 %rcx 227#define arg5 %r8 228#define arg6 %r9 229#define arg7 STACK_OFFSET+8*1(%r14) 230#define arg8 STACK_OFFSET+8*2(%r14) 231#define arg9 STACK_OFFSET+8*3(%r14) 232 233i = 0 234j = 0 235 236out_order = 0 237in_order = 1 238DEC = 0 239ENC = 1 240 241.macro define_reg r n 242reg_\r = %xmm\n 243.endm 244 245.macro setreg 246.altmacro 247define_reg i %i 248define_reg j %j 249.noaltmacro 250.endm 251 252# need to push 4 registers into stack to maintain 253STACK_OFFSET = 8*4 254 255TMP1 = 16*0 # Temporary storage for AAD 256TMP2 = 16*1 # Temporary storage for AES State 2 (State 1 is stored in an XMM register) 257TMP3 = 16*2 # Temporary storage for AES State 3 258TMP4 = 16*3 # Temporary storage for AES State 4 259TMP5 = 16*4 # Temporary storage for AES State 5 260TMP6 = 16*5 # Temporary storage for AES State 6 261TMP7 = 16*6 # Temporary storage for AES State 7 262TMP8 = 16*7 # Temporary storage for AES State 8 263 264VARIABLE_OFFSET = 16*8 265 266################################ 267# Utility Macros 268################################ 269 270# Encryption of a single block 271.macro ENCRYPT_SINGLE_BLOCK XMM0 272 vpxor (arg1), \XMM0, \XMM0 273 i = 1 274 setreg 275.rep 9 276 vaesenc 16*i(arg1), \XMM0, \XMM0 277 i = (i+1) 278 setreg 279.endr 280 vaesenclast 16*10(arg1), \XMM0, \XMM0 281.endm 282 283#ifdef CONFIG_AS_AVX 284############################################################################### 285# GHASH_MUL MACRO to implement: Data*HashKey mod (128,127,126,121,0) 286# Input: A and B (128-bits each, bit-reflected) 287# Output: C = A*B*x mod poly, (i.e. >>1 ) 288# To compute GH = GH*HashKey mod poly, give HK = HashKey<<1 mod poly as input 289# GH = GH * HK * x mod poly which is equivalent to GH*HashKey mod poly. 290############################################################################### 291.macro GHASH_MUL_AVX GH HK T1 T2 T3 T4 T5 292 293 vpshufd $0b01001110, \GH, \T2 294 vpshufd $0b01001110, \HK, \T3 295 vpxor \GH , \T2, \T2 # T2 = (a1+a0) 296 vpxor \HK , \T3, \T3 # T3 = (b1+b0) 297 298 vpclmulqdq $0x11, \HK, \GH, \T1 # T1 = a1*b1 299 vpclmulqdq $0x00, \HK, \GH, \GH # GH = a0*b0 300 vpclmulqdq $0x00, \T3, \T2, \T2 # T2 = (a1+a0)*(b1+b0) 301 vpxor \GH, \T2,\T2 302 vpxor \T1, \T2,\T2 # T2 = a0*b1+a1*b0 303 304 vpslldq $8, \T2,\T3 # shift-L T3 2 DWs 305 vpsrldq $8, \T2,\T2 # shift-R T2 2 DWs 306 vpxor \T3, \GH, \GH 307 vpxor \T2, \T1, \T1 # <T1:GH> = GH x HK 308 309 #first phase of the reduction 310 vpslld $31, \GH, \T2 # packed right shifting << 31 311 vpslld $30, \GH, \T3 # packed right shifting shift << 30 312 vpslld $25, \GH, \T4 # packed right shifting shift << 25 313 314 vpxor \T3, \T2, \T2 # xor the shifted versions 315 vpxor \T4, \T2, \T2 316 317 vpsrldq $4, \T2, \T5 # shift-R T5 1 DW 318 319 vpslldq $12, \T2, \T2 # shift-L T2 3 DWs 320 vpxor \T2, \GH, \GH # first phase of the reduction complete 321 322 #second phase of the reduction 323 324 vpsrld $1,\GH, \T2 # packed left shifting >> 1 325 vpsrld $2,\GH, \T3 # packed left shifting >> 2 326 vpsrld $7,\GH, \T4 # packed left shifting >> 7 327 vpxor \T3, \T2, \T2 # xor the shifted versions 328 vpxor \T4, \T2, \T2 329 330 vpxor \T5, \T2, \T2 331 vpxor \T2, \GH, \GH 332 vpxor \T1, \GH, \GH # the result is in GH 333 334 335.endm 336 337.macro PRECOMPUTE_AVX HK T1 T2 T3 T4 T5 T6 338 339 # Haskey_i_k holds XORed values of the low and high parts of the Haskey_i 340 vmovdqa \HK, \T5 341 342 vpshufd $0b01001110, \T5, \T1 343 vpxor \T5, \T1, \T1 344 vmovdqa \T1, HashKey_k(arg1) 345 346 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^2<<1 mod poly 347 vmovdqa \T5, HashKey_2(arg1) # [HashKey_2] = HashKey^2<<1 mod poly 348 vpshufd $0b01001110, \T5, \T1 349 vpxor \T5, \T1, \T1 350 vmovdqa \T1, HashKey_2_k(arg1) 351 352 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^3<<1 mod poly 353 vmovdqa \T5, HashKey_3(arg1) 354 vpshufd $0b01001110, \T5, \T1 355 vpxor \T5, \T1, \T1 356 vmovdqa \T1, HashKey_3_k(arg1) 357 358 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^4<<1 mod poly 359 vmovdqa \T5, HashKey_4(arg1) 360 vpshufd $0b01001110, \T5, \T1 361 vpxor \T5, \T1, \T1 362 vmovdqa \T1, HashKey_4_k(arg1) 363 364 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^5<<1 mod poly 365 vmovdqa \T5, HashKey_5(arg1) 366 vpshufd $0b01001110, \T5, \T1 367 vpxor \T5, \T1, \T1 368 vmovdqa \T1, HashKey_5_k(arg1) 369 370 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^6<<1 mod poly 371 vmovdqa \T5, HashKey_6(arg1) 372 vpshufd $0b01001110, \T5, \T1 373 vpxor \T5, \T1, \T1 374 vmovdqa \T1, HashKey_6_k(arg1) 375 376 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^7<<1 mod poly 377 vmovdqa \T5, HashKey_7(arg1) 378 vpshufd $0b01001110, \T5, \T1 379 vpxor \T5, \T1, \T1 380 vmovdqa \T1, HashKey_7_k(arg1) 381 382 GHASH_MUL_AVX \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^8<<1 mod poly 383 vmovdqa \T5, HashKey_8(arg1) 384 vpshufd $0b01001110, \T5, \T1 385 vpxor \T5, \T1, \T1 386 vmovdqa \T1, HashKey_8_k(arg1) 387 388.endm 389 390## if a = number of total plaintext bytes 391## b = floor(a/16) 392## num_initial_blocks = b mod 4# 393## encrypt the initial num_initial_blocks blocks and apply ghash on the ciphertext 394## r10, r11, r12, rax are clobbered 395## arg1, arg2, arg3, r14 are used as a pointer only, not modified 396 397.macro INITIAL_BLOCKS_AVX num_initial_blocks T1 T2 T3 T4 T5 CTR XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 T6 T_key ENC_DEC 398 i = (8-\num_initial_blocks) 399 j = 0 400 setreg 401 402 mov arg6, %r10 # r10 = AAD 403 mov arg7, %r12 # r12 = aadLen 404 405 406 mov %r12, %r11 407 408 vpxor reg_j, reg_j, reg_j 409 vpxor reg_i, reg_i, reg_i 410 cmp $16, %r11 411 jl _get_AAD_rest8\@ 412_get_AAD_blocks\@: 413 vmovdqu (%r10), reg_i 414 vpshufb SHUF_MASK(%rip), reg_i, reg_i 415 vpxor reg_i, reg_j, reg_j 416 GHASH_MUL_AVX reg_j, \T2, \T1, \T3, \T4, \T5, \T6 417 add $16, %r10 418 sub $16, %r12 419 sub $16, %r11 420 cmp $16, %r11 421 jge _get_AAD_blocks\@ 422 vmovdqu reg_j, reg_i 423 cmp $0, %r11 424 je _get_AAD_done\@ 425 426 vpxor reg_i, reg_i, reg_i 427 428 /* read the last <16B of AAD. since we have at least 4B of 429 data right after the AAD (the ICV, and maybe some CT), we can 430 read 4B/8B blocks safely, and then get rid of the extra stuff */ 431_get_AAD_rest8\@: 432 cmp $4, %r11 433 jle _get_AAD_rest4\@ 434 movq (%r10), \T1 435 add $8, %r10 436 sub $8, %r11 437 vpslldq $8, \T1, \T1 438 vpsrldq $8, reg_i, reg_i 439 vpxor \T1, reg_i, reg_i 440 jmp _get_AAD_rest8\@ 441_get_AAD_rest4\@: 442 cmp $0, %r11 443 jle _get_AAD_rest0\@ 444 mov (%r10), %eax 445 movq %rax, \T1 446 add $4, %r10 447 sub $4, %r11 448 vpslldq $12, \T1, \T1 449 vpsrldq $4, reg_i, reg_i 450 vpxor \T1, reg_i, reg_i 451_get_AAD_rest0\@: 452 /* finalize: shift out the extra bytes we read, and align 453 left. since pslldq can only shift by an immediate, we use 454 vpshufb and an array of shuffle masks */ 455 movq %r12, %r11 456 salq $4, %r11 457 movdqu aad_shift_arr(%r11), \T1 458 vpshufb \T1, reg_i, reg_i 459_get_AAD_rest_final\@: 460 vpshufb SHUF_MASK(%rip), reg_i, reg_i 461 vpxor reg_j, reg_i, reg_i 462 GHASH_MUL_AVX reg_i, \T2, \T1, \T3, \T4, \T5, \T6 463 464_get_AAD_done\@: 465 # initialize the data pointer offset as zero 466 xor %r11, %r11 467 468 # start AES for num_initial_blocks blocks 469 mov arg5, %rax # rax = *Y0 470 vmovdqu (%rax), \CTR # CTR = Y0 471 vpshufb SHUF_MASK(%rip), \CTR, \CTR 472 473 474 i = (9-\num_initial_blocks) 475 setreg 476.rep \num_initial_blocks 477 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 478 vmovdqa \CTR, reg_i 479 vpshufb SHUF_MASK(%rip), reg_i, reg_i # perform a 16Byte swap 480 i = (i+1) 481 setreg 482.endr 483 484 vmovdqa (arg1), \T_key 485 i = (9-\num_initial_blocks) 486 setreg 487.rep \num_initial_blocks 488 vpxor \T_key, reg_i, reg_i 489 i = (i+1) 490 setreg 491.endr 492 493 j = 1 494 setreg 495.rep 9 496 vmovdqa 16*j(arg1), \T_key 497 i = (9-\num_initial_blocks) 498 setreg 499.rep \num_initial_blocks 500 vaesenc \T_key, reg_i, reg_i 501 i = (i+1) 502 setreg 503.endr 504 505 j = (j+1) 506 setreg 507.endr 508 509 510 vmovdqa 16*10(arg1), \T_key 511 i = (9-\num_initial_blocks) 512 setreg 513.rep \num_initial_blocks 514 vaesenclast \T_key, reg_i, reg_i 515 i = (i+1) 516 setreg 517.endr 518 519 i = (9-\num_initial_blocks) 520 setreg 521.rep \num_initial_blocks 522 vmovdqu (arg3, %r11), \T1 523 vpxor \T1, reg_i, reg_i 524 vmovdqu reg_i, (arg2 , %r11) # write back ciphertext for num_initial_blocks blocks 525 add $16, %r11 526.if \ENC_DEC == DEC 527 vmovdqa \T1, reg_i 528.endif 529 vpshufb SHUF_MASK(%rip), reg_i, reg_i # prepare ciphertext for GHASH computations 530 i = (i+1) 531 setreg 532.endr 533 534 535 i = (8-\num_initial_blocks) 536 j = (9-\num_initial_blocks) 537 setreg 538 539.rep \num_initial_blocks 540 vpxor reg_i, reg_j, reg_j 541 GHASH_MUL_AVX reg_j, \T2, \T1, \T3, \T4, \T5, \T6 # apply GHASH on num_initial_blocks blocks 542 i = (i+1) 543 j = (j+1) 544 setreg 545.endr 546 # XMM8 has the combined result here 547 548 vmovdqa \XMM8, TMP1(%rsp) 549 vmovdqa \XMM8, \T3 550 551 cmp $128, %r13 552 jl _initial_blocks_done\@ # no need for precomputed constants 553 554############################################################################### 555# Haskey_i_k holds XORed values of the low and high parts of the Haskey_i 556 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 557 vmovdqa \CTR, \XMM1 558 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 559 560 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 561 vmovdqa \CTR, \XMM2 562 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 563 564 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 565 vmovdqa \CTR, \XMM3 566 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 567 568 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 569 vmovdqa \CTR, \XMM4 570 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 571 572 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 573 vmovdqa \CTR, \XMM5 574 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 575 576 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 577 vmovdqa \CTR, \XMM6 578 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 579 580 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 581 vmovdqa \CTR, \XMM7 582 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 583 584 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 585 vmovdqa \CTR, \XMM8 586 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 587 588 vmovdqa (arg1), \T_key 589 vpxor \T_key, \XMM1, \XMM1 590 vpxor \T_key, \XMM2, \XMM2 591 vpxor \T_key, \XMM3, \XMM3 592 vpxor \T_key, \XMM4, \XMM4 593 vpxor \T_key, \XMM5, \XMM5 594 vpxor \T_key, \XMM6, \XMM6 595 vpxor \T_key, \XMM7, \XMM7 596 vpxor \T_key, \XMM8, \XMM8 597 598 i = 1 599 setreg 600.rep 9 # do 9 rounds 601 vmovdqa 16*i(arg1), \T_key 602 vaesenc \T_key, \XMM1, \XMM1 603 vaesenc \T_key, \XMM2, \XMM2 604 vaesenc \T_key, \XMM3, \XMM3 605 vaesenc \T_key, \XMM4, \XMM4 606 vaesenc \T_key, \XMM5, \XMM5 607 vaesenc \T_key, \XMM6, \XMM6 608 vaesenc \T_key, \XMM7, \XMM7 609 vaesenc \T_key, \XMM8, \XMM8 610 i = (i+1) 611 setreg 612.endr 613 614 615 vmovdqa 16*i(arg1), \T_key 616 vaesenclast \T_key, \XMM1, \XMM1 617 vaesenclast \T_key, \XMM2, \XMM2 618 vaesenclast \T_key, \XMM3, \XMM3 619 vaesenclast \T_key, \XMM4, \XMM4 620 vaesenclast \T_key, \XMM5, \XMM5 621 vaesenclast \T_key, \XMM6, \XMM6 622 vaesenclast \T_key, \XMM7, \XMM7 623 vaesenclast \T_key, \XMM8, \XMM8 624 625 vmovdqu (arg3, %r11), \T1 626 vpxor \T1, \XMM1, \XMM1 627 vmovdqu \XMM1, (arg2 , %r11) 628 .if \ENC_DEC == DEC 629 vmovdqa \T1, \XMM1 630 .endif 631 632 vmovdqu 16*1(arg3, %r11), \T1 633 vpxor \T1, \XMM2, \XMM2 634 vmovdqu \XMM2, 16*1(arg2 , %r11) 635 .if \ENC_DEC == DEC 636 vmovdqa \T1, \XMM2 637 .endif 638 639 vmovdqu 16*2(arg3, %r11), \T1 640 vpxor \T1, \XMM3, \XMM3 641 vmovdqu \XMM3, 16*2(arg2 , %r11) 642 .if \ENC_DEC == DEC 643 vmovdqa \T1, \XMM3 644 .endif 645 646 vmovdqu 16*3(arg3, %r11), \T1 647 vpxor \T1, \XMM4, \XMM4 648 vmovdqu \XMM4, 16*3(arg2 , %r11) 649 .if \ENC_DEC == DEC 650 vmovdqa \T1, \XMM4 651 .endif 652 653 vmovdqu 16*4(arg3, %r11), \T1 654 vpxor \T1, \XMM5, \XMM5 655 vmovdqu \XMM5, 16*4(arg2 , %r11) 656 .if \ENC_DEC == DEC 657 vmovdqa \T1, \XMM5 658 .endif 659 660 vmovdqu 16*5(arg3, %r11), \T1 661 vpxor \T1, \XMM6, \XMM6 662 vmovdqu \XMM6, 16*5(arg2 , %r11) 663 .if \ENC_DEC == DEC 664 vmovdqa \T1, \XMM6 665 .endif 666 667 vmovdqu 16*6(arg3, %r11), \T1 668 vpxor \T1, \XMM7, \XMM7 669 vmovdqu \XMM7, 16*6(arg2 , %r11) 670 .if \ENC_DEC == DEC 671 vmovdqa \T1, \XMM7 672 .endif 673 674 vmovdqu 16*7(arg3, %r11), \T1 675 vpxor \T1, \XMM8, \XMM8 676 vmovdqu \XMM8, 16*7(arg2 , %r11) 677 .if \ENC_DEC == DEC 678 vmovdqa \T1, \XMM8 679 .endif 680 681 add $128, %r11 682 683 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 684 vpxor TMP1(%rsp), \XMM1, \XMM1 # combine GHASHed value with the corresponding ciphertext 685 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 686 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 687 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 688 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 689 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 690 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 691 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 692 693############################################################################### 694 695_initial_blocks_done\@: 696 697.endm 698 699# encrypt 8 blocks at a time 700# ghash the 8 previously encrypted ciphertext blocks 701# arg1, arg2, arg3 are used as pointers only, not modified 702# r11 is the data offset value 703.macro GHASH_8_ENCRYPT_8_PARALLEL_AVX T1 T2 T3 T4 T5 T6 CTR XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 T7 loop_idx ENC_DEC 704 705 vmovdqa \XMM1, \T2 706 vmovdqa \XMM2, TMP2(%rsp) 707 vmovdqa \XMM3, TMP3(%rsp) 708 vmovdqa \XMM4, TMP4(%rsp) 709 vmovdqa \XMM5, TMP5(%rsp) 710 vmovdqa \XMM6, TMP6(%rsp) 711 vmovdqa \XMM7, TMP7(%rsp) 712 vmovdqa \XMM8, TMP8(%rsp) 713 714.if \loop_idx == in_order 715 vpaddd ONE(%rip), \CTR, \XMM1 # INCR CNT 716 vpaddd ONE(%rip), \XMM1, \XMM2 717 vpaddd ONE(%rip), \XMM2, \XMM3 718 vpaddd ONE(%rip), \XMM3, \XMM4 719 vpaddd ONE(%rip), \XMM4, \XMM5 720 vpaddd ONE(%rip), \XMM5, \XMM6 721 vpaddd ONE(%rip), \XMM6, \XMM7 722 vpaddd ONE(%rip), \XMM7, \XMM8 723 vmovdqa \XMM8, \CTR 724 725 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 726 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 727 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 728 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 729 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 730 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 731 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 732 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 733.else 734 vpaddd ONEf(%rip), \CTR, \XMM1 # INCR CNT 735 vpaddd ONEf(%rip), \XMM1, \XMM2 736 vpaddd ONEf(%rip), \XMM2, \XMM3 737 vpaddd ONEf(%rip), \XMM3, \XMM4 738 vpaddd ONEf(%rip), \XMM4, \XMM5 739 vpaddd ONEf(%rip), \XMM5, \XMM6 740 vpaddd ONEf(%rip), \XMM6, \XMM7 741 vpaddd ONEf(%rip), \XMM7, \XMM8 742 vmovdqa \XMM8, \CTR 743.endif 744 745 746 ####################################################################### 747 748 vmovdqu (arg1), \T1 749 vpxor \T1, \XMM1, \XMM1 750 vpxor \T1, \XMM2, \XMM2 751 vpxor \T1, \XMM3, \XMM3 752 vpxor \T1, \XMM4, \XMM4 753 vpxor \T1, \XMM5, \XMM5 754 vpxor \T1, \XMM6, \XMM6 755 vpxor \T1, \XMM7, \XMM7 756 vpxor \T1, \XMM8, \XMM8 757 758 ####################################################################### 759 760 761 762 763 764 vmovdqu 16*1(arg1), \T1 765 vaesenc \T1, \XMM1, \XMM1 766 vaesenc \T1, \XMM2, \XMM2 767 vaesenc \T1, \XMM3, \XMM3 768 vaesenc \T1, \XMM4, \XMM4 769 vaesenc \T1, \XMM5, \XMM5 770 vaesenc \T1, \XMM6, \XMM6 771 vaesenc \T1, \XMM7, \XMM7 772 vaesenc \T1, \XMM8, \XMM8 773 774 vmovdqu 16*2(arg1), \T1 775 vaesenc \T1, \XMM1, \XMM1 776 vaesenc \T1, \XMM2, \XMM2 777 vaesenc \T1, \XMM3, \XMM3 778 vaesenc \T1, \XMM4, \XMM4 779 vaesenc \T1, \XMM5, \XMM5 780 vaesenc \T1, \XMM6, \XMM6 781 vaesenc \T1, \XMM7, \XMM7 782 vaesenc \T1, \XMM8, \XMM8 783 784 785 ####################################################################### 786 787 vmovdqa HashKey_8(arg1), \T5 788 vpclmulqdq $0x11, \T5, \T2, \T4 # T4 = a1*b1 789 vpclmulqdq $0x00, \T5, \T2, \T7 # T7 = a0*b0 790 791 vpshufd $0b01001110, \T2, \T6 792 vpxor \T2, \T6, \T6 793 794 vmovdqa HashKey_8_k(arg1), \T5 795 vpclmulqdq $0x00, \T5, \T6, \T6 796 797 vmovdqu 16*3(arg1), \T1 798 vaesenc \T1, \XMM1, \XMM1 799 vaesenc \T1, \XMM2, \XMM2 800 vaesenc \T1, \XMM3, \XMM3 801 vaesenc \T1, \XMM4, \XMM4 802 vaesenc \T1, \XMM5, \XMM5 803 vaesenc \T1, \XMM6, \XMM6 804 vaesenc \T1, \XMM7, \XMM7 805 vaesenc \T1, \XMM8, \XMM8 806 807 vmovdqa TMP2(%rsp), \T1 808 vmovdqa HashKey_7(arg1), \T5 809 vpclmulqdq $0x11, \T5, \T1, \T3 810 vpxor \T3, \T4, \T4 811 vpclmulqdq $0x00, \T5, \T1, \T3 812 vpxor \T3, \T7, \T7 813 814 vpshufd $0b01001110, \T1, \T3 815 vpxor \T1, \T3, \T3 816 vmovdqa HashKey_7_k(arg1), \T5 817 vpclmulqdq $0x10, \T5, \T3, \T3 818 vpxor \T3, \T6, \T6 819 820 vmovdqu 16*4(arg1), \T1 821 vaesenc \T1, \XMM1, \XMM1 822 vaesenc \T1, \XMM2, \XMM2 823 vaesenc \T1, \XMM3, \XMM3 824 vaesenc \T1, \XMM4, \XMM4 825 vaesenc \T1, \XMM5, \XMM5 826 vaesenc \T1, \XMM6, \XMM6 827 vaesenc \T1, \XMM7, \XMM7 828 vaesenc \T1, \XMM8, \XMM8 829 830 ####################################################################### 831 832 vmovdqa TMP3(%rsp), \T1 833 vmovdqa HashKey_6(arg1), \T5 834 vpclmulqdq $0x11, \T5, \T1, \T3 835 vpxor \T3, \T4, \T4 836 vpclmulqdq $0x00, \T5, \T1, \T3 837 vpxor \T3, \T7, \T7 838 839 vpshufd $0b01001110, \T1, \T3 840 vpxor \T1, \T3, \T3 841 vmovdqa HashKey_6_k(arg1), \T5 842 vpclmulqdq $0x10, \T5, \T3, \T3 843 vpxor \T3, \T6, \T6 844 845 vmovdqu 16*5(arg1), \T1 846 vaesenc \T1, \XMM1, \XMM1 847 vaesenc \T1, \XMM2, \XMM2 848 vaesenc \T1, \XMM3, \XMM3 849 vaesenc \T1, \XMM4, \XMM4 850 vaesenc \T1, \XMM5, \XMM5 851 vaesenc \T1, \XMM6, \XMM6 852 vaesenc \T1, \XMM7, \XMM7 853 vaesenc \T1, \XMM8, \XMM8 854 855 vmovdqa TMP4(%rsp), \T1 856 vmovdqa HashKey_5(arg1), \T5 857 vpclmulqdq $0x11, \T5, \T1, \T3 858 vpxor \T3, \T4, \T4 859 vpclmulqdq $0x00, \T5, \T1, \T3 860 vpxor \T3, \T7, \T7 861 862 vpshufd $0b01001110, \T1, \T3 863 vpxor \T1, \T3, \T3 864 vmovdqa HashKey_5_k(arg1), \T5 865 vpclmulqdq $0x10, \T5, \T3, \T3 866 vpxor \T3, \T6, \T6 867 868 vmovdqu 16*6(arg1), \T1 869 vaesenc \T1, \XMM1, \XMM1 870 vaesenc \T1, \XMM2, \XMM2 871 vaesenc \T1, \XMM3, \XMM3 872 vaesenc \T1, \XMM4, \XMM4 873 vaesenc \T1, \XMM5, \XMM5 874 vaesenc \T1, \XMM6, \XMM6 875 vaesenc \T1, \XMM7, \XMM7 876 vaesenc \T1, \XMM8, \XMM8 877 878 879 vmovdqa TMP5(%rsp), \T1 880 vmovdqa HashKey_4(arg1), \T5 881 vpclmulqdq $0x11, \T5, \T1, \T3 882 vpxor \T3, \T4, \T4 883 vpclmulqdq $0x00, \T5, \T1, \T3 884 vpxor \T3, \T7, \T7 885 886 vpshufd $0b01001110, \T1, \T3 887 vpxor \T1, \T3, \T3 888 vmovdqa HashKey_4_k(arg1), \T5 889 vpclmulqdq $0x10, \T5, \T3, \T3 890 vpxor \T3, \T6, \T6 891 892 vmovdqu 16*7(arg1), \T1 893 vaesenc \T1, \XMM1, \XMM1 894 vaesenc \T1, \XMM2, \XMM2 895 vaesenc \T1, \XMM3, \XMM3 896 vaesenc \T1, \XMM4, \XMM4 897 vaesenc \T1, \XMM5, \XMM5 898 vaesenc \T1, \XMM6, \XMM6 899 vaesenc \T1, \XMM7, \XMM7 900 vaesenc \T1, \XMM8, \XMM8 901 902 vmovdqa TMP6(%rsp), \T1 903 vmovdqa HashKey_3(arg1), \T5 904 vpclmulqdq $0x11, \T5, \T1, \T3 905 vpxor \T3, \T4, \T4 906 vpclmulqdq $0x00, \T5, \T1, \T3 907 vpxor \T3, \T7, \T7 908 909 vpshufd $0b01001110, \T1, \T3 910 vpxor \T1, \T3, \T3 911 vmovdqa HashKey_3_k(arg1), \T5 912 vpclmulqdq $0x10, \T5, \T3, \T3 913 vpxor \T3, \T6, \T6 914 915 916 vmovdqu 16*8(arg1), \T1 917 vaesenc \T1, \XMM1, \XMM1 918 vaesenc \T1, \XMM2, \XMM2 919 vaesenc \T1, \XMM3, \XMM3 920 vaesenc \T1, \XMM4, \XMM4 921 vaesenc \T1, \XMM5, \XMM5 922 vaesenc \T1, \XMM6, \XMM6 923 vaesenc \T1, \XMM7, \XMM7 924 vaesenc \T1, \XMM8, \XMM8 925 926 vmovdqa TMP7(%rsp), \T1 927 vmovdqa HashKey_2(arg1), \T5 928 vpclmulqdq $0x11, \T5, \T1, \T3 929 vpxor \T3, \T4, \T4 930 vpclmulqdq $0x00, \T5, \T1, \T3 931 vpxor \T3, \T7, \T7 932 933 vpshufd $0b01001110, \T1, \T3 934 vpxor \T1, \T3, \T3 935 vmovdqa HashKey_2_k(arg1), \T5 936 vpclmulqdq $0x10, \T5, \T3, \T3 937 vpxor \T3, \T6, \T6 938 939 ####################################################################### 940 941 vmovdqu 16*9(arg1), \T5 942 vaesenc \T5, \XMM1, \XMM1 943 vaesenc \T5, \XMM2, \XMM2 944 vaesenc \T5, \XMM3, \XMM3 945 vaesenc \T5, \XMM4, \XMM4 946 vaesenc \T5, \XMM5, \XMM5 947 vaesenc \T5, \XMM6, \XMM6 948 vaesenc \T5, \XMM7, \XMM7 949 vaesenc \T5, \XMM8, \XMM8 950 951 vmovdqa TMP8(%rsp), \T1 952 vmovdqa HashKey(arg1), \T5 953 vpclmulqdq $0x11, \T5, \T1, \T3 954 vpxor \T3, \T4, \T4 955 vpclmulqdq $0x00, \T5, \T1, \T3 956 vpxor \T3, \T7, \T7 957 958 vpshufd $0b01001110, \T1, \T3 959 vpxor \T1, \T3, \T3 960 vmovdqa HashKey_k(arg1), \T5 961 vpclmulqdq $0x10, \T5, \T3, \T3 962 vpxor \T3, \T6, \T6 963 964 vpxor \T4, \T6, \T6 965 vpxor \T7, \T6, \T6 966 967 vmovdqu 16*10(arg1), \T5 968 969 i = 0 970 j = 1 971 setreg 972.rep 8 973 vpxor 16*i(arg3, %r11), \T5, \T2 974 .if \ENC_DEC == ENC 975 vaesenclast \T2, reg_j, reg_j 976 .else 977 vaesenclast \T2, reg_j, \T3 978 vmovdqu 16*i(arg3, %r11), reg_j 979 vmovdqu \T3, 16*i(arg2, %r11) 980 .endif 981 i = (i+1) 982 j = (j+1) 983 setreg 984.endr 985 ####################################################################### 986 987 988 vpslldq $8, \T6, \T3 # shift-L T3 2 DWs 989 vpsrldq $8, \T6, \T6 # shift-R T2 2 DWs 990 vpxor \T3, \T7, \T7 991 vpxor \T4, \T6, \T6 # accumulate the results in T6:T7 992 993 994 995 ####################################################################### 996 #first phase of the reduction 997 ####################################################################### 998 vpslld $31, \T7, \T2 # packed right shifting << 31 999 vpslld $30, \T7, \T3 # packed right shifting shift << 30 1000 vpslld $25, \T7, \T4 # packed right shifting shift << 25 1001 1002 vpxor \T3, \T2, \T2 # xor the shifted versions 1003 vpxor \T4, \T2, \T2 1004 1005 vpsrldq $4, \T2, \T1 # shift-R T1 1 DW 1006 1007 vpslldq $12, \T2, \T2 # shift-L T2 3 DWs 1008 vpxor \T2, \T7, \T7 # first phase of the reduction complete 1009 ####################################################################### 1010 .if \ENC_DEC == ENC 1011 vmovdqu \XMM1, 16*0(arg2,%r11) # Write to the Ciphertext buffer 1012 vmovdqu \XMM2, 16*1(arg2,%r11) # Write to the Ciphertext buffer 1013 vmovdqu \XMM3, 16*2(arg2,%r11) # Write to the Ciphertext buffer 1014 vmovdqu \XMM4, 16*3(arg2,%r11) # Write to the Ciphertext buffer 1015 vmovdqu \XMM5, 16*4(arg2,%r11) # Write to the Ciphertext buffer 1016 vmovdqu \XMM6, 16*5(arg2,%r11) # Write to the Ciphertext buffer 1017 vmovdqu \XMM7, 16*6(arg2,%r11) # Write to the Ciphertext buffer 1018 vmovdqu \XMM8, 16*7(arg2,%r11) # Write to the Ciphertext buffer 1019 .endif 1020 1021 ####################################################################### 1022 #second phase of the reduction 1023 vpsrld $1, \T7, \T2 # packed left shifting >> 1 1024 vpsrld $2, \T7, \T3 # packed left shifting >> 2 1025 vpsrld $7, \T7, \T4 # packed left shifting >> 7 1026 vpxor \T3, \T2, \T2 # xor the shifted versions 1027 vpxor \T4, \T2, \T2 1028 1029 vpxor \T1, \T2, \T2 1030 vpxor \T2, \T7, \T7 1031 vpxor \T7, \T6, \T6 # the result is in T6 1032 ####################################################################### 1033 1034 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 1035 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 1036 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 1037 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 1038 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 1039 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 1040 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 1041 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 1042 1043 1044 vpxor \T6, \XMM1, \XMM1 1045 1046 1047 1048.endm 1049 1050 1051# GHASH the last 4 ciphertext blocks. 1052.macro GHASH_LAST_8_AVX T1 T2 T3 T4 T5 T6 T7 XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 1053 1054 ## Karatsuba Method 1055 1056 1057 vpshufd $0b01001110, \XMM1, \T2 1058 vpxor \XMM1, \T2, \T2 1059 vmovdqa HashKey_8(arg1), \T5 1060 vpclmulqdq $0x11, \T5, \XMM1, \T6 1061 vpclmulqdq $0x00, \T5, \XMM1, \T7 1062 1063 vmovdqa HashKey_8_k(arg1), \T3 1064 vpclmulqdq $0x00, \T3, \T2, \XMM1 1065 1066 ###################### 1067 1068 vpshufd $0b01001110, \XMM2, \T2 1069 vpxor \XMM2, \T2, \T2 1070 vmovdqa HashKey_7(arg1), \T5 1071 vpclmulqdq $0x11, \T5, \XMM2, \T4 1072 vpxor \T4, \T6, \T6 1073 1074 vpclmulqdq $0x00, \T5, \XMM2, \T4 1075 vpxor \T4, \T7, \T7 1076 1077 vmovdqa HashKey_7_k(arg1), \T3 1078 vpclmulqdq $0x00, \T3, \T2, \T2 1079 vpxor \T2, \XMM1, \XMM1 1080 1081 ###################### 1082 1083 vpshufd $0b01001110, \XMM3, \T2 1084 vpxor \XMM3, \T2, \T2 1085 vmovdqa HashKey_6(arg1), \T5 1086 vpclmulqdq $0x11, \T5, \XMM3, \T4 1087 vpxor \T4, \T6, \T6 1088 1089 vpclmulqdq $0x00, \T5, \XMM3, \T4 1090 vpxor \T4, \T7, \T7 1091 1092 vmovdqa HashKey_6_k(arg1), \T3 1093 vpclmulqdq $0x00, \T3, \T2, \T2 1094 vpxor \T2, \XMM1, \XMM1 1095 1096 ###################### 1097 1098 vpshufd $0b01001110, \XMM4, \T2 1099 vpxor \XMM4, \T2, \T2 1100 vmovdqa HashKey_5(arg1), \T5 1101 vpclmulqdq $0x11, \T5, \XMM4, \T4 1102 vpxor \T4, \T6, \T6 1103 1104 vpclmulqdq $0x00, \T5, \XMM4, \T4 1105 vpxor \T4, \T7, \T7 1106 1107 vmovdqa HashKey_5_k(arg1), \T3 1108 vpclmulqdq $0x00, \T3, \T2, \T2 1109 vpxor \T2, \XMM1, \XMM1 1110 1111 ###################### 1112 1113 vpshufd $0b01001110, \XMM5, \T2 1114 vpxor \XMM5, \T2, \T2 1115 vmovdqa HashKey_4(arg1), \T5 1116 vpclmulqdq $0x11, \T5, \XMM5, \T4 1117 vpxor \T4, \T6, \T6 1118 1119 vpclmulqdq $0x00, \T5, \XMM5, \T4 1120 vpxor \T4, \T7, \T7 1121 1122 vmovdqa HashKey_4_k(arg1), \T3 1123 vpclmulqdq $0x00, \T3, \T2, \T2 1124 vpxor \T2, \XMM1, \XMM1 1125 1126 ###################### 1127 1128 vpshufd $0b01001110, \XMM6, \T2 1129 vpxor \XMM6, \T2, \T2 1130 vmovdqa HashKey_3(arg1), \T5 1131 vpclmulqdq $0x11, \T5, \XMM6, \T4 1132 vpxor \T4, \T6, \T6 1133 1134 vpclmulqdq $0x00, \T5, \XMM6, \T4 1135 vpxor \T4, \T7, \T7 1136 1137 vmovdqa HashKey_3_k(arg1), \T3 1138 vpclmulqdq $0x00, \T3, \T2, \T2 1139 vpxor \T2, \XMM1, \XMM1 1140 1141 ###################### 1142 1143 vpshufd $0b01001110, \XMM7, \T2 1144 vpxor \XMM7, \T2, \T2 1145 vmovdqa HashKey_2(arg1), \T5 1146 vpclmulqdq $0x11, \T5, \XMM7, \T4 1147 vpxor \T4, \T6, \T6 1148 1149 vpclmulqdq $0x00, \T5, \XMM7, \T4 1150 vpxor \T4, \T7, \T7 1151 1152 vmovdqa HashKey_2_k(arg1), \T3 1153 vpclmulqdq $0x00, \T3, \T2, \T2 1154 vpxor \T2, \XMM1, \XMM1 1155 1156 ###################### 1157 1158 vpshufd $0b01001110, \XMM8, \T2 1159 vpxor \XMM8, \T2, \T2 1160 vmovdqa HashKey(arg1), \T5 1161 vpclmulqdq $0x11, \T5, \XMM8, \T4 1162 vpxor \T4, \T6, \T6 1163 1164 vpclmulqdq $0x00, \T5, \XMM8, \T4 1165 vpxor \T4, \T7, \T7 1166 1167 vmovdqa HashKey_k(arg1), \T3 1168 vpclmulqdq $0x00, \T3, \T2, \T2 1169 1170 vpxor \T2, \XMM1, \XMM1 1171 vpxor \T6, \XMM1, \XMM1 1172 vpxor \T7, \XMM1, \T2 1173 1174 1175 1176 1177 vpslldq $8, \T2, \T4 1178 vpsrldq $8, \T2, \T2 1179 1180 vpxor \T4, \T7, \T7 1181 vpxor \T2, \T6, \T6 # <T6:T7> holds the result of 1182 # the accumulated carry-less multiplications 1183 1184 ####################################################################### 1185 #first phase of the reduction 1186 vpslld $31, \T7, \T2 # packed right shifting << 31 1187 vpslld $30, \T7, \T3 # packed right shifting shift << 30 1188 vpslld $25, \T7, \T4 # packed right shifting shift << 25 1189 1190 vpxor \T3, \T2, \T2 # xor the shifted versions 1191 vpxor \T4, \T2, \T2 1192 1193 vpsrldq $4, \T2, \T1 # shift-R T1 1 DW 1194 1195 vpslldq $12, \T2, \T2 # shift-L T2 3 DWs 1196 vpxor \T2, \T7, \T7 # first phase of the reduction complete 1197 ####################################################################### 1198 1199 1200 #second phase of the reduction 1201 vpsrld $1, \T7, \T2 # packed left shifting >> 1 1202 vpsrld $2, \T7, \T3 # packed left shifting >> 2 1203 vpsrld $7, \T7, \T4 # packed left shifting >> 7 1204 vpxor \T3, \T2, \T2 # xor the shifted versions 1205 vpxor \T4, \T2, \T2 1206 1207 vpxor \T1, \T2, \T2 1208 vpxor \T2, \T7, \T7 1209 vpxor \T7, \T6, \T6 # the result is in T6 1210 1211.endm 1212 1213 1214# combined for GCM encrypt and decrypt functions 1215# clobbering all xmm registers 1216# clobbering r10, r11, r12, r13, r14, r15 1217.macro GCM_ENC_DEC_AVX ENC_DEC 1218 1219 #the number of pushes must equal STACK_OFFSET 1220 push %r12 1221 push %r13 1222 push %r14 1223 push %r15 1224 1225 mov %rsp, %r14 1226 1227 1228 1229 1230 sub $VARIABLE_OFFSET, %rsp 1231 and $~63, %rsp # align rsp to 64 bytes 1232 1233 1234 vmovdqu HashKey(arg1), %xmm13 # xmm13 = HashKey 1235 1236 mov arg4, %r13 # save the number of bytes of plaintext/ciphertext 1237 and $-16, %r13 # r13 = r13 - (r13 mod 16) 1238 1239 mov %r13, %r12 1240 shr $4, %r12 1241 and $7, %r12 1242 jz _initial_num_blocks_is_0\@ 1243 1244 cmp $7, %r12 1245 je _initial_num_blocks_is_7\@ 1246 cmp $6, %r12 1247 je _initial_num_blocks_is_6\@ 1248 cmp $5, %r12 1249 je _initial_num_blocks_is_5\@ 1250 cmp $4, %r12 1251 je _initial_num_blocks_is_4\@ 1252 cmp $3, %r12 1253 je _initial_num_blocks_is_3\@ 1254 cmp $2, %r12 1255 je _initial_num_blocks_is_2\@ 1256 1257 jmp _initial_num_blocks_is_1\@ 1258 1259_initial_num_blocks_is_7\@: 1260 INITIAL_BLOCKS_AVX 7, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1261 sub $16*7, %r13 1262 jmp _initial_blocks_encrypted\@ 1263 1264_initial_num_blocks_is_6\@: 1265 INITIAL_BLOCKS_AVX 6, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1266 sub $16*6, %r13 1267 jmp _initial_blocks_encrypted\@ 1268 1269_initial_num_blocks_is_5\@: 1270 INITIAL_BLOCKS_AVX 5, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1271 sub $16*5, %r13 1272 jmp _initial_blocks_encrypted\@ 1273 1274_initial_num_blocks_is_4\@: 1275 INITIAL_BLOCKS_AVX 4, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1276 sub $16*4, %r13 1277 jmp _initial_blocks_encrypted\@ 1278 1279_initial_num_blocks_is_3\@: 1280 INITIAL_BLOCKS_AVX 3, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1281 sub $16*3, %r13 1282 jmp _initial_blocks_encrypted\@ 1283 1284_initial_num_blocks_is_2\@: 1285 INITIAL_BLOCKS_AVX 2, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1286 sub $16*2, %r13 1287 jmp _initial_blocks_encrypted\@ 1288 1289_initial_num_blocks_is_1\@: 1290 INITIAL_BLOCKS_AVX 1, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1291 sub $16*1, %r13 1292 jmp _initial_blocks_encrypted\@ 1293 1294_initial_num_blocks_is_0\@: 1295 INITIAL_BLOCKS_AVX 0, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 1296 1297 1298_initial_blocks_encrypted\@: 1299 cmp $0, %r13 1300 je _zero_cipher_left\@ 1301 1302 sub $128, %r13 1303 je _eight_cipher_left\@ 1304 1305 1306 1307 1308 vmovd %xmm9, %r15d 1309 and $255, %r15d 1310 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1311 1312 1313_encrypt_by_8_new\@: 1314 cmp $(255-8), %r15d 1315 jg _encrypt_by_8\@ 1316 1317 1318 1319 add $8, %r15b 1320 GHASH_8_ENCRYPT_8_PARALLEL_AVX %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm15, out_order, \ENC_DEC 1321 add $128, %r11 1322 sub $128, %r13 1323 jne _encrypt_by_8_new\@ 1324 1325 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1326 jmp _eight_cipher_left\@ 1327 1328_encrypt_by_8\@: 1329 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1330 add $8, %r15b 1331 GHASH_8_ENCRYPT_8_PARALLEL_AVX %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm15, in_order, \ENC_DEC 1332 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1333 add $128, %r11 1334 sub $128, %r13 1335 jne _encrypt_by_8_new\@ 1336 1337 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1338 1339 1340 1341 1342_eight_cipher_left\@: 1343 GHASH_LAST_8_AVX %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm15, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8 1344 1345 1346_zero_cipher_left\@: 1347 cmp $16, arg4 1348 jl _only_less_than_16\@ 1349 1350 mov arg4, %r13 1351 and $15, %r13 # r13 = (arg4 mod 16) 1352 1353 je _multiple_of_16_bytes\@ 1354 1355 # handle the last <16 Byte block seperately 1356 1357 1358 vpaddd ONE(%rip), %xmm9, %xmm9 # INCR CNT to get Yn 1359 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1360 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Yn) 1361 1362 sub $16, %r11 1363 add %r13, %r11 1364 vmovdqu (arg3, %r11), %xmm1 # receive the last <16 Byte block 1365 1366 lea SHIFT_MASK+16(%rip), %r12 1367 sub %r13, %r12 # adjust the shuffle mask pointer to be 1368 # able to shift 16-r13 bytes (r13 is the 1369 # number of bytes in plaintext mod 16) 1370 vmovdqu (%r12), %xmm2 # get the appropriate shuffle mask 1371 vpshufb %xmm2, %xmm1, %xmm1 # shift right 16-r13 bytes 1372 jmp _final_ghash_mul\@ 1373 1374_only_less_than_16\@: 1375 # check for 0 length 1376 mov arg4, %r13 1377 and $15, %r13 # r13 = (arg4 mod 16) 1378 1379 je _multiple_of_16_bytes\@ 1380 1381 # handle the last <16 Byte block seperately 1382 1383 1384 vpaddd ONE(%rip), %xmm9, %xmm9 # INCR CNT to get Yn 1385 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1386 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Yn) 1387 1388 1389 lea SHIFT_MASK+16(%rip), %r12 1390 sub %r13, %r12 # adjust the shuffle mask pointer to be 1391 # able to shift 16-r13 bytes (r13 is the 1392 # number of bytes in plaintext mod 16) 1393 1394_get_last_16_byte_loop\@: 1395 movb (arg3, %r11), %al 1396 movb %al, TMP1 (%rsp , %r11) 1397 add $1, %r11 1398 cmp %r13, %r11 1399 jne _get_last_16_byte_loop\@ 1400 1401 vmovdqu TMP1(%rsp), %xmm1 1402 1403 sub $16, %r11 1404 1405_final_ghash_mul\@: 1406 .if \ENC_DEC == DEC 1407 vmovdqa %xmm1, %xmm2 1408 vpxor %xmm1, %xmm9, %xmm9 # Plaintext XOR E(K, Yn) 1409 vmovdqu ALL_F-SHIFT_MASK(%r12), %xmm1 # get the appropriate mask to 1410 # mask out top 16-r13 bytes of xmm9 1411 vpand %xmm1, %xmm9, %xmm9 # mask out top 16-r13 bytes of xmm9 1412 vpand %xmm1, %xmm2, %xmm2 1413 vpshufb SHUF_MASK(%rip), %xmm2, %xmm2 1414 vpxor %xmm2, %xmm14, %xmm14 1415 #GHASH computation for the last <16 Byte block 1416 GHASH_MUL_AVX %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 1417 sub %r13, %r11 1418 add $16, %r11 1419 .else 1420 vpxor %xmm1, %xmm9, %xmm9 # Plaintext XOR E(K, Yn) 1421 vmovdqu ALL_F-SHIFT_MASK(%r12), %xmm1 # get the appropriate mask to 1422 # mask out top 16-r13 bytes of xmm9 1423 vpand %xmm1, %xmm9, %xmm9 # mask out top 16-r13 bytes of xmm9 1424 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 1425 vpxor %xmm9, %xmm14, %xmm14 1426 #GHASH computation for the last <16 Byte block 1427 GHASH_MUL_AVX %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 1428 sub %r13, %r11 1429 add $16, %r11 1430 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 # shuffle xmm9 back to output as ciphertext 1431 .endif 1432 1433 1434 ############################# 1435 # output r13 Bytes 1436 vmovq %xmm9, %rax 1437 cmp $8, %r13 1438 jle _less_than_8_bytes_left\@ 1439 1440 mov %rax, (arg2 , %r11) 1441 add $8, %r11 1442 vpsrldq $8, %xmm9, %xmm9 1443 vmovq %xmm9, %rax 1444 sub $8, %r13 1445 1446_less_than_8_bytes_left\@: 1447 movb %al, (arg2 , %r11) 1448 add $1, %r11 1449 shr $8, %rax 1450 sub $1, %r13 1451 jne _less_than_8_bytes_left\@ 1452 ############################# 1453 1454_multiple_of_16_bytes\@: 1455 mov arg7, %r12 # r12 = aadLen (number of bytes) 1456 shl $3, %r12 # convert into number of bits 1457 vmovd %r12d, %xmm15 # len(A) in xmm15 1458 1459 shl $3, arg4 # len(C) in bits (*128) 1460 vmovq arg4, %xmm1 1461 vpslldq $8, %xmm15, %xmm15 # xmm15 = len(A)|| 0x0000000000000000 1462 vpxor %xmm1, %xmm15, %xmm15 # xmm15 = len(A)||len(C) 1463 1464 vpxor %xmm15, %xmm14, %xmm14 1465 GHASH_MUL_AVX %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 # final GHASH computation 1466 vpshufb SHUF_MASK(%rip), %xmm14, %xmm14 # perform a 16Byte swap 1467 1468 mov arg5, %rax # rax = *Y0 1469 vmovdqu (%rax), %xmm9 # xmm9 = Y0 1470 1471 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Y0) 1472 1473 vpxor %xmm14, %xmm9, %xmm9 1474 1475 1476 1477_return_T\@: 1478 mov arg8, %r10 # r10 = authTag 1479 mov arg9, %r11 # r11 = auth_tag_len 1480 1481 cmp $16, %r11 1482 je _T_16\@ 1483 1484 cmp $8, %r11 1485 jl _T_4\@ 1486 1487_T_8\@: 1488 vmovq %xmm9, %rax 1489 mov %rax, (%r10) 1490 add $8, %r10 1491 sub $8, %r11 1492 vpsrldq $8, %xmm9, %xmm9 1493 cmp $0, %r11 1494 je _return_T_done\@ 1495_T_4\@: 1496 vmovd %xmm9, %eax 1497 mov %eax, (%r10) 1498 add $4, %r10 1499 sub $4, %r11 1500 vpsrldq $4, %xmm9, %xmm9 1501 cmp $0, %r11 1502 je _return_T_done\@ 1503_T_123\@: 1504 vmovd %xmm9, %eax 1505 cmp $2, %r11 1506 jl _T_1\@ 1507 mov %ax, (%r10) 1508 cmp $2, %r11 1509 je _return_T_done\@ 1510 add $2, %r10 1511 sar $16, %eax 1512_T_1\@: 1513 mov %al, (%r10) 1514 jmp _return_T_done\@ 1515 1516_T_16\@: 1517 vmovdqu %xmm9, (%r10) 1518 1519_return_T_done\@: 1520 mov %r14, %rsp 1521 1522 pop %r15 1523 pop %r14 1524 pop %r13 1525 pop %r12 1526.endm 1527 1528 1529############################################################# 1530#void aesni_gcm_precomp_avx_gen2 1531# (gcm_data *my_ctx_data, 1532# u8 *hash_subkey)# /* H, the Hash sub key input. Data starts on a 16-byte boundary. */ 1533############################################################# 1534ENTRY(aesni_gcm_precomp_avx_gen2) 1535 #the number of pushes must equal STACK_OFFSET 1536 push %r12 1537 push %r13 1538 push %r14 1539 push %r15 1540 1541 mov %rsp, %r14 1542 1543 1544 1545 sub $VARIABLE_OFFSET, %rsp 1546 and $~63, %rsp # align rsp to 64 bytes 1547 1548 vmovdqu (arg2), %xmm6 # xmm6 = HashKey 1549 1550 vpshufb SHUF_MASK(%rip), %xmm6, %xmm6 1551 ############### PRECOMPUTATION of HashKey<<1 mod poly from the HashKey 1552 vmovdqa %xmm6, %xmm2 1553 vpsllq $1, %xmm6, %xmm6 1554 vpsrlq $63, %xmm2, %xmm2 1555 vmovdqa %xmm2, %xmm1 1556 vpslldq $8, %xmm2, %xmm2 1557 vpsrldq $8, %xmm1, %xmm1 1558 vpor %xmm2, %xmm6, %xmm6 1559 #reduction 1560 vpshufd $0b00100100, %xmm1, %xmm2 1561 vpcmpeqd TWOONE(%rip), %xmm2, %xmm2 1562 vpand POLY(%rip), %xmm2, %xmm2 1563 vpxor %xmm2, %xmm6, %xmm6 # xmm6 holds the HashKey<<1 mod poly 1564 ####################################################################### 1565 vmovdqa %xmm6, HashKey(arg1) # store HashKey<<1 mod poly 1566 1567 1568 PRECOMPUTE_AVX %xmm6, %xmm0, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5 1569 1570 mov %r14, %rsp 1571 1572 pop %r15 1573 pop %r14 1574 pop %r13 1575 pop %r12 1576 ret 1577ENDPROC(aesni_gcm_precomp_avx_gen2) 1578 1579############################################################################### 1580#void aesni_gcm_enc_avx_gen2( 1581# gcm_data *my_ctx_data, /* aligned to 16 Bytes */ 1582# u8 *out, /* Ciphertext output. Encrypt in-place is allowed. */ 1583# const u8 *in, /* Plaintext input */ 1584# u64 plaintext_len, /* Length of data in Bytes for encryption. */ 1585# u8 *iv, /* Pre-counter block j0: 4 byte salt 1586# (from Security Association) concatenated with 8 byte 1587# Initialisation Vector (from IPSec ESP Payload) 1588# concatenated with 0x00000001. 16-byte aligned pointer. */ 1589# const u8 *aad, /* Additional Authentication Data (AAD)*/ 1590# u64 aad_len, /* Length of AAD in bytes. With RFC4106 this is going to be 8 or 12 Bytes */ 1591# u8 *auth_tag, /* Authenticated Tag output. */ 1592# u64 auth_tag_len)# /* Authenticated Tag Length in bytes. 1593# Valid values are 16 (most likely), 12 or 8. */ 1594############################################################################### 1595ENTRY(aesni_gcm_enc_avx_gen2) 1596 GCM_ENC_DEC_AVX ENC 1597 ret 1598ENDPROC(aesni_gcm_enc_avx_gen2) 1599 1600############################################################################### 1601#void aesni_gcm_dec_avx_gen2( 1602# gcm_data *my_ctx_data, /* aligned to 16 Bytes */ 1603# u8 *out, /* Plaintext output. Decrypt in-place is allowed. */ 1604# const u8 *in, /* Ciphertext input */ 1605# u64 plaintext_len, /* Length of data in Bytes for encryption. */ 1606# u8 *iv, /* Pre-counter block j0: 4 byte salt 1607# (from Security Association) concatenated with 8 byte 1608# Initialisation Vector (from IPSec ESP Payload) 1609# concatenated with 0x00000001. 16-byte aligned pointer. */ 1610# const u8 *aad, /* Additional Authentication Data (AAD)*/ 1611# u64 aad_len, /* Length of AAD in bytes. With RFC4106 this is going to be 8 or 12 Bytes */ 1612# u8 *auth_tag, /* Authenticated Tag output. */ 1613# u64 auth_tag_len)# /* Authenticated Tag Length in bytes. 1614# Valid values are 16 (most likely), 12 or 8. */ 1615############################################################################### 1616ENTRY(aesni_gcm_dec_avx_gen2) 1617 GCM_ENC_DEC_AVX DEC 1618 ret 1619ENDPROC(aesni_gcm_dec_avx_gen2) 1620#endif /* CONFIG_AS_AVX */ 1621 1622#ifdef CONFIG_AS_AVX2 1623############################################################################### 1624# GHASH_MUL MACRO to implement: Data*HashKey mod (128,127,126,121,0) 1625# Input: A and B (128-bits each, bit-reflected) 1626# Output: C = A*B*x mod poly, (i.e. >>1 ) 1627# To compute GH = GH*HashKey mod poly, give HK = HashKey<<1 mod poly as input 1628# GH = GH * HK * x mod poly which is equivalent to GH*HashKey mod poly. 1629############################################################################### 1630.macro GHASH_MUL_AVX2 GH HK T1 T2 T3 T4 T5 1631 1632 vpclmulqdq $0x11,\HK,\GH,\T1 # T1 = a1*b1 1633 vpclmulqdq $0x00,\HK,\GH,\T2 # T2 = a0*b0 1634 vpclmulqdq $0x01,\HK,\GH,\T3 # T3 = a1*b0 1635 vpclmulqdq $0x10,\HK,\GH,\GH # GH = a0*b1 1636 vpxor \T3, \GH, \GH 1637 1638 1639 vpsrldq $8 , \GH, \T3 # shift-R GH 2 DWs 1640 vpslldq $8 , \GH, \GH # shift-L GH 2 DWs 1641 1642 vpxor \T3, \T1, \T1 1643 vpxor \T2, \GH, \GH 1644 1645 ####################################################################### 1646 #first phase of the reduction 1647 vmovdqa POLY2(%rip), \T3 1648 1649 vpclmulqdq $0x01, \GH, \T3, \T2 1650 vpslldq $8, \T2, \T2 # shift-L T2 2 DWs 1651 1652 vpxor \T2, \GH, \GH # first phase of the reduction complete 1653 ####################################################################### 1654 #second phase of the reduction 1655 vpclmulqdq $0x00, \GH, \T3, \T2 1656 vpsrldq $4, \T2, \T2 # shift-R T2 1 DW (Shift-R only 1-DW to obtain 2-DWs shift-R) 1657 1658 vpclmulqdq $0x10, \GH, \T3, \GH 1659 vpslldq $4, \GH, \GH # shift-L GH 1 DW (Shift-L 1-DW to obtain result with no shifts) 1660 1661 vpxor \T2, \GH, \GH # second phase of the reduction complete 1662 ####################################################################### 1663 vpxor \T1, \GH, \GH # the result is in GH 1664 1665 1666.endm 1667 1668.macro PRECOMPUTE_AVX2 HK T1 T2 T3 T4 T5 T6 1669 1670 # Haskey_i_k holds XORed values of the low and high parts of the Haskey_i 1671 vmovdqa \HK, \T5 1672 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^2<<1 mod poly 1673 vmovdqa \T5, HashKey_2(arg1) # [HashKey_2] = HashKey^2<<1 mod poly 1674 1675 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^3<<1 mod poly 1676 vmovdqa \T5, HashKey_3(arg1) 1677 1678 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^4<<1 mod poly 1679 vmovdqa \T5, HashKey_4(arg1) 1680 1681 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^5<<1 mod poly 1682 vmovdqa \T5, HashKey_5(arg1) 1683 1684 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^6<<1 mod poly 1685 vmovdqa \T5, HashKey_6(arg1) 1686 1687 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^7<<1 mod poly 1688 vmovdqa \T5, HashKey_7(arg1) 1689 1690 GHASH_MUL_AVX2 \T5, \HK, \T1, \T3, \T4, \T6, \T2 # T5 = HashKey^8<<1 mod poly 1691 vmovdqa \T5, HashKey_8(arg1) 1692 1693.endm 1694 1695 1696## if a = number of total plaintext bytes 1697## b = floor(a/16) 1698## num_initial_blocks = b mod 4# 1699## encrypt the initial num_initial_blocks blocks and apply ghash on the ciphertext 1700## r10, r11, r12, rax are clobbered 1701## arg1, arg2, arg3, r14 are used as a pointer only, not modified 1702 1703.macro INITIAL_BLOCKS_AVX2 num_initial_blocks T1 T2 T3 T4 T5 CTR XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 T6 T_key ENC_DEC VER 1704 i = (8-\num_initial_blocks) 1705 j = 0 1706 setreg 1707 1708 mov arg6, %r10 # r10 = AAD 1709 mov arg7, %r12 # r12 = aadLen 1710 1711 1712 mov %r12, %r11 1713 1714 vpxor reg_j, reg_j, reg_j 1715 vpxor reg_i, reg_i, reg_i 1716 1717 cmp $16, %r11 1718 jl _get_AAD_rest8\@ 1719_get_AAD_blocks\@: 1720 vmovdqu (%r10), reg_i 1721 vpshufb SHUF_MASK(%rip), reg_i, reg_i 1722 vpxor reg_i, reg_j, reg_j 1723 GHASH_MUL_AVX2 reg_j, \T2, \T1, \T3, \T4, \T5, \T6 1724 add $16, %r10 1725 sub $16, %r12 1726 sub $16, %r11 1727 cmp $16, %r11 1728 jge _get_AAD_blocks\@ 1729 vmovdqu reg_j, reg_i 1730 cmp $0, %r11 1731 je _get_AAD_done\@ 1732 1733 vpxor reg_i, reg_i, reg_i 1734 1735 /* read the last <16B of AAD. since we have at least 4B of 1736 data right after the AAD (the ICV, and maybe some CT), we can 1737 read 4B/8B blocks safely, and then get rid of the extra stuff */ 1738_get_AAD_rest8\@: 1739 cmp $4, %r11 1740 jle _get_AAD_rest4\@ 1741 movq (%r10), \T1 1742 add $8, %r10 1743 sub $8, %r11 1744 vpslldq $8, \T1, \T1 1745 vpsrldq $8, reg_i, reg_i 1746 vpxor \T1, reg_i, reg_i 1747 jmp _get_AAD_rest8\@ 1748_get_AAD_rest4\@: 1749 cmp $0, %r11 1750 jle _get_AAD_rest0\@ 1751 mov (%r10), %eax 1752 movq %rax, \T1 1753 add $4, %r10 1754 sub $4, %r11 1755 vpslldq $12, \T1, \T1 1756 vpsrldq $4, reg_i, reg_i 1757 vpxor \T1, reg_i, reg_i 1758_get_AAD_rest0\@: 1759 /* finalize: shift out the extra bytes we read, and align 1760 left. since pslldq can only shift by an immediate, we use 1761 vpshufb and an array of shuffle masks */ 1762 movq %r12, %r11 1763 salq $4, %r11 1764 movdqu aad_shift_arr(%r11), \T1 1765 vpshufb \T1, reg_i, reg_i 1766_get_AAD_rest_final\@: 1767 vpshufb SHUF_MASK(%rip), reg_i, reg_i 1768 vpxor reg_j, reg_i, reg_i 1769 GHASH_MUL_AVX2 reg_i, \T2, \T1, \T3, \T4, \T5, \T6 1770 1771_get_AAD_done\@: 1772 # initialize the data pointer offset as zero 1773 xor %r11, %r11 1774 1775 # start AES for num_initial_blocks blocks 1776 mov arg5, %rax # rax = *Y0 1777 vmovdqu (%rax), \CTR # CTR = Y0 1778 vpshufb SHUF_MASK(%rip), \CTR, \CTR 1779 1780 1781 i = (9-\num_initial_blocks) 1782 setreg 1783.rep \num_initial_blocks 1784 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1785 vmovdqa \CTR, reg_i 1786 vpshufb SHUF_MASK(%rip), reg_i, reg_i # perform a 16Byte swap 1787 i = (i+1) 1788 setreg 1789.endr 1790 1791 vmovdqa (arg1), \T_key 1792 i = (9-\num_initial_blocks) 1793 setreg 1794.rep \num_initial_blocks 1795 vpxor \T_key, reg_i, reg_i 1796 i = (i+1) 1797 setreg 1798.endr 1799 1800 j = 1 1801 setreg 1802.rep 9 1803 vmovdqa 16*j(arg1), \T_key 1804 i = (9-\num_initial_blocks) 1805 setreg 1806.rep \num_initial_blocks 1807 vaesenc \T_key, reg_i, reg_i 1808 i = (i+1) 1809 setreg 1810.endr 1811 1812 j = (j+1) 1813 setreg 1814.endr 1815 1816 1817 vmovdqa 16*10(arg1), \T_key 1818 i = (9-\num_initial_blocks) 1819 setreg 1820.rep \num_initial_blocks 1821 vaesenclast \T_key, reg_i, reg_i 1822 i = (i+1) 1823 setreg 1824.endr 1825 1826 i = (9-\num_initial_blocks) 1827 setreg 1828.rep \num_initial_blocks 1829 vmovdqu (arg3, %r11), \T1 1830 vpxor \T1, reg_i, reg_i 1831 vmovdqu reg_i, (arg2 , %r11) # write back ciphertext for 1832 # num_initial_blocks blocks 1833 add $16, %r11 1834.if \ENC_DEC == DEC 1835 vmovdqa \T1, reg_i 1836.endif 1837 vpshufb SHUF_MASK(%rip), reg_i, reg_i # prepare ciphertext for GHASH computations 1838 i = (i+1) 1839 setreg 1840.endr 1841 1842 1843 i = (8-\num_initial_blocks) 1844 j = (9-\num_initial_blocks) 1845 setreg 1846 1847.rep \num_initial_blocks 1848 vpxor reg_i, reg_j, reg_j 1849 GHASH_MUL_AVX2 reg_j, \T2, \T1, \T3, \T4, \T5, \T6 # apply GHASH on num_initial_blocks blocks 1850 i = (i+1) 1851 j = (j+1) 1852 setreg 1853.endr 1854 # XMM8 has the combined result here 1855 1856 vmovdqa \XMM8, TMP1(%rsp) 1857 vmovdqa \XMM8, \T3 1858 1859 cmp $128, %r13 1860 jl _initial_blocks_done\@ # no need for precomputed constants 1861 1862############################################################################### 1863# Haskey_i_k holds XORed values of the low and high parts of the Haskey_i 1864 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1865 vmovdqa \CTR, \XMM1 1866 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 1867 1868 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1869 vmovdqa \CTR, \XMM2 1870 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 1871 1872 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1873 vmovdqa \CTR, \XMM3 1874 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 1875 1876 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1877 vmovdqa \CTR, \XMM4 1878 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 1879 1880 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1881 vmovdqa \CTR, \XMM5 1882 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 1883 1884 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1885 vmovdqa \CTR, \XMM6 1886 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 1887 1888 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1889 vmovdqa \CTR, \XMM7 1890 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 1891 1892 vpaddd ONE(%rip), \CTR, \CTR # INCR Y0 1893 vmovdqa \CTR, \XMM8 1894 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 1895 1896 vmovdqa (arg1), \T_key 1897 vpxor \T_key, \XMM1, \XMM1 1898 vpxor \T_key, \XMM2, \XMM2 1899 vpxor \T_key, \XMM3, \XMM3 1900 vpxor \T_key, \XMM4, \XMM4 1901 vpxor \T_key, \XMM5, \XMM5 1902 vpxor \T_key, \XMM6, \XMM6 1903 vpxor \T_key, \XMM7, \XMM7 1904 vpxor \T_key, \XMM8, \XMM8 1905 1906 i = 1 1907 setreg 1908.rep 9 # do 9 rounds 1909 vmovdqa 16*i(arg1), \T_key 1910 vaesenc \T_key, \XMM1, \XMM1 1911 vaesenc \T_key, \XMM2, \XMM2 1912 vaesenc \T_key, \XMM3, \XMM3 1913 vaesenc \T_key, \XMM4, \XMM4 1914 vaesenc \T_key, \XMM5, \XMM5 1915 vaesenc \T_key, \XMM6, \XMM6 1916 vaesenc \T_key, \XMM7, \XMM7 1917 vaesenc \T_key, \XMM8, \XMM8 1918 i = (i+1) 1919 setreg 1920.endr 1921 1922 1923 vmovdqa 16*i(arg1), \T_key 1924 vaesenclast \T_key, \XMM1, \XMM1 1925 vaesenclast \T_key, \XMM2, \XMM2 1926 vaesenclast \T_key, \XMM3, \XMM3 1927 vaesenclast \T_key, \XMM4, \XMM4 1928 vaesenclast \T_key, \XMM5, \XMM5 1929 vaesenclast \T_key, \XMM6, \XMM6 1930 vaesenclast \T_key, \XMM7, \XMM7 1931 vaesenclast \T_key, \XMM8, \XMM8 1932 1933 vmovdqu (arg3, %r11), \T1 1934 vpxor \T1, \XMM1, \XMM1 1935 vmovdqu \XMM1, (arg2 , %r11) 1936 .if \ENC_DEC == DEC 1937 vmovdqa \T1, \XMM1 1938 .endif 1939 1940 vmovdqu 16*1(arg3, %r11), \T1 1941 vpxor \T1, \XMM2, \XMM2 1942 vmovdqu \XMM2, 16*1(arg2 , %r11) 1943 .if \ENC_DEC == DEC 1944 vmovdqa \T1, \XMM2 1945 .endif 1946 1947 vmovdqu 16*2(arg3, %r11), \T1 1948 vpxor \T1, \XMM3, \XMM3 1949 vmovdqu \XMM3, 16*2(arg2 , %r11) 1950 .if \ENC_DEC == DEC 1951 vmovdqa \T1, \XMM3 1952 .endif 1953 1954 vmovdqu 16*3(arg3, %r11), \T1 1955 vpxor \T1, \XMM4, \XMM4 1956 vmovdqu \XMM4, 16*3(arg2 , %r11) 1957 .if \ENC_DEC == DEC 1958 vmovdqa \T1, \XMM4 1959 .endif 1960 1961 vmovdqu 16*4(arg3, %r11), \T1 1962 vpxor \T1, \XMM5, \XMM5 1963 vmovdqu \XMM5, 16*4(arg2 , %r11) 1964 .if \ENC_DEC == DEC 1965 vmovdqa \T1, \XMM5 1966 .endif 1967 1968 vmovdqu 16*5(arg3, %r11), \T1 1969 vpxor \T1, \XMM6, \XMM6 1970 vmovdqu \XMM6, 16*5(arg2 , %r11) 1971 .if \ENC_DEC == DEC 1972 vmovdqa \T1, \XMM6 1973 .endif 1974 1975 vmovdqu 16*6(arg3, %r11), \T1 1976 vpxor \T1, \XMM7, \XMM7 1977 vmovdqu \XMM7, 16*6(arg2 , %r11) 1978 .if \ENC_DEC == DEC 1979 vmovdqa \T1, \XMM7 1980 .endif 1981 1982 vmovdqu 16*7(arg3, %r11), \T1 1983 vpxor \T1, \XMM8, \XMM8 1984 vmovdqu \XMM8, 16*7(arg2 , %r11) 1985 .if \ENC_DEC == DEC 1986 vmovdqa \T1, \XMM8 1987 .endif 1988 1989 add $128, %r11 1990 1991 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 1992 vpxor TMP1(%rsp), \XMM1, \XMM1 # combine GHASHed value with 1993 # the corresponding ciphertext 1994 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 1995 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 1996 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 1997 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 1998 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 1999 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 2000 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 2001 2002############################################################################### 2003 2004_initial_blocks_done\@: 2005 2006 2007.endm 2008 2009 2010 2011# encrypt 8 blocks at a time 2012# ghash the 8 previously encrypted ciphertext blocks 2013# arg1, arg2, arg3 are used as pointers only, not modified 2014# r11 is the data offset value 2015.macro GHASH_8_ENCRYPT_8_PARALLEL_AVX2 T1 T2 T3 T4 T5 T6 CTR XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 T7 loop_idx ENC_DEC 2016 2017 vmovdqa \XMM1, \T2 2018 vmovdqa \XMM2, TMP2(%rsp) 2019 vmovdqa \XMM3, TMP3(%rsp) 2020 vmovdqa \XMM4, TMP4(%rsp) 2021 vmovdqa \XMM5, TMP5(%rsp) 2022 vmovdqa \XMM6, TMP6(%rsp) 2023 vmovdqa \XMM7, TMP7(%rsp) 2024 vmovdqa \XMM8, TMP8(%rsp) 2025 2026.if \loop_idx == in_order 2027 vpaddd ONE(%rip), \CTR, \XMM1 # INCR CNT 2028 vpaddd ONE(%rip), \XMM1, \XMM2 2029 vpaddd ONE(%rip), \XMM2, \XMM3 2030 vpaddd ONE(%rip), \XMM3, \XMM4 2031 vpaddd ONE(%rip), \XMM4, \XMM5 2032 vpaddd ONE(%rip), \XMM5, \XMM6 2033 vpaddd ONE(%rip), \XMM6, \XMM7 2034 vpaddd ONE(%rip), \XMM7, \XMM8 2035 vmovdqa \XMM8, \CTR 2036 2037 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 2038 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 2039 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 2040 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 2041 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 2042 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 2043 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 2044 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 2045.else 2046 vpaddd ONEf(%rip), \CTR, \XMM1 # INCR CNT 2047 vpaddd ONEf(%rip), \XMM1, \XMM2 2048 vpaddd ONEf(%rip), \XMM2, \XMM3 2049 vpaddd ONEf(%rip), \XMM3, \XMM4 2050 vpaddd ONEf(%rip), \XMM4, \XMM5 2051 vpaddd ONEf(%rip), \XMM5, \XMM6 2052 vpaddd ONEf(%rip), \XMM6, \XMM7 2053 vpaddd ONEf(%rip), \XMM7, \XMM8 2054 vmovdqa \XMM8, \CTR 2055.endif 2056 2057 2058 ####################################################################### 2059 2060 vmovdqu (arg1), \T1 2061 vpxor \T1, \XMM1, \XMM1 2062 vpxor \T1, \XMM2, \XMM2 2063 vpxor \T1, \XMM3, \XMM3 2064 vpxor \T1, \XMM4, \XMM4 2065 vpxor \T1, \XMM5, \XMM5 2066 vpxor \T1, \XMM6, \XMM6 2067 vpxor \T1, \XMM7, \XMM7 2068 vpxor \T1, \XMM8, \XMM8 2069 2070 ####################################################################### 2071 2072 2073 2074 2075 2076 vmovdqu 16*1(arg1), \T1 2077 vaesenc \T1, \XMM1, \XMM1 2078 vaesenc \T1, \XMM2, \XMM2 2079 vaesenc \T1, \XMM3, \XMM3 2080 vaesenc \T1, \XMM4, \XMM4 2081 vaesenc \T1, \XMM5, \XMM5 2082 vaesenc \T1, \XMM6, \XMM6 2083 vaesenc \T1, \XMM7, \XMM7 2084 vaesenc \T1, \XMM8, \XMM8 2085 2086 vmovdqu 16*2(arg1), \T1 2087 vaesenc \T1, \XMM1, \XMM1 2088 vaesenc \T1, \XMM2, \XMM2 2089 vaesenc \T1, \XMM3, \XMM3 2090 vaesenc \T1, \XMM4, \XMM4 2091 vaesenc \T1, \XMM5, \XMM5 2092 vaesenc \T1, \XMM6, \XMM6 2093 vaesenc \T1, \XMM7, \XMM7 2094 vaesenc \T1, \XMM8, \XMM8 2095 2096 2097 ####################################################################### 2098 2099 vmovdqa HashKey_8(arg1), \T5 2100 vpclmulqdq $0x11, \T5, \T2, \T4 # T4 = a1*b1 2101 vpclmulqdq $0x00, \T5, \T2, \T7 # T7 = a0*b0 2102 vpclmulqdq $0x01, \T5, \T2, \T6 # T6 = a1*b0 2103 vpclmulqdq $0x10, \T5, \T2, \T5 # T5 = a0*b1 2104 vpxor \T5, \T6, \T6 2105 2106 vmovdqu 16*3(arg1), \T1 2107 vaesenc \T1, \XMM1, \XMM1 2108 vaesenc \T1, \XMM2, \XMM2 2109 vaesenc \T1, \XMM3, \XMM3 2110 vaesenc \T1, \XMM4, \XMM4 2111 vaesenc \T1, \XMM5, \XMM5 2112 vaesenc \T1, \XMM6, \XMM6 2113 vaesenc \T1, \XMM7, \XMM7 2114 vaesenc \T1, \XMM8, \XMM8 2115 2116 vmovdqa TMP2(%rsp), \T1 2117 vmovdqa HashKey_7(arg1), \T5 2118 vpclmulqdq $0x11, \T5, \T1, \T3 2119 vpxor \T3, \T4, \T4 2120 2121 vpclmulqdq $0x00, \T5, \T1, \T3 2122 vpxor \T3, \T7, \T7 2123 2124 vpclmulqdq $0x01, \T5, \T1, \T3 2125 vpxor \T3, \T6, \T6 2126 2127 vpclmulqdq $0x10, \T5, \T1, \T3 2128 vpxor \T3, \T6, \T6 2129 2130 vmovdqu 16*4(arg1), \T1 2131 vaesenc \T1, \XMM1, \XMM1 2132 vaesenc \T1, \XMM2, \XMM2 2133 vaesenc \T1, \XMM3, \XMM3 2134 vaesenc \T1, \XMM4, \XMM4 2135 vaesenc \T1, \XMM5, \XMM5 2136 vaesenc \T1, \XMM6, \XMM6 2137 vaesenc \T1, \XMM7, \XMM7 2138 vaesenc \T1, \XMM8, \XMM8 2139 2140 ####################################################################### 2141 2142 vmovdqa TMP3(%rsp), \T1 2143 vmovdqa HashKey_6(arg1), \T5 2144 vpclmulqdq $0x11, \T5, \T1, \T3 2145 vpxor \T3, \T4, \T4 2146 2147 vpclmulqdq $0x00, \T5, \T1, \T3 2148 vpxor \T3, \T7, \T7 2149 2150 vpclmulqdq $0x01, \T5, \T1, \T3 2151 vpxor \T3, \T6, \T6 2152 2153 vpclmulqdq $0x10, \T5, \T1, \T3 2154 vpxor \T3, \T6, \T6 2155 2156 vmovdqu 16*5(arg1), \T1 2157 vaesenc \T1, \XMM1, \XMM1 2158 vaesenc \T1, \XMM2, \XMM2 2159 vaesenc \T1, \XMM3, \XMM3 2160 vaesenc \T1, \XMM4, \XMM4 2161 vaesenc \T1, \XMM5, \XMM5 2162 vaesenc \T1, \XMM6, \XMM6 2163 vaesenc \T1, \XMM7, \XMM7 2164 vaesenc \T1, \XMM8, \XMM8 2165 2166 vmovdqa TMP4(%rsp), \T1 2167 vmovdqa HashKey_5(arg1), \T5 2168 vpclmulqdq $0x11, \T5, \T1, \T3 2169 vpxor \T3, \T4, \T4 2170 2171 vpclmulqdq $0x00, \T5, \T1, \T3 2172 vpxor \T3, \T7, \T7 2173 2174 vpclmulqdq $0x01, \T5, \T1, \T3 2175 vpxor \T3, \T6, \T6 2176 2177 vpclmulqdq $0x10, \T5, \T1, \T3 2178 vpxor \T3, \T6, \T6 2179 2180 vmovdqu 16*6(arg1), \T1 2181 vaesenc \T1, \XMM1, \XMM1 2182 vaesenc \T1, \XMM2, \XMM2 2183 vaesenc \T1, \XMM3, \XMM3 2184 vaesenc \T1, \XMM4, \XMM4 2185 vaesenc \T1, \XMM5, \XMM5 2186 vaesenc \T1, \XMM6, \XMM6 2187 vaesenc \T1, \XMM7, \XMM7 2188 vaesenc \T1, \XMM8, \XMM8 2189 2190 2191 vmovdqa TMP5(%rsp), \T1 2192 vmovdqa HashKey_4(arg1), \T5 2193 vpclmulqdq $0x11, \T5, \T1, \T3 2194 vpxor \T3, \T4, \T4 2195 2196 vpclmulqdq $0x00, \T5, \T1, \T3 2197 vpxor \T3, \T7, \T7 2198 2199 vpclmulqdq $0x01, \T5, \T1, \T3 2200 vpxor \T3, \T6, \T6 2201 2202 vpclmulqdq $0x10, \T5, \T1, \T3 2203 vpxor \T3, \T6, \T6 2204 2205 vmovdqu 16*7(arg1), \T1 2206 vaesenc \T1, \XMM1, \XMM1 2207 vaesenc \T1, \XMM2, \XMM2 2208 vaesenc \T1, \XMM3, \XMM3 2209 vaesenc \T1, \XMM4, \XMM4 2210 vaesenc \T1, \XMM5, \XMM5 2211 vaesenc \T1, \XMM6, \XMM6 2212 vaesenc \T1, \XMM7, \XMM7 2213 vaesenc \T1, \XMM8, \XMM8 2214 2215 vmovdqa TMP6(%rsp), \T1 2216 vmovdqa HashKey_3(arg1), \T5 2217 vpclmulqdq $0x11, \T5, \T1, \T3 2218 vpxor \T3, \T4, \T4 2219 2220 vpclmulqdq $0x00, \T5, \T1, \T3 2221 vpxor \T3, \T7, \T7 2222 2223 vpclmulqdq $0x01, \T5, \T1, \T3 2224 vpxor \T3, \T6, \T6 2225 2226 vpclmulqdq $0x10, \T5, \T1, \T3 2227 vpxor \T3, \T6, \T6 2228 2229 vmovdqu 16*8(arg1), \T1 2230 vaesenc \T1, \XMM1, \XMM1 2231 vaesenc \T1, \XMM2, \XMM2 2232 vaesenc \T1, \XMM3, \XMM3 2233 vaesenc \T1, \XMM4, \XMM4 2234 vaesenc \T1, \XMM5, \XMM5 2235 vaesenc \T1, \XMM6, \XMM6 2236 vaesenc \T1, \XMM7, \XMM7 2237 vaesenc \T1, \XMM8, \XMM8 2238 2239 vmovdqa TMP7(%rsp), \T1 2240 vmovdqa HashKey_2(arg1), \T5 2241 vpclmulqdq $0x11, \T5, \T1, \T3 2242 vpxor \T3, \T4, \T4 2243 2244 vpclmulqdq $0x00, \T5, \T1, \T3 2245 vpxor \T3, \T7, \T7 2246 2247 vpclmulqdq $0x01, \T5, \T1, \T3 2248 vpxor \T3, \T6, \T6 2249 2250 vpclmulqdq $0x10, \T5, \T1, \T3 2251 vpxor \T3, \T6, \T6 2252 2253 2254 ####################################################################### 2255 2256 vmovdqu 16*9(arg1), \T5 2257 vaesenc \T5, \XMM1, \XMM1 2258 vaesenc \T5, \XMM2, \XMM2 2259 vaesenc \T5, \XMM3, \XMM3 2260 vaesenc \T5, \XMM4, \XMM4 2261 vaesenc \T5, \XMM5, \XMM5 2262 vaesenc \T5, \XMM6, \XMM6 2263 vaesenc \T5, \XMM7, \XMM7 2264 vaesenc \T5, \XMM8, \XMM8 2265 2266 vmovdqa TMP8(%rsp), \T1 2267 vmovdqa HashKey(arg1), \T5 2268 2269 vpclmulqdq $0x00, \T5, \T1, \T3 2270 vpxor \T3, \T7, \T7 2271 2272 vpclmulqdq $0x01, \T5, \T1, \T3 2273 vpxor \T3, \T6, \T6 2274 2275 vpclmulqdq $0x10, \T5, \T1, \T3 2276 vpxor \T3, \T6, \T6 2277 2278 vpclmulqdq $0x11, \T5, \T1, \T3 2279 vpxor \T3, \T4, \T1 2280 2281 2282 vmovdqu 16*10(arg1), \T5 2283 2284 i = 0 2285 j = 1 2286 setreg 2287.rep 8 2288 vpxor 16*i(arg3, %r11), \T5, \T2 2289 .if \ENC_DEC == ENC 2290 vaesenclast \T2, reg_j, reg_j 2291 .else 2292 vaesenclast \T2, reg_j, \T3 2293 vmovdqu 16*i(arg3, %r11), reg_j 2294 vmovdqu \T3, 16*i(arg2, %r11) 2295 .endif 2296 i = (i+1) 2297 j = (j+1) 2298 setreg 2299.endr 2300 ####################################################################### 2301 2302 2303 vpslldq $8, \T6, \T3 # shift-L T3 2 DWs 2304 vpsrldq $8, \T6, \T6 # shift-R T2 2 DWs 2305 vpxor \T3, \T7, \T7 2306 vpxor \T6, \T1, \T1 # accumulate the results in T1:T7 2307 2308 2309 2310 ####################################################################### 2311 #first phase of the reduction 2312 vmovdqa POLY2(%rip), \T3 2313 2314 vpclmulqdq $0x01, \T7, \T3, \T2 2315 vpslldq $8, \T2, \T2 # shift-L xmm2 2 DWs 2316 2317 vpxor \T2, \T7, \T7 # first phase of the reduction complete 2318 ####################################################################### 2319 .if \ENC_DEC == ENC 2320 vmovdqu \XMM1, 16*0(arg2,%r11) # Write to the Ciphertext buffer 2321 vmovdqu \XMM2, 16*1(arg2,%r11) # Write to the Ciphertext buffer 2322 vmovdqu \XMM3, 16*2(arg2,%r11) # Write to the Ciphertext buffer 2323 vmovdqu \XMM4, 16*3(arg2,%r11) # Write to the Ciphertext buffer 2324 vmovdqu \XMM5, 16*4(arg2,%r11) # Write to the Ciphertext buffer 2325 vmovdqu \XMM6, 16*5(arg2,%r11) # Write to the Ciphertext buffer 2326 vmovdqu \XMM7, 16*6(arg2,%r11) # Write to the Ciphertext buffer 2327 vmovdqu \XMM8, 16*7(arg2,%r11) # Write to the Ciphertext buffer 2328 .endif 2329 2330 ####################################################################### 2331 #second phase of the reduction 2332 vpclmulqdq $0x00, \T7, \T3, \T2 2333 vpsrldq $4, \T2, \T2 # shift-R xmm2 1 DW (Shift-R only 1-DW to obtain 2-DWs shift-R) 2334 2335 vpclmulqdq $0x10, \T7, \T3, \T4 2336 vpslldq $4, \T4, \T4 # shift-L xmm0 1 DW (Shift-L 1-DW to obtain result with no shifts) 2337 2338 vpxor \T2, \T4, \T4 # second phase of the reduction complete 2339 ####################################################################### 2340 vpxor \T4, \T1, \T1 # the result is in T1 2341 2342 vpshufb SHUF_MASK(%rip), \XMM1, \XMM1 # perform a 16Byte swap 2343 vpshufb SHUF_MASK(%rip), \XMM2, \XMM2 # perform a 16Byte swap 2344 vpshufb SHUF_MASK(%rip), \XMM3, \XMM3 # perform a 16Byte swap 2345 vpshufb SHUF_MASK(%rip), \XMM4, \XMM4 # perform a 16Byte swap 2346 vpshufb SHUF_MASK(%rip), \XMM5, \XMM5 # perform a 16Byte swap 2347 vpshufb SHUF_MASK(%rip), \XMM6, \XMM6 # perform a 16Byte swap 2348 vpshufb SHUF_MASK(%rip), \XMM7, \XMM7 # perform a 16Byte swap 2349 vpshufb SHUF_MASK(%rip), \XMM8, \XMM8 # perform a 16Byte swap 2350 2351 2352 vpxor \T1, \XMM1, \XMM1 2353 2354 2355 2356.endm 2357 2358 2359# GHASH the last 4 ciphertext blocks. 2360.macro GHASH_LAST_8_AVX2 T1 T2 T3 T4 T5 T6 T7 XMM1 XMM2 XMM3 XMM4 XMM5 XMM6 XMM7 XMM8 2361 2362 ## Karatsuba Method 2363 2364 vmovdqa HashKey_8(arg1), \T5 2365 2366 vpshufd $0b01001110, \XMM1, \T2 2367 vpshufd $0b01001110, \T5, \T3 2368 vpxor \XMM1, \T2, \T2 2369 vpxor \T5, \T3, \T3 2370 2371 vpclmulqdq $0x11, \T5, \XMM1, \T6 2372 vpclmulqdq $0x00, \T5, \XMM1, \T7 2373 2374 vpclmulqdq $0x00, \T3, \T2, \XMM1 2375 2376 ###################### 2377 2378 vmovdqa HashKey_7(arg1), \T5 2379 vpshufd $0b01001110, \XMM2, \T2 2380 vpshufd $0b01001110, \T5, \T3 2381 vpxor \XMM2, \T2, \T2 2382 vpxor \T5, \T3, \T3 2383 2384 vpclmulqdq $0x11, \T5, \XMM2, \T4 2385 vpxor \T4, \T6, \T6 2386 2387 vpclmulqdq $0x00, \T5, \XMM2, \T4 2388 vpxor \T4, \T7, \T7 2389 2390 vpclmulqdq $0x00, \T3, \T2, \T2 2391 2392 vpxor \T2, \XMM1, \XMM1 2393 2394 ###################### 2395 2396 vmovdqa HashKey_6(arg1), \T5 2397 vpshufd $0b01001110, \XMM3, \T2 2398 vpshufd $0b01001110, \T5, \T3 2399 vpxor \XMM3, \T2, \T2 2400 vpxor \T5, \T3, \T3 2401 2402 vpclmulqdq $0x11, \T5, \XMM3, \T4 2403 vpxor \T4, \T6, \T6 2404 2405 vpclmulqdq $0x00, \T5, \XMM3, \T4 2406 vpxor \T4, \T7, \T7 2407 2408 vpclmulqdq $0x00, \T3, \T2, \T2 2409 2410 vpxor \T2, \XMM1, \XMM1 2411 2412 ###################### 2413 2414 vmovdqa HashKey_5(arg1), \T5 2415 vpshufd $0b01001110, \XMM4, \T2 2416 vpshufd $0b01001110, \T5, \T3 2417 vpxor \XMM4, \T2, \T2 2418 vpxor \T5, \T3, \T3 2419 2420 vpclmulqdq $0x11, \T5, \XMM4, \T4 2421 vpxor \T4, \T6, \T6 2422 2423 vpclmulqdq $0x00, \T5, \XMM4, \T4 2424 vpxor \T4, \T7, \T7 2425 2426 vpclmulqdq $0x00, \T3, \T2, \T2 2427 2428 vpxor \T2, \XMM1, \XMM1 2429 2430 ###################### 2431 2432 vmovdqa HashKey_4(arg1), \T5 2433 vpshufd $0b01001110, \XMM5, \T2 2434 vpshufd $0b01001110, \T5, \T3 2435 vpxor \XMM5, \T2, \T2 2436 vpxor \T5, \T3, \T3 2437 2438 vpclmulqdq $0x11, \T5, \XMM5, \T4 2439 vpxor \T4, \T6, \T6 2440 2441 vpclmulqdq $0x00, \T5, \XMM5, \T4 2442 vpxor \T4, \T7, \T7 2443 2444 vpclmulqdq $0x00, \T3, \T2, \T2 2445 2446 vpxor \T2, \XMM1, \XMM1 2447 2448 ###################### 2449 2450 vmovdqa HashKey_3(arg1), \T5 2451 vpshufd $0b01001110, \XMM6, \T2 2452 vpshufd $0b01001110, \T5, \T3 2453 vpxor \XMM6, \T2, \T2 2454 vpxor \T5, \T3, \T3 2455 2456 vpclmulqdq $0x11, \T5, \XMM6, \T4 2457 vpxor \T4, \T6, \T6 2458 2459 vpclmulqdq $0x00, \T5, \XMM6, \T4 2460 vpxor \T4, \T7, \T7 2461 2462 vpclmulqdq $0x00, \T3, \T2, \T2 2463 2464 vpxor \T2, \XMM1, \XMM1 2465 2466 ###################### 2467 2468 vmovdqa HashKey_2(arg1), \T5 2469 vpshufd $0b01001110, \XMM7, \T2 2470 vpshufd $0b01001110, \T5, \T3 2471 vpxor \XMM7, \T2, \T2 2472 vpxor \T5, \T3, \T3 2473 2474 vpclmulqdq $0x11, \T5, \XMM7, \T4 2475 vpxor \T4, \T6, \T6 2476 2477 vpclmulqdq $0x00, \T5, \XMM7, \T4 2478 vpxor \T4, \T7, \T7 2479 2480 vpclmulqdq $0x00, \T3, \T2, \T2 2481 2482 vpxor \T2, \XMM1, \XMM1 2483 2484 ###################### 2485 2486 vmovdqa HashKey(arg1), \T5 2487 vpshufd $0b01001110, \XMM8, \T2 2488 vpshufd $0b01001110, \T5, \T3 2489 vpxor \XMM8, \T2, \T2 2490 vpxor \T5, \T3, \T3 2491 2492 vpclmulqdq $0x11, \T5, \XMM8, \T4 2493 vpxor \T4, \T6, \T6 2494 2495 vpclmulqdq $0x00, \T5, \XMM8, \T4 2496 vpxor \T4, \T7, \T7 2497 2498 vpclmulqdq $0x00, \T3, \T2, \T2 2499 2500 vpxor \T2, \XMM1, \XMM1 2501 vpxor \T6, \XMM1, \XMM1 2502 vpxor \T7, \XMM1, \T2 2503 2504 2505 2506 2507 vpslldq $8, \T2, \T4 2508 vpsrldq $8, \T2, \T2 2509 2510 vpxor \T4, \T7, \T7 2511 vpxor \T2, \T6, \T6 # <T6:T7> holds the result of the 2512 # accumulated carry-less multiplications 2513 2514 ####################################################################### 2515 #first phase of the reduction 2516 vmovdqa POLY2(%rip), \T3 2517 2518 vpclmulqdq $0x01, \T7, \T3, \T2 2519 vpslldq $8, \T2, \T2 # shift-L xmm2 2 DWs 2520 2521 vpxor \T2, \T7, \T7 # first phase of the reduction complete 2522 ####################################################################### 2523 2524 2525 #second phase of the reduction 2526 vpclmulqdq $0x00, \T7, \T3, \T2 2527 vpsrldq $4, \T2, \T2 # shift-R T2 1 DW (Shift-R only 1-DW to obtain 2-DWs shift-R) 2528 2529 vpclmulqdq $0x10, \T7, \T3, \T4 2530 vpslldq $4, \T4, \T4 # shift-L T4 1 DW (Shift-L 1-DW to obtain result with no shifts) 2531 2532 vpxor \T2, \T4, \T4 # second phase of the reduction complete 2533 ####################################################################### 2534 vpxor \T4, \T6, \T6 # the result is in T6 2535.endm 2536 2537 2538 2539# combined for GCM encrypt and decrypt functions 2540# clobbering all xmm registers 2541# clobbering r10, r11, r12, r13, r14, r15 2542.macro GCM_ENC_DEC_AVX2 ENC_DEC 2543 2544 #the number of pushes must equal STACK_OFFSET 2545 push %r12 2546 push %r13 2547 push %r14 2548 push %r15 2549 2550 mov %rsp, %r14 2551 2552 2553 2554 2555 sub $VARIABLE_OFFSET, %rsp 2556 and $~63, %rsp # align rsp to 64 bytes 2557 2558 2559 vmovdqu HashKey(arg1), %xmm13 # xmm13 = HashKey 2560 2561 mov arg4, %r13 # save the number of bytes of plaintext/ciphertext 2562 and $-16, %r13 # r13 = r13 - (r13 mod 16) 2563 2564 mov %r13, %r12 2565 shr $4, %r12 2566 and $7, %r12 2567 jz _initial_num_blocks_is_0\@ 2568 2569 cmp $7, %r12 2570 je _initial_num_blocks_is_7\@ 2571 cmp $6, %r12 2572 je _initial_num_blocks_is_6\@ 2573 cmp $5, %r12 2574 je _initial_num_blocks_is_5\@ 2575 cmp $4, %r12 2576 je _initial_num_blocks_is_4\@ 2577 cmp $3, %r12 2578 je _initial_num_blocks_is_3\@ 2579 cmp $2, %r12 2580 je _initial_num_blocks_is_2\@ 2581 2582 jmp _initial_num_blocks_is_1\@ 2583 2584_initial_num_blocks_is_7\@: 2585 INITIAL_BLOCKS_AVX2 7, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2586 sub $16*7, %r13 2587 jmp _initial_blocks_encrypted\@ 2588 2589_initial_num_blocks_is_6\@: 2590 INITIAL_BLOCKS_AVX2 6, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2591 sub $16*6, %r13 2592 jmp _initial_blocks_encrypted\@ 2593 2594_initial_num_blocks_is_5\@: 2595 INITIAL_BLOCKS_AVX2 5, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2596 sub $16*5, %r13 2597 jmp _initial_blocks_encrypted\@ 2598 2599_initial_num_blocks_is_4\@: 2600 INITIAL_BLOCKS_AVX2 4, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2601 sub $16*4, %r13 2602 jmp _initial_blocks_encrypted\@ 2603 2604_initial_num_blocks_is_3\@: 2605 INITIAL_BLOCKS_AVX2 3, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2606 sub $16*3, %r13 2607 jmp _initial_blocks_encrypted\@ 2608 2609_initial_num_blocks_is_2\@: 2610 INITIAL_BLOCKS_AVX2 2, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2611 sub $16*2, %r13 2612 jmp _initial_blocks_encrypted\@ 2613 2614_initial_num_blocks_is_1\@: 2615 INITIAL_BLOCKS_AVX2 1, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2616 sub $16*1, %r13 2617 jmp _initial_blocks_encrypted\@ 2618 2619_initial_num_blocks_is_0\@: 2620 INITIAL_BLOCKS_AVX2 0, %xmm12, %xmm13, %xmm14, %xmm15, %xmm11, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm10, %xmm0, \ENC_DEC 2621 2622 2623_initial_blocks_encrypted\@: 2624 cmp $0, %r13 2625 je _zero_cipher_left\@ 2626 2627 sub $128, %r13 2628 je _eight_cipher_left\@ 2629 2630 2631 2632 2633 vmovd %xmm9, %r15d 2634 and $255, %r15d 2635 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2636 2637 2638_encrypt_by_8_new\@: 2639 cmp $(255-8), %r15d 2640 jg _encrypt_by_8\@ 2641 2642 2643 2644 add $8, %r15b 2645 GHASH_8_ENCRYPT_8_PARALLEL_AVX2 %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm15, out_order, \ENC_DEC 2646 add $128, %r11 2647 sub $128, %r13 2648 jne _encrypt_by_8_new\@ 2649 2650 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2651 jmp _eight_cipher_left\@ 2652 2653_encrypt_by_8\@: 2654 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2655 add $8, %r15b 2656 GHASH_8_ENCRYPT_8_PARALLEL_AVX2 %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm9, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8, %xmm15, in_order, \ENC_DEC 2657 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2658 add $128, %r11 2659 sub $128, %r13 2660 jne _encrypt_by_8_new\@ 2661 2662 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2663 2664 2665 2666 2667_eight_cipher_left\@: 2668 GHASH_LAST_8_AVX2 %xmm0, %xmm10, %xmm11, %xmm12, %xmm13, %xmm14, %xmm15, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5, %xmm6, %xmm7, %xmm8 2669 2670 2671_zero_cipher_left\@: 2672 cmp $16, arg4 2673 jl _only_less_than_16\@ 2674 2675 mov arg4, %r13 2676 and $15, %r13 # r13 = (arg4 mod 16) 2677 2678 je _multiple_of_16_bytes\@ 2679 2680 # handle the last <16 Byte block seperately 2681 2682 2683 vpaddd ONE(%rip), %xmm9, %xmm9 # INCR CNT to get Yn 2684 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2685 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Yn) 2686 2687 sub $16, %r11 2688 add %r13, %r11 2689 vmovdqu (arg3, %r11), %xmm1 # receive the last <16 Byte block 2690 2691 lea SHIFT_MASK+16(%rip), %r12 2692 sub %r13, %r12 # adjust the shuffle mask pointer 2693 # to be able to shift 16-r13 bytes 2694 # (r13 is the number of bytes in plaintext mod 16) 2695 vmovdqu (%r12), %xmm2 # get the appropriate shuffle mask 2696 vpshufb %xmm2, %xmm1, %xmm1 # shift right 16-r13 bytes 2697 jmp _final_ghash_mul\@ 2698 2699_only_less_than_16\@: 2700 # check for 0 length 2701 mov arg4, %r13 2702 and $15, %r13 # r13 = (arg4 mod 16) 2703 2704 je _multiple_of_16_bytes\@ 2705 2706 # handle the last <16 Byte block seperately 2707 2708 2709 vpaddd ONE(%rip), %xmm9, %xmm9 # INCR CNT to get Yn 2710 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2711 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Yn) 2712 2713 2714 lea SHIFT_MASK+16(%rip), %r12 2715 sub %r13, %r12 # adjust the shuffle mask pointer to be 2716 # able to shift 16-r13 bytes (r13 is the 2717 # number of bytes in plaintext mod 16) 2718 2719_get_last_16_byte_loop\@: 2720 movb (arg3, %r11), %al 2721 movb %al, TMP1 (%rsp , %r11) 2722 add $1, %r11 2723 cmp %r13, %r11 2724 jne _get_last_16_byte_loop\@ 2725 2726 vmovdqu TMP1(%rsp), %xmm1 2727 2728 sub $16, %r11 2729 2730_final_ghash_mul\@: 2731 .if \ENC_DEC == DEC 2732 vmovdqa %xmm1, %xmm2 2733 vpxor %xmm1, %xmm9, %xmm9 # Plaintext XOR E(K, Yn) 2734 vmovdqu ALL_F-SHIFT_MASK(%r12), %xmm1 # get the appropriate mask to mask out top 16-r13 bytes of xmm9 2735 vpand %xmm1, %xmm9, %xmm9 # mask out top 16-r13 bytes of xmm9 2736 vpand %xmm1, %xmm2, %xmm2 2737 vpshufb SHUF_MASK(%rip), %xmm2, %xmm2 2738 vpxor %xmm2, %xmm14, %xmm14 2739 #GHASH computation for the last <16 Byte block 2740 GHASH_MUL_AVX2 %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 2741 sub %r13, %r11 2742 add $16, %r11 2743 .else 2744 vpxor %xmm1, %xmm9, %xmm9 # Plaintext XOR E(K, Yn) 2745 vmovdqu ALL_F-SHIFT_MASK(%r12), %xmm1 # get the appropriate mask to mask out top 16-r13 bytes of xmm9 2746 vpand %xmm1, %xmm9, %xmm9 # mask out top 16-r13 bytes of xmm9 2747 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 2748 vpxor %xmm9, %xmm14, %xmm14 2749 #GHASH computation for the last <16 Byte block 2750 GHASH_MUL_AVX2 %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 2751 sub %r13, %r11 2752 add $16, %r11 2753 vpshufb SHUF_MASK(%rip), %xmm9, %xmm9 # shuffle xmm9 back to output as ciphertext 2754 .endif 2755 2756 2757 ############################# 2758 # output r13 Bytes 2759 vmovq %xmm9, %rax 2760 cmp $8, %r13 2761 jle _less_than_8_bytes_left\@ 2762 2763 mov %rax, (arg2 , %r11) 2764 add $8, %r11 2765 vpsrldq $8, %xmm9, %xmm9 2766 vmovq %xmm9, %rax 2767 sub $8, %r13 2768 2769_less_than_8_bytes_left\@: 2770 movb %al, (arg2 , %r11) 2771 add $1, %r11 2772 shr $8, %rax 2773 sub $1, %r13 2774 jne _less_than_8_bytes_left\@ 2775 ############################# 2776 2777_multiple_of_16_bytes\@: 2778 mov arg7, %r12 # r12 = aadLen (number of bytes) 2779 shl $3, %r12 # convert into number of bits 2780 vmovd %r12d, %xmm15 # len(A) in xmm15 2781 2782 shl $3, arg4 # len(C) in bits (*128) 2783 vmovq arg4, %xmm1 2784 vpslldq $8, %xmm15, %xmm15 # xmm15 = len(A)|| 0x0000000000000000 2785 vpxor %xmm1, %xmm15, %xmm15 # xmm15 = len(A)||len(C) 2786 2787 vpxor %xmm15, %xmm14, %xmm14 2788 GHASH_MUL_AVX2 %xmm14, %xmm13, %xmm0, %xmm10, %xmm11, %xmm5, %xmm6 # final GHASH computation 2789 vpshufb SHUF_MASK(%rip), %xmm14, %xmm14 # perform a 16Byte swap 2790 2791 mov arg5, %rax # rax = *Y0 2792 vmovdqu (%rax), %xmm9 # xmm9 = Y0 2793 2794 ENCRYPT_SINGLE_BLOCK %xmm9 # E(K, Y0) 2795 2796 vpxor %xmm14, %xmm9, %xmm9 2797 2798 2799 2800_return_T\@: 2801 mov arg8, %r10 # r10 = authTag 2802 mov arg9, %r11 # r11 = auth_tag_len 2803 2804 cmp $16, %r11 2805 je _T_16\@ 2806 2807 cmp $8, %r11 2808 jl _T_4\@ 2809 2810_T_8\@: 2811 vmovq %xmm9, %rax 2812 mov %rax, (%r10) 2813 add $8, %r10 2814 sub $8, %r11 2815 vpsrldq $8, %xmm9, %xmm9 2816 cmp $0, %r11 2817 je _return_T_done\@ 2818_T_4\@: 2819 vmovd %xmm9, %eax 2820 mov %eax, (%r10) 2821 add $4, %r10 2822 sub $4, %r11 2823 vpsrldq $4, %xmm9, %xmm9 2824 cmp $0, %r11 2825 je _return_T_done\@ 2826_T_123\@: 2827 vmovd %xmm9, %eax 2828 cmp $2, %r11 2829 jl _T_1\@ 2830 mov %ax, (%r10) 2831 cmp $2, %r11 2832 je _return_T_done\@ 2833 add $2, %r10 2834 sar $16, %eax 2835_T_1\@: 2836 mov %al, (%r10) 2837 jmp _return_T_done\@ 2838 2839_T_16\@: 2840 vmovdqu %xmm9, (%r10) 2841 2842_return_T_done\@: 2843 mov %r14, %rsp 2844 2845 pop %r15 2846 pop %r14 2847 pop %r13 2848 pop %r12 2849.endm 2850 2851 2852############################################################# 2853#void aesni_gcm_precomp_avx_gen4 2854# (gcm_data *my_ctx_data, 2855# u8 *hash_subkey)# /* H, the Hash sub key input. 2856# Data starts on a 16-byte boundary. */ 2857############################################################# 2858ENTRY(aesni_gcm_precomp_avx_gen4) 2859 #the number of pushes must equal STACK_OFFSET 2860 push %r12 2861 push %r13 2862 push %r14 2863 push %r15 2864 2865 mov %rsp, %r14 2866 2867 2868 2869 sub $VARIABLE_OFFSET, %rsp 2870 and $~63, %rsp # align rsp to 64 bytes 2871 2872 vmovdqu (arg2), %xmm6 # xmm6 = HashKey 2873 2874 vpshufb SHUF_MASK(%rip), %xmm6, %xmm6 2875 ############### PRECOMPUTATION of HashKey<<1 mod poly from the HashKey 2876 vmovdqa %xmm6, %xmm2 2877 vpsllq $1, %xmm6, %xmm6 2878 vpsrlq $63, %xmm2, %xmm2 2879 vmovdqa %xmm2, %xmm1 2880 vpslldq $8, %xmm2, %xmm2 2881 vpsrldq $8, %xmm1, %xmm1 2882 vpor %xmm2, %xmm6, %xmm6 2883 #reduction 2884 vpshufd $0b00100100, %xmm1, %xmm2 2885 vpcmpeqd TWOONE(%rip), %xmm2, %xmm2 2886 vpand POLY(%rip), %xmm2, %xmm2 2887 vpxor %xmm2, %xmm6, %xmm6 # xmm6 holds the HashKey<<1 mod poly 2888 ####################################################################### 2889 vmovdqa %xmm6, HashKey(arg1) # store HashKey<<1 mod poly 2890 2891 2892 PRECOMPUTE_AVX2 %xmm6, %xmm0, %xmm1, %xmm2, %xmm3, %xmm4, %xmm5 2893 2894 mov %r14, %rsp 2895 2896 pop %r15 2897 pop %r14 2898 pop %r13 2899 pop %r12 2900 ret 2901ENDPROC(aesni_gcm_precomp_avx_gen4) 2902 2903 2904############################################################################### 2905#void aesni_gcm_enc_avx_gen4( 2906# gcm_data *my_ctx_data, /* aligned to 16 Bytes */ 2907# u8 *out, /* Ciphertext output. Encrypt in-place is allowed. */ 2908# const u8 *in, /* Plaintext input */ 2909# u64 plaintext_len, /* Length of data in Bytes for encryption. */ 2910# u8 *iv, /* Pre-counter block j0: 4 byte salt 2911# (from Security Association) concatenated with 8 byte 2912# Initialisation Vector (from IPSec ESP Payload) 2913# concatenated with 0x00000001. 16-byte aligned pointer. */ 2914# const u8 *aad, /* Additional Authentication Data (AAD)*/ 2915# u64 aad_len, /* Length of AAD in bytes. With RFC4106 this is going to be 8 or 12 Bytes */ 2916# u8 *auth_tag, /* Authenticated Tag output. */ 2917# u64 auth_tag_len)# /* Authenticated Tag Length in bytes. 2918# Valid values are 16 (most likely), 12 or 8. */ 2919############################################################################### 2920ENTRY(aesni_gcm_enc_avx_gen4) 2921 GCM_ENC_DEC_AVX2 ENC 2922 ret 2923ENDPROC(aesni_gcm_enc_avx_gen4) 2924 2925############################################################################### 2926#void aesni_gcm_dec_avx_gen4( 2927# gcm_data *my_ctx_data, /* aligned to 16 Bytes */ 2928# u8 *out, /* Plaintext output. Decrypt in-place is allowed. */ 2929# const u8 *in, /* Ciphertext input */ 2930# u64 plaintext_len, /* Length of data in Bytes for encryption. */ 2931# u8 *iv, /* Pre-counter block j0: 4 byte salt 2932# (from Security Association) concatenated with 8 byte 2933# Initialisation Vector (from IPSec ESP Payload) 2934# concatenated with 0x00000001. 16-byte aligned pointer. */ 2935# const u8 *aad, /* Additional Authentication Data (AAD)*/ 2936# u64 aad_len, /* Length of AAD in bytes. With RFC4106 this is going to be 8 or 12 Bytes */ 2937# u8 *auth_tag, /* Authenticated Tag output. */ 2938# u64 auth_tag_len)# /* Authenticated Tag Length in bytes. 2939# Valid values are 16 (most likely), 12 or 8. */ 2940############################################################################### 2941ENTRY(aesni_gcm_dec_avx_gen4) 2942 GCM_ENC_DEC_AVX2 DEC 2943 ret 2944ENDPROC(aesni_gcm_dec_avx_gen4) 2945 2946#endif /* CONFIG_AS_AVX2 */ 2947