Add clear TPM owner request

This adds two new flags to crossystem:
   clear_tpm_owner_request
   clear_tpm_owner_done

The first one requests that the firmware clear the TPM owner on the
next boot.  When the firmware does this, it will set
clear_tpm_owner_request=0, and set clear_tpm_owner_done=1.  The OS can
use the done-flag as a hint that trusted things guarded by the TPM are
no longer trustable.

BUG=chromium-os:31974
TEST=manual

crossystem
  // both flags initially 0
crossystem clear_tpm_owner_request=1
crossystem clear_tpm_owner_done=1
  // request=1, done=0; done can be cleared but not set by crossystem
reboot
tpmc getownership
  // owned=no
crossystem
  // request=0, done=1
crossystem clear_tpm_owner_done=0
crossystem
  // both flags 0 again

Signed-off-by: Randall Spangler <rspangler@chromium.org>
Change-Id: I49f83f3c39c3efc3945116c51a241d255c2e42cd
Reviewed-on: https://gerrit.chromium.org/gerrit/25646
diff --git a/firmware/include/vboot_nvstorage.h b/firmware/include/vboot_nvstorage.h
index fbc847f..8748a5c 100644
--- a/firmware/include/vboot_nvstorage.h
+++ b/firmware/include/vboot_nvstorage.h
@@ -57,6 +57,10 @@
   /* Set and cleared by vboot to request that the video Option ROM be loaded at
    * boot time, so that BIOS screens can be displayed. 0=no, 1=yes. */
   VBNV_OPROM_NEEDED,
+  /* Request that the firmware clear the TPM owner on the next boot. */
+  VBNV_CLEAR_TPM_OWNER_REQUEST,
+  /* Flag that TPM owner was cleared on request. */
+  VBNV_CLEAR_TPM_OWNER_DONE,
 } VbNvParam;
 
 
diff --git a/firmware/lib/include/rollback_index.h b/firmware/lib/include/rollback_index.h
index 20df5b3..51e6ec1 100644
--- a/firmware/lib/include/rollback_index.h
+++ b/firmware/lib/include/rollback_index.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  *
@@ -70,6 +70,7 @@
 /* This must be called. */
 uint32_t RollbackFirmwareSetup(int recovery_mode, int is_hw_dev,
                                int disable_dev_request,
+                               int clear_tpm_owner_request,
                                /* two outputs on success */
                                int *is_virt_dev, uint32_t *tpm_version);
 
@@ -118,7 +119,8 @@
 /* SetupTPM starts the TPM and establishes the root of trust for the
  * anti-rollback mechanism. */
 uint32_t SetupTPM(int recovery_mode, int developer_mode,
-                  int disable_dev_request, RollbackSpaceFirmware* rsf);
+                  int disable_dev_request, int clear_tpm_owner_request,
+                  RollbackSpaceFirmware* rsf);
 
 /* Utility function to turn the virtual dev-mode flag on or off. 0=off, 1=on */
 uint32_t SetVirtualDevMode(int val);
diff --git a/firmware/lib/mocked_rollback_index.c b/firmware/lib/mocked_rollback_index.c
index f60e2f2..65dfd4d 100644
--- a/firmware/lib/mocked_rollback_index.c
+++ b/firmware/lib/mocked_rollback_index.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  *
@@ -22,7 +22,8 @@
 
 
 uint32_t SetupTPM(int recovery_mode, int developer_mode,
-                  int disable_dev_request, RollbackSpaceFirmware* rsf) {
+                  int disable_dev_request, int clear_tpm_owner_request,
+                  RollbackSpaceFirmware* rsf) {
   return TPM_SUCCESS;
 }
 
@@ -34,6 +35,7 @@
 
 uint32_t RollbackFirmwareSetup(int recovery_mode, int is_hw_dev,
                                int disable_dev_request,
+                               int clear_tpm_owner_request,
                                int *is_virt_dev, uint32_t *version) {
   *version = 0;
   return TPM_SUCCESS;
diff --git a/firmware/lib/rollback_index.c b/firmware/lib/rollback_index.c
index 668312e..a5bc6ae 100644
--- a/firmware/lib/rollback_index.c
+++ b/firmware/lib/rollback_index.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  *
@@ -298,7 +298,8 @@
  * the durability of the NVRAM.
  */
 uint32_t SetupTPM(int recovery_mode, int developer_mode,
-                  int disable_dev_request, RollbackSpaceFirmware* rsf) {
+                  int disable_dev_request, int clear_tpm_owner_request,
+                  RollbackSpaceFirmware* rsf) {
 
   uint8_t in_flags;
   uint8_t disable;
@@ -398,11 +399,15 @@
   if (rsf->flags & FLAG_VIRTUAL_DEV_MODE_ON)
     developer_mode = 1;
 
-  /* Clears ownership if developer flag has toggled */
+  /* Clears ownership if developer flag has toggled, or if an owner-clear has
+   * been requested. */
   if ((developer_mode ? FLAG_LAST_BOOT_DEVELOPER : 0) !=
       (in_flags & FLAG_LAST_BOOT_DEVELOPER)) {
     VBDEBUG(("TPM: Developer flag changed; clearing owner.\n"));
     RETURN_ON_FAILURE(TPMClearAndReenable());
+  } else if (clear_tpm_owner_request) {
+    VBDEBUG(("TPM: Clearing owner as specifically requested.\n"));
+    RETURN_ON_FAILURE(TPMClearAndReenable());
   }
 
   if (developer_mode)
@@ -441,6 +446,7 @@
 
 uint32_t RollbackFirmwareSetup(int recovery_mode, int is_hw_dev,
                                int disable_dev_request,
+                               int clear_tpm_owner_request,
                                int *is_virt_dev, uint32_t *version) {
 #ifndef CHROMEOS_ENVIRONMENT
   /* Initialize the TPM, but ignores return codes.  In ChromeOS
@@ -495,14 +501,15 @@
 
 uint32_t RollbackFirmwareSetup(int recovery_mode, int is_hw_dev,
                                int disable_dev_request,
+                               int clear_tpm_owner_request,
                                int *is_virt_dev, uint32_t *version) {
   RollbackSpaceFirmware rsf;
 
   /* Set version to 0 in case we fail */
   *version = 0;
 
-  RETURN_ON_FAILURE(SetupTPM(recovery_mode, is_hw_dev,
-                             disable_dev_request, &rsf));
+  RETURN_ON_FAILURE(SetupTPM(recovery_mode, is_hw_dev, disable_dev_request,
+                             clear_tpm_owner_request, &rsf));
   *version = rsf.fw_versions;
   *is_virt_dev = (rsf.flags & FLAG_VIRTUAL_DEV_MODE_ON) ? 1 : 0;
   VBDEBUG(("TPM: RollbackFirmwareSetup %x\n", (int)rsf.fw_versions));
diff --git a/firmware/lib/vboot_api_init.c b/firmware/lib/vboot_api_init.c
index a561890..8d1540b 100644
--- a/firmware/lib/vboot_api_init.c
+++ b/firmware/lib/vboot_api_init.c
@@ -29,6 +29,7 @@
   int is_hw_dev = 0;
   int is_virt_dev = 0;
   uint32_t disable_dev_request = 0;
+  uint32_t clear_tpm_owner_request = 0;
   int is_dev = 0;
 
   VBDEBUG(("VbInit() input flags 0x%x\n", iparams->flags));
@@ -136,12 +137,16 @@
     if (gbb->flags & GBB_FLAG_FORCE_DEV_SWITCH_ON)
       is_hw_dev = 1;
 
+    /* Check if we've been explicitly asked to clear the TPM owner */
+    VbNvGet(&vnc, VBNV_CLEAR_TPM_OWNER_REQUEST, &clear_tpm_owner_request);
+
     VBPERFSTART("VB_TPMI");
     /* Initialize the TPM. If the developer mode state has changed since the
      * last boot, we need to clear TPM ownership. If the TPM space is
      * initialized by this call, the virtual dev-switch will be disabled by
      * default) */
     tpm_status = RollbackFirmwareSetup(recovery, is_hw_dev, disable_dev_request,
+                                       clear_tpm_owner_request,
                                        /* two outputs on success */
                                        &is_virt_dev, &tpm_version);
     VBPERFEND("VB_TPMI");
@@ -180,6 +185,10 @@
     }
     if (disable_dev_request && !is_virt_dev)
       VbNvSet(&vnc, VBNV_DISABLE_DEV_REQUEST, 0);
+    if (clear_tpm_owner_request) {
+      VbNvSet(&vnc, VBNV_CLEAR_TPM_OWNER_REQUEST, 0);
+      VbNvSet(&vnc, VBNV_CLEAR_TPM_OWNER_DONE, 1);
+    }
   }
 
   /* Allow BIOS to load arbitrary option ROMs? */
diff --git a/firmware/lib/vboot_nvstorage.c b/firmware/lib/vboot_nvstorage.c
index bde0b40..0f4633b 100644
--- a/firmware/lib/vboot_nvstorage.c
+++ b/firmware/lib/vboot_nvstorage.c
@@ -33,6 +33,10 @@
 #define DEV_BOOT_USB_MASK               0x01
 #define DEV_BOOT_SIGNED_ONLY_MASK       0x02
 
+#define TPM_FLAGS_OFFSET             5
+#define TPM_CLEAR_OWNER_REQUEST         0x01
+#define TPM_CLEAR_OWNER_DONE            0x02
+
 #define KERNEL_FIELD_OFFSET         11
 #define CRC_OFFSET                  15
 
@@ -124,6 +128,14 @@
       *dest = (raw[BOOT_OFFSET] & BOOT_OPROM_NEEDED ? 1 : 0);
       return 0;
 
+    case VBNV_CLEAR_TPM_OWNER_REQUEST:
+      *dest = (raw[TPM_FLAGS_OFFSET] & TPM_CLEAR_OWNER_REQUEST ? 1 : 0);
+      return 0;
+
+    case VBNV_CLEAR_TPM_OWNER_DONE:
+      *dest = (raw[TPM_FLAGS_OFFSET] & TPM_CLEAR_OWNER_DONE ? 1 : 0);
+      return 0;
+
     default:
       return 1;
   }
@@ -219,6 +231,20 @@
         raw[BOOT_OFFSET] &= ~BOOT_OPROM_NEEDED;
       break;
 
+    case VBNV_CLEAR_TPM_OWNER_REQUEST:
+      if (value)
+        raw[TPM_FLAGS_OFFSET] |= TPM_CLEAR_OWNER_REQUEST;
+      else
+        raw[TPM_FLAGS_OFFSET] &= ~TPM_CLEAR_OWNER_REQUEST;
+      break;
+
+    case VBNV_CLEAR_TPM_OWNER_DONE:
+      if (value)
+        raw[TPM_FLAGS_OFFSET] |= TPM_CLEAR_OWNER_DONE;
+      else
+        raw[TPM_FLAGS_OFFSET] &= ~TPM_CLEAR_OWNER_DONE;
+      break;
+
     default:
       return 1;
   }
diff --git a/firmware/linktest/main.c b/firmware/linktest/main.c
index 020b589..c5ce2c1 100644
--- a/firmware/linktest/main.c
+++ b/firmware/linktest/main.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  */
@@ -29,7 +29,7 @@
 
   /* rollback_index.h */
   RollbackS3Resume();
-  RollbackFirmwareSetup(0, 0, 0, 0, 0);
+  RollbackFirmwareSetup(0, 0, 0, 0, 0, 0);
   RollbackFirmwareWrite(0);
   RollbackFirmwareLock();
   RollbackKernelRead(0);
diff --git a/host/lib/crossystem.c b/host/lib/crossystem.c
index e120abc..d89c85c 100644
--- a/host/lib/crossystem.c
+++ b/host/lib/crossystem.c
@@ -403,6 +403,10 @@
     value = VbGetNvStorage(VBNV_DEBUG_RESET_MODE);
   } else if (!strcasecmp(name,"disable_dev_request")) {
     value = VbGetNvStorage(VBNV_DISABLE_DEV_REQUEST);
+  } else if (!strcasecmp(name,"clear_tpm_owner_request")) {
+    value = VbGetNvStorage(VBNV_CLEAR_TPM_OWNER_REQUEST);
+  } else if (!strcasecmp(name,"clear_tpm_owner_done")) {
+    value = VbGetNvStorage(VBNV_CLEAR_TPM_OWNER_DONE);
   } else if (!strcasecmp(name,"fwb_tries")) {
     value = VbGetNvStorage(VBNV_TRY_B_COUNT);
   } else if (!strcasecmp(name,"fwupdate_tries")) {
@@ -493,6 +497,11 @@
     return VbSetNvStorage(VBNV_DEBUG_RESET_MODE, value);
   } else if (!strcasecmp(name,"disable_dev_request")) {
     return VbSetNvStorage(VBNV_DISABLE_DEV_REQUEST, value);
+  } else if (!strcasecmp(name,"clear_tpm_owner_request")) {
+    return VbSetNvStorage(VBNV_CLEAR_TPM_OWNER_REQUEST, value);
+  } else if (!strcasecmp(name,"clear_tpm_owner_done")) {
+    /* Can only clear this flag; it's set by firmware. */
+    return VbSetNvStorage(VBNV_CLEAR_TPM_OWNER_DONE, 0);
   } else if (!strcasecmp(name,"fwb_tries")) {
     return VbSetNvStorage(VBNV_TRY_B_COUNT, value);
   } else if (!strcasecmp(name,"fwupdate_tries")) {
diff --git a/tests/rollback_index2_tests.c b/tests/rollback_index2_tests.c
index 6de33bc..4a12a6e 100644
--- a/tests/rollback_index2_tests.c
+++ b/tests/rollback_index2_tests.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  *
@@ -558,7 +558,7 @@
 
   /* Complete setup */
   ResetMocks(0, 0);
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), 0, "SetupTPM()");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), 0, "SetupTPM()");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -570,7 +570,7 @@
   /* If TPM is disabled or deactivated, must enable it */
   ResetMocks(0, 0);
   mock_pflags.disable = 1;
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), TPM_E_MUST_REBOOT, "SetupTPM() disabled");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), TPM_E_MUST_REBOOT, "SetupTPM() disabled");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -582,7 +582,8 @@
 
   ResetMocks(0, 0);
   mock_pflags.deactivated = 1;
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), TPM_E_MUST_REBOOT, "SetupTPM() deactivated");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), TPM_E_MUST_REBOOT,
+          "SetupTPM() deactivated");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -594,7 +595,7 @@
 
   /* If physical presence command isn't enabled, should try to enable it */
   ResetMocks(3, TPM_E_IOERROR);
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), 0, "SetupTPM() pp cmd");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), 0, "SetupTPM() pp cmd");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -609,7 +610,7 @@
   ResetMocks(5, TPM_E_BADINDEX);
   mock_pflags.physicalPresenceLifetimeLock = 1;
   mock_pflags.nvLocked = 1;
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), 0, "SetupTPM() no firmware space");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), 0, "SetupTPM() no firmware space");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -632,7 +633,7 @@
 
   /* Other firmware space error is passed through */
   ResetMocks(5, TPM_E_IOERROR);
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), TPM_E_CORRUPTED_STATE,
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), TPM_E_CORRUPTED_STATE,
           "SetupTPM() bad firmware space");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
@@ -644,7 +645,7 @@
 
   /* If developer flag has toggled, clear ownership and write new flag */
   ResetMocks(0, 0);
-  TEST_EQ(SetupTPM(0, 1, 0, &rsf), 0, "SetupTPM() to dev");
+  TEST_EQ(SetupTPM(0, 1, 0, 0, &rsf), 0, "SetupTPM() to dev");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -661,7 +662,7 @@
 
   ResetMocks(0, 0);
   mock_rsf.flags = FLAG_LAST_BOOT_DEVELOPER;
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), 0, "SetupTPM() from dev");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), 0, "SetupTPM() from dev");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
               "TlclStartup()\n"
@@ -676,6 +677,20 @@
               "tlcl calls");
   TEST_EQ(mock_rsf.flags, 0, "fw space flags from dev 1");
 
+  /* If TPM clear request, clear ownership also */
+  ResetMocks(0, 0);
+  TEST_EQ(SetupTPM(0, 0, 0, 1, &rsf), 0, "SetupTPM() clear owner");
+  TEST_STR_EQ(mock_calls,
+              "TlclLibInit()\n"
+              "TlclStartup()\n"
+              "TlclAssertPhysicalPresence()\n"
+              "TlclGetPermanentFlags()\n"
+              "TlclRead(0x1007, 10)\n"
+              "TlclForceClear()\n"
+              "TlclSetEnable()\n"
+              "TlclSetDeactivated(0)\n",
+              "tlcl calls");
+
   /* Note: SetupTPM() recovery_mode parameter sets a global flag in
    * rollback_index.c; this is tested along with RollbackKernelLock() below. */
 }
@@ -691,7 +706,7 @@
   dev_mode = 0;
   version = 123;
   mock_rsf.fw_versions = 0x12345678;
-  TEST_EQ(RollbackFirmwareSetup(0, 0, dev_mode, &dev_mode, &version), 0,
+  TEST_EQ(RollbackFirmwareSetup(0, 0, dev_mode, 0, &dev_mode, &version), 0,
           "RollbackFirmwareSetup()");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
@@ -707,7 +722,7 @@
   dev_mode = 0;
   version = 123;
   mock_rsf.fw_versions = 0x12345678;
-  TEST_EQ(RollbackFirmwareSetup(0, 0, dev_mode, &dev_mode, &version),
+  TEST_EQ(RollbackFirmwareSetup(0, 0, dev_mode, 0, &dev_mode, &version),
           TPM_E_IOERROR,
           "RollbackFirmwareSetup() error");
   TEST_STR_EQ(mock_calls,
@@ -718,7 +733,7 @@
   /* Developer mode flag gets passed properly */
   ResetMocks(0, 0);
   dev_mode = 1;
-  TEST_EQ(RollbackFirmwareSetup(0, dev_mode, 0, &dev_mode, &version), 0,
+  TEST_EQ(RollbackFirmwareSetup(0, dev_mode, 0, 0, &dev_mode, &version), 0,
           "RollbackFirmwareSetup() to dev");
   TEST_STR_EQ(mock_calls,
               "TlclLibInit()\n"
@@ -734,6 +749,22 @@
               "tlcl calls");
   TEST_EQ(mock_rsf.flags, FLAG_LAST_BOOT_DEVELOPER, "fw space flags to dev 2");
 
+  /* So does clear-TPM request */
+  ResetMocks(0, 0);
+  dev_mode = 0;
+  TEST_EQ(RollbackFirmwareSetup(0, dev_mode, 0, 1, &dev_mode, &version), 0,
+          "RollbackFirmwareSetup() clear owner");
+  TEST_STR_EQ(mock_calls,
+              "TlclLibInit()\n"
+              "TlclStartup()\n"
+              "TlclAssertPhysicalPresence()\n"
+              "TlclGetPermanentFlags()\n"
+              "TlclRead(0x1007, 10)\n"
+              "TlclForceClear()\n"
+              "TlclSetEnable()\n"
+              "TlclSetDeactivated(0)\n",
+              "tlcl calls");
+
   /* Test write */
   ResetMocks(0, 0);
   TEST_EQ(RollbackFirmwareWrite(0xBEAD1234), 0, "RollbackFirmwareWrite()");
@@ -770,7 +801,7 @@
   /* RollbackKernel*() functions use a global flag inside
    * rollback_index.c based on recovery mode, which is set by
    * SetupTPM().  Clear the flag for the first set of tests. */
-  TEST_EQ(SetupTPM(0, 0, 0, &rsf), 0, "SetupTPM()");
+  TEST_EQ(SetupTPM(0, 0, 0, 0, &rsf), 0, "SetupTPM()");
 
   /* Normal read */
   ResetMocks(0, 0);
@@ -831,7 +862,7 @@
   TEST_EQ(RollbackKernelLock(), TPM_E_IOERROR, "RollbackKernelLock() error");
 
   /* Test lock with recovery on; shouldn't lock PP */
-  SetupTPM(1, 0, 0, &rsf);
+  SetupTPM(1, 0, 0, 0, &rsf);
   ResetMocks(0, 0);
   TEST_EQ(RollbackKernelLock(), 0, "RollbackKernelLock() in recovery");
   TEST_STR_EQ(mock_calls, "", "no tlcl calls");
diff --git a/tests/vboot_api_init_tests.c b/tests/vboot_api_init_tests.c
index 2278b1d..3816e07 100644
--- a/tests/vboot_api_init_tests.c
+++ b/tests/vboot_api_init_tests.c
@@ -89,6 +89,7 @@
 
 uint32_t RollbackFirmwareSetup(int recovery_mode, int is_hw_dev,
                                int disable_dev_request,
+                               int clear_tpm_owner_request,
                                /* two outputs on success */
                                int *is_virt_dev, uint32_t *version) {
   *is_virt_dev = mock_virt_dev_sw;
diff --git a/tests/vboot_nvstorage_test.c b/tests/vboot_nvstorage_test.c
index 46219df..a555ac7 100644
--- a/tests/vboot_nvstorage_test.c
+++ b/tests/vboot_nvstorage_test.c
@@ -31,6 +31,9 @@
   {VBNV_KERNEL_FIELD, 0, 0x12345678, 0xFEDCBA98, "kernel field"},
   {VBNV_DEV_BOOT_USB, 0, 1, 0, "dev boot usb"},
   {VBNV_DEV_BOOT_SIGNED_ONLY, 0, 1, 0, "dev boot custom"},
+  {VBNV_DISABLE_DEV_REQUEST, 0, 1, 0, "disable dev request"},
+  {VBNV_CLEAR_TPM_OWNER_REQUEST, 0, 1, 0, "clear tpm owner request"},
+  {VBNV_CLEAR_TPM_OWNER_DONE, 0, 1, 0, "clear tpm owner done"},
   {0, 0, 0, 0, NULL}
 };
 
diff --git a/utility/crossystem_main.c b/utility/crossystem_main.c
index ecd1e4f..1b92665 100644
--- a/utility/crossystem_main.c
+++ b/utility/crossystem_main.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
  * Use of this source code is governed by a BSD-style license that can be
  * found in the LICENSE file.
  *
@@ -35,6 +35,8 @@
 /* List of parameters, terminated with a param with NULL name */
 const Param sys_param_list[] = {
   {"arch", IS_STRING, "Platform architecture"},
+  {"clear_tpm_owner_request", CAN_WRITE, "Clear TPM owner on next boot"},
+  {"clear_tpm_owner_done", CAN_WRITE, "Clear TPM owner done"},
   {"cros_debug", 0, "OS should allow debug features"},
   {"dbg_reset", CAN_WRITE, "Debug reset mode request (writable)"},
   {"ddr_type", IS_STRING, "Type of DDR RAM"},