]> git.proxmox.com Git - mirror_edk2.git/blame - SecurityPkg/Library/Tpm2CommandLib/Tpm2Help.c
UefiCpuPkg: Move AsmRelocateApLoopStart from Mpfuncs.nasm to AmdSev.nasm
[mirror_edk2.git] / SecurityPkg / Library / Tpm2CommandLib / Tpm2Help.c
CommitLineData
c1d93242
JY
1/** @file\r
2 Implement TPM2 help.\r
3\r
dd577319 4Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved. <BR>\r
289b714b 5SPDX-License-Identifier: BSD-2-Clause-Patent\r
c1d93242
JY
6\r
7**/\r
8\r
9#include <IndustryStandard/UefiTcgPlatform.h>\r
10#include <Library/Tpm2CommandLib.h>\r
11#include <Library/Tpm2DeviceLib.h>\r
12#include <Library/BaseMemoryLib.h>\r
13#include <Library/BaseLib.h>\r
14#include <Library/DebugLib.h>\r
15\r
16typedef struct {\r
c411b485
MK
17 TPMI_ALG_HASH HashAlgo;\r
18 UINT16 HashSize;\r
19 UINT32 HashMask;\r
c1d93242
JY
20} INTERNAL_HASH_INFO;\r
21\r
c411b485
MK
22STATIC INTERNAL_HASH_INFO mHashInfo[] = {\r
23 { TPM_ALG_SHA1, SHA1_DIGEST_SIZE, HASH_ALG_SHA1 },\r
24 { TPM_ALG_SHA256, SHA256_DIGEST_SIZE, HASH_ALG_SHA256 },\r
25 { TPM_ALG_SM3_256, SM3_256_DIGEST_SIZE, HASH_ALG_SM3_256 },\r
26 { TPM_ALG_SHA384, SHA384_DIGEST_SIZE, HASH_ALG_SHA384 },\r
27 { TPM_ALG_SHA512, SHA512_DIGEST_SIZE, HASH_ALG_SHA512 },\r
c1d93242
JY
28};\r
29\r
30/**\r
31 Return size of digest.\r
32\r
33 @param[in] HashAlgo Hash algorithm\r
34\r
35 @return size of digest\r
36**/\r
37UINT16\r
38EFIAPI\r
39GetHashSizeFromAlgo (\r
c411b485 40 IN TPMI_ALG_HASH HashAlgo\r
c1d93242
JY
41 )\r
42{\r
43 UINTN Index;\r
44\r
c411b485 45 for (Index = 0; Index < sizeof (mHashInfo)/sizeof (mHashInfo[0]); Index++) {\r
c1d93242
JY
46 if (mHashInfo[Index].HashAlgo == HashAlgo) {\r
47 return mHashInfo[Index].HashSize;\r
48 }\r
49 }\r
c411b485 50\r
c1d93242
JY
51 return 0;\r
52}\r
53\r
b8ae1f4d
SZ
54/**\r
55 Get hash mask from algorithm.\r
56\r
57 @param[in] HashAlgo Hash algorithm\r
58\r
59 @return Hash mask\r
60**/\r
61UINT32\r
62EFIAPI\r
63GetHashMaskFromAlgo (\r
c411b485 64 IN TPMI_ALG_HASH HashAlgo\r
b8ae1f4d
SZ
65 )\r
66{\r
67 UINTN Index;\r
68\r
c411b485 69 for (Index = 0; Index < sizeof (mHashInfo)/sizeof (mHashInfo[0]); Index++) {\r
b8ae1f4d
SZ
70 if (mHashInfo[Index].HashAlgo == HashAlgo) {\r
71 return mHashInfo[Index].HashMask;\r
72 }\r
73 }\r
c411b485 74\r
b8ae1f4d
SZ
75 return 0;\r
76}\r
77\r
c1d93242
JY
78/**\r
79 Copy AuthSessionIn to TPM2 command buffer.\r
80\r
81 @param [in] AuthSessionIn Input AuthSession data\r
82 @param [out] AuthSessionOut Output AuthSession data in TPM2 command buffer\r
83\r
84 @return AuthSession size\r
85**/\r
86UINT32\r
87EFIAPI\r
88CopyAuthSessionCommand (\r
c411b485
MK
89 IN TPMS_AUTH_COMMAND *AuthSessionIn OPTIONAL,\r
90 OUT UINT8 *AuthSessionOut\r
c1d93242
JY
91 )\r
92{\r
93 UINT8 *Buffer;\r
94\r
95 Buffer = (UINT8 *)AuthSessionOut;\r
b3548d32 96\r
c1d93242
JY
97 //\r
98 // Add in Auth session\r
99 //\r
100 if (AuthSessionIn != NULL) {\r
101 // sessionHandle\r
c411b485
MK
102 WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32 (AuthSessionIn->sessionHandle));\r
103 Buffer += sizeof (UINT32);\r
c1d93242
JY
104\r
105 // nonce\r
106 WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (AuthSessionIn->nonce.size));\r
c411b485 107 Buffer += sizeof (UINT16);\r
c1d93242
JY
108\r
109 CopyMem (Buffer, AuthSessionIn->nonce.buffer, AuthSessionIn->nonce.size);\r
110 Buffer += AuthSessionIn->nonce.size;\r
111\r
112 // sessionAttributes\r
113 *(UINT8 *)Buffer = *(UINT8 *)&AuthSessionIn->sessionAttributes;\r
58dbfc3c 114 Buffer++;\r
c1d93242
JY
115\r
116 // hmac\r
117 WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (AuthSessionIn->hmac.size));\r
c411b485 118 Buffer += sizeof (UINT16);\r
c1d93242
JY
119\r
120 CopyMem (Buffer, AuthSessionIn->hmac.buffer, AuthSessionIn->hmac.size);\r
121 Buffer += AuthSessionIn->hmac.size;\r
122 } else {\r
123 // sessionHandle\r
c411b485
MK
124 WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32 (TPM_RS_PW));\r
125 Buffer += sizeof (UINT32);\r
c1d93242
JY
126\r
127 // nonce = nullNonce\r
c411b485
MK
128 WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (0));\r
129 Buffer += sizeof (UINT16);\r
c1d93242
JY
130\r
131 // sessionAttributes = 0\r
132 *(UINT8 *)Buffer = 0x00;\r
58dbfc3c 133 Buffer++;\r
c1d93242
JY
134\r
135 // hmac = nullAuth\r
c411b485
MK
136 WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (0));\r
137 Buffer += sizeof (UINT16);\r
c1d93242
JY
138 }\r
139\r
4333b99d 140 return (UINT32)((UINTN)Buffer - (UINTN)AuthSessionOut);\r
c1d93242
JY
141}\r
142\r
143/**\r
144 Copy AuthSessionIn from TPM2 response buffer.\r
145\r
146 @param [in] AuthSessionIn Input AuthSession data in TPM2 response buffer\r
147 @param [out] AuthSessionOut Output AuthSession data\r
148\r
dd577319
ZC
149 @return 0 copy failed\r
150 else AuthSession size\r
c1d93242
JY
151**/\r
152UINT32\r
153EFIAPI\r
154CopyAuthSessionResponse (\r
c411b485
MK
155 IN UINT8 *AuthSessionIn,\r
156 OUT TPMS_AUTH_RESPONSE *AuthSessionOut OPTIONAL\r
c1d93242
JY
157 )\r
158{\r
c411b485
MK
159 UINT8 *Buffer;\r
160 TPMS_AUTH_RESPONSE LocalAuthSessionOut;\r
c1d93242
JY
161\r
162 if (AuthSessionOut == NULL) {\r
163 AuthSessionOut = &LocalAuthSessionOut;\r
164 }\r
165\r
166 Buffer = (UINT8 *)AuthSessionIn;\r
167\r
168 // nonce\r
169 AuthSessionOut->nonce.size = SwapBytes16 (ReadUnaligned16 ((UINT16 *)Buffer));\r
c411b485
MK
170 Buffer += sizeof (UINT16);\r
171 if (AuthSessionOut->nonce.size > sizeof (TPMU_HA)) {\r
dd577319
ZC
172 DEBUG ((DEBUG_ERROR, "CopyAuthSessionResponse - nonce.size error %x\n", AuthSessionOut->nonce.size));\r
173 return 0;\r
174 }\r
c1d93242
JY
175\r
176 CopyMem (AuthSessionOut->nonce.buffer, Buffer, AuthSessionOut->nonce.size);\r
177 Buffer += AuthSessionOut->nonce.size;\r
178\r
179 // sessionAttributes\r
c411b485 180 *(UINT8 *) &AuthSessionOut->sessionAttributes = *(UINT8 *)Buffer;\r
58dbfc3c 181 Buffer++;\r
c1d93242
JY
182\r
183 // hmac\r
184 AuthSessionOut->hmac.size = SwapBytes16 (ReadUnaligned16 ((UINT16 *)Buffer));\r
c411b485
MK
185 Buffer += sizeof (UINT16);\r
186 if (AuthSessionOut->hmac.size > sizeof (TPMU_HA)) {\r
dd577319
ZC
187 DEBUG ((DEBUG_ERROR, "CopyAuthSessionResponse - hmac.size error %x\n", AuthSessionOut->hmac.size));\r
188 return 0;\r
189 }\r
c1d93242
JY
190\r
191 CopyMem (AuthSessionOut->hmac.buffer, Buffer, AuthSessionOut->hmac.size);\r
192 Buffer += AuthSessionOut->hmac.size;\r
193\r
4333b99d 194 return (UINT32)((UINTN)Buffer - (UINTN)AuthSessionIn);\r
c1d93242 195}\r
d4b9b2c3 196\r
f5e34e37
JY
197/**\r
198 Return if hash alg is supported in HashAlgorithmMask.\r
199\r
200 @param HashAlg Hash algorithm to be checked.\r
201 @param HashAlgorithmMask Bitfield of allowed hash algorithms.\r
202\r
203 @retval TRUE Hash algorithm is supported.\r
204 @retval FALSE Hash algorithm is not supported.\r
205**/\r
206BOOLEAN\r
697c30b1 207EFIAPI\r
c411b485 208IsHashAlgSupportedInHashAlgorithmMask (\r
f5e34e37
JY
209 IN TPMI_ALG_HASH HashAlg,\r
210 IN UINT32 HashAlgorithmMask\r
211 )\r
212{\r
213 switch (HashAlg) {\r
c411b485
MK
214 case TPM_ALG_SHA1:\r
215 if ((HashAlgorithmMask & HASH_ALG_SHA1) != 0) {\r
216 return TRUE;\r
217 }\r
218\r
219 break;\r
220 case TPM_ALG_SHA256:\r
221 if ((HashAlgorithmMask & HASH_ALG_SHA256) != 0) {\r
222 return TRUE;\r
223 }\r
224\r
225 break;\r
226 case TPM_ALG_SHA384:\r
227 if ((HashAlgorithmMask & HASH_ALG_SHA384) != 0) {\r
228 return TRUE;\r
229 }\r
230\r
231 break;\r
232 case TPM_ALG_SHA512:\r
233 if ((HashAlgorithmMask & HASH_ALG_SHA512) != 0) {\r
234 return TRUE;\r
235 }\r
236\r
237 break;\r
238 case TPM_ALG_SM3_256:\r
239 if ((HashAlgorithmMask & HASH_ALG_SM3_256) != 0) {\r
240 return TRUE;\r
241 }\r
242\r
243 break;\r
f5e34e37
JY
244 }\r
245\r
246 return FALSE;\r
247}\r
248\r
249/**\r
250 Copy TPML_DIGEST_VALUES into a buffer\r
251\r
ae1a4284 252 @param[in,out] Buffer Buffer to hold copied TPML_DIGEST_VALUES compact binary.\r
f5e34e37
JY
253 @param[in] DigestList TPML_DIGEST_VALUES to be copied.\r
254 @param[in] HashAlgorithmMask HASH bits corresponding to the desired digests to copy.\r
255\r
256 @return The end of buffer to hold TPML_DIGEST_VALUES.\r
257**/\r
258VOID *\r
259EFIAPI\r
260CopyDigestListToBuffer (\r
c411b485
MK
261 IN OUT VOID *Buffer,\r
262 IN TPML_DIGEST_VALUES *DigestList,\r
263 IN UINT32 HashAlgorithmMask\r
f5e34e37
JY
264 )\r
265{\r
c411b485
MK
266 UINTN Index;\r
267 UINT16 DigestSize;\r
268 UINT32 DigestListCount;\r
269 UINT32 *DigestListCountPtr;\r
270\r
271 DigestListCountPtr = (UINT32 *)Buffer;\r
272 DigestListCount = 0;\r
273 Buffer = (UINT8 *)Buffer + sizeof (DigestList->count);\r
f5e34e37 274 for (Index = 0; Index < DigestList->count; Index++) {\r
c411b485 275 if (!IsHashAlgSupportedInHashAlgorithmMask (DigestList->digests[Index].hashAlg, HashAlgorithmMask)) {\r
e905fbb0 276 DEBUG ((DEBUG_ERROR, "WARNING: TPM2 Event log has HashAlg unsupported by PCR bank (0x%x)\n", DigestList->digests[Index].hashAlg));\r
f5e34e37
JY
277 continue;\r
278 }\r
c411b485
MK
279\r
280 CopyMem (Buffer, &DigestList->digests[Index].hashAlg, sizeof (DigestList->digests[Index].hashAlg));\r
281 Buffer = (UINT8 *)Buffer + sizeof (DigestList->digests[Index].hashAlg);\r
f5e34e37
JY
282 DigestSize = GetHashSizeFromAlgo (DigestList->digests[Index].hashAlg);\r
283 CopyMem (Buffer, &DigestList->digests[Index].digest, DigestSize);\r
284 Buffer = (UINT8 *)Buffer + DigestSize;\r
be93a17b 285 DigestListCount++;\r
f5e34e37 286 }\r
c411b485 287\r
be93a17b 288 WriteUnaligned32 (DigestListCountPtr, DigestListCount);\r
f5e34e37
JY
289\r
290 return Buffer;\r
291}\r
292\r
77e55cf4
JY
293/**\r
294 Get TPML_DIGEST_VALUES data size.\r
295\r
296 @param[in] DigestList TPML_DIGEST_VALUES data.\r
297\r
298 @return TPML_DIGEST_VALUES data size.\r
299**/\r
300UINT32\r
301EFIAPI\r
302GetDigestListSize (\r
c411b485 303 IN TPML_DIGEST_VALUES *DigestList\r
77e55cf4
JY
304 )\r
305{\r
c411b485
MK
306 UINTN Index;\r
307 UINT16 DigestSize;\r
308 UINT32 TotalSize;\r
77e55cf4 309\r
c411b485 310 TotalSize = sizeof (DigestList->count);\r
77e55cf4
JY
311 for (Index = 0; Index < DigestList->count; Index++) {\r
312 DigestSize = GetHashSizeFromAlgo (DigestList->digests[Index].hashAlg);\r
c411b485 313 TotalSize += sizeof (DigestList->digests[Index].hashAlg) + DigestSize;\r
77e55cf4
JY
314 }\r
315\r
316 return TotalSize;\r
317}\r
318\r
d4b9b2c3
JY
319/**\r
320 This function get digest from digest list.\r
321\r
f28ab849
SZ
322 @param[in] HashAlg Digest algorithm\r
323 @param[in] DigestList Digest list\r
324 @param[out] Digest Digest\r
d4b9b2c3 325\r
f28ab849
SZ
326 @retval EFI_SUCCESS Digest is found and returned.\r
327 @retval EFI_NOT_FOUND Digest is not found.\r
d4b9b2c3
JY
328**/\r
329EFI_STATUS\r
330EFIAPI\r
331GetDigestFromDigestList (\r
c411b485
MK
332 IN TPMI_ALG_HASH HashAlg,\r
333 IN TPML_DIGEST_VALUES *DigestList,\r
334 OUT VOID *Digest\r
d4b9b2c3
JY
335 )\r
336{\r
c411b485
MK
337 UINTN Index;\r
338 UINT16 DigestSize;\r
d4b9b2c3
JY
339\r
340 DigestSize = GetHashSizeFromAlgo (HashAlg);\r
341 for (Index = 0; Index < DigestList->count; Index++) {\r
342 if (DigestList->digests[Index].hashAlg == HashAlg) {\r
343 CopyMem (\r
344 Digest,\r
345 &DigestList->digests[Index].digest,\r
346 DigestSize\r
347 );\r
348 return EFI_SUCCESS;\r
349 }\r
350 }\r
351\r
352 return EFI_NOT_FOUND;\r
f28ab849 353}\r