Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(364)

Side by Side Diff: firmware/lib/rollback_index.c

Issue 3229011: Add physical presence initialization and locking to one-time initializations. (Closed) Base URL: ssh://git@gitrw.chromium.org:9222/vboot_reference.git
Patch Set: version change Created 10 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | firmware/lib/tpm_lite/include/tlcl.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 80 matching lines...) Expand 10 before | Expand all | Expand 10 after
91 #ifndef DISABLE_ROLLBACK_TPM 91 #ifndef DISABLE_ROLLBACK_TPM
92 static uint32_t ReadSpaceKernel(RollbackSpaceKernel* rsk) { 92 static uint32_t ReadSpaceKernel(RollbackSpaceKernel* rsk) {
93 return TlclRead(KERNEL_NV_INDEX, rsk, sizeof(RollbackSpaceKernel)); 93 return TlclRead(KERNEL_NV_INDEX, rsk, sizeof(RollbackSpaceKernel));
94 } 94 }
95 #endif 95 #endif
96 96
97 static uint32_t WriteSpaceKernel(const RollbackSpaceKernel* rsk) { 97 static uint32_t WriteSpaceKernel(const RollbackSpaceKernel* rsk) {
98 return SafeWrite(KERNEL_NV_INDEX, rsk, sizeof(RollbackSpaceKernel)); 98 return SafeWrite(KERNEL_NV_INDEX, rsk, sizeof(RollbackSpaceKernel));
99 } 99 }
100 100
101 /* Creates the NVRAM spaces, and sets their initial values as needed. */ 101 /* Performs one-time initializations. Creates the NVRAM spaces, and sets their
102 static uint32_t InitializeSpaces(RollbackSpaceFirmware* rsf, 102 * initial values as needed. Sets the nvLocked bit and ensures the physical
103 RollbackSpaceKernel* rsk) { 103 * presence command is enabled and locked.
104 */
105 static uint32_t OneTimeInitializeTPM(RollbackSpaceFirmware* rsf,
106 RollbackSpaceKernel* rsk) {
104 static const RollbackSpaceFirmware rsf_init = { 107 static const RollbackSpaceFirmware rsf_init = {
105 ROLLBACK_SPACE_FIRMWARE_VERSION, 0, 0, 0}; 108 ROLLBACK_SPACE_FIRMWARE_VERSION, 0, 0, 0};
106 static const RollbackSpaceKernel rsk_init = { 109 static const RollbackSpaceKernel rsk_init = {
107 ROLLBACK_SPACE_KERNEL_VERSION, ROLLBACK_SPACE_KERNEL_UID, 0, 0}; 110 ROLLBACK_SPACE_KERNEL_VERSION, ROLLBACK_SPACE_KERNEL_UID, 0, 0};
108 uint8_t nvlocked = 0; 111 uint8_t nvlocked = 0;
109 112
110 VBDEBUG(("TPM: Initializing spaces\n")); 113 VBDEBUG(("TPM: One-time initialization\n"));
114
115 RETURN_ON_FAILURE(TlclFinalizePhysicalPresence());
111 116
112 /* The TPM will not enforce the NV authorization restrictions until the 117 /* The TPM will not enforce the NV authorization restrictions until the
113 * execution of a TPM_NV_DefineSpace with the handle of TPM_NV_INDEX_LOCK. 118 * execution of a TPM_NV_DefineSpace with the handle of TPM_NV_INDEX_LOCK.
114 * Create that space if it doesn't already exist. */ 119 * Here we create that space if it doesn't already exist. */
115 RETURN_ON_FAILURE(TlclGetFlags(NULL, NULL, &nvlocked)); 120 RETURN_ON_FAILURE(TlclGetFlags(NULL, NULL, &nvlocked));
116 VBDEBUG(("TPM: nvlocked=%d\n", nvlocked)); 121 VBDEBUG(("TPM: nvlocked=%d\n", nvlocked));
117 if (!nvlocked) { 122 if (!nvlocked) {
118 VBDEBUG(("TPM: Enabling NV locking\n")); 123 VBDEBUG(("TPM: Enabling NV locking\n"));
119 RETURN_ON_FAILURE(TlclSetNvLocked()); 124 RETURN_ON_FAILURE(TlclSetNvLocked());
120 } 125 }
121 126
122 /* Initialize the firmware and kernel spaces */ 127 /* Initializes the firmware and kernel spaces */
123 Memcpy(rsf, &rsf_init, sizeof(RollbackSpaceFirmware)); 128 Memcpy(rsf, &rsf_init, sizeof(RollbackSpaceFirmware));
124 Memcpy(rsk, &rsk_init, sizeof(RollbackSpaceKernel)); 129 Memcpy(rsk, &rsk_init, sizeof(RollbackSpaceKernel));
125 130
126 /* Define and set firmware and kernel spaces */ 131 /* Defines and sets firmware and kernel spaces */
127 RETURN_ON_FAILURE(SafeDefineSpace(FIRMWARE_NV_INDEX, 132 RETURN_ON_FAILURE(SafeDefineSpace(FIRMWARE_NV_INDEX,
128 TPM_NV_PER_GLOBALLOCK | TPM_NV_PER_PPWRITE, 133 TPM_NV_PER_GLOBALLOCK | TPM_NV_PER_PPWRITE,
129 sizeof(RollbackSpaceFirmware))); 134 sizeof(RollbackSpaceFirmware)));
130 RETURN_ON_FAILURE(WriteSpaceFirmware(rsf)); 135 RETURN_ON_FAILURE(WriteSpaceFirmware(rsf));
131 RETURN_ON_FAILURE(SafeDefineSpace(KERNEL_NV_INDEX, TPM_NV_PER_PPWRITE, 136 RETURN_ON_FAILURE(SafeDefineSpace(KERNEL_NV_INDEX, TPM_NV_PER_PPWRITE,
132 sizeof(RollbackSpaceKernel))); 137 sizeof(RollbackSpaceKernel)));
133 RETURN_ON_FAILURE(WriteSpaceKernel(rsk)); 138 RETURN_ON_FAILURE(WriteSpaceKernel(rsk));
134 return TPM_SUCCESS; 139 return TPM_SUCCESS;
135 } 140 }
136 141
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
170 175
171 RETURN_ON_FAILURE(TlclStartup()); 176 RETURN_ON_FAILURE(TlclStartup());
172 #ifdef USE_CONTINUE_SELF_TEST 177 #ifdef USE_CONTINUE_SELF_TEST
173 /* TODO: ContinueSelfTest() should be faster than SelfTestFull, but 178 /* TODO: ContinueSelfTest() should be faster than SelfTestFull, but
174 * may also not work properly in older TPM firmware. For now, do 179 * may also not work properly in older TPM firmware. For now, do
175 * the full self test. */ 180 * the full self test. */
176 RETURN_ON_FAILURE(TlclContinueSelfTest()); 181 RETURN_ON_FAILURE(TlclContinueSelfTest());
177 #else 182 #else
178 RETURN_ON_FAILURE(TlclSelfTestFull()); 183 RETURN_ON_FAILURE(TlclSelfTestFull());
179 #endif 184 #endif
180 RETURN_ON_FAILURE(TlclAssertPhysicalPresence()); 185 result = TlclAssertPhysicalPresence();
186 if (result != 0) {
187 /* It is possible that the TPM was delivered with the physical presence
188 * command disabled. This tries enabling it, then tries asserting PP
189 * again.
190 */
191 RETURN_ON_FAILURE(TlclPhysicalPresenceCMDEnable());
192 RETURN_ON_FAILURE(TlclAssertPhysicalPresence());
193 }
181 194
182 /* Check that the TPM is enabled and activated. */ 195 /* Checks that the TPM is enabled and activated. */
183 RETURN_ON_FAILURE(TlclGetFlags(&disable, &deactivated, NULL)); 196 RETURN_ON_FAILURE(TlclGetFlags(&disable, &deactivated, NULL));
184 if (disable || deactivated) { 197 if (disable || deactivated) {
185 VBDEBUG(("TPM: disabled (%d) or deactivated (%d). Fixing...\n", 198 VBDEBUG(("TPM: disabled (%d) or deactivated (%d). Fixing...\n",
186 disable, deactivated)); 199 disable, deactivated));
187 RETURN_ON_FAILURE(TlclSetEnable()); 200 RETURN_ON_FAILURE(TlclSetEnable());
188 RETURN_ON_FAILURE(TlclSetDeactivated(0)); 201 RETURN_ON_FAILURE(TlclSetDeactivated(0));
189 VBDEBUG(("TPM: Must reboot to re-enable\n")); 202 VBDEBUG(("TPM: Must reboot to re-enable\n"));
190 return TPM_E_MUST_REBOOT; 203 return TPM_E_MUST_REBOOT;
191 } 204 }
192 205
193 /* Read the firmware space. */ 206 /* Reads the firmware space. */
194 result = ReadSpaceFirmware(rsf); 207 result = ReadSpaceFirmware(rsf);
195 if (TPM_E_BADINDEX == result) { 208 if (TPM_E_BADINDEX == result) {
196 RollbackSpaceKernel rsk; 209 RollbackSpaceKernel rsk;
197 210
198 /* This is the first time we've run, and the TPM has not been 211 /* This is the first time we've run, and the TPM has not been
199 * initialized. Initialize it. */ 212 * initialized. This initializes it. */
200 VBDEBUG(("TPM: Not initialized yet.\n")); 213 VBDEBUG(("TPM: Not initialized yet.\n"));
201 RETURN_ON_FAILURE(InitializeSpaces(rsf, &rsk)); 214 RETURN_ON_FAILURE(OneTimeInitializeTPM(rsf, &rsk));
202 } else if (TPM_SUCCESS != result) { 215 } else if (TPM_SUCCESS != result) {
203 VBDEBUG(("TPM: Firmware space in a bad state; giving up.\n")); 216 VBDEBUG(("TPM: Firmware space in a bad state; giving up.\n"));
204 return TPM_E_CORRUPTED_STATE; 217 return TPM_E_CORRUPTED_STATE;
205 } 218 }
206 VBDEBUG(("TPM: Firmware space sv%d f%x v%x\n", 219 VBDEBUG(("TPM: Firmware space sv%d f%x v%x\n",
207 rsf->struct_version, rsf->flags, rsf->fw_versions)); 220 rsf->struct_version, rsf->flags, rsf->fw_versions));
208 221
209 /* Clear ownership if developer flag has toggled */ 222 /* Clears ownership if developer flag has toggled */
210 if ((developer_mode ? FLAG_LAST_BOOT_DEVELOPER : 0) != 223 if ((developer_mode ? FLAG_LAST_BOOT_DEVELOPER : 0) !=
211 (rsf->flags & FLAG_LAST_BOOT_DEVELOPER)) { 224 (rsf->flags & FLAG_LAST_BOOT_DEVELOPER)) {
212 VBDEBUG(("TPM: Developer flag changed; clearing owner.\n")); 225 VBDEBUG(("TPM: Developer flag changed; clearing owner.\n"));
213 RETURN_ON_FAILURE(TPMClearAndReenable()); 226 RETURN_ON_FAILURE(TPMClearAndReenable());
214 } 227 }
215 228
216 /* Update flags */ 229 /* Updates flags */
217 if (developer_mode) 230 if (developer_mode)
218 new_flags |= FLAG_LAST_BOOT_DEVELOPER; 231 new_flags |= FLAG_LAST_BOOT_DEVELOPER;
219 if (recovery_mode) 232 if (recovery_mode)
220 g_rollback_recovery_mode = 1; /* Global variables are usable in 233 g_rollback_recovery_mode = 1; /* Global variables are usable in
221 * recovery mode */ 234 * recovery mode */
222 235
223 if (rsf->flags != new_flags) { 236 if (rsf->flags != new_flags) {
224 rsf->flags = new_flags; 237 rsf->flags = new_flags;
225 rsf_dirty = 1; 238 rsf_dirty = 1;
226 } 239 }
227 240
228 /* If firmware space is dirty, flush it back to the TPM */ 241 /* If firmware space is dirty, this flushes it back to the TPM */
229 if (rsf_dirty) { 242 if (rsf_dirty) {
230 VBDEBUG(("TPM: Updating firmware space.\n")); 243 VBDEBUG(("TPM: Updating firmware space.\n"));
231 RETURN_ON_FAILURE(WriteSpaceFirmware(rsf)); 244 RETURN_ON_FAILURE(WriteSpaceFirmware(rsf));
232 } 245 }
233 246
234 VBDEBUG(("TPM: SetupTPM() succeeded\n")); 247 VBDEBUG(("TPM: SetupTPM() succeeded\n"));
235 return TPM_SUCCESS; 248 return TPM_SUCCESS;
236 } 249 }
237 250
238 /* disable MSVC warnings on unused arguments */ 251 /* disable MSVC warnings on unused arguments */
239 __pragma(warning (disable: 4100)) 252 __pragma(warning (disable: 4100))
240 253
241 254
242 #ifdef DISABLE_ROLLBACK_TPM 255 #ifdef DISABLE_ROLLBACK_TPM
243 256
244 /* Dummy implementations which don't support TPM rollback protection */ 257 /* Dummy implementations which don't support TPM rollback protection */
245 258
246 uint32_t RollbackFirmwareSetup(int developer_mode, uint32_t* version) { 259 uint32_t RollbackFirmwareSetup(int developer_mode, uint32_t* version) {
247 #ifndef CHROMEOS_ENVIRONMENT 260 #ifndef CHROMEOS_ENVIRONMENT
248 /* Initialize the TPM, but ignore return codes. In ChromeOS 261 /* Initializes the TPM, but ignores return codes. In ChromeOS
249 * environment, don't even talk to the TPM. */ 262 * environment, doesn't even talk to the TPM. */
250 TlclLibInit(); 263 TlclLibInit();
251 TlclStartup(); 264 TlclStartup();
252 TlclSelfTestFull(); 265 TlclSelfTestFull();
253 #endif 266 #endif
254 267
255 *version = 0; 268 *version = 0;
256 return TPM_SUCCESS; 269 return TPM_SUCCESS;
257 } 270 }
258 271
259 uint32_t RollbackFirmwareWrite(uint32_t version) { 272 uint32_t RollbackFirmwareWrite(uint32_t version) {
260 return TPM_SUCCESS; 273 return TPM_SUCCESS;
261 } 274 }
262 275
263 uint32_t RollbackFirmwareLock(void) { 276 uint32_t RollbackFirmwareLock(void) {
264 return TPM_SUCCESS; 277 return TPM_SUCCESS;
265 } 278 }
266 279
267 uint32_t RollbackKernelRecovery(int developer_mode) { 280 uint32_t RollbackKernelRecovery(int developer_mode) {
268 #ifndef CHROMEOS_ENVIRONMENT 281 #ifndef CHROMEOS_ENVIRONMENT
269 /* Initialize the TPM, but ignore return codes. In ChromeOS 282 /* Initializes the TPM, but ignore return codes. In ChromeOS
270 * environment, don't even talk to the TPM. */ 283 * environment, doesn't even talk to the TPM. */
271 TlclLibInit(); 284 TlclLibInit();
272 TlclStartup(); 285 TlclStartup();
273 TlclSelfTestFull(); 286 TlclSelfTestFull();
274 #endif 287 #endif
275 return TPM_SUCCESS; 288 return TPM_SUCCESS;
276 } 289 }
277 290
278 uint32_t RollbackKernelRead(uint32_t* version) { 291 uint32_t RollbackKernelRead(uint32_t* version) {
279 *version = 0; 292 *version = 0;
280 return TPM_SUCCESS; 293 return TPM_SUCCESS;
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
376 389
377 uint32_t RollbackKernelLock(void) { 390 uint32_t RollbackKernelLock(void) {
378 if (g_rollback_recovery_mode) { 391 if (g_rollback_recovery_mode) {
379 return TPM_SUCCESS; 392 return TPM_SUCCESS;
380 } else { 393 } else {
381 return TlclLockPhysicalPresence(); 394 return TlclLockPhysicalPresence();
382 } 395 }
383 } 396 }
384 397
385 #endif // DISABLE_ROLLBACK_TPM 398 #endif // DISABLE_ROLLBACK_TPM
OLDNEW
« no previous file with comments | « no previous file | firmware/lib/tpm_lite/include/tlcl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698