1
2 /*
3 * Licensed Materials - Property of IBM
4 *
5 * trousers - An open source TCG Software Stack
6 *
7 * (C) Copyright International Business Machines Corp. 2004-2006
8 *
9 */
10
11 #include <stdlib.h>
12 #include <stdio.h>
13 #include <string.h>
14 #include <inttypes.h>
15
16 #include "trousers/tss.h"
17 #include "trousers/trousers.h"
18 #include "trousers_types.h"
19 #include "spi_utils.h"
20 #include "capabilities.h"
21 #include "tsplog.h"
22 #include "obj.h"
23
24
25 TSS_RESULT
Tspi_TPM_SelfTestFull(TSS_HTPM hTPM)26 Tspi_TPM_SelfTestFull(TSS_HTPM hTPM) /* in */
27 {
28 TSS_RESULT result;
29 TSS_HCONTEXT tspContext;
30
31 if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext)))
32 return result;
33
34 return TCS_API(tspContext)->SelfTestFull(tspContext);
35 }
36
37 TSS_RESULT
Tspi_TPM_CertifySelfTest(TSS_HTPM hTPM,TSS_HKEY hKey,TSS_VALIDATION * pValidationData)38 Tspi_TPM_CertifySelfTest(TSS_HTPM hTPM, /* in */
39 TSS_HKEY hKey, /* in */
40 TSS_VALIDATION *pValidationData) /* in, out */
41 {
42 TCPA_RESULT result;
43 TPM_AUTH keyAuth;
44 UINT64 offset = 0;
45 TCPA_DIGEST digest;
46 TCPA_NONCE antiReplay;
47 UINT32 outDataSize;
48 BYTE *outData;
49 TSS_HPOLICY hPolicy;
50 TCS_KEY_HANDLE keyTCSKeyHandle;
51 BYTE *keyData = NULL;
52 UINT32 keyDataSize;
53 TSS_KEY keyContainer;
54 TPM_AUTH *pKeyAuth;
55 TSS_BOOL useAuth;
56 TSS_HCONTEXT tspContext;
57 Trspi_HashCtx hashCtx;
58
59
60 if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext)))
61 return result;
62
63 if ((result = obj_rsakey_get_policy(hKey, TSS_POLICY_USAGE,
64 &hPolicy, &useAuth)))
65 return result;
66
67 if ((result = obj_rsakey_get_tcs_handle(hKey, &keyTCSKeyHandle)))
68 return result;
69
70 if (pValidationData == NULL) {
71 if ((result = get_local_random(tspContext, FALSE, sizeof(TCPA_NONCE),
72 (BYTE **)antiReplay.nonce))) {
73 LogError("Failed creating random nonce");
74 return TSPERR(TSS_E_INTERNAL_ERROR);
75 }
76 } else {
77 if (pValidationData->ulExternalDataLength < sizeof(antiReplay.nonce))
78 return TSPERR(TSS_E_BAD_PARAMETER);
79
80 memcpy(antiReplay.nonce, pValidationData->rgbExternalData,
81 sizeof(antiReplay.nonce));
82 }
83
84 if (useAuth) {
85 LogDebug("Uses Auth");
86
87 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1);
88 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_CertifySelfTest);
89 result |= Trspi_HashUpdate(&hashCtx, sizeof(TCPA_NONCE), antiReplay.nonce);
90 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest)))
91 return result;
92
93 if ((result = secret_PerformAuth_OIAP(hKey, TPM_ORD_CertifySelfTest, hPolicy, FALSE,
94 &digest, &keyAuth)))
95 return result;
96 pKeyAuth = &keyAuth;
97 } else {
98 LogDebug("No Auth");
99 pKeyAuth = NULL;
100 }
101
102 if ((result = TCS_API(tspContext)->CertifySelfTest(tspContext, keyTCSKeyHandle, antiReplay,
103 pKeyAuth, &outDataSize, &outData)))
104 return result;
105
106 /* validate auth */
107 if (useAuth) {
108 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1);
109 result |= Trspi_Hash_UINT32(&hashCtx, result);
110 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_CertifySelfTest);
111 result |= Trspi_Hash_UINT32(&hashCtx, outDataSize);
112 result |= Trspi_HashUpdate(&hashCtx, outDataSize, outData);
113 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest)))
114 return result;
115
116 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &keyAuth)))
117 return result;
118 }
119
120 if (pValidationData == NULL) {
121 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_KEY_BLOB,
122 TSS_TSPATTRIB_KEYBLOB_BLOB, &keyDataSize, &keyData))) {
123 LogError("Failed call to GetAttribData to get key blob");
124 return TSPERR(TSS_E_INTERNAL_ERROR);
125 }
126
127 offset = 0;
128 __tspi_memset(&keyContainer, 0, sizeof(TSS_KEY));
129 if ((result = UnloadBlob_TSS_KEY(&offset, keyData, &keyContainer)))
130 return result;
131
132 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1);
133 result |= Trspi_HashUpdate(&hashCtx, strlen("Test Passed"), (BYTE *)"Test Passed");
134 result |= Trspi_HashUpdate(&hashCtx, sizeof(TCPA_NONCE), antiReplay.nonce);
135 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_CertifySelfTest);
136 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest)))
137 return result;
138
139 if ((result = Trspi_Verify(TSS_HASH_SHA1, digest.digest, 20,
140 keyContainer.pubKey.key, keyContainer.pubKey.keyLength,
141 outData, outDataSize))) {
142 free(outData);
143 free_key_refs(&keyContainer);
144 return TSPERR(TSS_E_VERIFICATION_FAILED);
145 }
146
147 } else {
148 pValidationData->ulDataLength = sizeof(TCPA_NONCE) + sizeof(UINT32) +
149 strlen("Test Passed");
150 pValidationData->rgbData = calloc_tspi(tspContext, pValidationData->ulDataLength);
151 if (pValidationData->rgbData == NULL) {
152 LogError("malloc of %u bytes failed.", pValidationData->ulDataLength);
153 pValidationData->ulDataLength = 0;
154 return TSPERR(TSS_E_OUTOFMEMORY);
155 }
156 offset = 0;
157 Trspi_LoadBlob(&offset, strlen("Test Passed"), pValidationData->rgbData,
158 (BYTE *)"Test Passed");
159 Trspi_LoadBlob(&offset, sizeof(TCPA_NONCE), pValidationData->rgbData,
160 antiReplay.nonce);
161 Trspi_LoadBlob_UINT32(&offset, TPM_ORD_CertifySelfTest, pValidationData->rgbData);
162 pValidationData->ulValidationDataLength = outDataSize;
163 pValidationData->rgbValidationData = calloc_tspi(tspContext, outDataSize);
164 if (pValidationData->rgbValidationData == NULL) {
165 free_tspi(tspContext, pValidationData->rgbData);
166 pValidationData->rgbData = NULL;
167 pValidationData->ulDataLength = 0;
168 LogError("malloc of %u bytes failed.",
169 pValidationData->ulValidationDataLength);
170 pValidationData->ulValidationDataLength = 0;
171 return TSPERR(TSS_E_OUTOFMEMORY);
172 }
173 memcpy(pValidationData->rgbValidationData, outData, outDataSize);
174 free(outData);
175 }
176
177 return TSS_SUCCESS;
178 }
179
180 TSS_RESULT
Tspi_TPM_GetTestResult(TSS_HTPM hTPM,UINT32 * pulTestResultLength,BYTE ** prgbTestResult)181 Tspi_TPM_GetTestResult(TSS_HTPM hTPM, /* in */
182 UINT32 * pulTestResultLength, /* out */
183 BYTE ** prgbTestResult) /* out */
184 {
185 TSS_HCONTEXT tspContext;
186 TSS_RESULT result;
187
188 if (pulTestResultLength == NULL || prgbTestResult == NULL)
189 return TSPERR(TSS_E_BAD_PARAMETER);
190
191 if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext)))
192 return result;
193
194 if ((result = TCS_API(tspContext)->GetTestResult(tspContext, pulTestResultLength,
195 prgbTestResult)))
196 return result;
197
198 if ((result = __tspi_add_mem_entry(tspContext, *prgbTestResult))) {
199 free(*prgbTestResult);
200 *prgbTestResult = NULL;
201 *pulTestResultLength = 0;
202 }
203
204 return TSS_SUCCESS;
205 }
206
207