1 /** @file
2   SHA-384 and SHA-512 Digest Wrapper Implementations over OpenSSL.
3 
4 Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution.  The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
9 
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12 
13 **/
14 
15 #include "InternalCryptLib.h"
16 #include <openssl/sha.h>
17 
18 /**
19   Retrieves the size, in bytes, of the context buffer required for SHA-384 hash operations.
20 
21   @return  The size, in bytes, of the context buffer required for SHA-384 hash operations.
22 
23 **/
24 UINTN
25 EFIAPI
Sha384GetContextSize(VOID)26 Sha384GetContextSize (
27   VOID
28   )
29 {
30   //
31   // Retrieves OpenSSL SHA-384 Context Size
32   //
33   return (UINTN) (sizeof (SHA512_CTX));
34 }
35 
36 /**
37   Initializes user-supplied memory pointed by Sha384Context as SHA-384 hash context for
38   subsequent use.
39 
40   If Sha384Context is NULL, then return FALSE.
41 
42   @param[out]  Sha384Context  Pointer to SHA-384 context being initialized.
43 
44   @retval TRUE   SHA-384 context initialization succeeded.
45   @retval FALSE  SHA-384 context initialization failed.
46 
47 **/
48 BOOLEAN
49 EFIAPI
Sha384Init(OUT VOID * Sha384Context)50 Sha384Init (
51   OUT  VOID  *Sha384Context
52   )
53 {
54   //
55   // Check input parameters.
56   //
57   if (Sha384Context == NULL) {
58     return FALSE;
59   }
60 
61   //
62   // OpenSSL SHA-384 Context Initialization
63   //
64   return (BOOLEAN) (SHA384_Init ((SHA512_CTX *) Sha384Context));
65 }
66 
67 /**
68   Makes a copy of an existing SHA-384 context.
69 
70   If Sha384Context is NULL, then return FALSE.
71   If NewSha384Context is NULL, then return FALSE.
72   If this interface is not supported, then return FALSE.
73 
74   @param[in]  Sha384Context     Pointer to SHA-384 context being copied.
75   @param[out] NewSha384Context  Pointer to new SHA-384 context.
76 
77   @retval TRUE   SHA-384 context copy succeeded.
78   @retval FALSE  SHA-384 context copy failed.
79   @retval FALSE  This interface is not supported.
80 
81 **/
82 BOOLEAN
83 EFIAPI
Sha384Duplicate(IN CONST VOID * Sha384Context,OUT VOID * NewSha384Context)84 Sha384Duplicate (
85   IN   CONST VOID  *Sha384Context,
86   OUT  VOID        *NewSha384Context
87   )
88 {
89   //
90   // Check input parameters.
91   //
92   if (Sha384Context == NULL || NewSha384Context == NULL) {
93     return FALSE;
94   }
95 
96   CopyMem (NewSha384Context, Sha384Context, sizeof (SHA512_CTX));
97 
98   return TRUE;
99 }
100 
101 /**
102   Digests the input data and updates SHA-384 context.
103 
104   This function performs SHA-384 digest on a data buffer of the specified size.
105   It can be called multiple times to compute the digest of long or discontinuous data streams.
106   SHA-384 context should be already correctly intialized by Sha384Init(), and should not be finalized
107   by Sha384Final(). Behavior with invalid context is undefined.
108 
109   If Sha384Context is NULL, then return FALSE.
110 
111   @param[in, out]  Sha384Context  Pointer to the SHA-384 context.
112   @param[in]       Data           Pointer to the buffer containing the data to be hashed.
113   @param[in]       DataSize       Size of Data buffer in bytes.
114 
115   @retval TRUE   SHA-384 data digest succeeded.
116   @retval FALSE  SHA-384 data digest failed.
117 
118 **/
119 BOOLEAN
120 EFIAPI
Sha384Update(IN OUT VOID * Sha384Context,IN CONST VOID * Data,IN UINTN DataSize)121 Sha384Update (
122   IN OUT  VOID        *Sha384Context,
123   IN      CONST VOID  *Data,
124   IN      UINTN       DataSize
125   )
126 {
127   //
128   // Check input parameters.
129   //
130   if (Sha384Context == NULL) {
131     return FALSE;
132   }
133 
134   //
135   // Check invalid parameters, in case that only DataLength was checked in OpenSSL
136   //
137   if (Data == NULL && DataSize != 0) {
138     return FALSE;
139   }
140 
141   //
142   // OpenSSL SHA-384 Hash Update
143   //
144   return (BOOLEAN) (SHA384_Update ((SHA512_CTX *) Sha384Context, Data, DataSize));
145 }
146 
147 /**
148   Completes computation of the SHA-384 digest value.
149 
150   This function completes SHA-384 hash computation and retrieves the digest value into
151   the specified memory. After this function has been called, the SHA-384 context cannot
152   be used again.
153   SHA-384 context should be already correctly intialized by Sha384Init(), and should not be
154   finalized by Sha384Final(). Behavior with invalid SHA-384 context is undefined.
155 
156   If Sha384Context is NULL, then return FALSE.
157   If HashValue is NULL, then return FALSE.
158 
159   @param[in, out]  Sha384Context  Pointer to the SHA-384 context.
160   @param[out]      HashValue      Pointer to a buffer that receives the SHA-384 digest
161                                   value (48 bytes).
162 
163   @retval TRUE   SHA-384 digest computation succeeded.
164   @retval FALSE  SHA-384 digest computation failed.
165 
166 **/
167 BOOLEAN
168 EFIAPI
Sha384Final(IN OUT VOID * Sha384Context,OUT UINT8 * HashValue)169 Sha384Final (
170   IN OUT  VOID   *Sha384Context,
171   OUT     UINT8  *HashValue
172   )
173 {
174   //
175   // Check input parameters.
176   //
177   if (Sha384Context == NULL || HashValue == NULL) {
178     return FALSE;
179   }
180 
181   //
182   // OpenSSL SHA-384 Hash Finalization
183   //
184   return (BOOLEAN) (SHA384_Final (HashValue, (SHA512_CTX *) Sha384Context));
185 }
186 
187 /**
188   Retrieves the size, in bytes, of the context buffer required for SHA-512 hash operations.
189 
190   @return  The size, in bytes, of the context buffer required for SHA-512 hash operations.
191 
192 **/
193 UINTN
194 EFIAPI
Sha512GetContextSize(VOID)195 Sha512GetContextSize (
196   VOID
197   )
198 {
199   //
200   // Retrieves OpenSSL SHA-512 Context Size
201   //
202   return (UINTN) (sizeof (SHA512_CTX));
203 }
204 
205 /**
206   Initializes user-supplied memory pointed by Sha512Context as SHA-512 hash context for
207   subsequent use.
208 
209   If Sha512Context is NULL, then return FALSE.
210 
211   @param[out]  Sha512Context  Pointer to SHA-512 context being initialized.
212 
213   @retval TRUE   SHA-512 context initialization succeeded.
214   @retval FALSE  SHA-512 context initialization failed.
215 
216 **/
217 BOOLEAN
218 EFIAPI
Sha512Init(OUT VOID * Sha512Context)219 Sha512Init (
220   OUT  VOID  *Sha512Context
221   )
222 {
223   //
224   // Check input parameters.
225   //
226   if (Sha512Context == NULL) {
227     return FALSE;
228   }
229 
230   //
231   // OpenSSL SHA-512 Context Initialization
232   //
233   return (BOOLEAN) (SHA512_Init ((SHA512_CTX *) Sha512Context));
234 }
235 
236 /**
237   Makes a copy of an existing SHA-512 context.
238 
239   If Sha512Context is NULL, then return FALSE.
240   If NewSha512Context is NULL, then return FALSE.
241   If this interface is not supported, then return FALSE.
242 
243   @param[in]  Sha512Context     Pointer to SHA-512 context being copied.
244   @param[out] NewSha512Context  Pointer to new SHA-512 context.
245 
246   @retval TRUE   SHA-512 context copy succeeded.
247   @retval FALSE  SHA-512 context copy failed.
248   @retval FALSE  This interface is not supported.
249 
250 **/
251 BOOLEAN
252 EFIAPI
Sha512Duplicate(IN CONST VOID * Sha512Context,OUT VOID * NewSha512Context)253 Sha512Duplicate (
254   IN   CONST VOID  *Sha512Context,
255   OUT  VOID        *NewSha512Context
256   )
257 {
258   //
259   // Check input parameters.
260   //
261   if (Sha512Context == NULL || NewSha512Context == NULL) {
262     return FALSE;
263   }
264 
265   CopyMem (NewSha512Context, Sha512Context, sizeof (SHA512_CTX));
266 
267   return TRUE;
268 }
269 
270 /**
271   Digests the input data and updates SHA-512 context.
272 
273   This function performs SHA-512 digest on a data buffer of the specified size.
274   It can be called multiple times to compute the digest of long or discontinuous data streams.
275   SHA-512 context should be already correctly intialized by Sha512Init(), and should not be finalized
276   by Sha512Final(). Behavior with invalid context is undefined.
277 
278   If Sha512Context is NULL, then return FALSE.
279 
280   @param[in, out]  Sha512Context  Pointer to the SHA-512 context.
281   @param[in]       Data           Pointer to the buffer containing the data to be hashed.
282   @param[in]       DataSize       Size of Data buffer in bytes.
283 
284   @retval TRUE   SHA-512 data digest succeeded.
285   @retval FALSE  SHA-512 data digest failed.
286 
287 **/
288 BOOLEAN
289 EFIAPI
Sha512Update(IN OUT VOID * Sha512Context,IN CONST VOID * Data,IN UINTN DataSize)290 Sha512Update (
291   IN OUT  VOID        *Sha512Context,
292   IN      CONST VOID  *Data,
293   IN      UINTN       DataSize
294   )
295 {
296   //
297   // Check input parameters.
298   //
299   if (Sha512Context == NULL) {
300     return FALSE;
301   }
302 
303   //
304   // Check invalid parameters, in case that only DataLength was checked in OpenSSL
305   //
306   if (Data == NULL && DataSize != 0) {
307     return FALSE;
308   }
309 
310   //
311   // OpenSSL SHA-512 Hash Update
312   //
313   return (BOOLEAN) (SHA512_Update ((SHA512_CTX *) Sha512Context, Data, DataSize));
314 }
315 
316 /**
317   Completes computation of the SHA-512 digest value.
318 
319   This function completes SHA-512 hash computation and retrieves the digest value into
320   the specified memory. After this function has been called, the SHA-512 context cannot
321   be used again.
322   SHA-512 context should be already correctly intialized by Sha512Init(), and should not be
323   finalized by Sha512Final(). Behavior with invalid SHA-512 context is undefined.
324 
325   If Sha512Context is NULL, then return FALSE.
326   If HashValue is NULL, then return FALSE.
327 
328   @param[in, out]  Sha512Context  Pointer to the SHA-512 context.
329   @param[out]      HashValue      Pointer to a buffer that receives the SHA-512 digest
330                                   value (64 bytes).
331 
332   @retval TRUE   SHA-512 digest computation succeeded.
333   @retval FALSE  SHA-512 digest computation failed.
334 
335 **/
336 BOOLEAN
337 EFIAPI
Sha512Final(IN OUT VOID * Sha512Context,OUT UINT8 * HashValue)338 Sha512Final (
339   IN OUT  VOID   *Sha512Context,
340   OUT     UINT8  *HashValue
341   )
342 {
343   //
344   // Check input parameters.
345   //
346   if (Sha512Context == NULL || HashValue == NULL) {
347     return FALSE;
348   }
349 
350   //
351   // OpenSSL SHA-512 Hash Finalization
352   //
353   return (BOOLEAN) (SHA384_Final (HashValue, (SHA512_CTX *) Sha512Context));
354 }
355