]>
git.proxmox.com Git - mirror_edk2.git/blob - SecurityPkg/RandomNumberGenerator/RngDxe/Rand/RdRand.c
2 Support routines for RDRAND instruction access.
4 Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR>
5 (C) Copyright 2015 Hewlett Packard Enterprise Development LP<BR>
6 SPDX-License-Identifier: BSD-2-Clause-Patent
9 #include <Library/RngLib.h>
13 #include "RngDxeInternals.h"
16 Creates a 128bit random value that is fully forward and backward prediction resistant,
17 suitable for seeding a NIST SP800-90 Compliant, FIPS 1402-2 certifiable SW DRBG.
18 This function takes multiple random numbers through RDRAND without intervening
19 delays to ensure reseeding and performs AES-CBC-MAC over the data to compute the
22 @param[out] SeedBuffer Pointer to a 128bit buffer to store the random seed.
24 @retval EFI_SUCCESS Random seed generation succeeded.
25 @retval EFI_NOT_READY Failed to request random bytes.
43 // Chose an arbitrary key and zero the feed_forward_value (FFV)
45 for (Index
= 0; Index
< 16; Index
++) {
46 Key
[Index
] = (UINT8
) Index
;
51 // Perform CBC_MAC over 32 * 128 bit values, with 10us gaps between 128 bit value
52 // The 10us gaps will ensure multiple reseeds within the HW RNG with a large design margin.
54 for (Index
= 0; Index
< 32; Index
++) {
55 MicroSecondDelay (10);
56 Status
= RngGetBytes (16, RandByte
);
57 if (EFI_ERROR (Status
)) {
62 // Perform XOR operations on two 128-bit value.
64 for (Index2
= 0; Index2
< 16; Index2
++) {
65 Xored
[Index2
] = RandByte
[Index2
] ^ Ffv
[Index2
];
68 AesEncrypt (Key
, Xored
, Ffv
);
71 for (Index
= 0; Index
< 16; Index
++) {
72 SeedBuffer
[Index
] = Ffv
[Index
];
79 Generate high-quality entropy source through RDRAND.
81 @param[in] Length Size of the buffer, in bytes, to fill with.
82 @param[out] Entropy Pointer to the buffer to store the entropy data.
84 @retval EFI_SUCCESS Entropy generation succeeded.
85 @retval EFI_NOT_READY Failed to request random data.
90 RdRandGenerateEntropy (
100 Status
= EFI_NOT_READY
;
101 BlockCount
= Length
/ 16;
102 Ptr
= (UINT8
*)Entropy
;
105 // Generate high-quality seed for DRBG Entropy
107 while (BlockCount
> 0) {
108 Status
= RdRandGetSeed128 (Seed
);
109 if (EFI_ERROR (Status
)) {
112 CopyMem (Ptr
, Seed
, 16);
119 // Populate the remained data as request.
121 Status
= RdRandGetSeed128 (Seed
);
122 if (EFI_ERROR (Status
)) {
125 CopyMem (Ptr
, Seed
, (Length
% 16));