[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] [xen-unstable] [VTPM_TOOLS] Hotplug script enabled the vtpm manager and removed the



# HG changeset patch
# User kaf24@xxxxxxxxxxxxxxxxxxxx
# Node ID 8589cdd096360970933a7c9112f2925c52d08696
# Parent  18587d3e94c8c3a6ccdf9bc5965eea426e6df87d
[VTPM_TOOLS] Hotplug script enabled the vtpm manager and removed the
control messages from the BE.

Signed-off-by: Vincent Scarlata <vincent.r.scarlata@xxxxxxxxx>
---
 linux-2.6-xen-sparse/drivers/xen/tpmback/common.h  |    2 
 linux-2.6-xen-sparse/drivers/xen/tpmback/tpmback.c |   89 -------------
 linux-2.6-xen-sparse/drivers/xen/tpmback/xenbus.c  |   23 ---
 tools/examples/Makefile                            |    2 
 tools/examples/vtpm-impl                           |  136 +++++++++++++++++++++
 tools/vtpm_manager/manager/dmictl.c                |   57 +++++---
 tools/vtpm_manager/manager/securestorage.c         |   29 +++-
 tools/vtpm_manager/manager/vtpm_manager.c          |    3 
 tools/vtpm_manager/manager/vtpm_manager.h          |   10 +
 tools/vtpm_manager/manager/vtpm_manager_handler.c  |   75 ++++++-----
 tools/vtpm_manager/manager/vtpmd.c                 |   40 +++---
 tools/vtpm_manager/manager/vtpmpriv.h              |   13 +-
 tools/vtpm_manager/manager/vtsp.c                  |   11 +
 tools/vtpm_manager/manager/vtsp.h                  |    2 
 tools/vtpm_manager/tcs/tcs.c                       |   43 ++++++
 tools/vtpm_manager/tcs/tcs.h                       |    5 
 tools/vtpm_manager/util/tcg.h                      |    5 
 17 files changed, 342 insertions(+), 203 deletions(-)

diff -r 18587d3e94c8 -r 8589cdd09636 
linux-2.6-xen-sparse/drivers/xen/tpmback/common.h
--- a/linux-2.6-xen-sparse/drivers/xen/tpmback/common.h Tue Jun 27 11:14:19 
2006 +0100
+++ b/linux-2.6-xen-sparse/drivers/xen/tpmback/common.h Tue Jun 27 11:15:48 
2006 +0100
@@ -63,8 +63,6 @@ void tpmif_xenbus_exit(void);
 void tpmif_xenbus_exit(void);
 int tpmif_map(tpmif_t *tpmif, unsigned long shared_page, unsigned int evtchn);
 irqreturn_t tpmif_be_int(int irq, void *dev_id, struct pt_regs *regs);
-int tpmif_vtpm_open(tpmif_t *tpmif, domid_t domain, u32 instance);
-int tpmif_vtpm_close(u32 instance);
 
 int vtpm_release_packets(tpmif_t * tpmif, int send_msgs);
 
diff -r 18587d3e94c8 -r 8589cdd09636 
linux-2.6-xen-sparse/drivers/xen/tpmback/tpmback.c
--- a/linux-2.6-xen-sparse/drivers/xen/tpmback/tpmback.c        Tue Jun 27 
11:14:19 2006 +0100
+++ b/linux-2.6-xen-sparse/drivers/xen/tpmback/tpmback.c        Tue Jun 27 
11:15:48 2006 +0100
@@ -685,95 +685,6 @@ static struct miscdevice vtpms_miscdevic
 };
 
 /***************************************************************
- Virtual TPM functions and data stuctures
-***************************************************************/
-
-static u8 create_cmd[] = {
-       1, 193,                 /* 0: TPM_TAG_RQU_COMMAMD */
-       0, 0, 0, 19,            /* 2: length */
-       0, 0, 0, 0x1,           /* 6: VTPM_ORD_OPEN */
-       0,                      /* 10: VTPM type */
-       0, 0, 0, 0,             /* 11: domain id */
-       0, 0, 0, 0              /* 15: instance id */
-};
-
-int tpmif_vtpm_open(tpmif_t * tpmif, domid_t domid, u32 instance)
-{
-       int rc = 0;
-       struct packet *pak;
-
-       pak = packet_alloc(tpmif,
-                          sizeof (create_cmd),
-                          create_cmd[1],
-                          PACKET_FLAG_DISCARD_RESPONSE |
-                          PACKET_FLAG_CHECK_RESPONSESTATUS);
-       if (pak) {
-               u8 buf[sizeof (create_cmd)];
-               u32 domid_no = htonl((u32) domid);
-               u32 instance_no = htonl(instance);
-
-               memcpy(buf, create_cmd, sizeof (create_cmd));
-
-               memcpy(&buf[11], &domid_no, sizeof (u32));
-               memcpy(&buf[15], &instance_no, sizeof (u32));
-
-               /* copy the buffer into the packet */
-               rc = packet_set(pak, buf, sizeof (buf));
-
-               if (rc == 0) {
-                       pak->tpm_instance = 0;
-                       rc = vtpm_queue_packet(pak);
-               }
-               if (rc < 0) {
-                       /* could not be queued or built */
-                       packet_free(pak);
-               }
-       } else {
-               rc = -ENOMEM;
-       }
-       return rc;
-}
-
-static u8 destroy_cmd[] = {
-       1, 193,                 /* 0: TPM_TAG_RQU_COMMAMD */
-       0, 0, 0, 14,            /* 2: length */
-       0, 0, 0, 0x2,           /* 6: VTPM_ORD_CLOSE */
-       0, 0, 0, 0              /* 10: instance id */
-};
-
-int tpmif_vtpm_close(u32 instid)
-{
-       int rc = 0;
-       struct packet *pak;
-
-       pak = packet_alloc(NULL,
-                          sizeof (destroy_cmd),
-                          destroy_cmd[1], PACKET_FLAG_DISCARD_RESPONSE);
-       if (pak) {
-               u8 buf[sizeof (destroy_cmd)];
-               u32 instid_no = htonl(instid);
-
-               memcpy(buf, destroy_cmd, sizeof (destroy_cmd));
-               memcpy(&buf[10], &instid_no, sizeof (u32));
-
-               /* copy the buffer into the packet */
-               rc = packet_set(pak, buf, sizeof (buf));
-
-               if (rc == 0) {
-                       pak->tpm_instance = 0;
-                       rc = vtpm_queue_packet(pak);
-               }
-               if (rc < 0) {
-                       /* could not be queued or built */
-                       packet_free(pak);
-               }
-       } else {
-               rc = -ENOMEM;
-       }
-       return rc;
-}
-
-/***************************************************************
  Utility functions
 ***************************************************************/
 
diff -r 18587d3e94c8 -r 8589cdd09636 
linux-2.6-xen-sparse/drivers/xen/tpmback/xenbus.c
--- a/linux-2.6-xen-sparse/drivers/xen/tpmback/xenbus.c Tue Jun 27 11:14:19 
2006 +0100
+++ b/linux-2.6-xen-sparse/drivers/xen/tpmback/xenbus.c Tue Jun 27 11:15:48 
2006 +0100
@@ -154,11 +154,6 @@ static void frontend_changed(struct xenb
                break;
 
        case XenbusStateClosed:
-               /*
-                * Notify the vTPM manager about the front-end
-                * having left.
-                */
-               tpmif_vtpm_close(be->instance);
                device_unregister(&be->dev->dev);
                tpmback_remove(dev);
                break;
@@ -177,28 +172,10 @@ static void frontend_changed(struct xenb
 
 static void maybe_connect(struct backend_info *be)
 {
-       int err;
-
        if (be->tpmif == NULL || be->tpmif->status == CONNECTED)
                return;
 
        connect(be);
-
-       /*
-        * Notify the vTPM manager about a new front-end.
-        */
-       err = tpmif_vtpm_open(be->tpmif,
-                             be->frontend_id,
-                             be->instance);
-       if (err) {
-               xenbus_dev_error(be->dev, err,
-                                "queueing vtpm open packet");
-               /*
-                * Should close down this device and notify FE
-                * about closure.
-                */
-               return;
-       }
 }
 
 
diff -r 18587d3e94c8 -r 8589cdd09636 tools/examples/Makefile
--- a/tools/examples/Makefile   Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/examples/Makefile   Tue Jun 27 11:15:48 2006 +0100
@@ -32,7 +32,7 @@ XEN_SCRIPT_DATA = xen-script-common.sh l
 XEN_SCRIPT_DATA = xen-script-common.sh locking.sh logging.sh
 XEN_SCRIPT_DATA += xen-hotplug-common.sh xen-network-common.sh vif-common.sh
 XEN_SCRIPT_DATA += block-common.sh vtpm-common.sh vtpm-hotplug-common.sh
-XEN_SCRIPT_DATA += vtpm-migration.sh
+XEN_SCRIPT_DATA += vtpm-migration.sh vtpm-impl
 
 XEN_HOTPLUG_DIR = /etc/hotplug
 XEN_HOTPLUG_SCRIPTS = xen-backend.agent
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/dmictl.c
--- a/tools/vtpm_manager/manager/dmictl.c       Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/dmictl.c       Tue Jun 27 11:15:48 2006 +0100
@@ -76,14 +76,13 @@ TPM_RESULT VTPM_Handle_New_DMI(const buf
   
   VTPM_DMI_RESOURCE *new_dmi=NULL;
   TPM_RESULT status=TPM_FAIL;
-  BYTE type;
-  UINT32 dmi_id, domain_id, *dmi_id_key; 
+  BYTE type, startup_mode;
+  UINT32 dmi_id, *dmi_id_key=NULL; 
 
   if (param_buf == NULL) { // Assume creation of Dom 0 control
-    type = 0;
-    domain_id = VTPM_CTL_DM;
+    type = VTPM_TYPE_NON_MIGRATABLE;
     dmi_id = VTPM_CTL_DM;
-  } else if (buffer_len(param_buf) != sizeof(BYTE) + sizeof(UINT32) *2) {
+  } else if (buffer_len(param_buf) != sizeof(BYTE) + sizeof(BYTE) + 
sizeof(UINT32)) {
     vtpmloginfo(VTPM_LOG_VTPM, "New DMI command wrong length: %d.\n", 
buffer_len(param_buf));
     status = TPM_BAD_PARAMETER;
     goto abort_egress;
@@ -91,13 +90,13 @@ TPM_RESULT VTPM_Handle_New_DMI(const buf
     vtpm_globals->connected_dmis++; // Put this here so we don't count Dom0
     BSG_UnpackList( param_buf->bytes, 3,
                    BSG_TYPE_BYTE, &type,
-                   BSG_TYPE_UINT32, &domain_id,
+                   BSG_TYPE_BYTE, &startup_mode,
                    BSG_TYPE_UINT32,  &dmi_id);
   }
-  
+
   new_dmi = (VTPM_DMI_RESOURCE *) hashtable_search(vtpm_globals->dmi_map, 
&dmi_id);
   if (new_dmi == NULL) { 
-    vtpmloginfo(VTPM_LOG_VTPM, "Creating new DMI instance %d attached on 
domain %d.\n", dmi_id, domain_id);
+    vtpmloginfo(VTPM_LOG_VTPM, "Creating new DMI instance %d attached.\n", 
dmi_id );
     // Brand New DMI. Initialize the persistent pieces
     if ((new_dmi = (VTPM_DMI_RESOURCE *) malloc (sizeof(VTPM_DMI_RESOURCE))) 
== NULL) {
       status = TPM_RESOURCES;
@@ -106,32 +105,44 @@ TPM_RESULT VTPM_Handle_New_DMI(const buf
     memset(new_dmi, 0, sizeof(VTPM_DMI_RESOURCE));
     new_dmi->dmi_id = dmi_id;
     new_dmi->connected = FALSE;
+
+    if (type != VTPM_TYPE_MIGRATED) {
+      new_dmi->dmi_type = type;
+    } else {
+      vtpmlogerror(VTPM_LOG_VTPM, "Creation of VTPM with illegal type.\n");
+      status = TPM_BAD_PARAMETER;
+      goto free_egress;
+    }
     
     if ((dmi_id_key = (UINT32 *) malloc (sizeof(UINT32))) == NULL) {
       status = TPM_RESOURCES;
-      goto abort_egress;
+      goto free_egress;
     }      
     *dmi_id_key = new_dmi->dmi_id;
     
     // install into map
     if (!hashtable_insert(vtpm_globals->dmi_map, dmi_id_key, new_dmi)){
-      free(new_dmi);
-      free(dmi_id_key);
+      vtpmlogerror(VTPM_LOG_VTPM, "Failed to insert instance into table. 
Aborting.\n", dmi_id);
       status = TPM_FAIL;
-      goto egress;
+      goto free_egress;
     }
    
   } else 
-    vtpmloginfo(VTPM_LOG_VTPM, "Re-attaching DMI instance %d on domain %d 
.\n", dmi_id, domain_id);
+    vtpmloginfo(VTPM_LOG_VTPM, "Re-attaching DMI instance %d.\n", dmi_id);
   
   if (new_dmi->connected) {
     vtpmlogerror(VTPM_LOG_VTPM, "Attempt to re-attach, currently attached 
instance %d. Ignoring\n", dmi_id);
     status = TPM_BAD_PARAMETER;
-    goto egress;
-  }
-  
+    goto abort_egress;
+  }
+  
+  if (type == VTPM_TYPE_MIGRATED) {
+    vtpmlogerror(VTPM_LOG_VTPM, "Attempt to re-attach previously migrated 
instance %d without recovering first. Ignoring\n", dmi_id);
+    status = TPM_BAD_PARAMETER;
+    goto abort_egress;
+  }
+
   // Initialize the Non-persistent pieces
-  new_dmi->dmi_domain_id = domain_id;
   new_dmi->NVMLocation = NULL;
   
   new_dmi->TCSContext = 0;
@@ -144,9 +155,13 @@ TPM_RESULT VTPM_Handle_New_DMI(const buf
 
   // Design specific new DMI code. 
   // Includes: create IPCs, Measuring DMI, and maybe launching DMI
-  status = VTPM_New_DMI_Extra(new_dmi);
-  goto egress;
-  
+  status = VTPM_New_DMI_Extra(new_dmi, startup_mode);
+  goto egress;
+  
+ free_egress:   // Error that requires freeing of newly allocated dmi 
+  free(new_dmi);
+  free(dmi_id_key);
+
  abort_egress:
   vtpmlogerror(VTPM_LOG_VTPM, "Failed to create DMI id=%d due to status=%s. 
Cleaning.\n", dmi_id, tpm_get_error_name(status));
   close_dmi(new_dmi );
@@ -221,7 +236,7 @@ TPM_RESULT VTPM_Handle_Delete_DMI( const
     goto abort_egress;
   }
   
-       //TODO: Automatically delete file dmi_res->NVMLocation
+  //vtpm scripts delete file dmi_res->NVMLocation for us
   
   // Close DMI first
   TPMTRYRETURN(close_dmi( dmi_res ));
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/securestorage.c
--- a/tools/vtpm_manager/manager/securestorage.c        Tue Jun 27 11:14:19 
2006 +0100
+++ b/tools/vtpm_manager/manager/securestorage.c        Tue Jun 27 11:15:48 
2006 +0100
@@ -190,8 +190,7 @@ TPM_RESULT VTPM_Handle_Save_NVM(VTPM_DMI
   long bytes_written;
   buffer_t sealed_NVM;
   
-  
-  vtpmloginfo(VTPM_LOG_VTPM_DEEP, "Save_NVMing[%d]: 0x\n", buffer_len(inbuf));
+  vtpmloginfo(VTPM_LOG_VTPM_DEEP, "Saving %d bytes of NVM.\n", 
buffer_len(inbuf));
 
   TPMTRYRETURN( envelope_encrypt(inbuf,
                                  &vtpm_globals->storageKey,
@@ -310,6 +309,7 @@ TPM_RESULT VTPM_SaveManagerData(void) {
   UINT32 bootKeySize = buffer_len(&vtpm_globals->bootKeyWrap);
   struct pack_buf_t storage_key_pack = {storageKeySize, 
vtpm_globals->storageKeyWrap.bytes};
   struct pack_buf_t boot_key_pack = {bootKeySize, 
vtpm_globals->bootKeyWrap.bytes};
+  BYTE vtpm_manager_gen = VTPM_MANAGER_GEN;
 
   struct hashtable_itr *dmi_itr;
   VTPM_DMI_RESOURCE *dmi_res;
@@ -321,7 +321,8 @@ TPM_RESULT VTPM_SaveManagerData(void) {
   boot_key_size =  sizeof(UINT32) +       // bootkeysize
                    bootKeySize;           // boot key
 
-  TPMTRYRETURN(buffer_init(&clear_flat_global, 3*sizeof(TPM_DIGEST) + // Auths
+  TPMTRYRETURN(buffer_init(&clear_flat_global,sizeof(BYTE) + // manager version
+                                              3*sizeof(TPM_DIGEST) + // Auths
                                               sizeof(UINT32) +// storagekeysize
                                               storageKeySize, NULL) ); // 
storage key
 
@@ -332,7 +333,8 @@ TPM_RESULT VTPM_SaveManagerData(void) {
   boot_key_size = BSG_PackList(flat_boot_key, 1,
                                BSG_TPM_SIZE32_DATA, &boot_key_pack);
 
-  BSG_PackList(clear_flat_global.bytes, 3,
+  BSG_PackList(clear_flat_global.bytes, 4,
+                BSG_TYPE_BYTE,    &vtpm_manager_gen,
                 BSG_TPM_AUTHDATA, &vtpm_globals->owner_usage_auth,
                 BSG_TPM_SECRET,   &vtpm_globals->storage_key_usage_auth,
                 BSG_TPM_SIZE32_DATA, &storage_key_pack);
@@ -348,7 +350,7 @@ TPM_RESULT VTPM_SaveManagerData(void) {
 
     flat_dmis = (BYTE *) malloc( 
                      (hashtable_count(vtpm_globals->dmi_map) - 1) * // num 
DMIS (-1 for Dom0)
-                     (sizeof(UINT32) + 2*sizeof(TPM_DIGEST)) ); // Per DMI info
+                     (sizeof(UINT32) +sizeof(BYTE) + 2*sizeof(TPM_DIGEST)) ); 
// Per DMI info
 
     dmi_itr = hashtable_iterator(vtpm_globals->dmi_map);
     do {
@@ -360,8 +362,9 @@ TPM_RESULT VTPM_SaveManagerData(void) {
         continue;
 
 
-      flat_dmis_size += BSG_PackList( flat_dmis + flat_dmis_size, 3,
+      flat_dmis_size += BSG_PackList( flat_dmis + flat_dmis_size, 4,
                                         BSG_TYPE_UINT32, &dmi_res->dmi_id,
+                                        BSG_TYPE_BYTE, &dmi_res->dmi_type,
                                         BSG_TPM_DIGEST, 
&dmi_res->NVM_measurement,
                                         BSG_TPM_DIGEST, 
&dmi_res->DMI_measurement);
 
@@ -408,6 +411,7 @@ TPM_RESULT VTPM_LoadManagerData(void) {
   buffer_t  unsealed_data;
   struct pack_buf_t storage_key_pack, boot_key_pack;
   UINT32 *dmi_id_key, enc_size;
+  BYTE vtpm_manager_gen;
 
   VTPM_DMI_RESOURCE *dmi_res;
   struct stat file_stat;
@@ -458,8 +462,14 @@ TPM_RESULT VTPM_LoadManagerData(void) {
                                  &unsealed_data) );
   step_size += enc_size;
 
+  if (*unsealed_data.bytes != VTPM_MANAGER_GEN) {
+      // Once there is more than one gen, this will include some compatability 
stuff
+      vtpmlogerror(VTPM_LOG_VTPM, "Warning: Manager Data file is gen %d, which 
this manager is gen %d.\n", vtpm_manager_gen, VTPM_MANAGER_GEN);
+  }
+
   // Global Values needing to be saved
-  BSG_UnpackList( unsealed_data.bytes, 3,
+  BSG_UnpackList( unsealed_data.bytes, 4,
+                  BSG_TYPE_BYTE,    &vtpm_manager_gen, 
                   BSG_TPM_AUTHDATA, &vtpm_globals->owner_usage_auth,
                   BSG_TPM_SECRET,   &vtpm_globals->storage_key_usage_auth,
                   BSG_TPM_SIZE32_DATA, &storage_key_pack);
@@ -469,7 +479,7 @@ TPM_RESULT VTPM_LoadManagerData(void) {
 
   // Per DMI values to be saved
   while ( step_size < fh_size ){
-    if (fh_size - step_size < (long) (sizeof(UINT32) + 2*sizeof(TPM_DIGEST))) {
+    if (fh_size - step_size < (long) (sizeof(UINT32) + sizeof(BYTE) + 
2*sizeof(TPM_DIGEST))) {
       vtpmlogerror(VTPM_LOG_VTPM, "Encountered %ld extra bytes at end of 
manager state.\n", fh_size-step_size);
       step_size = fh_size;
     } else {
@@ -478,8 +488,9 @@ TPM_RESULT VTPM_LoadManagerData(void) {
 
       dmi_res->connected = FALSE;
 
-      step_size += BSG_UnpackList(flat_table + step_size, 3,
+      step_size += BSG_UnpackList(flat_table + step_size, 4,
                                  BSG_TYPE_UINT32, &dmi_res->dmi_id,
+                                 BSG_TYPE_BYTE, &dmi_res->dmi_type,
                                  BSG_TPM_DIGEST, &dmi_res->NVM_measurement,
                                  BSG_TPM_DIGEST, &dmi_res->DMI_measurement);
 
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtpm_manager.c
--- a/tools/vtpm_manager/manager/vtpm_manager.c Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtpm_manager.c Tue Jun 27 11:15:48 2006 +0100
@@ -168,6 +168,7 @@ TPM_RESULT VTPM_Create_Manager(){
                               &vtpm_globals->bootKey,
                               TRUE ) );
 
+  TPMTRYRETURN( VTSP_SaveState(vtpm_globals->manager_tcs_handle) );
   goto egress;
   
  abort_egress:
@@ -218,7 +219,7 @@ TPM_RESULT VTPM_Init_Manager() {
                           &vtpm_globals->keyAuth) );
   vtpm_globals->keyAuth.fContinueAuthSession = TRUE;
 
-       // If failed, create new Manager.
+  // If failed, create new Manager.
   serviceStatus = VTPM_LoadManagerData();
   if (serviceStatus == TPM_IOERROR) {
     vtpmloginfo(VTPM_LOG_VTPM, "Failed to read manager file. Assuming first 
time initialization.\n");
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtpm_manager.h
--- a/tools/vtpm_manager/manager/vtpm_manager.h Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtpm_manager.h Tue Jun 27 11:15:48 2006 +0100
@@ -73,6 +73,12 @@
 #define VTPM_RESTORE_CONTEXT_FAILED    4
 #define VTPM_INVALID_REQUEST       5
 
+//*********************** Parameter Values *************************
+#define VTPM_TYPE_NON_MIGRATABLE  0x00
+#define VTPM_TYPE_MIGRATABLE      0x01
+#define VTPM_TYPE_MIGRATED        0xFF // VTPM has been migrated.
+                                       // VTPM can be recovered or deleted only
+
 /******************* Command Parameter API *************************
 
 VTPM Command Format
@@ -94,8 +100,8 @@ VTPM Response Format
 
 VTPM_Open:
   Input Parameters:
-    Domain_type: 1 byte
-    domain_id: 4 bytes
+    Domain_type: 1 byte 
+    startup_mode: 1 byte // Cold Boot = 1, resume = 2, deactive = 3
     instance_id: 4 bytes
   Output Parameters:
     None
diff -r 18587d3e94c8 -r 8589cdd09636 
tools/vtpm_manager/manager/vtpm_manager_handler.c
--- a/tools/vtpm_manager/manager/vtpm_manager_handler.c Tue Jun 27 11:14:19 
2006 +0100
+++ b/tools/vtpm_manager/manager/vtpm_manager_handler.c Tue Jun 27 11:15:48 
2006 +0100
@@ -78,13 +78,14 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
                                  BOOL is_priv,
                                  char *thread_name) {
   TPM_RESULT      status =  TPM_FAIL; // Should never return
-  UINT32          dmi, in_param_size, cmd_size, out_param_size, 
out_message_size, out_message_size_full;
-  BYTE            *cmd_header, *in_param, *out_message;
+  UINT32          dmi, in_param_size, cmd_size, out_param_size, 
out_message_size, reply_size;
+  BYTE            *cmd_header=NULL, *in_param=NULL, *out_message=NULL, *reply;
   buffer_t        *command_buf=NULL, *result_buf=NULL;
   TPM_TAG         tag;
   TPM_COMMAND_CODE ord;
   VTPM_DMI_RESOURCE *dmi_res;
   int  size_read, size_write, i;
+  BOOL add_header=TRUE; // This indicates to prepend a header on result_buf 
before sending
   
   cmd_header = (BYTE *) malloc(VTPM_COMMAND_HEADER_SIZE_SRV);
   command_buf = (buffer_t *) malloc(sizeof(buffer_t));
@@ -100,7 +101,7 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
     // Read command header 
     size_read = vtpm_ipc_read(rx_ipc_h, NULL, cmd_header, 
VTPM_COMMAND_HEADER_SIZE_SRV);
     if (size_read > 0) {
-      vtpmhandlerloginfo(VTPM_LOG_VTPM_DEEP, "RECV[%d}: 0x", size_read);
+      vtpmhandlerloginfo(VTPM_LOG_VTPM_DEEP, "RECV[%d]: 0x", size_read);
       for (i=0; i<size_read; i++) 
        vtpmhandlerloginfomore(VTPM_LOG_VTPM_DEEP, "%x ", cmd_header[i]);
     } else {
@@ -165,6 +166,7 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
          (!dmi_res->connected) ) {
       vtpmhandlerlogerror(VTPM_LOG_VTPM, "Attempted access to non-existent or 
disconnected DMI %d. Aborting...\n", dmi);
       status = TPM_BAD_PARAMETER;
+      goto abort_with_error;
     }
 
     if (tag == VTPM_TAG_REQ) { 
@@ -176,9 +178,14 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
         status = vtpm_manager_handle_tpm_cmd(fw_tx_ipc_h, fw_rx_ipc_h, 
dmi_res, cmd_header, command_buf, result_buf, thread_name);
 
         // This means calling the DMI failed, not that the cmd failed in the 
DMI
+        // Since the return will be interpretted by a TPM app, all errors are 
IO_ERRORs to the app
         if (status != TPM_SUCCESS) { 
+          status = TPM_IOERROR;
          goto abort_with_error;
         }
+        // Unlike all other commands, forwarded commands yield a result_buf 
that includes the DMI's status. This
+        // should be forwarded to the caller VM
+        add_header = FALSE;
       } else {
         // We are not supposed to forward TPM commands at all.
         int i;
@@ -205,38 +212,43 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
 #ifndef VTPM_MULTI_VM
  abort_with_error:
 #endif
-    
-    // Prepend VTPM header with destination DM stamped
-    out_param_size = buffer_len(result_buf);
-    out_message_size = VTPM_COMMAND_HEADER_SIZE_CLT + out_param_size;
-    out_message_size_full = VTPM_COMMAND_HEADER_SIZE_SRV + out_param_size;
-    out_message = (BYTE *) malloc (out_message_size_full);
-    
-    BSG_PackList(out_message, 4,
-                BSG_TYPE_UINT32, (BYTE *) &dmi,
-                BSG_TPM_TAG, (BYTE *) &tag,
-                BSG_TYPE_UINT32, (BYTE *) &out_message_size,
-                BSG_TPM_RESULT, (BYTE *) &status);
-    
-    if (buffer_len(result_buf) > 0) 
-      memcpy(out_message + VTPM_COMMAND_HEADER_SIZE_SRV, result_buf->bytes, 
out_param_size);
-
-    //Note: Send message + dmi_id
-    size_write = vtpm_ipc_write(tx_ipc_h, dmi_res->tx_vtpm_ipc_h, out_message, 
out_message_size_full );
+   
+    if (add_header) { 
+      // Prepend VTPM header with destination DM stamped
+      out_param_size = buffer_len(result_buf);
+      out_message_size = VTPM_COMMAND_HEADER_SIZE_CLT + out_param_size;
+      reply_size = VTPM_COMMAND_HEADER_SIZE_SRV + out_param_size;
+      out_message = (BYTE *) malloc (reply_size);
+      reply = out_message;
+    
+      BSG_PackList(out_message, 4,
+                  BSG_TYPE_UINT32, (BYTE *) &dmi,
+                  BSG_TPM_TAG, (BYTE *) &tag,
+                  BSG_TYPE_UINT32, (BYTE *) &out_message_size,
+                  BSG_TPM_RESULT, (BYTE *) &status);
+    
+      if (buffer_len(result_buf) > 0) 
+        memcpy(out_message + VTPM_COMMAND_HEADER_SIZE_SRV, result_buf->bytes, 
out_param_size);
+      //Note: Send message + dmi_id
+    } else {
+      reply = result_buf->bytes;
+      reply_size = buffer_len(result_buf);
+    }  
+    size_write = vtpm_ipc_write(tx_ipc_h, (dmi_res ? dmi_res->tx_vtpm_ipc_h : 
NULL), reply, reply_size );
     if (size_write > 0) {
       vtpmhandlerloginfo(VTPM_LOG_VTPM_DEEP, "SENT: 0x");
-      for (i=0; i < out_message_size_full; i++) 
-       vtpmhandlerloginfomore(VTPM_LOG_VTPM_DEEP, "%x ", out_message[i]);
+      for (i=0; i < reply_size; i++) 
+       vtpmhandlerloginfomore(VTPM_LOG_VTPM_DEEP, "%x ", reply[i]);
       
       vtpmhandlerloginfomore(VTPM_LOG_VTPM_DEEP, "\n");            
     } else {
       vtpmhandlerlogerror(VTPM_LOG_VTPM, "%s had error writing to ipc. 
Aborting... \n", thread_name);
       goto abort_command;
     }
-    free(out_message);
-    
-    if (size_write < (int)out_message_size_full) {
-      vtpmhandlerlogerror(VTPM_LOG_VTPM, "%s unable to write full command to 
ipc (%d/%d)\n", thread_name, size_write, out_message_size_full);
+    free(out_message); out_message=NULL;
+    
+    if (size_write < (int)reply_size) {
+      vtpmhandlerlogerror(VTPM_LOG_VTPM, "%s unable to write full command to 
ipc (%d/%d)\n", thread_name, size_write, reply_size);
       goto abort_command;
     }
     
@@ -246,9 +258,7 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
     //free buffers
     bzero(cmd_header, VTPM_COMMAND_HEADER_SIZE_SRV);
     //free(in_param); // This was converted to command_buf. No need to free 
-    if (command_buf != result_buf) 
-      buffer_free(result_buf);
-    
+    buffer_free(result_buf);
     buffer_free(command_buf);
 
     // If we have a write lock, save the manager table
@@ -258,6 +268,7 @@ TPM_RESULT VTPM_Manager_Handler( vtpm_ip
     }
 
     vtpm_lock_unlock();
+    add_header = TRUE; // Reset to the default
   } // End while(1)
   
 }
@@ -369,6 +380,7 @@ TPM_RESULT vtpm_manager_handle_tpm_cmd(v
     dmi_cmd_size = VTPM_COMMAND_HEADER_SIZE_SRV;
     size_write = vtpm_ipc_write(tx_ipc_h, dmi_res->tx_tpm_ipc_h, cmd_header, 
VTPM_COMMAND_HEADER_SIZE_SRV );
     if (size_write > 0) {
+      vtpmhandlerloginfo(VTPM_LOG_VTPM_DEEP, "SENT (DMI): 0x");
       for (i=0; i<VTPM_COMMAND_HEADER_SIZE_SRV; i++) 
         vtpmhandlerloginfomore(VTPM_LOG_VTPM_DEEP, "%x ", cmd_header[i]);
 
@@ -438,7 +450,8 @@ TPM_RESULT vtpm_manager_handle_tpm_cmd(v
     vtpmhandlerloginfomore(VTPM_LOG_VTPM, "\n");
   }
    
-  if (buffer_init_convert(result_buf, adj_param_size, in_param) != 
TPM_SUCCESS) {
+  if ( (buffer_init(result_buf, VTPM_COMMAND_HEADER_SIZE_SRV, cmd_header) != 
TPM_SUCCESS) || 
+       (buffer_append_raw(result_buf, adj_param_size, in_param) != 
TPM_SUCCESS) ) {
     vtpmhandlerlogerror(VTPM_LOG_VTPM, "Failed to setup buffers. 
Aborting...\n");
     status = TPM_FAIL;
     goto abort_with_error;
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtpmd.c
--- a/tools/vtpm_manager/manager/vtpmd.c        Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtpmd.c        Tue Jun 27 11:15:48 2006 +0100
@@ -64,14 +64,6 @@
 #define VTPM_TX_HP_FNAME       "/var/vtpm/fifos/to_console.fifo"
 #define VTPM_RX_HP_FNAME       "/var/vtpm/fifos/from_console.fifo"
 
-
-#define GUEST_TX_FIFO "/var/vtpm/fifos/guest-to-%d.fifo"
-#define GUEST_RX_FIFO "/var/vtpm/fifos/guest-from-all.fifo"
-
-#define VTPM_TX_FIFO  "/var/vtpm/fifos/vtpm-to-%d.fifo"
-#define VTPM_RX_FIFO  "/var/vtpm/fifos/vtpm-from-all.fifo"
-
-
 struct vtpm_thread_params_s {
   vtpm_ipc_handle_t *tx_ipc_h;
   vtpm_ipc_handle_t *rx_ipc_h;
@@ -113,7 +105,7 @@ void signal_handler(int reason) {
 
 struct sigaction ctl_c_handler;
 
-TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_RESOURCE *dmi_res) {
+TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_RESOURCE *dmi_res, BYTE startup_mode) {
 
   TPM_RESULT status = TPM_SUCCESS;
   int fh;
@@ -150,14 +142,14 @@ TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_R
 
     // Measure DMI
     // FIXME: This will measure DMI. Until then use a fixed DMI_Measurement 
value
-    // Also, this mechanism is specific to 1 VM.
+    // Also, this mechanism is specific to 1 VM architecture.
     /*
     fh = open(TPM_EMULATOR_PATH, O_RDONLY);
     stat_ret = fstat(fh, &file_stat);
     if (stat_ret == 0)
       dmi_size = file_stat.st_size;
     else {
-      vtpmlogerror(VTPM_LOG_VTPM, "Could not open tpm_emulator!!\n");
+      vtpmlogerror(VTPM_LOG_VTPM, "Could not open vtpmd!!\n");
       status = TPM_IOERROR;
       goto abort_egress;
     }
@@ -179,10 +171,20 @@ TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_R
       status = TPM_RESOURCES;
       goto abort_egress;
     } else if (pid == 0) {
-      if ( stat(dmi_res->NVMLocation, &file_info) == -1)
+      switch (startup_mode) {
+      case TPM_ST_CLEAR:
         execl (TPM_EMULATOR_PATH, "vtmpd", "clear", dmi_id_str, NULL);
-      else
+        break;
+      case TPM_ST_STATE:
         execl (TPM_EMULATOR_PATH, "vtpmd", "save", dmi_id_str, NULL);
+        break;
+      case TPM_ST_DEACTIVATED:
+        execl (TPM_EMULATOR_PATH, "vtpmd", "deactivated", dmi_id_str, NULL);
+        break;
+      default:
+        status = TPM_BAD_PARAMETER;
+        goto abort_egress;
+      }
 
       // Returning from these at all is an error.
       vtpmlogerror(VTPM_LOG_VTPM, "Could not exec to launch vtpm\n");
@@ -309,7 +311,7 @@ int main(int argc, char **argv) {
   be_thread_params.fw_tpm = TRUE;
   be_thread_params.fw_tx_ipc_h = NULL;
   be_thread_params.fw_rx_ipc_h = &rx_tpm_ipc_h;
-  be_thread_params.is_priv = TRUE;                   //FIXME: Change when HP 
is up
+  be_thread_params.is_priv = FALSE;
   be_thread_params.thread_name = "Backend Listener";
 
   dmi_thread_params.tx_ipc_h = NULL;
@@ -318,7 +320,7 @@ int main(int argc, char **argv) {
   dmi_thread_params.fw_tx_ipc_h = NULL;
   dmi_thread_params.fw_rx_ipc_h = NULL;
   dmi_thread_params.is_priv = FALSE; 
-  dmi_thread_params.thread_name = "VTPM Listeners";
+  dmi_thread_params.thread_name = "VTPM Listener";
 
   hp_thread_params.tx_ipc_h = &tx_hp_ipc_h;
   hp_thread_params.rx_ipc_h = &rx_hp_ipc_h;
@@ -345,10 +347,10 @@ int main(int argc, char **argv) {
   }
 
  
-//  if (pthread_create(&hp_thread, NULL, vtpm_manager_thread, 
&hp_thread_params) != 0) {
-//    vtpmlogerror(VTPM_LOG_VTPM, "Failed to launch HP Thread.\n");
-//    exit(-1);
-//  }
+  if (pthread_create(&hp_thread, NULL, vtpm_manager_thread, &hp_thread_params) 
!= 0) {
+    vtpmlogerror(VTPM_LOG_VTPM, "Failed to launch HP Thread.\n");
+    exit(-1);
+  }
  
   //Join the other threads until exit time.
   pthread_join(be_thread, NULL);
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtpmpriv.h
--- a/tools/vtpm_manager/manager/vtpmpriv.h     Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtpmpriv.h     Tue Jun 27 11:15:48 2006 +0100
@@ -40,15 +40,19 @@
 #ifndef __VTPMPRIV_H__
 #define __VTPMPRIV_H__
 
+#include "vtpm_manager.h"
 #include "tcg.h"
 #include "tcs.h"
 #include "buffer.h"
 #include "crypto.h"
 #include "vtpm_ipc.h"
 
-#define STATE_FILE    "/var/vtpm/VTPM"
-#define DMI_NVM_FILE  "/var/vtpm/vtpm_dm_%d.data"
-#define VTPM_CTL_DM   0
+#define VTPM_MANAGER_GEN   2     // This is incremented when the manager's 
table
+                                 // is changed. It's used for backwards 
compatability
+
+#define STATE_FILE         "/var/vtpm/VTPM"
+#define DMI_NVM_FILE       "/var/vtpm/vtpm_dm_%d.data"
+#define VTPM_CTL_DM        0
 
 // ------------------------ Private Structures -----------------------
 typedef struct VTPM_DMI_RESOURCE_T {
@@ -70,6 +74,7 @@ typedef struct VTPM_DMI_RESOURCE_T {
                                         // of NVM.
   // Persistent Information about DMI
   UINT32                dmi_id;
+  BYTE                  dmi_type;
   TPM_DIGEST            NVM_measurement;  // Equal to the SHA1 of the blob
   TPM_DIGEST            DMI_measurement;  // Correct measurement of the owning 
DMI
 } VTPM_DMI_RESOURCE;
@@ -138,7 +143,7 @@ TPM_RESULT VTPM_SaveManagerData(void);
 TPM_RESULT VTPM_SaveManagerData(void);
 TPM_RESULT VTPM_LoadManagerData(void);
 
-TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_RESOURCE *dmi_res);
+TPM_RESULT VTPM_New_DMI_Extra(VTPM_DMI_RESOURCE *dmi_res, BYTE startup_mode);
 
 TPM_RESULT VTPM_Close_DMI_Extra(VTPM_DMI_RESOURCE *dmi_res);
 
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtsp.c
--- a/tools/vtpm_manager/manager/vtsp.c Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtsp.c Tue Jun 27 11:15:48 2006 +0100
@@ -971,6 +971,17 @@ TPM_RESULT VTSP_Unseal(const TCS_CONTEXT
   return status;
 }
 
+TPM_RESULT VTSP_SaveState( const TCS_CONTEXT_HANDLE    hContext) {
+
+  vtpmloginfo(VTPM_LOG_VTSP, "Calling TPM_SaveState.\n");
+
+  TPM_RESULT status = TPM_SUCCESS;
+
+  // Call TCS
+  return ( TCSP_SaveState ( hContext ) );
+
+}
+
 
 // Function Reaches into unsupported TCS command, beware.
 TPM_RESULT VTSP_RawTransmit(const TCS_CONTEXT_HANDLE    hContext,
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/manager/vtsp.h
--- a/tools/vtpm_manager/manager/vtsp.h Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/manager/vtsp.h Tue Jun 27 11:15:48 2006 +0100
@@ -118,4 +118,6 @@ TPM_RESULT VTSP_Unseal(const TCS_CONTEXT
                        TCS_AUTH                    *auth,
                        TCS_AUTH                    *dataAuth);
 
+TPM_RESULT VTSP_SaveState( const TCS_CONTEXT_HANDLE    hContext);
+
 #endif //_VTSP_H_
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/tcs/tcs.c
--- a/tools/vtpm_manager/tcs/tcs.c      Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/tcs/tcs.c      Tue Jun 27 11:15:48 2006 +0100
@@ -1126,6 +1126,49 @@ TPM_RESULT TCSP_ReadPubek(TCS_CONTEXT_HA
   return(returnCode);
 }
 
+
+TPM_RESULT TCSP_SaveState(TCS_CONTEXT_HANDLE   hContext)  // in
+{
+  // setup input/output parameters block
+  TPM_TAG tag = TPM_TAG_RQU_COMMAND;
+  UINT32 paramSize = 0;
+  TPM_COMMAND_CODE ordinal = TPM_ORD_SaveState;
+  TPM_RESULT returnCode = TPM_SUCCESS;
+
+  // setup the TPM driver input and output buffers
+  TDDL_RESULT hRes = TDDL_E_FAIL;
+  TDDL_UINT32  InLength = TCPA_MAX_BUFFER_LENGTH;
+  TDDL_UINT32  OutLength = TCPA_MAX_BUFFER_LENGTH;
+
+  // Convert Byte Input parameter in the input byte stream InBuf
+  InLength = BSG_PackList(InBuf, 3,
+                          BSG_TPM_TAG, &tag,
+                          BSG_TYPE_UINT32, &paramSize,
+                          BSG_TPM_COMMAND_CODE, &ordinal);
+  // fill paramSize again as we now have the correct size
+  BSG_Pack(BSG_TYPE_UINT32, &InLength, InBuf+2);
+
+  vtpmloginfo(VTPM_LOG_TCS_DEEP, "Sending paramSize = %d\n", InLength);
+
+  // call the TPM driver
+  if ((hRes = TDDL_TransmitData(InBuf, InLength, OutBuf, &OutLength)) == 
TDDL_SUCCESS) {
+    // unpack OutBuf to get the tag, paramSize, & returnCode
+    BSG_UnpackList(OutBuf, 3,
+                           BSG_TPM_TAG, &tag,
+                           BSG_TYPE_UINT32, &paramSize,
+                           BSG_TPM_COMMAND_CODE, &returnCode);
+
+    if (returnCode == TPM_SUCCESS && tag == TPM_TAG_RSP_COMMAND) {
+      vtpmloginfo(VTPM_LOG_TCS_DEEP, "Received paramSize : %d\n", paramSize);
+    } else {
+      vtpmlogerror(VTPM_LOG_TCS, "TCSP_SaveState Failed with return code 
%s\n", tpm_get_error_name(returnCode));
+    }
+  }
+
+  return(returnCode);
+}
+
+
 TPM_RESULT TCSP_RawTransmitData(   UINT32 inDataSize,  // in
                                   BYTE *inData,       // in
                                   UINT32 *outDataSize,// in/out
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/tcs/tcs.h
--- a/tools/vtpm_manager/tcs/tcs.h      Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/tcs/tcs.h      Tue Jun 27 11:15:48 2006 +0100
@@ -229,7 +229,10 @@ TPM_RESULT TCSP_ReadPubek (  TCS_CONTEXT
                             );
 
 
-// Non-Standard TCSP call to give direct access to TransmitData.
+// Non-Standard TCSP calls
+TPM_RESULT TCSP_SaveState(TCS_CONTEXT_HANDLE   hContext);  // in
+
+//Give direct access to TransmitData.
 // Key and Auth Management is done before transfering command to TDDL.
 TPM_RESULT TCSP_RawTransmitData(UINT32 inDataSize,  // in
                                BYTE *inData,       // in
diff -r 18587d3e94c8 -r 8589cdd09636 tools/vtpm_manager/util/tcg.h
--- a/tools/vtpm_manager/util/tcg.h     Tue Jun 27 11:14:19 2006 +0100
+++ b/tools/vtpm_manager/util/tcg.h     Tue Jun 27 11:15:48 2006 +0100
@@ -389,6 +389,11 @@ typedef struct pack_constbuf_t {
 #define TPM_DELEGATE_ADMIN      TPM_BASE + 77 // Delegation table management 
not enabled
 #define TPM_TRANSPORT_EXCLUSIVE    TPM_BASE + 78 // There was a command 
executed outside of an exclusive transport session
 
+// TPM_STARTUP_TYPE values
+#define TPM_ST_CLEAR 0x0001
+#define TPM_ST_STATE 0x0002
+#define TPM_ST_DEACTIVATED 0x003
+
 // TPM_TAG values
 #define TPM_TAG_RQU_COMMAND 0x00c1
 #define TPM_TAG_RQU_AUTH1_COMMAND 0x00c2
diff -r 18587d3e94c8 -r 8589cdd09636 tools/examples/vtpm-impl
--- /dev/null   Thu Jan 01 00:00:00 1970 +0000
+++ b/tools/examples/vtpm-impl  Tue Jun 27 11:15:48 2006 +0100
@@ -0,0 +1,136 @@
+#!/bin/bash
+# ===================================================================
+# 
+# Copyright (c) 2005, Intel Corp.
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without 
+# modification, are permitted provided that the following conditions 
+# are met:
+#
+#   * Redistributions of source code must retain the above copyright 
+#     notice, this list of conditions and the following disclaimer.
+#   * Redistributions in binary form must reproduce the above 
+#     copyright notice, this list of conditions and the following 
+#     disclaimer in the documentation and/or other materials provided 
+#     with the distribution.
+#   * Neither the name of Intel Corporation nor the names of its 
+#     contributors may be used to endorse or promote products derived
+#     from this software without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
+# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 
+# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 
+# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 
+# COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 
+# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 
+# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+# OF THE POSSIBILITY OF SUCH DAMAGE.
+# ===================================================================
+
+VTPM_IMPL_DEFINED=1
+
+#            |        SRC        |    TAG  |      CMD SIZE     |        ORD    
   | type| mode
+TPM_CMD_OPEN=\\x00\\x00\\x00\\x00\\x01\\xc1\\x00\\x00\\x00\\x10\\x01\\x00\\x00\\x01\\x01\\x01
+TPM_CMD_RESM=\\x00\\x00\\x00\\x00\\x01\\xc1\\x00\\x00\\x00\\x10\\x01\\x00\\x00\\x01\\x01\\x02
+TPM_CMD_CLOS=\\x00\\x00\\x00\\x00\\x01\\xc1\\x00\\x00\\x00\\x0e\\x01\\x00\\x00\\x02
+TPM_CMD_DELE=\\x00\\x00\\x00\\x00\\x01\\xc1\\x00\\x00\\x00\\x0e\\x01\\x00\\x00\\x03
+
+TPM_SUCCESS=00000000
+
+TX_VTPM_MANAGER=/var/vtpm/fifos/from_console.fifo
+RX_VTPM_MANAGER=/var/vtpm/fifos/to_console.fifo
+
+# -------------------- Helpers for binary streams -----------
+
+function str_to_hex32() {
+ printf "%0.8x" $1
+}
+
+function hex32_to_bin() {
+ local inst=$(str_to_hex32 $1);
+ 
+ local n1=`echo $inst | sed 's/\(..\)....../\\\\x\1/'`
+ local n2=`echo $inst | sed 's/..\(..\)..../\\\\x\1/'`
+ local n3=`echo $inst | sed 's/....\(..\)../\\\\x\1/'`
+ local n4=`echo $inst | sed 's/......\(..\)/\\\\x\1/'`
+
+ echo "$n1$n2$n3$n4"
+}
+
+function vtpm_manager_cmd() {
+ local cmd=$1;
+ local inst=$2;
+ local inst_bin=$(hex32_to_bin $inst);
+
+ #send cmd to vtpm_manager
+ printf "$cmd$inst_bin" > $TX_VTPM_MANAGER
+
+ #recv response
+ local resp_hex=`dd skip=10 bs=1 count=4 if=$RX_VTPM_MANAGER 2> /dev/null | 
xxd -ps`
+
+ #return whether the command was successful
+ if [ $resp_hex != $TPM_SUCCESS ]; then
+   vtpm_fatal_error=1
+   false
+  else
+   true
+ fi
+}
+
+# ------------------ Command handlers -----------------
+
+# Create new vtpm instance & set it up for use
+function vtpm_create () {
+ # Creation is handled implicitly by the manager on first setup
+ # so just set it up for use
+ $(vtpm_start $1)
+}
+
+# Setup vtpm instance for use.
+function vtpm_start() {
+ $(vtpm_manager_cmd $TPM_CMD_OPEN $1)
+}
+
+function vtpm_resume() {
+ $(vtpm_manager_cmd $TPM_CMD_RESM $1)
+}
+
+# Reset the vtpm AKA clear PCRs
+function vtpm_reset() {
+ #not used by current implemenation
+ true
+}
+
+# Shutdown the vtpm while the vm is down
+# This could be a suspend of shutdown
+# we cannot distinquish, so save the state
+# and decide on startup if we should keep is
+function vtpm_suspend() {
+ $(vtpm_manager_cmd $TPM_CMD_CLOS $1)
+}
+
+
+function vtpm_delete() {
+ local inst=$1
+ if $(vtpm_manager_cmd $TPM_CMD_DELE $inst); then
+   rm -f /var/vtpm/vtpm_dm_$1.data
+   true
+ else 
+   vtpm_fatal_error=1
+   false
+ fi
+}
+
+function vtpm_migrate() {
+ echo "Error: vTPM migration accross machines not implemented."
+}
+
+function vtpm_migrate_recover() {
+ true
+}
+

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.