]> git.proxmox.com Git - mirror_edk2.git/blob - MdePkg/Library/DxeRngLib/DxeRngLib.c
MdePkg: Apply uncrustify changes
[mirror_edk2.git] / MdePkg / Library / DxeRngLib / DxeRngLib.c
1 /** @file
2 Provides an implementation of the library class RngLib that uses the Rng protocol.
3
4 Copyright (c) Microsoft Corporation. All rights reserved.
5 SPDX-License-Identifier: BSD-2-Clause-Patent
6
7 **/
8 #include <Uefi.h>
9 #include <Library/UefiBootServicesTableLib.h>
10 #include <Library/DebugLib.h>
11 #include <Library/RngLib.h>
12 #include <Protocol/Rng.h>
13
14 /**
15 Routine Description:
16
17 Generates a random number via the NIST
18 800-9A algorithm. Refer to
19 http://csrc.nist.gov/groups/STM/cavp/documents/drbg/DRBGVS.pdf
20 for more information.
21
22 @param[out] Buffer Buffer to receive the random number.
23 @param[in] BufferSize Number of bytes in Buffer.
24
25 @retval EFI_SUCCESS or underlying failure code.
26 **/
27 STATIC
28 EFI_STATUS
29 GenerateRandomNumberViaNist800Algorithm (
30 OUT UINT8 *Buffer,
31 IN UINTN BufferSize
32 )
33 {
34 EFI_STATUS Status;
35 EFI_RNG_PROTOCOL *RngProtocol;
36
37 RngProtocol = NULL;
38
39 if (Buffer == NULL) {
40 DEBUG ((DEBUG_ERROR, "%a: Buffer == NULL.\n", __FUNCTION__));
41 return EFI_INVALID_PARAMETER;
42 }
43
44 Status = gBS->LocateProtocol (&gEfiRngProtocolGuid, NULL, (VOID **)&RngProtocol);
45 if (EFI_ERROR (Status) || (RngProtocol == NULL)) {
46 DEBUG ((DEBUG_ERROR, "%a: Could not locate RNG prototocol, Status = %r\n", __FUNCTION__, Status));
47 return Status;
48 }
49
50 Status = RngProtocol->GetRNG (RngProtocol, &gEfiRngAlgorithmSp80090Ctr256Guid, BufferSize, Buffer);
51 DEBUG ((DEBUG_INFO, "%a: GetRNG algorithm CTR-256 - Status = %r\n", __FUNCTION__, Status));
52 if (!EFI_ERROR (Status)) {
53 return Status;
54 }
55
56 Status = RngProtocol->GetRNG (RngProtocol, &gEfiRngAlgorithmSp80090Hmac256Guid, BufferSize, Buffer);
57 DEBUG ((DEBUG_INFO, "%a: GetRNG algorithm HMAC-256 - Status = %r\n", __FUNCTION__, Status));
58 if (!EFI_ERROR (Status)) {
59 return Status;
60 }
61
62 Status = RngProtocol->GetRNG (RngProtocol, &gEfiRngAlgorithmSp80090Hash256Guid, BufferSize, Buffer);
63 DEBUG ((DEBUG_INFO, "%a: GetRNG algorithm Hash-256 - Status = %r\n", __FUNCTION__, Status));
64 if (!EFI_ERROR (Status)) {
65 return Status;
66 }
67
68 // If all the other methods have failed, use the default method from the RngProtocol
69 Status = RngProtocol->GetRNG (RngProtocol, NULL, BufferSize, Buffer);
70 DEBUG ((DEBUG_INFO, "%a: GetRNG algorithm Hash-256 - Status = %r\n", __FUNCTION__, Status));
71 if (!EFI_ERROR (Status)) {
72 return Status;
73 }
74
75 // If we get to this point, we have failed
76 DEBUG ((DEBUG_ERROR, "%a: GetRNG() failed, staus = %r\n", __FUNCTION__, Status));
77
78 return Status;
79 }// GenerateRandomNumberViaNist800Algorithm()
80
81 /**
82 Generates a 16-bit random number.
83
84 if Rand is NULL, return FALSE.
85
86 @param[out] Rand Buffer pointer to store the 16-bit random value.
87
88 @retval TRUE Random number generated successfully.
89 @retval FALSE Failed to generate the random number.
90
91 **/
92 BOOLEAN
93 EFIAPI
94 GetRandomNumber16 (
95 OUT UINT16 *Rand
96 )
97 {
98 EFI_STATUS Status;
99
100 if (Rand == NULL) {
101 return FALSE;
102 }
103
104 Status = GenerateRandomNumberViaNist800Algorithm ((UINT8 *)Rand, sizeof (UINT16));
105 if (EFI_ERROR (Status)) {
106 return FALSE;
107 }
108
109 return TRUE;
110 }
111
112 /**
113 Generates a 32-bit random number.
114
115 if Rand is NULL, return FALSE.
116
117 @param[out] Rand Buffer pointer to store the 32-bit random value.
118
119 @retval TRUE Random number generated successfully.
120 @retval FALSE Failed to generate the random number.
121
122 **/
123 BOOLEAN
124 EFIAPI
125 GetRandomNumber32 (
126 OUT UINT32 *Rand
127 )
128 {
129 EFI_STATUS Status;
130
131 if (Rand == NULL) {
132 return FALSE;
133 }
134
135 Status = GenerateRandomNumberViaNist800Algorithm ((UINT8 *)Rand, sizeof (UINT32));
136 if (EFI_ERROR (Status)) {
137 return FALSE;
138 }
139
140 return TRUE;
141 }
142
143 /**
144 Generates a 64-bit random number.
145
146 if Rand is NULL, return FALSE.
147
148 @param[out] Rand Buffer pointer to store the 64-bit random value.
149
150 @retval TRUE Random number generated successfully.
151 @retval FALSE Failed to generate the random number.
152
153 **/
154 BOOLEAN
155 EFIAPI
156 GetRandomNumber64 (
157 OUT UINT64 *Rand
158 )
159 {
160 EFI_STATUS Status;
161
162 if (Rand == NULL) {
163 return FALSE;
164 }
165
166 Status = GenerateRandomNumberViaNist800Algorithm ((UINT8 *)Rand, sizeof (UINT64));
167 if (EFI_ERROR (Status)) {
168 return FALSE;
169 }
170
171 return TRUE;
172 }
173
174 /**
175 Generates a 128-bit random number.
176
177 if Rand is NULL, return FALSE.
178
179 @param[out] Rand Buffer pointer to store the 128-bit random value.
180
181 @retval TRUE Random number generated successfully.
182 @retval FALSE Failed to generate the random number.
183
184 **/
185 BOOLEAN
186 EFIAPI
187 GetRandomNumber128 (
188 OUT UINT64 *Rand
189 )
190 {
191 EFI_STATUS Status;
192
193 if (Rand == NULL) {
194 return FALSE;
195 }
196
197 Status = GenerateRandomNumberViaNist800Algorithm ((UINT8 *)Rand, 2 * sizeof (UINT64));
198 if (EFI_ERROR (Status)) {
199 return FALSE;
200 }
201
202 return TRUE;
203 }