# HG changeset patch
# User Keir Fraser <keir.fraser@xxxxxxxxxx>
# Date 1251097732 -3600
# Node ID 4e67ba3c321affda3f90734ba62ce04b23fce66c
# Parent dde06d43143b71a72d979d8040a887534e321b32
vtpm: Upgrade to using tpm_emulator-0.5.1
The newer version of the emulator contains several bug fixes, one that
we were seeing in our use of vtpm.
This patch also defines TPM_STRONG_PERSISTENCE for the new emulator.
A couple of important notes about this patch:
-This has only been tested on PVM domU's. In theory it should work for
HVM but I have not tried it at all and can guarantee nothing.
-All the relevant changes in tools/vtpm/vtpm.patch have been ported
to tpm_emulator-0.5.1.
-None of the changes in tpm_emulator.patch have been ported. In
particular this means the BUILD_EMULATOR option, which as I understand
lets you use the tpm_emulator in dom0 for a machine that does
not have a real hardware TPM does not work. This functionality should
be easy to add though because the new emulator already comes with a
kernel module interface.
-No considerations were made for the VTPM_MULTI_VM feature (which is
supposedly unfinished). This patch may or may not break any progress
made on that feature.
Signed-off-by: Matt Fioravante <Matthew.Fioravante@xxxxxxxxxx>
---
tools/vtpm/Makefile | 34 ----
tools/vtpm/vtpm-0.5.1.patch | 301 ++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 307 insertions(+), 28 deletions(-)
diff -r dde06d43143b -r 4e67ba3c321a tools/vtpm/Makefile
--- a/tools/vtpm/Makefile Mon Aug 24 08:05:46 2009 +0100
+++ b/tools/vtpm/Makefile Mon Aug 24 08:08:52 2009 +0100
@@ -10,7 +10,7 @@ ORIG_DIR = orig
ORIG_DIR = orig
# Emulator tarball name
-TPM_EMULATOR_NAME = tpm_emulator-0.4
+TPM_EMULATOR_NAME = tpm_emulator-0.5.1
TPM_EMULATOR_TARFILE = $(TPM_EMULATOR_NAME).tar.gz
GMP_HEADER = /usr/include/gmp.h
@@ -19,13 +19,10 @@ all: build
all: build
.PHONY: build
-build: $(VTPM_DIR) $(TPM_EMULATOR_DIR) build_sub
+build: build_sub
.PHONY: install
install: build
- if [ "$(BUILD_EMULATOR)" = "y" ]; then \
- $(MAKE) -C $(TPM_EMULATOR_DIR) $@ ;\
- fi
$(MAKE) -C $(VTPM_DIR) $@
.PHONY: clean
@@ -46,25 +43,14 @@ mrproper:
$(TPM_EMULATOR_TARFILE):
wget http://download.berlios.de/tpm-emulator/$(TPM_EMULATOR_TARFILE)
-# Create vtpm and TPM emulator dirs
-# apply patches for 1) used as dom0 tpm driver 2) used as vtpm device instance
-$(TPM_EMULATOR_DIR): $(TPM_EMULATOR_TARFILE) tpm_emulator.patch
- set -e; if [ "$(BUILD_EMULATOR)" = "y" ]; then \
- rm -rf $(TPM_EMULATOR_DIR); \
- tar -xzf $(TPM_EMULATOR_TARFILE); \
- mv $(TPM_EMULATOR_NAME) $(TPM_EMULATOR_DIR); \
- cd $(TPM_EMULATOR_DIR); \
- patch -p1 <../tpm_emulator.patch; \
- fi
-
-$(VTPM_DIR): $(TPM_EMULATOR_TARFILE) vtpm.patch
+# Create vtpm dirs
+$(VTPM_DIR)/tpmd/tpmd: $(TPM_EMULATOR_TARFILE) vtpm-0.5.1.patch
rm -rf $(VTPM_DIR)
tar -xzf $(TPM_EMULATOR_TARFILE)
mv $(TPM_EMULATOR_NAME) $(VTPM_DIR)
set -e; cd $(VTPM_DIR); \
- patch -p1 < ../tpm_emulator.patch; \
- patch -p1 < ../vtpm.patch
+ patch -p1 < ../vtpm-0.5.1.patch
orig: $(TPM_EMULATOR_TARFILE)
mkdir $(ORIG_DIR);
@@ -72,22 +58,14 @@ orig: $(TPM_EMULATOR_TARFILE)
tar -xzf ../$(TPM_EMULATOR_TARFILE);
updatepatches: clean orig
- set -e; if [ "$(BUILD_EMULATOR)" = "y" ]; then \
- find $(TPM_EMULATOR_DIR) -name "*.orig" -print | xargs rm -f; \
- mv tpm_emulator.patch tpm_emulator.patch.old; \
- diff -uprN orig/$(TPM_EMULATOR_NAME) $(TPM_EMULATOR_DIR) >
tpm_emulator.patch || true; \
- fi;
find $(VTPM_DIR) -name "*.orig" -print | xargs rm -f;
mv vtpm.patch vtpm.patch.old;
diff -uprN $(TPM_EMULATOR_DIR) $(VTPM_DIR) > vtpm.patch || true;
.PHONY: build_sub
-build_sub:
+build_sub: $(VTPM_DIR)/tpmd/tpmd
set -e; if [ -e $(GMP_HEADER) ]; then \
$(MAKE) -C $(VTPM_DIR); \
- if [ "$(BUILD_EMULATOR)" = "y" ]; then \
- $(MAKE) -C $(TPM_EMULATOR_DIR); \
- fi \
else \
echo "=== Unable to build VTPMs. libgmp could not be found."; \
fi
diff -r dde06d43143b -r 4e67ba3c321a tools/vtpm/vtpm-0.5.1.patch
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/tools/vtpm/vtpm-0.5.1.patch Mon Aug 24 08:08:52 2009 +0100
@@ -0,0 +1,766 @@
+diff -Naurp tpm_emulator-0.5.1/Makefile tpm5-test/Makefile
+--- tpm_emulator-0.5.1/Makefile 2008-02-14 03:22:48.000000000 -0500
++++ tpm5-test/Makefile 2009-07-15 09:45:28.000000000 -0400
+@@ -10,7 +10,7 @@ VERSION_MINOR := 5
+ VERSION_BUILD := $(shell date +"%s")
+ VERSION_SUFFIX := .1
+
+-SUBDIRS := tpmd tpmd_dev tddl
++SUBDIRS := tpmd
+
+ all: version all-recursive
+
+@@ -48,12 +48,12 @@ user_install: user
+ modules_install: modules
+ @$(MAKE) -C tpmd_dev install || exit -1
+
+-DIRS := . tpm crypto tpmd tpmd_dev tddl tpmd_dev_openbsd
++DIRS := . tpm crypto tpmd
+ DISTSRC := $(foreach dir, $(DIRS), $(wildcard $(dir)/*.c))
+ DISTSRC += $(foreach dir, $(DIRS), $(wildcard $(dir)/*.h))
+-DIRS := . tpmd tpmd_dev tddl tpmd_dev_openbsd
++DIRS := . tpmd
+ DISTSRC += $(foreach dir, $(DIRS), $(dir)/Makefile)
+-DISTSRC += ./README ./AUTHORS ./ChangeLog tpmd_dev/tpmd_dev.rules.in
++DISTSRC += ./README ./AUTHORS ./ChangeLog
+ DISTDIR := tpm_emulator-$(VERSION_MAJOR).$(VERSION_MINOR)$(VERSION_SUFFIX)
+
+ dist: $(DISTSRC)
+diff -Naurp tpm_emulator-0.5.1/tpm/tpm_capability.c
tpm5-test/tpm/tpm_capability.c
+--- tpm_emulator-0.5.1/tpm/tpm_capability.c 2008-02-14 03:22:48.000000000
-0500
++++ tpm5-test/tpm/tpm_capability.c 2009-07-16 12:04:20.000000000 -0400
+@@ -136,8 +136,19 @@ static TPM_RESULT cap_property(UINT32 su
+
+ case TPM_CAP_PROP_TIS_TIMEOUT:
+ debug("[TPM_CAP_PROP_TIS_TIMEOUT]");
+- /* TODO: TPM_CAP_PROP_TIS_TIMEOUT */
+- return TPM_FAIL;
++ /* TODO: TPM_CAP_PROP_TIS_TIMEOUT: Measure these values and determine
correct ones */
++ UINT32 len = *respSize = 16;
++ BYTE *ptr = *resp = tpm_malloc(*respSize);
++ if (ptr == NULL ||
++ tpm_marshal_UINT32(&ptr, &len, 200000) ||
++ tpm_marshal_UINT32(&ptr, &len, 200000) ||
++ tpm_marshal_UINT32(&ptr, &len, 200000) ||
++ tpm_marshal_UINT32(&ptr, &len, 200000)) {
++ tpm_free(*resp);
++ return TPM_FAIL;
++ }
++ return TPM_SUCCESS;
++
+
+ case TPM_CAP_PROP_STARTUP_EFFECT:
+ debug("[TPM_CAP_PROP_STARTUP_EFFECT]");
+@@ -189,8 +200,12 @@ static TPM_RESULT cap_property(UINT32 su
+
+ case TPM_CAP_PROP_DURATION:
+ debug("[TPM_CAP_PROP_DURATION]");
+- /* TODO: TPM_CAP_PROP_DURATION */
+- return TPM_FAIL;
++ /* TODO: TPM_CAP_PROP_DURATION: Measure these values and return
accurate ones */
++ BYTE dur[]=
{0x0,0x0,0x0,0xc,0x0,0x7,0xa1,0x20,0x0,0x1e,0x84,0x80,0x11,0xe1,0xa3,0x0};
++ *respSize = 16;
++ *resp = tpm_malloc(*respSize);
++ memcpy(*resp,dur,16);
++
+
+ case TPM_CAP_PROP_ACTIVE_COUNTER:
+ debug("[TPM_CAP_PROP_ACTIVE_COUNTER]");
+diff -Naurp tpm_emulator-0.5.1/tpmd/Makefile tpm5-test/tpmd/Makefile
+--- tpm_emulator-0.5.1/tpmd/Makefile 2008-02-14 03:22:48.000000000 -0500
++++ tpm5-test/tpmd/Makefile 2009-07-16 12:08:26.000000000 -0400
+@@ -8,9 +8,10 @@ WFLAGS := -Wall -Wno-unused -Wpointer-a
+ -Wwrite-strings -Wsign-compare -Wno-multichar
+ #WFLAGS += -Wextra -Wcast-qual -Wmissing-prototypes
-Wmissing-declarations -Wstrict-aliasing
+ CFLAGS += $(WFLAGS) -g -I.. -I. -O2 -fno-strict-aliasing
++CFLAGS += -I../../../../tools/vtpm_manager/manager
+ LDFLAGS += -lgmp
+
+-BINDIR := /usr/sbin/
++BINDIR := /usr/bin/
+
+ TPMD := tpmd
+ DIRS := ../tpm ../crypto
+@@ -18,6 +19,8 @@ SRCS := $(foreach dir, $(DIRS), $(wil
+ OBJS := $(patsubst %.c, %.o, $(SRCS))
+ OBJS := $(foreach dir, $(DIRS), $(patsubst $(dir)/%.o, %.o, $(filter
$(dir)/%.o, $(OBJS))))
+
++VTPM_BIN := vtpmd
++
+ vpath %.c $(strip $(DIRS))
+
+ all: $(TPMD)
+@@ -32,10 +35,8 @@ TPMD_GROUP ?= tss
+ INSTALL ?= install
+
+ install: $(TPMD)
+- $(INSTALL) -m 755 -o $(TPMD_USER) -g $(TPMD_GROUP) -d
$(DESTDIR)/var/lib/tpm
+- $(INSTALL) -m 755 -o $(TPMD_USER) -g $(TPMD_GROUP) -d
$(DESTDIR)/var/run/tpm
+ $(INSTALL) -D -d $(DESTDIR)/$(BINDIR)
+- $(INSTALL) -m 755 $(TPMD) $(DESTDIR)/$(BINDIR)
++ $(INSTALL) -m 755 $(TPMD) $(DESTDIR)/$(BINDIR)/$(VTPM_BIN)
+
+ .PHONY: all clean install
+
+diff -Naurp tpm_emulator-0.5.1/tpmd/tpmd.c tpm5-test/tpmd/tpmd.c
+--- tpm_emulator-0.5.1/tpmd/tpmd.c 2008-02-14 03:22:48.000000000 -0500
++++ tpm5-test/tpmd/tpmd.c 2009-07-16 11:19:05.000000000 -0400
+@@ -32,6 +32,9 @@
+ #include <grp.h>
+ #include "tpm_emulator_config.h"
+ #include "tpm/tpm_emulator.h"
++#include "tpm/tpm_structures.h"
++#include "tpm/tpm_marshalling.h"
++#include "vtpm_manager.h"
+
+ #define TPM_DAEMON_NAME "tpmd"
+ #define TPM_CMD_BUF_SIZE 4096
+@@ -39,6 +42,24 @@
+ #define TPM_RANDOM_DEVICE "/dev/urandom"
+ #undef TPM_MKDIRS
+
++#ifdef VTPM_MULTI_VM
++ #define DEV_BE "/dev/vtpm"
++ #define DEV_FE "/dev/tpm"
++#else
++ #define PVM_RX_FIFO_D "/var/vtpm/fifos/tpm_cmd_to_%d.fifo"
++ #define PVM_TX_FIFO "/var/vtpm/fifos/tpm_rsp_from_all.fifo"
++ #define HVM_RX_FIFO_D "/var/vtpm/socks/%d.socket"
++
++ #define VTPM_RX_FIFO_D "/var/vtpm/fifos/vtpm_rsp_to_%d.fifo"
++ #define VTPM_TX_FIFO "/var/vtpm/fifos/vtpm_cmd_from_all.fifo"
++
++ static char *vtpm_rx_name=NULL;
++#endif
++
++ static int vtpm_tx_fh=-1, vtpm_rx_fh=-1;
++
++#define BUFFER_SIZE 2048
++
+ static volatile int stopflag = 0;
+ static int is_daemon = 0;
+ static int opt_debug = 0;
+@@ -49,6 +70,8 @@ static const char *opt_storage_file = "/
+ static uid_t opt_uid = 0;
+ static gid_t opt_gid = 0;
+ static int tpm_startup = 2;
++static int vtpm_type = VTPM_TYPE_PVM;
++int dmi_id = 0;
+ static int rand_fh;
+
+ void tpm_log(int priority, const char *fmt, ...)
+@@ -90,56 +113,241 @@ uint64_t tpm_get_ticks(void)
+
+ int tpm_write_to_file(uint8_t *data, size_t data_length)
+ {
+- int fh;
+- ssize_t res;
+- fh = open(opt_storage_file, O_WRONLY | O_TRUNC | O_CREAT, S_IRUSR |
S_IWUSR);
+- if (fh < 0) return -1;
+- while (data_length > 0) {
+- res = write(fh, data, data_length);
+- if (res < 0) {
+- close(fh);
+- return -1;
+- }
+- data_length -= res;
+- data += res;
++ int res, out_data_size, in_header_size;
++ BYTE *ptr, *out_data, *in_header;
++ UINT32 result, len, in_rsp_size;
++ UINT16 tag = VTPM_TAG_REQ;
++
++ printf("Saving NVM\n");
++ if (vtpm_tx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_tx_fh = open(DEV_FE, O_RDWR);
++#else
++ vtpm_tx_fh = open(VTPM_TX_FIFO, O_WRONLY);
++#endif
++ }
++
++ if (vtpm_tx_fh < 0) {
++ return -1;
++ }
++
++ // Send request to VTPM Manager to encrypt data
++#ifdef VTPM_MUTLI_VM
++ out_data_size = len = VTPM_COMMAND_HEADER_SIZE_CLT + data_length;
++#else
++ out_data_size = len = VTPM_COMMAND_HEADER_SIZE_SRV + data_length;
++#endif
++
++ out_data = ptr = (BYTE *) malloc(len);
++
++ if (ptr == NULL
++#ifndef VTPM_MUTLI_VM
++ || tpm_marshal_UINT32(&ptr, &len, dmi_id)
++#endif
++ || tpm_marshal_UINT16(&ptr, &len, tag)
++#ifdef VTPM_MUTLI_VM
++ || tpm_marshal_UINT32(&ptr, &len, out_data_size)
++#else
++ || tpm_marshal_UINT32(&ptr, &len, out_data_size - sizeof(uint32_t))
++#endif
++ || tpm_marshal_UINT32(&ptr, &len, VTPM_ORD_SAVENVM)
++ || tpm_marshal_BYTE_ARRAY(&ptr, &len, data, data_length)) {
++ free(out_data);
++ return -1;
++ }
++
++ printf("\tSending SaveNVM Command.\n");
++ res = write(vtpm_tx_fh, out_data, out_data_size);
++ free(out_data);
++ if (res != out_data_size) return -1;
++
++ if (vtpm_rx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_rx_fh = vtpm_tx_fh
++#else
++ if (vtpm_rx_name == NULL) {
++ vtpm_rx_name = malloc(10 + strlen(VTPM_RX_FIFO_D));
++ sprintf(vtpm_rx_name, VTPM_RX_FIFO_D, (uint32_t) dmi_id);
+ }
+- close(fh);
+- return 0;
++ vtpm_rx_fh = open(vtpm_rx_name, O_RDONLY);
++#endif
++ }
++
++ if (vtpm_rx_fh < 0) {
++ return -1;
++ }
++
++ // Read Header of response so we can get the size & status
++#ifdef VTPM_MUTLI_VM
++ in_header_size = len = VTPM_COMMAND_HEADER_SIZE_CLT;
++#else
++ in_header_size = len = VTPM_COMMAND_HEADER_SIZE_SRV;
++#endif
++ in_header = ptr = malloc(in_header_size);
++
++ printf("\tReading SaveNVM header.\n");
++ res = read(vtpm_rx_fh, in_header, in_header_size);
++
++ if ( (res != in_header_size)
++#ifndef VTPM_MUTLI_VM
++ || tpm_unmarshal_UINT32(&ptr, &len, (UINT32*)&dmi_id)
++#endif
++ || tpm_unmarshal_UINT16(&ptr, &len, &tag)
++ || tpm_unmarshal_UINT32(&ptr, &len, &in_rsp_size)
++ || tpm_unmarshal_UINT32(&ptr, &len, &result) ) {
++ free(in_header);
++ return -1;
++ }
++ free(in_header);
++
++ if (result != VTPM_SUCCESS) {
++ return -1;
++ }
++
++#ifdef VTPM_MUTLI_VM
++ close(vtpm_tx_fh); close(vtpm_rx_fh);
++#endif
++
++ printf("\tFinishing up SaveNVM\n");
++ return (0);
+ }
+
+ int tpm_read_from_file(uint8_t **data, size_t *data_length)
+ {
+- int fh;
+- ssize_t res;
+- size_t total_length;
+- fh = open(opt_storage_file, O_RDONLY);
+- if (fh < 0) return -1;
+- total_length = lseek(fh, 0, SEEK_END);
+- lseek(fh, 0, SEEK_SET);
+- *data = tpm_malloc(total_length);
+- if (*data == NULL) {
+- close(fh);
+- return -1;
+- }
+- *data_length = 0;
+- while (total_length > 0) {
+- res = read(fh, &(*data)[*data_length], total_length);
+- if (res < 0) {
+- close(fh);
+- tpm_free(*data);
+- return -1;
+- }
+- *data_length += res;
+- total_length -= res;
++ int res, out_data_size, in_header_size;
++ uint8_t *ptr, *out_data, *in_header;
++ UINT16 tag = VTPM_TAG_REQ;
++ UINT32 len, in_rsp_size, result;
++#ifdef VTPM_MUTLI_VM
++ int vtpm_rx_fh, vtpm_tx_fh;
++#endif
++
++ printf("Loading NVM.\n");
++ if (vtpm_tx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_tx_fh = open(DEV_FE, O_RDWR);
++#else
++ vtpm_tx_fh = open(VTPM_TX_FIFO, O_WRONLY);
++#endif
++ }
++
++ if (vtpm_tx_fh < 0) {
++ printf("Error in read_from_file:301\n");
++ return -1;
++ }
++
++ // Send request to VTPM Manager to encrypt data
++#ifdef VTPM_MUTLI_VM
++ out_data_size = len = VTPM_COMMAND_HEADER_SIZE_CLT;
++#else
++ out_data_size = len = VTPM_COMMAND_HEADER_SIZE_SRV;
++#endif
++ out_data = ptr = (BYTE *) malloc(len);
++
++ if (ptr == NULL
++#ifndef VTPM_MUTLI_VM
++ || tpm_marshal_UINT32(&ptr, &len, dmi_id)
++#endif
++ || tpm_marshal_UINT16(&ptr, &len, tag)
++#ifdef VTPM_MUTLI_VM
++ || tpm_marshal_UINT32(&ptr, &len, out_data_size)
++#else
++ || tpm_marshal_UINT32(&ptr, &len, out_data_size - sizeof(uint32_t))
++#endif
++ || tpm_marshal_UINT32(&ptr, &len, VTPM_ORD_LOADNVM)) {
++ free(out_data);
++ printf("Error in read_from_file:325\n");
++
++ return -1;
++ }
++
++ printf("\tSending LoadNVM command\n");
++ res = write(vtpm_tx_fh, out_data, out_data_size);
++ free(out_data);
++ if (res != out_data_size)
++ {
++ printf("Error in read_from_file:335\n");
++ return -1;
++ }
++
++ if (vtpm_rx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_rx_fh = vtpm_tx_fh;
++#else
++ if (vtpm_rx_name == NULL) {
++ vtpm_rx_name = malloc(10 + strlen(VTPM_RX_FIFO_D));
++ sprintf(vtpm_rx_name, VTPM_RX_FIFO_D, (uint32_t) dmi_id);
+ }
+- close(fh);
+- return 0;
++ vtpm_rx_fh = open(vtpm_rx_name, O_RDONLY);
++#endif
++ }
++
++ if (vtpm_rx_fh < 0) {
++ printf("Error in read_from_file:352\n");
++ return -1;
++ }
++
++ // Read Header of response so we can get the size & status
++#ifdef VTPM_MUTLI_VM
++ in_header_size = len = VTPM_COMMAND_HEADER_SIZE_CLT;
++#else
++ in_header_size = len = VTPM_COMMAND_HEADER_SIZE_SRV;
++#endif
++ in_header = ptr = malloc(in_header_size);
++
++ printf("\tReading LoadNVM header\n");
++ res = read(vtpm_rx_fh, in_header, in_header_size);
++
++ if ( (res != in_header_size)
++#ifndef VTPM_MUTLI_VM
++ || tpm_unmarshal_UINT32(&ptr, &len, (UINT32*)&dmi_id)
++#endif
++ || tpm_unmarshal_UINT16(&ptr, &len, &tag)
++ || tpm_unmarshal_UINT32(&ptr, &len, &in_rsp_size)
++ || tpm_unmarshal_UINT32(&ptr, &len, &result) ) {
++ free(in_header);
++ printf("Error in read_from_file:375\n");
++ return -1;
++ }
++ free(in_header);
++
++ if (result != VTPM_SUCCESS) {
++ printf("Error in read_from_file:381\n");
++ return -1;
++ }
++
++ // Read Encrypted data from VTPM Manager
++ *data_length = in_rsp_size - VTPM_COMMAND_HEADER_SIZE_CLT;
++ *data = (uint8_t *) malloc(*data_length);
++
++ printf("\tReading clear data from LoadNVM.\n");
++ res = read(vtpm_rx_fh, *data, *data_length);
++#ifdef VTPM_MUTLI_VM
++ close(vtpm_rx_fh);close(vtpm_tx_fh);
++#endif
++
++ printf("\tReturing from loading NVM\n");
++ if (res != (int)*data_length) {
++ free(*data);
++ printf("Error in read_from_file:398\n");
++ return -1;
++ } else {
++ return 0;
++ }
++
++
++
+ }
+
+ static void print_usage(char *name)
+ {
+ printf("usage: %s [-d] [-f] [-s storage file] [-u unix socket name] "
+- "[-o user name] [-g group name] [-h] [startup mode]\n", name);
++ "[-o user name] [-g group name] [-h]"
++#ifdef VTPM_MULTI_VM
++ "clear|save|deactivated\n", name);
++#else
++ "clear|save|deactivated pvm|hvm vtpmid\n", name);
++#endif
+ printf(" d : enable debug mode\n");
+ printf(" f : forces the application to run in the foreground\n");
+ printf(" s : storage file to use (default: %s)\n", opt_storage_file);
+@@ -205,7 +413,13 @@ static void parse_options(int argc, char
+ exit(EXIT_SUCCESS);
+ }
+ }
+- if (optind < argc) {
++ /*Make sure we have all required options*/
++#ifdef VTPM_MULTI_VM
++#define EXTRA_OPTS 0
++#else
++#define EXTRA_OPTS 2
++#endif
++ if (optind < argc - EXTRA_OPTS ) {
+ debug("startup mode = '%s'", argv[optind]);
+ if (!strcmp(argv[optind], "clear")) {
+ tpm_startup = 1;
+@@ -219,6 +433,25 @@ static void parse_options(int argc, char
+ print_usage(argv[0]);
+ exit(EXIT_SUCCESS);
+ }
++#ifndef VTPM_MULTI_VM
++ ++optind;
++ if(!strcmp(argv[optind], "pvm")) {
++ vtpm_type = VTPM_TYPE_PVM; // Get commands from vTPM
Manager through fifo
++ } else if (!strcmp(argv[optind], "hvm")) {
++ vtpm_type = VTPM_TYPE_HVM; // Get commands from qemu via
socket
++ } else {
++ error("Invalid vm mode '%s'; must be 'pvm', "
++ "or 'hvm' ", argv[optind]);
++ print_usage(argv[0]);
++ exit(EXIT_SUCCESS);
++ }
++ ++optind;
++ dmi_id = atoi(argv[optind]);
++#endif
++ } else {
++ error("Invalid number of arguments");
++ print_usage(argv[0]);
++ exit(EXIT_SUCCESS);
+ }
+ }
+
+@@ -348,93 +581,180 @@ static int init_socket(const char *name)
+
+ static void main_loop(void)
+ {
+- int sock, fh, res;
+- int32_t in_len;
++ int32_t in_len, written;
+ uint32_t out_len;
+- uint8_t in[TPM_CMD_BUF_SIZE], *out;
++ uint8_t in[TPM_CMD_BUF_SIZE], *out, *addressed_out;
++ int guest_id=-1;
++ int i;
++ char *vtpm_rx_file=NULL;
++ int res;
++
++#ifndef VTPM_MULTI_VM
++ int sockfd = -1;
+ struct sockaddr_un addr;
+- socklen_t addr_len;
+- fd_set rfds;
+- struct timeval tv;
++ struct sockaddr_un client_addr;
++ unsigned int client_length;
++#endif
++
++ int vtpm_tx_fh=-1, vtpm_rx_fh=-1;
++
++#ifndef VTPM_MULTI_VM
++ if (vtpm_type == VTPM_TYPE_PVM) {
++ vtpm_rx_file = malloc(10 + strlen(PVM_RX_FIFO_D));
++ sprintf(vtpm_rx_file, PVM_RX_FIFO_D, (uint32_t) dmi_id);
++ } else {
++ vtpm_rx_file = malloc(10 + strlen(HVM_RX_FIFO_D));
++ sprintf(vtpm_rx_file, HVM_RX_FIFO_D, (uint32_t) dmi_id);
++
++ if ( (sockfd = socket(PF_UNIX,SOCK_STREAM,0)) < 0) {
++ error("Unable to create socket. errno = %d\n", errno);
++ exit (-1);
++ }
++
++ memset(&addr, 0, sizeof(addr));
++ addr.sun_family = AF_UNIX;
++ strcpy(addr.sun_path,vtpm_rx_file );
++ unlink(addr.sun_path);
++ }
++#endif
+
+ info("staring main loop");
+- /* open UNIX socket */
+- sock = init_socket(opt_socket_name);
+- if (sock < 0) exit(EXIT_FAILURE);
+ /* init tpm emulator */
+- debug("initializing TPM emulator: %d", tpm_startup);
++#ifdef VTPM_MULTI_VM
++ debug("initializing TPM emulator: state=%d", tpm_startup);
++#else
++ debug("initializing TPM emulator: state=%d, type=%d, id=%d", tpm_startup,
vtpm_type, dmi_id);
++#endif
+ tpm_emulator_init(tpm_startup);
+ /* start command processing */
+ while (!stopflag) {
+ /* wait for incomming connections */
+ debug("waiting for connections...");
+- FD_ZERO(&rfds);
+- FD_SET(sock, &rfds);
+- tv.tv_sec = 10;
+- tv.tv_usec = 0;
+- res = select(sock + 1, &rfds, NULL, NULL, &tv);
+- if (res < 0) {
+- error("select(sock) failed: %s", strerror(errno));
+- break;
+- } else if (res == 0) {
+- continue;
+- }
+- addr_len = sizeof(addr);
+- fh = accept(sock, (struct sockaddr*)&addr, &addr_len);
+- if (fh < 0) {
+- error("accept() failed: %s", strerror(errno));
+- continue;
+- }
++ if (vtpm_rx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_rx_fh = open(DEV_BE, O_RDWR);
++#else
++ if (vtpm_type == VTPM_TYPE_PVM)
++ {
++ vtpm_rx_fh = open(vtpm_rx_file, O_RDONLY);
++ } else {
++ if (bind(sockfd, (struct sockaddr *)&addr, sizeof(addr)) < 0) {
++ error("Unable to bind(). errno = %d\n", errno);
++ exit (-1);
++ }
++
++ if (listen(sockfd, 10) <0) {
++ error("Unable to listen(). errno = %d\n", errno);
++ exit (-1);
++ }
++
++ memset(&client_addr, 0, sizeof(client_addr));
++ client_length = sizeof(client_addr);
++
++ vtpm_rx_fh = vtpm_tx_fh = accept(sockfd, (struct sockaddr
*)&client_addr, &client_length);
++ }
++#endif
++ }
++
++ /*Error Checking*/
++ if (vtpm_rx_fh < 0) {
++ error("Failed to open devices to listen to guest.\n");
++ exit(-1);
++ }
++
+ /* receive and handle commands */
+ in_len = 0;
+ do {
+ debug("waiting for commands...");
+- FD_ZERO(&rfds);
+- FD_SET(fh, &rfds);
+- tv.tv_sec = TPM_COMMAND_TIMEOUT;
+- tv.tv_usec = 0;
+- res = select(fh + 1, &rfds, NULL, NULL, &tv);
+- if (res < 0) {
+- error("select(fh) failed: %s", strerror(errno));
+- close(fh);
+- break;
+- } else if (res == 0) {
+-#ifdef TPMD_DISCONNECT_IDLE_CLIENTS
+- info("connection closed due to inactivity");
+- close(fh);
+- break;
+-#else
+- continue;
+-#endif
+- }
+- in_len = read(fh, in, sizeof(in));
+- if (in_len > 0) {
++
++ in_len = read(vtpm_rx_fh, in, sizeof(in));
++ /*Magic size of minimum TPM command is 6*/
++ //FIXME Magic size check may not be required anymore
++ if (in_len < 6) {
++ info("Recv incomplete command of %d bytes.", in_len);
++ if (in_len <= 0) {
++ close(vtpm_rx_fh);
++ vtpm_rx_fh = -1;
++ continue;
++ }
++ } else {
++ /*Debug Printouts*/
+ debug("received %d bytes", in_len);
++ debug_nostop("Recv[%d]: 0x", in_len);
++ for (i=0; i< in_len; i++)
++ debug_more("%x ", in[i]);
++ debug_more("\n");
++ /*Multiple Guest check*/
++ if (guest_id == -1) {
++ guest_id = *((int32_t *) in);
++ } else {
++ if (guest_id != *((int32_t *) in) ) {
++ error("WARNING: More than one guest attached\n");
++ }
++ }
++
++ /*Open tx handle now*/
++ if (vtpm_tx_fh < 0) {
++#ifdef VTPM_MUTLI_VM
++ vtpm_tx_fh = open(DEV_BE, O_RDWR);
++ vtpm_rx_fh = vtpm_tx_fh;
++#else
++ if (vtpm_type == VTPM_TYPE_PVM) {
++ vtpm_tx_fh = open(PVM_TX_FIFO, O_WRONLY);
++ } // No need to open the other direction for HVM
++#endif
++ }
++ if (vtpm_tx_fh < 0) {
++ error("Failed to open devices to respond to guest.\n");
++ exit(-1);
++ }
++
++ /*Handle the TPM command now*/
+ out = NULL;
+- res = tpm_handle_command(in, in_len, &out, &out_len);
++ res = tpm_handle_command(in + sizeof(uint32_t), in_len -
sizeof(uint32_t), &out, &out_len);
+ if (res < 0) {
+ error("tpm_handle_command() failed");
+ } else {
+ debug("sending %d bytes", out_len);
++ //FIXME this prepending may or may not be needed
++ /*Prepend the first 4 bytes of the in buffer.. why?*/
++ addressed_out = (uint8_t *) tpm_malloc(sizeof(uint32_t) +
out_len);
++ *(uint32_t *) addressed_out = *(uint32_t *) in;
++ memcpy(addressed_out + sizeof(uint32_t), out, out_len);
++ out_len += sizeof(uint32_t);
++ /*End Prepend*/
++
++ /*Perform write operation now*/
+ while (out_len > 0) {
+- res = write(fh, out, out_len);
++ res = write(vtpm_tx_fh, addressed_out, out_len);
++
+ if (res < 0) {
+ error("write(%d) failed: %s", out_len,
strerror(errno));
+ break;
+- }
++ } else {
++ debug_nostop("Sent[%Zu]: ", out_len);
++ for (i=0; (unsigned int)i< out_len; i++)
++ debug_more("%x ", addressed_out[i]);
++ debug_more("\n");
++ }
+ out_len -= res;
+ }
+ tpm_free(out);
++ tpm_free(addressed_out);
+ }
+ }
+ } while (in_len > 0);
+- close(fh);
++ //close(fh);
+ }
++
+ /* shutdown tpm emulator */
+ tpm_emulator_shutdown();
+- /* close socket */
+- close(sock);
+- unlink(opt_socket_name);
++ /* Close handles */
++ close(vtpm_tx_fh);
++#ifndef VTPM_MULTI_VM
++ close(vtpm_rx_fh);
++ free(vtpm_rx_file);
++#endif
+ info("main loop stopped");
+ }
+
+@@ -450,12 +770,13 @@ int main(int argc, char **argv)
+ /* open random device */
+ init_random();
+ /* init signal handlers */
+- init_signal_handler();
++ //init_signal_handler();
+ /* unless requested otherwiese, fork and daemonize process */
+- if (!opt_foreground) daemonize();
++ //if (!opt_foreground) daemonize();
+ /* start main processing loop */
+ main_loop();
+ info("stopping TPM Emulator daemon");
+ closelog();
+ return 0;
+ }
++
+diff -Naurp tpm_emulator-0.5.1/tpmd/tpm_emulator_config.h
tpm5-test/tpmd/tpm_emulator_config.h
+--- tpm_emulator-0.5.1/tpmd/tpm_emulator_config.h 2008-02-14
03:22:48.000000000 -0500
++++ tpm5-test/tpmd/tpm_emulator_config.h 2009-07-16 11:25:26.000000000
-0400
+@@ -29,23 +29,28 @@
+
+ /* TPM emulator configuration */
+
+-#undef TPM_STRONG_PERSISTENCE
+-#undef TPM_GENERATE_EK
++#define TPM_STRONG_PERSISTENCE
++#define TPM_GENERATE_EK
+ #undef TPM_GENERATE_SEED_DAA
+ #undef TPM_MEMORY_ALIGNMENT_MANDATORY
+
++extern int dmi_id;
++
+ /* log macros */
+
+ void tpm_log(int priority, const char *fmt, ...);
+
+-#define debug(fmt, ...) tpm_log(LOG_DEBUG, "%s:%d: Debug: " fmt "\n", \
+- __FILE__, __LINE__, ## __VA_ARGS__)
+-#define info(fmt, ...) tpm_log(LOG_INFO, "%s:%d: Info: " fmt "\n", \
+- __FILE__, __LINE__, ## __VA_ARGS__)
+-#define error(fmt, ...) tpm_log(LOG_ERR, "%s:%d: Error: " fmt "\n", \
+- __FILE__, __LINE__, ## __VA_ARGS__)
+-#define alert(fmt, ...) tpm_log(LOG_ALERT, "%s:%d: Alert: " fmt "\n", \
+- __FILE__, __LINE__, ## __VA_ARGS__)
++#define debug(fmt, ...) tpm_log(LOG_DEBUG, "VTPMD[%d]: %s:%d: Debug: " fmt
"\n", \
++ dmi_id, __FILE__, __LINE__, ## __VA_ARGS__)
++#define info(fmt, ...) tpm_log(LOG_INFO, "VTPMD[%d]: %s:%d: Info: " fmt
"\n", \
++ dmi_id, __FILE__, __LINE__, ## __VA_ARGS__)
++#define error(fmt, ...) tpm_log(LOG_ERR, "VTPMD[%d]: %s:%d: Error: " fmt
"\n", \
++ dmi_id, __FILE__, __LINE__, ## __VA_ARGS__)
++#define alert(fmt, ...) tpm_log(LOG_ALERT, "VTPMD[%d]: %s:%d: Alert: " fmt
"\n", \
++ dmi_id, __FILE__, __LINE__, ## __VA_ARGS__)
++#define debug_nostop(fmt, ...) tpm_log(LOG_DEBUG, "VTPMD[%d]: %s:%d: Debug: "
fmt, \
++ dmi_id, __FILE__, __LINE__, ## __VA_ARGS__)
++#define debug_more(fmt, ...) tpm_log(LOG_DEBUG, fmt, ## __VA_ARGS__)
+
+ /* min/max macros that also do strict type-checking */
+
_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog
|