1 /*===----------------- keylockerintrin.h - KL Intrinsics -------------------=== 2 * 3 * Permission is hereby granted, free of charge, to any person obtaining a copy 4 * of this software and associated documentation files (the "Software"), to deal 5 * in the Software without restriction, including without limitation the rights 6 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 * copies of the Software, and to permit persons to whom the Software is 8 * furnished to do so, subject to the following conditions: 9 * 10 * The above copyright notice and this permission notice shall be included in 11 * all copies or substantial portions of the Software. 12 * 13 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 15 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 16 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 17 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 18 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 19 * THE SOFTWARE. 20 * 21 *===-----------------------------------------------------------------------=== 22 */ 23 24 #ifndef __IMMINTRIN_H 25 #error "Never use <keylockerintrin.h> directly; include <immintrin.h> instead." 26 #endif 27 28 #ifndef _KEYLOCKERINTRIN_H 29 #define _KEYLOCKERINTRIN_H 30 31 #if !(defined(_MSC_VER) || defined(__SCE__)) || __has_feature(modules) || \ 32 defined(__KL__) 33 34 /* Define the default attributes for the functions in this file. */ 35 #define __DEFAULT_FN_ATTRS \ 36 __attribute__((__always_inline__, __nodebug__, __target__("kl"),\ 37 __min_vector_width__(128))) 38 39 /// Load internal wrapping key from __intkey, __enkey_lo and __enkey_hi. __ctl 40 /// will assigned to EAX, whch specifies the KeySource and whether backing up 41 /// the key is permitted. The 256-bit encryption key is loaded from the two 42 /// explicit operands (__enkey_lo and __enkey_hi). The 128-bit integrity key is 43 /// loaded from the implicit operand XMM0 which assigned by __intkey. 44 /// 45 /// \headerfile <x86intrin.h> 46 /// 47 /// This intrinsic corresponds to the <c> LOADIWKEY </c> instructions. 48 /// 49 /// \operation 50 /// IF CPL > 0 // LOADKWKEY only allowed at ring 0 (supervisor mode) 51 /// GP (0) 52 /// FI 53 /// IF “LOADIWKEY exiting” VM execution control set 54 /// VMexit 55 /// FI 56 /// IF __ctl[4:1] > 1 // Reserved KeySource encoding used 57 /// GP (0) 58 /// FI 59 /// IF __ctl[31:5] != 0 // Reserved bit in __ctl is set 60 /// GP (0) 61 /// FI 62 /// IF __ctl[0] AND (CPUID.19H.ECX[0] == 0) // NoBackup is not supported on this part 63 /// GP (0) 64 /// FI 65 /// IF (__ctl[4:1] == 1) AND (CPUID.19H.ECX[1] == 0) // KeySource of 1 is not supported on this part 66 /// GP (0) 67 /// FI 68 /// IF (__ctl[4:1] == 0) // KeySource of 0. 69 /// IWKey.Encryption Key[127:0] := __enkey_hi[127:0]: 70 /// IWKey.Encryption Key[255:128] := __enkey_lo[127:0] 71 /// IWKey.IntegrityKey[127:0] := __intkey[127:0] 72 /// IWKey.NoBackup := __ctl[0] 73 /// IWKey.KeySource := __ctl[4:1] 74 /// ZF := 0 75 /// ELSE // KeySource of 1. See RDSEED definition for details of randomness 76 /// IF HW_NRND_GEN.ready == 1 // Full-entropy random data from RDSEED was received 77 /// IWKey.Encryption Key[127:0] := __enkey_hi[127:0] XOR HW_NRND_GEN.data[127:0] 78 /// IWKey.Encryption Key[255:128] := __enkey_lo[127:0] XOR HW_NRND_GEN.data[255:128] 79 /// IWKey.Encryption Key[255:0] := __enkey_hi[127:0]:__enkey_lo[127:0] XOR HW_NRND_GEN.data[255:0] 80 /// IWKey.IntegrityKey[127:0] := __intkey[127:0] XOR HW_NRND_GEN.data[383:256] 81 /// IWKey.NoBackup := __ctl[0] 82 /// IWKey.KeySource := __ctl[4:1] 83 /// ZF := 0 84 /// ELSE // Random data was not returned from RDSEED. IWKey was not loaded 85 /// ZF := 1 86 /// FI 87 /// FI 88 /// dst := ZF 89 /// OF := 0 90 /// SF := 0 91 /// AF := 0 92 /// PF := 0 93 /// CF := 0 94 /// \endoperation 95 static __inline__ void __DEFAULT_FN_ATTRS 96 _mm_loadiwkey (unsigned int __ctl, __m128i __intkey, 97 __m128i __enkey_lo, __m128i __enkey_hi) { 98 __builtin_ia32_loadiwkey (__intkey, __enkey_lo, __enkey_hi, __ctl); 99 } 100 101 /// Wrap a 128-bit AES key from __key into a key handle and output in 102 /// ((__m128i*)__h) to ((__m128i*)__h) + 5 and a 32-bit value as return. 103 /// The explicit source operand __htype specifies handle restrictions. 104 /// 105 /// \headerfile <x86intrin.h> 106 /// 107 /// This intrinsic corresponds to the <c> ENCODEKEY128 </c> instructions. 108 /// 109 /// \operation 110 /// InputKey[127:0] := __key[127:0] 111 /// KeyMetadata[2:0] := __htype[2:0] 112 /// KeyMetadata[23:3] := 0 // Reserved for future usage 113 /// KeyMetadata[27:24] := 0 // KeyType is AES-128 (value of 0) 114 /// KeyMetadata[127:28] := 0 // Reserved for future usage 115 /// Handle[383:0] := WrapKey128(InputKey[127:0], KeyMetadata[127:0], 116 /// IWKey.Integrity Key[127:0], IWKey.Encryption Key[255:0]) 117 /// dst[0] := IWKey.NoBackup 118 /// dst[4:1] := IWKey.KeySource[3:0] 119 /// dst[31:5] := 0 120 /// MEM[__h+127:__h] := Handle[127:0] // AAD 121 /// MEM[__h+255:__h+128] := Handle[255:128] // Integrity Tag 122 /// MEM[__h+383:__h+256] := Handle[383:256] // CipherText 123 /// MEM[__h+511:__h+384] := 0 // Reserved for future usage 124 /// MEM[__h+639:__h+512] := 0 // Reserved for future usage 125 /// MEM[__h+767:__h+640] := 0 // Reserved for future usage 126 /// OF := 0 127 /// SF := 0 128 /// ZF := 0 129 /// AF := 0 130 /// PF := 0 131 /// CF := 0 132 /// \endoperation 133 static __inline__ unsigned int __DEFAULT_FN_ATTRS 134 _mm_encodekey128_u32(unsigned int __htype, __m128i __key, void *__h) { 135 return __builtin_ia32_encodekey128_u32(__htype, (__v2di)__key, __h); 136 } 137 138 /// Wrap a 256-bit AES key from __key_hi:__key_lo into a key handle, then 139 /// output handle in ((__m128i*)__h) to ((__m128i*)__h) + 6 and 140 /// a 32-bit value as return. 141 /// The explicit source operand __htype specifies handle restrictions. 142 /// 143 /// \headerfile <x86intrin.h> 144 /// 145 /// This intrinsic corresponds to the <c> ENCODEKEY256 </c> instructions. 146 /// 147 /// \operation 148 /// InputKey[127:0] := __key_lo[127:0] 149 /// InputKey[255:128] := __key_hi[255:128] 150 /// KeyMetadata[2:0] := __htype[2:0] 151 /// KeyMetadata[23:3] := 0 // Reserved for future usage 152 /// KeyMetadata[27:24] := 1 // KeyType is AES-256 (value of 1) 153 /// KeyMetadata[127:28] := 0 // Reserved for future usage 154 /// Handle[511:0] := WrapKey256(InputKey[255:0], KeyMetadata[127:0], 155 /// IWKey.Integrity Key[127:0], IWKey.Encryption Key[255:0]) 156 /// dst[0] := IWKey.NoBackup 157 /// dst[4:1] := IWKey.KeySource[3:0] 158 /// dst[31:5] := 0 159 /// MEM[__h+127:__h] := Handle[127:0] // AAD 160 /// MEM[__h+255:__h+128] := Handle[255:128] // Tag 161 /// MEM[__h+383:__h+256] := Handle[383:256] // CipherText[127:0] 162 /// MEM[__h+511:__h+384] := Handle[511:384] // CipherText[255:128] 163 /// MEM[__h+639:__h+512] := 0 // Reserved for future usage 164 /// MEM[__h+767:__h+640] := 0 // Reserved for future usage 165 /// MEM[__h+895:__h+768] := 0 Integrity// Reserved for future usage 166 /// OF := 0 167 /// SF := 0 168 /// ZF := 0 169 /// AF := 0 170 /// PF := 0 171 /// CF := 0 172 /// \endoperation 173 static __inline__ unsigned int __DEFAULT_FN_ATTRS 174 _mm_encodekey256_u32(unsigned int __htype, __m128i __key_lo, __m128i __key_hi, 175 void *__h) { 176 return __builtin_ia32_encodekey256_u32(__htype, (__v2di)__key_lo, 177 (__v2di)__key_hi, __h); 178 } 179 180 /// The AESENC128KL performs 10 rounds of AES to encrypt the __idata using 181 /// the 128-bit key in the handle from the __h. It stores the result in the 182 /// __odata. And return the affected ZF flag status. 183 /// 184 /// \headerfile <x86intrin.h> 185 /// 186 /// This intrinsic corresponds to the <c> AESENC128KL </c> instructions. 187 /// 188 /// \operation 189 /// Handle[383:0] := MEM[__h+383:__h] // Load is not guaranteed to be atomic. 190 /// IllegalHandle := ( HandleReservedBitSet (Handle[383:0]) || 191 /// (Handle[127:0] AND (CPL > 0)) || 192 /// Handle[383:256] || 193 /// HandleKeyType (Handle[383:0]) != HANDLE_KEY_TYPE_AES128 ) 194 /// IF (IllegalHandle) 195 /// ZF := 1 196 /// ELSE 197 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey) 198 /// IF (Authentic == 0) 199 /// ZF := 1 200 /// ELSE 201 /// MEM[__odata+127:__odata] := AES128Encrypt (__idata[127:0], UnwrappedKey) 202 /// ZF := 0 203 /// FI 204 /// FI 205 /// dst := ZF 206 /// OF := 0 207 /// SF := 0 208 /// AF := 0 209 /// PF := 0 210 /// CF := 0 211 /// \endoperation 212 static __inline__ unsigned char __DEFAULT_FN_ATTRS 213 _mm_aesenc128kl_u8(__m128i* __odata, __m128i __idata, const void *__h) { 214 return __builtin_ia32_aesenc128kl_u8((__v2di *)__odata, (__v2di)__idata, __h); 215 } 216 217 /// The AESENC256KL performs 14 rounds of AES to encrypt the __idata using 218 /// the 256-bit key in the handle from the __h. It stores the result in the 219 /// __odata. And return the affected ZF flag status. 220 /// 221 /// \headerfile <x86intrin.h> 222 /// 223 /// This intrinsic corresponds to the <c> AESENC256KL </c> instructions. 224 /// 225 /// \operation 226 /// Handle[511:0] := MEM[__h+511:__h] // Load is not guaranteed to be atomic. 227 /// IllegalHandle := ( HandleReservedBitSet (Handle[511:0]) || 228 /// (Handle[127:0] AND (CPL > 0)) || 229 /// Handle[255:128] || 230 /// HandleKeyType (Handle[511:0]) != HANDLE_KEY_TYPE_AES256 ) 231 /// IF (IllegalHandle) 232 /// ZF := 1 233 /// ELSE 234 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey) 235 /// IF (Authentic == 0) 236 /// ZF := 1 237 /// ELSE 238 /// MEM[__odata+127:__odata] := AES256Encrypt (__idata[127:0], UnwrappedKey) 239 /// ZF := 0 240 /// FI 241 /// FI 242 /// dst := ZF 243 /// OF := 0 244 /// SF := 0 245 /// AF := 0 246 /// PF := 0 247 /// CF := 0 248 /// \endoperation 249 static __inline__ unsigned char __DEFAULT_FN_ATTRS 250 _mm_aesenc256kl_u8(__m128i* __odata, __m128i __idata, const void *__h) { 251 return __builtin_ia32_aesenc256kl_u8((__v2di *)__odata, (__v2di)__idata, __h); 252 } 253 254 /// The AESDEC128KL performs 10 rounds of AES to decrypt the __idata using 255 /// the 128-bit key in the handle from the __h. It stores the result in the 256 /// __odata. And return the affected ZF flag status. 257 /// 258 /// \headerfile <x86intrin.h> 259 /// 260 /// This intrinsic corresponds to the <c> AESDEC128KL </c> instructions. 261 /// 262 /// \operation 263 /// Handle[383:0] := MEM[__h+383:__h] // Load is not guaranteed to be atomic. 264 /// IllegalHandle := (HandleReservedBitSet (Handle[383:0]) || 265 /// (Handle[127:0] AND (CPL > 0)) || 266 /// Handle[383:256] || 267 /// HandleKeyType (Handle[383:0]) != HANDLE_KEY_TYPE_AES128) 268 /// IF (IllegalHandle) 269 /// ZF := 1 270 /// ELSE 271 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey) 272 /// IF (Authentic == 0) 273 /// ZF := 1 274 /// ELSE 275 /// MEM[__odata+127:__odata] := AES128Decrypt (__idata[127:0], UnwrappedKey) 276 /// ZF := 0 277 /// FI 278 /// FI 279 /// dst := ZF 280 /// OF := 0 281 /// SF := 0 282 /// AF := 0 283 /// PF := 0 284 /// CF := 0 285 /// \endoperation 286 static __inline__ unsigned char __DEFAULT_FN_ATTRS 287 _mm_aesdec128kl_u8(__m128i* __odata, __m128i __idata, const void *__h) { 288 return __builtin_ia32_aesdec128kl_u8((__v2di *)__odata, (__v2di)__idata, __h); 289 } 290 291 /// The AESDEC256KL performs 10 rounds of AES to decrypt the __idata using 292 /// the 256-bit key in the handle from the __h. It stores the result in the 293 /// __odata. And return the affected ZF flag status. 294 /// 295 /// \headerfile <x86intrin.h> 296 /// 297 /// This intrinsic corresponds to the <c> AESDEC256KL </c> instructions. 298 /// 299 /// \operation 300 /// Handle[511:0] := MEM[__h+511:__h] 301 /// IllegalHandle := (HandleReservedBitSet (Handle[511:0]) || 302 /// (Handle[127:0] AND (CPL > 0)) || 303 /// Handle[383:256] || 304 /// HandleKeyType (Handle[511:0]) != HANDLE_KEY_TYPE_AES256) 305 /// IF (IllegalHandle) 306 /// ZF := 1 307 /// ELSE 308 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey) 309 /// IF (Authentic == 0) 310 /// ZF := 1 311 /// ELSE 312 /// MEM[__odata+127:__odata] := AES256Decrypt (__idata[127:0], UnwrappedKey) 313 /// ZF := 0 314 /// FI 315 /// FI 316 /// dst := ZF 317 /// OF := 0 318 /// SF := 0 319 /// AF := 0 320 /// PF := 0 321 /// CF := 0 322 /// \endoperation 323 static __inline__ unsigned char __DEFAULT_FN_ATTRS 324 _mm_aesdec256kl_u8(__m128i* __odata, __m128i __idata, const void *__h) { 325 return __builtin_ia32_aesdec256kl_u8((__v2di *)__odata, (__v2di)__idata, __h); 326 } 327 328 #undef __DEFAULT_FN_ATTRS 329 330 #endif /* !(defined(_MSC_VER) || defined(__SCE__)) || __has_feature(modules) \ 331 || defined(__KL__) */ 332 333 #if !(defined(_MSC_VER) || defined(__SCE__)) || __has_feature(modules) || \ 334 defined(__WIDEKL__) 335 336 /* Define the default attributes for the functions in this file. */ 337 #define __DEFAULT_FN_ATTRS \ 338 __attribute__((__always_inline__, __nodebug__, __target__("kl,widekl"),\ 339 __min_vector_width__(128))) 340 341 /// Encrypt __idata[0] to __idata[7] using 128-bit AES key indicated by handle 342 /// at __h and store each resultant block back from __odata to __odata+7. And 343 /// return the affected ZF flag status. 344 /// 345 /// \headerfile <x86intrin.h> 346 /// 347 /// This intrinsic corresponds to the <c> AESENCWIDE128KL </c> instructions. 348 /// 349 /// \operation 350 /// Handle := MEM[__h+383:__h] 351 /// IllegalHandle := ( HandleReservedBitSet (Handle[383:0]) || 352 /// (Handle[127:0] AND (CPL > 0)) || 353 /// Handle[255:128] || 354 /// HandleKeyType (Handle[383:0]) != HANDLE_KEY_TYPE_AES128 ) 355 /// IF (IllegalHandle) 356 /// ZF := 1 357 /// ELSE 358 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey) 359 /// IF Authentic == 0 360 /// ZF := 1 361 /// ELSE 362 /// FOR i := 0 to 7 363 /// __odata[i] := AES128Encrypt (__idata[i], UnwrappedKey) 364 /// ENDFOR 365 /// ZF := 0 366 /// FI 367 /// FI 368 /// dst := ZF 369 /// OF := 0 370 /// SF := 0 371 /// AF := 0 372 /// PF := 0 373 /// CF := 0 374 /// \endoperation 375 static __inline__ unsigned char __DEFAULT_FN_ATTRS 376 _mm_aesencwide128kl_u8(__m128i __odata[8], const __m128i __idata[8], const void* __h) { 377 return __builtin_ia32_aesencwide128kl_u8((__v2di *)__odata, 378 (const __v2di *)__idata, __h); 379 } 380 381 /// Encrypt __idata[0] to __idata[7] using 256-bit AES key indicated by handle 382 /// at __h and store each resultant block back from __odata to __odata+7. And 383 /// return the affected ZF flag status. 384 /// 385 /// \headerfile <x86intrin.h> 386 /// 387 /// This intrinsic corresponds to the <c> AESENCWIDE256KL </c> instructions. 388 /// 389 /// \operation 390 /// Handle[511:0] := MEM[__h+511:__h] 391 /// IllegalHandle := ( HandleReservedBitSet (Handle[511:0]) || 392 /// (Handle[127:0] AND (CPL > 0)) || 393 /// Handle[255:128] || 394 /// HandleKeyType (Handle[511:0]) != HANDLE_KEY_TYPE_AES512 ) 395 /// IF (IllegalHandle) 396 /// ZF := 1 397 /// ELSE 398 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey) 399 /// IF Authentic == 0 400 /// ZF := 1 401 /// ELSE 402 /// FOR i := 0 to 7 403 /// __odata[i] := AES256Encrypt (__idata[i], UnwrappedKey) 404 /// ENDFOR 405 /// ZF := 0 406 /// FI 407 /// FI 408 /// dst := ZF 409 /// OF := 0 410 /// SF := 0 411 /// AF := 0 412 /// PF := 0 413 /// CF := 0 414 /// \endoperation 415 static __inline__ unsigned char __DEFAULT_FN_ATTRS 416 _mm_aesencwide256kl_u8(__m128i __odata[8], const __m128i __idata[8], const void* __h) { 417 return __builtin_ia32_aesencwide256kl_u8((__v2di *)__odata, 418 (const __v2di *)__idata, __h); 419 } 420 421 /// Decrypt __idata[0] to __idata[7] using 128-bit AES key indicated by handle 422 /// at __h and store each resultant block back from __odata to __odata+7. And 423 /// return the affected ZF flag status. 424 /// 425 /// \headerfile <x86intrin.h> 426 /// 427 /// This intrinsic corresponds to the <c> AESDECWIDE128KL </c> instructions. 428 /// 429 /// \operation 430 /// Handle[383:0] := MEM[__h+383:__h] 431 /// IllegalHandle := ( HandleReservedBitSet (Handle[383:0]) || 432 /// (Handle[127:0] AND (CPL > 0)) || 433 /// Handle[255:128] || 434 /// HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES128 ) 435 /// IF (IllegalHandle) 436 /// ZF := 1 437 /// ELSE 438 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate384 (Handle[383:0], IWKey) 439 /// IF Authentic == 0 440 /// ZF := 1 441 /// ELSE 442 /// FOR i := 0 to 7 443 /// __odata[i] := AES128Decrypt (__idata[i], UnwrappedKey) 444 /// ENDFOR 445 /// ZF := 0 446 /// FI 447 /// FI 448 /// dst := ZF 449 /// OF := 0 450 /// SF := 0 451 /// AF := 0 452 /// PF := 0 453 /// CF := 0 454 /// \endoperation 455 static __inline__ unsigned char __DEFAULT_FN_ATTRS 456 _mm_aesdecwide128kl_u8(__m128i __odata[8], const __m128i __idata[8], const void* __h) { 457 return __builtin_ia32_aesdecwide128kl_u8((__v2di *)__odata, 458 (const __v2di *)__idata, __h); 459 } 460 461 /// Decrypt __idata[0] to __idata[7] using 256-bit AES key indicated by handle 462 /// at __h and store each resultant block back from __odata to __odata+7. And 463 /// return the affected ZF flag status. 464 /// 465 /// \headerfile <x86intrin.h> 466 /// 467 /// This intrinsic corresponds to the <c> AESDECWIDE256KL </c> instructions. 468 /// 469 /// \operation 470 /// Handle[511:0] := MEM[__h+511:__h] 471 /// IllegalHandle = ( HandleReservedBitSet (Handle[511:0]) || 472 /// (Handle[127:0] AND (CPL > 0)) || 473 /// Handle[255:128] || 474 /// HandleKeyType (Handle) != HANDLE_KEY_TYPE_AES512 ) 475 /// If (IllegalHandle) 476 /// ZF := 1 477 /// ELSE 478 /// (UnwrappedKey, Authentic) := UnwrapKeyAndAuthenticate512 (Handle[511:0], IWKey) 479 /// IF Authentic == 0 480 /// ZF := 1 481 /// ELSE 482 /// FOR i := 0 to 7 483 /// __odata[i] := AES256Decrypt (__idata[i], UnwrappedKey) 484 /// ENDFOR 485 /// ZF := 0 486 /// FI 487 /// FI 488 /// dst := ZF 489 /// OF := 0 490 /// SF := 0 491 /// AF := 0 492 /// PF := 0 493 /// CF := 0 494 /// \endoperation 495 static __inline__ unsigned char __DEFAULT_FN_ATTRS 496 _mm_aesdecwide256kl_u8(__m128i __odata[8], const __m128i __idata[8], const void* __h) { 497 return __builtin_ia32_aesdecwide256kl_u8((__v2di *)__odata, 498 (const __v2di *)__idata, __h); 499 } 500 501 #undef __DEFAULT_FN_ATTRS 502 503 #endif /* !(defined(_MSC_VER) || defined(__SCE__)) || __has_feature(modules) \ 504 || defined(__WIDEKL__) */ 505 506 #endif /* _KEYLOCKERINTRIN_H */ 507