1 /** @file
2   Implement TPM2 help.
3 
4 Copyright (c) 2013 - 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 <IndustryStandard/UefiTcgPlatform.h>
16 #include <Library/Tpm2CommandLib.h>
17 #include <Library/Tpm2DeviceLib.h>
18 #include <Library/BaseMemoryLib.h>
19 #include <Library/BaseLib.h>
20 #include <Library/DebugLib.h>
21 
22 typedef struct {
23   TPMI_ALG_HASH              HashAlgo;
24   UINT16                     HashSize;
25 } INTERNAL_HASH_INFO;
26 
27 STATIC INTERNAL_HASH_INFO mHashInfo[] = {
28   {TPM_ALG_SHA1,          SHA1_DIGEST_SIZE},
29   {TPM_ALG_SHA256,        SHA256_DIGEST_SIZE},
30   {TPM_ALG_SM3_256,       SM3_256_DIGEST_SIZE},
31   {TPM_ALG_SHA384,        SHA384_DIGEST_SIZE},
32   {TPM_ALG_SHA512,        SHA512_DIGEST_SIZE},
33 };
34 
35 /**
36   Return size of digest.
37 
38   @param[in] HashAlgo  Hash algorithm
39 
40   @return size of digest
41 **/
42 UINT16
43 EFIAPI
GetHashSizeFromAlgo(IN TPMI_ALG_HASH HashAlgo)44 GetHashSizeFromAlgo (
45   IN TPMI_ALG_HASH    HashAlgo
46   )
47 {
48   UINTN  Index;
49 
50   for (Index = 0; Index < sizeof(mHashInfo)/sizeof(mHashInfo[0]); Index++) {
51     if (mHashInfo[Index].HashAlgo == HashAlgo) {
52       return mHashInfo[Index].HashSize;
53     }
54   }
55   return 0;
56 }
57 
58 /**
59   Copy AuthSessionIn to TPM2 command buffer.
60 
61   @param [in]  AuthSessionIn   Input AuthSession data
62   @param [out] AuthSessionOut  Output AuthSession data in TPM2 command buffer
63 
64   @return AuthSession size
65 **/
66 UINT32
67 EFIAPI
CopyAuthSessionCommand(IN TPMS_AUTH_COMMAND * AuthSessionIn,OPTIONAL OUT UINT8 * AuthSessionOut)68 CopyAuthSessionCommand (
69   IN      TPMS_AUTH_COMMAND         *AuthSessionIn, OPTIONAL
70   OUT     UINT8                     *AuthSessionOut
71   )
72 {
73   UINT8  *Buffer;
74 
75   Buffer = (UINT8 *)AuthSessionOut;
76 
77   //
78   // Add in Auth session
79   //
80   if (AuthSessionIn != NULL) {
81     //  sessionHandle
82     WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32(AuthSessionIn->sessionHandle));
83     Buffer += sizeof(UINT32);
84 
85     // nonce
86     WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (AuthSessionIn->nonce.size));
87     Buffer += sizeof(UINT16);
88 
89     CopyMem (Buffer, AuthSessionIn->nonce.buffer, AuthSessionIn->nonce.size);
90     Buffer += AuthSessionIn->nonce.size;
91 
92     // sessionAttributes
93     *(UINT8 *)Buffer = *(UINT8 *)&AuthSessionIn->sessionAttributes;
94     Buffer++;
95 
96     // hmac
97     WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16 (AuthSessionIn->hmac.size));
98     Buffer += sizeof(UINT16);
99 
100     CopyMem (Buffer, AuthSessionIn->hmac.buffer, AuthSessionIn->hmac.size);
101     Buffer += AuthSessionIn->hmac.size;
102   } else {
103     //  sessionHandle
104     WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32(TPM_RS_PW));
105     Buffer += sizeof(UINT32);
106 
107     // nonce = nullNonce
108     WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16(0));
109     Buffer += sizeof(UINT16);
110 
111     // sessionAttributes = 0
112     *(UINT8 *)Buffer = 0x00;
113     Buffer++;
114 
115     // hmac = nullAuth
116     WriteUnaligned16 ((UINT16 *)Buffer, SwapBytes16(0));
117     Buffer += sizeof(UINT16);
118   }
119 
120   return (UINT32)(UINTN)(Buffer - (UINT8 *)AuthSessionOut);
121 }
122 
123 /**
124   Copy AuthSessionIn from TPM2 response buffer.
125 
126   @param [in]  AuthSessionIn   Input AuthSession data in TPM2 response buffer
127   @param [out] AuthSessionOut  Output AuthSession data
128 
129   @return AuthSession size
130 **/
131 UINT32
132 EFIAPI
CopyAuthSessionResponse(IN UINT8 * AuthSessionIn,OUT TPMS_AUTH_RESPONSE * AuthSessionOut OPTIONAL)133 CopyAuthSessionResponse (
134   IN      UINT8                      *AuthSessionIn,
135   OUT     TPMS_AUTH_RESPONSE         *AuthSessionOut OPTIONAL
136   )
137 {
138   UINT8                      *Buffer;
139   TPMS_AUTH_RESPONSE         LocalAuthSessionOut;
140 
141   if (AuthSessionOut == NULL) {
142     AuthSessionOut = &LocalAuthSessionOut;
143   }
144 
145   Buffer = (UINT8 *)AuthSessionIn;
146 
147   // nonce
148   AuthSessionOut->nonce.size = SwapBytes16 (ReadUnaligned16 ((UINT16 *)Buffer));
149   Buffer += sizeof(UINT16);
150 
151   CopyMem (AuthSessionOut->nonce.buffer, Buffer, AuthSessionOut->nonce.size);
152   Buffer += AuthSessionOut->nonce.size;
153 
154   // sessionAttributes
155   *(UINT8 *)&AuthSessionOut->sessionAttributes = *(UINT8 *)Buffer;
156   Buffer++;
157 
158   // hmac
159   AuthSessionOut->hmac.size = SwapBytes16 (ReadUnaligned16 ((UINT16 *)Buffer));
160   Buffer += sizeof(UINT16);
161 
162   CopyMem (AuthSessionOut->hmac.buffer, Buffer, AuthSessionOut->hmac.size);
163   Buffer += AuthSessionOut->hmac.size;
164 
165   return (UINT32)(UINTN)(Buffer - (UINT8 *)AuthSessionIn);
166 }
167