OLD | NEW |
1 /* Copyright (c) 2010 The Chromium OS Authors. All rights reserved. | 1 /* Copyright (c) 2010 The Chromium OS Authors. All rights reserved. |
2 * Use of this source code is governed by a BSD-style license that can be | 2 * Use of this source code is governed by a BSD-style license that can be |
3 * found in the LICENSE file. | 3 * found in the LICENSE file. |
4 * | 4 * |
5 * Functions for querying, manipulating and locking rollback indices | 5 * Functions for querying, manipulating and locking rollback indices |
6 * stored in the TPM NVRAM. | 6 * stored in the TPM NVRAM. |
7 */ | 7 */ |
8 | 8 |
9 #include "rollback_index.h" | 9 #include "rollback_index.h" |
10 | 10 |
(...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
165 | 165 |
166 g_firmware_key_version = firmware_versions >> 16; | 166 g_firmware_key_version = firmware_versions >> 16; |
167 g_firmware_version = firmware_versions && 0xffff; | 167 g_firmware_version = firmware_versions && 0xffff; |
168 g_kernel_key_version = kernel_versions >> 16; | 168 g_kernel_key_version = kernel_versions >> 16; |
169 g_kernel_version = kernel_versions && 0xffff; | 169 g_kernel_version = kernel_versions && 0xffff; |
170 | 170 |
171 return 1; | 171 return 1; |
172 } | 172 } |
173 | 173 |
174 | 174 |
175 void SetupTPM(void) { | 175 int SetupTPM(void) { |
176 uint8_t disable; | 176 uint8_t disable; |
177 uint8_t deactivated; | 177 uint8_t deactivated; |
178 TlclLibinit(); | 178 TlclLibinit(); |
179 TlclStartup(); | 179 TlclStartup(); |
180 /* TODO(gauravsh): The call to self test should probably be deferred. | 180 /* TODO(gauravsh): The call to self test should probably be deferred. |
181 * As per semenzato@chromium.org - | 181 * As per semenzato@chromium.org - |
182 * TlclStartup should be called before the firmware initializes the memory | 182 * TlclStartup should be called before the firmware initializes the memory |
183 * controller, so the selftest can run in parallel with that. Here we should | 183 * controller, so the selftest can run in parallel with that. Here we should |
184 * just call TlclSelftestFull to make sure the self test has | 184 * just call TlclSelftestFull to make sure the self test has |
185 * completed---unless we want to rely on the NVRAM operations being available | 185 * completed---unless we want to rely on the NVRAM operations being available |
186 * before the selftest completes. */ | 186 * before the selftest completes. */ |
187 TlclSelftestfull(); | 187 TlclSelftestfull(); |
188 TlclAssertPhysicalPresence(); | 188 TlclAssertPhysicalPresence(); |
189 /* Check that the TPM is enabled and activated. */ | 189 /* Check that the TPM is enabled and activated. */ |
190 if(TlclGetFlags(&disable, &deactivated) != TPM_SUCCESS) { | 190 if(TlclGetFlags(&disable, &deactivated) != TPM_SUCCESS) { |
191 debug("failed to get TPM flags"); | 191 debug("failed to get TPM flags"); |
192 EnterRecovery(1); | 192 return 1; |
193 } | 193 } |
194 if (disable || deactivated) { | 194 if (disable || deactivated) { |
195 TlclSetEnable(); | 195 TlclSetEnable(); |
196 if (TlclSetDeactivated(0) != TPM_SUCCESS) { | 196 if (TlclSetDeactivated(0) != TPM_SUCCESS) { |
197 debug("failed to activate TPM"); | 197 debug("failed to activate TPM"); |
198 EnterRecovery(1); | 198 return 1; |
199 } | 199 } |
200 } | 200 } |
201 /* We expect this to fail the first time we run on a device, indicating that | 201 /* We expect this to fail the first time we run on a device, indicating that |
202 * the TPM has not been initialized yet. */ | 202 * the TPM has not been initialized yet. */ |
203 if (!GetTPMRollbackIndices()) { | 203 if (!GetTPMRollbackIndices()) { |
204 debug("failed to get rollback indices"); | 204 debug("failed to get rollback indices"); |
205 if (!InitializeSpaces()) { | 205 if (!InitializeSpaces()) { |
206 /* If InitializeSpaces() fails (possibly because it had been executed | 206 /* If InitializeSpaces() fails (possibly because it had been executed |
207 * already), something is wrong. */ | 207 * already), something is wrong. */ |
208 EnterRecovery(1); | 208 return 1; |
209 } | 209 } |
210 } | 210 } |
| 211 |
| 212 return 0; |
211 } | 213 } |
212 | 214 |
213 void GetStoredVersions(int type, uint16_t* key_version, uint16_t* version) { | 215 int GetStoredVersions(int type, uint16_t* key_version, uint16_t* version) { |
| 216 |
| 217 /* TODO: should verify that SetupTPM() has been called. Note that |
| 218 * SetupTPM() does hardware setup AND sets global variables. When we |
| 219 * get down into kernel verification, the hardware setup persists, but |
| 220 * we don't have access to the global variables. So I guess we DO need |
| 221 * to call SetupTPM() there, and have it be smart enough not to redo the |
| 222 * hardware init, but it still needs to re-read the flags... */ |
| 223 |
214 switch (type) { | 224 switch (type) { |
215 case FIRMWARE_VERSIONS: | 225 case FIRMWARE_VERSIONS: |
216 *key_version = g_firmware_key_version; | 226 *key_version = g_firmware_key_version; |
217 *version = g_firmware_version; | 227 *version = g_firmware_version; |
218 break; | 228 break; |
219 case KERNEL_VERSIONS: | 229 case KERNEL_VERSIONS: |
220 *key_version = g_kernel_key_version; | 230 *key_version = g_kernel_key_version; |
221 *version = g_kernel_version; | 231 *version = g_kernel_version; |
222 break; | 232 break; |
223 } | 233 } |
| 234 |
| 235 return 0; |
224 } | 236 } |
225 | 237 |
226 int WriteStoredVersions(int type, uint16_t key_version, uint16_t version) { | 238 int WriteStoredVersions(int type, uint16_t key_version, uint16_t version) { |
227 uint32_t combined_version = (key_version << 16) & version; | 239 uint32_t combined_version = (key_version << 16) & version; |
228 switch (type) { | 240 switch (type) { |
229 case FIRMWARE_VERSIONS: | 241 case FIRMWARE_VERSIONS: |
230 return (TPM_SUCCESS == TlclWrite(FIRMWARE_VERSIONS_NV_INDEX, | 242 return (TPM_SUCCESS != TlclWrite(FIRMWARE_VERSIONS_NV_INDEX, |
231 (uint8_t*) &combined_version, | 243 (uint8_t*) &combined_version, |
232 sizeof(uint32_t))); | 244 sizeof(uint32_t))); |
233 break; | 245 |
234 case KERNEL_VERSIONS: | 246 case KERNEL_VERSIONS: |
235 return (TPM_SUCCESS == TlclWrite(KERNEL_VERSIONS_NV_INDEX, | 247 return (TPM_SUCCESS != TlclWrite(KERNEL_VERSIONS_NV_INDEX, |
236 (uint8_t*) &combined_version, | 248 (uint8_t*) &combined_version, |
237 sizeof(uint32_t))); | 249 sizeof(uint32_t))); |
238 break; | |
239 } | 250 } |
240 /* TODO(nelson): ForceClear and reboot if unowned. */ | 251 /* TODO(nelson): ForceClear and reboot if unowned. */ |
241 | 252 |
| 253 return 1; |
| 254 } |
| 255 |
| 256 int LockFirmwareVersions() { |
| 257 if (TlclSetGlobalLock() != TPM_SUCCESS) { |
| 258 debug("failed to set global lock"); |
| 259 return 1; |
| 260 } |
242 return 0; | 261 return 0; |
243 } | 262 } |
244 | 263 |
245 void LockFirmwareVersions() { | 264 int LockKernelVersionsByLockingPP() { |
246 if (TlclSetGlobalLock() != TPM_SUCCESS) { | |
247 debug("failed to set global lock"); | |
248 EnterRecovery(1); | |
249 } | |
250 } | |
251 | |
252 void LockKernelVersionsByLockingPP() { | |
253 if (TlclLockPhysicalPresence() != TPM_SUCCESS) { | 265 if (TlclLockPhysicalPresence() != TPM_SUCCESS) { |
254 debug("failed to turn off PP"); | 266 debug("failed to turn off PP"); |
255 EnterRecovery(1); | 267 return 1; |
256 } | 268 } |
| 269 return 0; |
257 } | 270 } |
OLD | NEW |