All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v5 ima-evm-utils 0/3] Add alternative calls to IBM TSS library
@ 2021-08-03 20:40 Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 1/3] Expand the INSTALL instructions Ken Goldman
                   ` (2 more replies)
  0 siblings, 3 replies; 5+ messages in thread
From: Ken Goldman @ 2021-08-03 20:40 UTC (permalink / raw)
  To: zohar, maroon, linux-integrity; +Cc: kgold, Ken Goldman

This patch set adds calls to C code.  This should be more stable and
easier to maintain.  INSTALL instructions are updated.

While the code is being touched, it changes the PCR handle from
a signed int to a uint32_t, removing the need for error checking.

Ken Goldman (3):
  Expand the INSTALL instructions.
  Change PCR iterator from int to uint32_t
  Create alternative tpm2_pcr_read() that uses IBM TSS

 INSTALL              |  27 +++++-
 configure.ac         |   8 ++
 src/Makefile.am      |  15 +++-
 src/evmctl.c         |  12 ++-
 src/pcr.h            |   2 +-
 src/pcr_ibmtss.c     | 192 +++++++++++++++++++++++++++++++++++++++++++
 src/pcr_tss.c        |   5 +-
 src/pcr_tsspcrread.c |   6 +-
 8 files changed, 253 insertions(+), 14 deletions(-)
 create mode 100644 src/pcr_ibmtss.c

-- 
2.25.1


^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH v5 ima-evm-utils 1/3] Expand the INSTALL instructions.
  2021-08-03 20:40 [PATCH v5 ima-evm-utils 0/3] Add alternative calls to IBM TSS library Ken Goldman
@ 2021-08-03 20:40 ` Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 2/3] Change PCR iterator from int to uint32_t Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS Ken Goldman
  2 siblings, 0 replies; 5+ messages in thread
From: Ken Goldman @ 2021-08-03 20:40 UTC (permalink / raw)
  To: zohar, maroon, linux-integrity; +Cc: kgold, Ken Goldman

Add some of the less obvious package, TPM, and TSS prerequisites.

autoreconf -i is required before ./configure

Signed-off-by: Ken Goldman <kgoldman@us.ibm.com>
---
 INSTALL | 27 +++++++++++++++++++++++++--
 1 file changed, 25 insertions(+), 2 deletions(-)

diff --git a/INSTALL b/INSTALL
index 007e939..052652d 100644
--- a/INSTALL
+++ b/INSTALL
@@ -9,10 +9,33 @@ are permitted in any medium without royalty provided the copyright
 notice and this notice are preserved.  This file is offered as-is,
 without warranty of any kind.
 
+Prerequisites
+=============
+
+This project has the following prerequisites:
+
+(Ubuntu package names)
+	libkeyutils-dev
+	libtasn1-dev
+	libgmp-dev
+	libnspr4-dev
+	libnss3-dev
+
+These software TPMs are supported:
+      https://sourceforge.net/projects/ibmswtpm2/
+      https://github.com/stefanberger/swtpm
+
+      swtpm depends upon
+      https://github.com/stefanberger/libtpms
+
+Supported TSSes include these.  Both are included in some distros.
+	  IBM TSS https://sourceforge.net/projects/ibmtpm20tss/
+	  Intel TSS
+
 Basic Installation
 ==================
 
-   Briefly, the shell commands `./configure; make; make install' should
+   Briefly, the shell commands `autoreconf -i; ./configure; make; make install' should
 configure, build, and install this package.  The following
 more-detailed instructions are generic; see the `README' file for
 instructions specific to this package.  Some packages provide this
@@ -51,7 +74,7 @@ of `autoconf'.
    The simplest way to compile this package is:
 
   1. `cd' to the directory containing the package's source code and type
-     `./configure' to configure the package for your system.
+     `autoreconf -i' and then `./configure' to configure the package for your system.
 
      Running `configure' might take a while.  While running, it prints
      some messages telling which features it is checking for.
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v5 ima-evm-utils 2/3] Change PCR iterator from int to uint32_t
  2021-08-03 20:40 [PATCH v5 ima-evm-utils 0/3] Add alternative calls to IBM TSS library Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 1/3] Expand the INSTALL instructions Ken Goldman
@ 2021-08-03 20:40 ` Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS Ken Goldman
  2 siblings, 0 replies; 5+ messages in thread
From: Ken Goldman @ 2021-08-03 20:40 UTC (permalink / raw)
  To: zohar, maroon, linux-integrity; +Cc: kgold, Ken Goldman

PCR numbers are naturally unsigned values.  Further, they are
32 bits, even on 64-bit machines. This change eliminates the
need for negative value and overflow tests.

The parameter name is changed from j and idx to pcr_handle, which is
more descriptive and is similar to the parameter name used in the TPM
2.0 specification.

Signed-off-by: Ken Goldman <kgoldman@us.ibm.com>
---
 src/evmctl.c         | 12 ++++++++----
 src/pcr.h            |  2 +-
 src/pcr_tss.c        |  5 +++--
 src/pcr_tsspcrread.c |  6 +++---
 4 files changed, 15 insertions(+), 10 deletions(-)

diff --git a/src/evmctl.c b/src/evmctl.c
index a8065bb..c999589 100644
--- a/src/evmctl.c
+++ b/src/evmctl.c
@@ -1914,7 +1914,8 @@ static int read_tpm_banks(int num_banks, struct tpm_bank_info *bank)
 {
 	int tpm_enabled = 0;
 	char *errmsg = NULL;
-	int i, j;
+	int i;
+	uint32_t pcr_handle;
 	int err;
 
 	/* If --pcrs was specified, read only from the specified file(s) */
@@ -1934,9 +1935,12 @@ static int read_tpm_banks(int num_banks, struct tpm_bank_info *bank)
 	/* Read PCRs from multiple TPM 2.0 banks */
 	for (i = 0; i < num_banks; i++) {
 		err = 0;
-		for (j = 0; j < NUM_PCRS && !err; j++) {
-			err = tpm2_pcr_read(bank[i].algo_name, j,
-					    bank[i].pcr[j], bank[i].digest_size,
+		for (pcr_handle = 0;
+		     pcr_handle < NUM_PCRS && !err;
+		     pcr_handle++) {
+			err = tpm2_pcr_read(bank[i].algo_name, pcr_handle,
+					    bank[i].pcr[pcr_handle],
+					    bank[i].digest_size,
 					    &errmsg);
 			if (err) {
 				log_debug("Failed to read %s PCRs: (%s)\n",
diff --git a/src/pcr.h b/src/pcr.h
index 79547bd..205bae8 100644
--- a/src/pcr.h
+++ b/src/pcr.h
@@ -1,3 +1,3 @@
 int tpm2_pcr_supported(void);
-int tpm2_pcr_read(const char *algo_name, int idx, uint8_t *hwpcr,
+int tpm2_pcr_read(const char *algo_name, uint32_t pcr_handle, uint8_t *hwpcr,
 		 int len, char **errmsg);
diff --git a/src/pcr_tss.c b/src/pcr_tss.c
index feb1ff7..10930e2 100644
--- a/src/pcr_tss.c
+++ b/src/pcr_tss.c
@@ -106,7 +106,7 @@ static TPM2_ALG_ID algo_to_tss2(const char *algo_name)
 	return TPM2_ALG_ERROR;
 }
 
-int tpm2_pcr_read(const char *algo_name, int idx, uint8_t *hwpcr,
+int tpm2_pcr_read(const char *algo_name, uint32_t pcr_handle, uint8_t *hwpcr,
 		 int len, char **errmsg)
 {
 	TSS2_ABI_VERSION abi_version = {
@@ -140,7 +140,8 @@ int tpm2_pcr_read(const char *algo_name, int idx, uint8_t *hwpcr,
 		}
 	};
 
-	pcr_select_in.pcrSelections[0].pcrSelect[idx / 8] = (1 << (idx % 8));
+	pcr_select_in.pcrSelections[0].pcrSelect[pcr_handle / 8] =
+	    (1 << (pcr_handle % 8));
 
 	ret = Esys_Initialize(&ctx, NULL, &abi_version);
 	if (ret != TPM2_RC_SUCCESS) {
diff --git a/src/pcr_tsspcrread.c b/src/pcr_tsspcrread.c
index 183dfc2..95048f8 100644
--- a/src/pcr_tsspcrread.c
+++ b/src/pcr_tsspcrread.c
@@ -68,7 +68,7 @@ int tpm2_pcr_supported(void)
 	return 1;
 }
 
-int tpm2_pcr_read(const char *algo_name, int idx, uint8_t *hwpcr,
+int tpm2_pcr_read(const char *algo_name, uint32_t pcr_handle, uint8_t *hwpcr,
 		 int len, char **errmsg)
 {
 	FILE *fp;
@@ -76,8 +76,8 @@ int tpm2_pcr_read(const char *algo_name, int idx, uint8_t *hwpcr,
 	char cmd[PATH_MAX + 50];
 	int ret;
 
-	sprintf(cmd, "%s -halg %s -ha %d -ns 2> /dev/null",
-		path, algo_name, idx);
+	sprintf(cmd, "%s -halg %s -ha %u -ns 2> /dev/null",
+		path, algo_name, pcr_handle);
 	fp = popen(cmd, "r");
 	if (!fp) {
 		ret = asprintf(errmsg, "popen failed: %s", strerror(errno));
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS
  2021-08-03 20:40 [PATCH v5 ima-evm-utils 0/3] Add alternative calls to IBM TSS library Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 1/3] Expand the INSTALL instructions Ken Goldman
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 2/3] Change PCR iterator from int to uint32_t Ken Goldman
@ 2021-08-03 20:40 ` Ken Goldman
  2021-08-11 10:57   ` Mimi Zohar
  2 siblings, 1 reply; 5+ messages in thread
From: Ken Goldman @ 2021-08-03 20:40 UTC (permalink / raw)
  To: zohar, maroon, linux-integrity; +Cc: kgold, Ken Goldman

Use the IBM TSS to implement the functions as an alternative to the
command line tools.

The algorithm_string_to_algid() function supports only the digest
algorithms in use.  The table has place holders for other algorithms
as they are needed and the C strings are defined.

The table can also be used for an algorithm ID to string function if
it's ever needed.

When using the IBM TSS, link in its library.

Signed-off-by: Ken Goldman <kgoldman@us.ibm.com>

Please review the configure.ac change.
---
 configure.ac     |   8 ++
 src/Makefile.am  |  15 +++-
 src/pcr_ibmtss.c | 192 +++++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 213 insertions(+), 2 deletions(-)
 create mode 100644 src/pcr_ibmtss.c

diff --git a/configure.ac b/configure.ac
index e1ed100..4f6fe7c 100644
--- a/configure.ac
+++ b/configure.ac
@@ -30,10 +30,17 @@ AC_SUBST(KERNEL_HEADERS)
 AC_CHECK_HEADER(unistd.h)
 AC_CHECK_HEADERS(openssl/conf.h)
 
+# Intel TSS
 AC_CHECK_LIB([tss2-esys], [Esys_Free])
 AC_CHECK_LIB([tss2-rc], [Tss2_RC_Decode])
 AM_CONDITIONAL([USE_PCRTSS], [test "x$ac_cv_lib_tss2_esys_Esys_Free" = "xyes"])
 
+# IBM TSS include files
+AC_CHECK_HEADER(ibmtss/tss.h, [have_ibmtss=true],
+			      [have_ibmtss=false],
+			      [[#define TPM_POSIX]])
+AM_CONDITIONAL([USE_IBMTSS], $have_ibmtss)
+
 AC_CHECK_HEADERS(sys/xattr.h, , [AC_MSG_ERROR([sys/xattr.h header not found. You need the c-library development package.])])
 AC_CHECK_HEADERS(keyutils.h, , [AC_MSG_ERROR([keyutils.h header not found. You need the libkeyutils development package.])])
 
@@ -79,5 +86,6 @@ echo	"          debug: $pkg_cv_enable_debug"
 echo	"   openssl-conf: $enable_openssl_conf"
 echo	"      tss2-esys: $ac_cv_lib_tss2_esys_Esys_Free"
 echo	" tss2-rc-decode: $ac_cv_lib_tss2_rc_Tss2_RC_Decode"
+echo    "         ibmtss: $have_ibmtss"
 echo	"            doc: $have_doc"
 echo
diff --git a/src/Makefile.am b/src/Makefile.am
index d6c779f..f89d971 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -22,10 +22,21 @@ evmctl_CPPFLAGS = $(AM_CPPFLAGS) $(LIBCRYPTO_CFLAGS)
 evmctl_LDFLAGS = $(LDFLAGS_READLINE)
 evmctl_LDADD =  $(LIBCRYPTO_LIBS) -lkeyutils libimaevm.la
 
+# USE_PCRTSS uses the Intel TSS
 if USE_PCRTSS
-evmctl_SOURCES += pcr_tss.c
+ evmctl_SOURCES += pcr_tss.c
+
+# USE_IBMTSS uses the IBM TSS
+else
+if USE_IBMTSS
+ evmctl_SOURCES += pcr_ibmtss.c
+ evmctl_LDADD += -libmtss
+
+# uses the IBM TSS command line utilities
 else
-evmctl_SOURCES += pcr_tsspcrread.c
+ evmctl_SOURCES += pcr_tsspcrread.c
+
+endif
 endif
 
 AM_CPPFLAGS = -I$(top_srcdir) -include config.h
diff --git a/src/pcr_ibmtss.c b/src/pcr_ibmtss.c
new file mode 100644
index 0000000..551f9c4
--- /dev/null
+++ b/src/pcr_ibmtss.c
@@ -0,0 +1,192 @@
+/*
+ * ima-evm-utils - IMA/EVM support utilities
+ *
+ * Copyright (C) 2021 IBM
+ *
+ * Authors:
+ * Ken Goldman <kgoldman@us.ibm.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ * As a special exception, the copyright holders give permission to link the
+ * code of portions of this program with the OpenSSL library under certain
+ * conditions as described in each individual source file and distribute
+ * linked combinations including the program with the OpenSSL library. You
+ * must comply with the GNU General Public License in all respects
+ * for all of the code used other than as permitted herein. If you modify
+ * file(s) with this exception, you may extend this exception to your
+ * version of the file(s), but you are not obligated to do so. If you do not
+ * wish to do so, delete this exception statement from your version. If you
+ * delete this exception statement from all source files in the program,
+ * then also delete it in the license file.
+ *
+ * File: pcr_tsspcrread.c
+ *	 PCR reading implementation based on IBM TSS2
+ */
+
+#include <errno.h>
+#include <limits.h>
+#include <stdio.h>
+#include <string.h>
+#include <stdint.h>
+
+#include <openssl/sha.h>
+
+#define USE_FPRINTF
+#include "utils.h"
+#include "imaevm.h"
+
+#define TPM_POSIX	/* use Posix, not Windows constructs in TSS */
+#undef MAX_DIGEST_SIZE	/* imaevm uses a different value than the TSS */
+#include <ibmtss/tss.h>
+
+#define CMD "tsspcrread"
+
+static char path[PATH_MAX];
+
+int tpm2_pcr_supported(void)
+{
+	if (imaevm_params.verbose > LOG_INFO)
+		log_info("Using %s to read PCRs.\n", CMD);
+
+	if (get_cmd_path(CMD, path, sizeof(path))) {
+		log_debug("Couldn't find '%s' in $PATH\n", CMD);
+		return 0;
+	}
+
+	log_debug("Found '%s' in $PATH\n", CMD);
+	return 1;
+}
+
+/* Table mapping C strings to TCG algorithm identifiers */
+typedef struct tdAlgorithm_Map {
+	const char *algorithm_string;
+	TPMI_ALG_HASH algid;
+} Algorithm_Map;
+
+Algorithm_Map algorithm_map[] = {
+				 { "sha1", TPM_ALG_SHA1},
+				 { "sha256", TPM_ALG_SHA256},
+#if 0	/* uncomment as these digest algorithms are supported */
+				 { "", TPM_ALG_SHA384},
+				 { "", TPM_ALG_SHA512},
+				 { "", TPM_ALG_SM3_256},
+				 { "", TPM_ALG_SHA3_256},
+				 { "", TPM_ALG_SHA3_384},
+				 { "", TPM_ALG_SHA3_512},
+#endif
+};
+
+/*
+ * algorithm_string_to_algid() converts a digest algorithm from a C string to a
+ * TCG algorithm identifier as defined in the TCG Algorithm Regisrty..
+ *
+ *  Returns TPM_ALG_ERROR if the string has an unsupported value.
+ */
+static TPMI_ALG_HASH algorithm_string_to_algid(const char *algorithm_string)
+{
+	size_t 	i;
+
+	for (i=0 ; i < sizeof(algorithm_map)/sizeof(Algorithm_Map) ; i++) {
+		if (strcmp(algorithm_string, algorithm_map[i].algorithm_string)
+		    == 0) {
+			return algorithm_map[i].algid; 		/* if match */
+		}
+	}
+	return TPM_ALG_ERROR;
+}
+
+/* tpm2_pcr_read() reads the PCR
+ *
+ * algo_name: PCR digest algorithm (the PCR bank) as a C string
+ * pcr_handle: PCR number to read
+ * hwpcr: buffer for the PCR output in binary
+ * len: allocated size of hwpcr and should match the digest algorithm
+ */
+int tpm2_pcr_read(const char *algo_name, uint32_t pcr_handle, uint8_t *hwpcr,
+		  int len, char **errmsg)
+{
+        int 			ret = 0;	/* function return code */
+	TPM_RC			rc = 0;		/* TCG return code */
+	TPM_RC 			rc1 = 0;	/* secondary return code */
+	PCR_Read_In 		pcr_read_in;	/* command input */
+	PCR_Read_Out 		pcr_read_out;	/* response output */
+	TSS_CONTEXT		*tss_context = NULL;
+	TPMI_ALG_HASH 		alg_id;		/* PCR algorithm */
+
+	alg_id = algorithm_string_to_algid(algo_name);
+	if (alg_id == TPM_ALG_ERROR) {
+		ret = asprintf(errmsg, "tpm2_pcr_read: unknown algorithm %s",
+			       algo_name);
+		if (ret == -1) 	/* the contents of errmsg is undefined */
+			*errmsg = NULL;
+		rc = 1;
+		goto end;
+	}
+	rc = TSS_Create(&tss_context);
+	if (rc != 0)
+		goto end;
+	/* call TSS to execute the command */
+	pcr_read_in.pcrSelectionIn.count = 1;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].hash = alg_id;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].sizeofSelect = 3;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[0] = 0;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[1] = 0;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[2] = 0;
+	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[pcr_handle / 8] =
+		1 << (pcr_handle % 8);
+	rc = TSS_Execute(tss_context,
+			 (RESPONSE_PARAMETERS *)&pcr_read_out,
+			 (COMMAND_PARAMETERS *)&pcr_read_in,
+			 NULL,
+			 TPM_CC_PCR_Read,
+			 TPM_RH_NULL, NULL, 0);
+	if (rc != 0)
+		goto end;
+	/* nothing read, bank missing */
+	if (pcr_read_out.pcrValues.count == 0) {
+		ret = asprintf(errmsg, "tpm2_pcr_read: returned count 0 for %s",
+			       algo_name);
+		if (ret == -1) /* the contents of errmsg is undefined */
+			*errmsg = NULL;
+		rc = 1;
+		goto end;
+	}
+	/* len parameter did not match the digest algorithm */
+	else if (pcr_read_out.pcrValues.digests[0].t.size != len) {
+		ret = asprintf(errmsg,
+			       "tpm2_pcr_read: "
+			       "expected length %d actual %u for %s",
+			       len, pcr_read_out.pcrValues.digests[0].t.size,
+			       algo_name);
+		if (ret == -1)	/* the contents of errmsg is undefined */
+			*errmsg = NULL;
+		rc = 1;
+		goto end;
+	}
+	else {
+		memcpy(hwpcr,
+		       pcr_read_out.pcrValues.digests[0].t.buffer,
+		       pcr_read_out.pcrValues.digests[0].t.size);
+	}
+ end:
+	rc1 = TSS_Delete(tss_context);
+	if (rc == 0)
+		rc = rc1;
+	/* map TCG return code to function return code */
+	if (rc == 0)
+		return 0;
+	else
+		return -1;
+}
+
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS
  2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS Ken Goldman
@ 2021-08-11 10:57   ` Mimi Zohar
  0 siblings, 0 replies; 5+ messages in thread
From: Mimi Zohar @ 2021-08-11 10:57 UTC (permalink / raw)
  To: Ken Goldman, linux-integrity; +Cc: kgold

Hi Ken,

On Tue, 2021-08-03 at 16:40 -0400, Ken Goldman wrote:
> Use the IBM TSS to implement the functions as an alternative to the
> command line tools.
> 
> The algorithm_string_to_algid() function supports only the digest
> algorithms in use.  The table has place holders for other algorithms
> as they are needed and the C strings are defined.
> 
> The table can also be used for an algorithm ID to string function if
> it's ever needed.
> 
> When using the IBM TSS, link in its library.
> 
> Signed-off-by: Ken Goldman <kgoldman@us.ibm.com>
> 
> Please review the configure.ac change.

FYI, the above comment/note for the commit belongs after the three-dash 
line.  From the README for git format-patch:

--notes[=<ref>]
--no-notes
Append the notes (see git-notes[1]) for the commit after the three-dash 
line.

The expected use case of this is to write supporting explanation for
the commit that does not belong to the commit log message proper, and
include it with the patch submission. While one can simply write these
explanations after format-patch has run but before sending, keeping
them as Git notes allows them to be maintained between versions of the
patch series (but see the discussion of the notes.rewrite configuration
options in git-notes[1] to use this workflow).

The default is --no-notes, unless the format.notes configuration is
set.

> ---

Comments/notes go here.

>  configure.ac     |   8 ++
>  src/Makefile.am  |  15 +++-
>  src/pcr_ibmtss.c | 192 +++++++++++++++++++++++++++++++++++++++++++++++
>  3 files changed, 213 insertions(+), 2 deletions(-)
>  create mode 100644 src/pcr_ibmtss.c
> 
> diff --git a/configure.ac b/configure.ac
> index e1ed100..4f6fe7c 100644
> --- a/configure.ac
> +++ b/configure.ac
> @@ -30,10 +30,17 @@ AC_SUBST(KERNEL_HEADERS)
>  AC_CHECK_HEADER(unistd.h)
>  AC_CHECK_HEADERS(openssl/conf.h)
>  
> +# Intel TSS
>  AC_CHECK_LIB([tss2-esys], [Esys_Free])
>  AC_CHECK_LIB([tss2-rc], [Tss2_RC_Decode])
>  AM_CONDITIONAL([USE_PCRTSS], [test "x$ac_cv_lib_tss2_esys_Esys_Free" = "xyes"])
>  
> +# IBM TSS include files
> +AC_CHECK_HEADER(ibmtss/tss.h, [have_ibmtss=true],
> +			      [have_ibmtss=false],
> +			      [[#define TPM_POSIX]])
> +AM_CONDITIONAL([USE_IBMTSS], $have_ibmtss)

There's no need to define "have_ibmtss".

+AC_CHECK_HEADER(ibmtss/tss.h, [], [], [[#define TPM_POSIX]])
+AM_CONDITIONAL([USE_IBMTSS], [test "x$ac_cv_header_ibmtss_tss_h" =
"xyes"])

> +
>  AC_CHECK_HEADERS(sys/xattr.h, , [AC_MSG_ERROR([sys/xattr.h header not found. You need the c-library development package.])])
>  AC_CHECK_HEADERS(keyutils.h, , [AC_MSG_ERROR([keyutils.h header not found. You need the libkeyutils development package.])])
>  
> @@ -79,5 +86,6 @@ echo	"          debug: $pkg_cv_enable_debug"
>  echo	"   openssl-conf: $enable_openssl_conf"
>  echo	"      tss2-esys: $ac_cv_lib_tss2_esys_Esys_Free"
>  echo	" tss2-rc-decode: $ac_cv_lib_tss2_rc_Tss2_RC_Decode"
> +echo    "         ibmtss: $have_ibmtss"

This would be:
+echo    "         ibmtss: $ac_cv_header_ibmtss_tss_h"

>  echo	"            doc: $have_doc"
>  echo
> diff --git a/src/Makefile.am b/src/Makefile.am
> index d6c779f..f89d971 100644
> --- a/src/Makefile.am
> +++ b/src/Makefile.am
> @@ -22,10 +22,21 @@ evmctl_CPPFLAGS = $(AM_CPPFLAGS) $(LIBCRYPTO_CFLAGS)
>  evmctl_LDFLAGS = $(LDFLAGS_READLINE)
>  evmctl_LDADD =  $(LIBCRYPTO_LIBS) -lkeyutils libimaevm.la
>  
> +# USE_PCRTSS uses the Intel TSS
>  if USE_PCRTSS
> -evmctl_SOURCES += pcr_tss.c
> + evmctl_SOURCES += pcr_tss.c
> +
> +# USE_IBMTSS uses the IBM TSS
> +else
> +if USE_IBMTSS
> + evmctl_SOURCES += pcr_ibmtss.c
> + evmctl_LDADD += -libmtss
> +
> +# uses the IBM TSS command line utilities
>  else
> -evmctl_SOURCES += pcr_tsspcrread.c
> + evmctl_SOURCES += pcr_tsspcrread.c
> +
> +endif
>  endif
>  
>  AM_CPPFLAGS = -I$(top_srcdir) -include config.h
> diff --git a/src/pcr_ibmtss.c b/src/pcr_ibmtss.c
> new file mode 100644
> index 0000000..551f9c4
> --- /dev/null
> +++ b/src/pcr_ibmtss.c
> @@ -0,0 +1,192 @@
> +/*
> + * ima-evm-utils - IMA/EVM support utilities
> + *
> + * Copyright (C) 2021 IBM
> + *
> + * Authors:
> + * Ken Goldman <kgoldman@us.ibm.com>
> + *
> + * This program is free software; you can redistribute it and/or
> + * modify it under the terms of the GNU General Public License
> + * version 2 as published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program.  If not, see <http://www.gnu.org/licenses/>.
> + *
> + * As a special exception, the copyright holders give permission to link the
> + * code of portions of this program with the OpenSSL library under certain
> + * conditions as described in each individual source file and distribute
> + * linked combinations including the program with the OpenSSL library. You
> + * must comply with the GNU General Public License in all respects
> + * for all of the code used other than as permitted herein. If you modify
> + * file(s) with this exception, you may extend this exception to your
> + * version of the file(s), but you are not obligated to do so. If you do not
> + * wish to do so, delete this exception statement from your version. If you
> + * delete this exception statement from all source files in the program,
> + * then also delete it in the license file.
> + *
> + * File: pcr_tsspcrread.c
> + *	 PCR reading implementation based on IBM TSS2
> + */
> +

Newer files are just including "// SPDX-License-Identifier: GPL-2.0"
instead of the entire license.

> +#include <errno.h>
> +#include <limits.h>
> +#include <stdio.h>
> +#include <string.h>
> +#include <stdint.h>
> +
> +#include <openssl/sha.h>
> +
> +#define USE_FPRINTF
> +#include "utils.h"
> +#include "imaevm.h"
> +
> +#define TPM_POSIX	/* use Posix, not Windows constructs in TSS */
> +#undef MAX_DIGEST_SIZE	/* imaevm uses a different value than the TSS */
> +#include <ibmtss/tss.h>
> +
> +#define CMD "tsspcrread"
> +
> +static char path[PATH_MAX];
> +
> +int tpm2_pcr_supported(void)
> +{
> +	if (imaevm_params.verbose > LOG_INFO)
> +		log_info("Using %s to read PCRs.\n", CMD);
> +
> +	if (get_cmd_path(CMD, path, sizeof(path))) {
> +		log_debug("Couldn't find '%s' in $PATH\n", CMD);
> +		return 0;
> +	}
> +
> +	log_debug("Found '%s' in $PATH\n", CMD);
> +	return 1;
> +}
> +
> +/* Table mapping C strings to TCG algorithm identifiers */
> +typedef struct tdAlgorithm_Map {
> +	const char *algorithm_string;
> +	TPMI_ALG_HASH algid;
> +} Algorithm_Map;
> +
> +Algorithm_Map algorithm_map[] = {
> +				 { "sha1", TPM_ALG_SHA1},
> +				 { "sha256", TPM_ALG_SHA256},
> +#if 0	/* uncomment as these digest algorithms are supported */
> +				 { "", TPM_ALG_SHA384},
> +				 { "", TPM_ALG_SHA512},
> +				 { "", TPM_ALG_SM3_256},
> +				 { "", TPM_ALG_SHA3_256},
> +				 { "", TPM_ALG_SHA3_384},
> +				 { "", TPM_ALG_SHA3_512},
> +#endif
> +};
> +
> +/*
> + * algorithm_string_to_algid() converts a digest algorithm from a C string to a
> + * TCG algorithm identifier as defined in the TCG Algorithm Regisrty..
> + *
> + *  Returns TPM_ALG_ERROR if the string has an unsupported value.
> + */
> +static TPMI_ALG_HASH algorithm_string_to_algid(const char *algorithm_string)
> +{
> +	size_t 	i;
> +
> +	for (i=0 ; i < sizeof(algorithm_map)/sizeof(Algorithm_Map) ; i++) {
> +		if (strcmp(algorithm_string, algorithm_map[i].algorithm_string)
> +		    == 0) {
> +			return algorithm_map[i].algid; 		/* if match */
> +		}
> +	}
> +	return TPM_ALG_ERROR;
> +}
> +
> +/* tpm2_pcr_read() reads the PCR

The function name should be on a separate line.

> + *
> + * algo_name: PCR digest algorithm (the PCR bank) as a C string
> + * pcr_handle: PCR number to read
> + * hwpcr: buffer for the PCR output in binary
> + * len: allocated size of hwpcr and should match the digest algorithm
> + */
> +int tpm2_pcr_read(const char *algo_name, uint32_t pcr_handle, uint8_t *hwpcr,
> +		  int len, char **errmsg)
> +{
> +        int 			ret = 0;	/* function return code */
> +	TPM_RC			rc = 0;		/* TCG return code */
> +	TPM_RC 			rc1 = 0;	/* secondary return code */
> +	PCR_Read_In 		pcr_read_in;	/* command input */
> +	PCR_Read_Out 		pcr_read_out;	/* response output */
> +	TSS_CONTEXT		*tss_context = NULL;
> +	TPMI_ALG_HASH 		alg_id;		/* PCR algorithm */
> +
> +	alg_id = algorithm_string_to_algid(algo_name);
> +	if (alg_id == TPM_ALG_ERROR) {
> +		ret = asprintf(errmsg, "tpm2_pcr_read: unknown algorithm %s",
> +			       algo_name);
> +		if (ret == -1) 	/* the contents of errmsg is undefined */
> +			*errmsg = NULL;
> +		rc = 1;
> +		goto end;
> +	}
> +	rc = TSS_Create(&tss_context);
> +	if (rc != 0)
> +		goto end;
> +	/* call TSS to execute the command */
> +	pcr_read_in.pcrSelectionIn.count = 1;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].hash = alg_id;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].sizeofSelect = 3;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[0] = 0;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[1] = 0;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[2] = 0;
> +	pcr_read_in.pcrSelectionIn.pcrSelections[0].pcrSelect[pcr_handle / 8] =
> +		1 << (pcr_handle % 8);
> +	rc = TSS_Execute(tss_context,
> +			 (RESPONSE_PARAMETERS *)&pcr_read_out,
> +			 (COMMAND_PARAMETERS *)&pcr_read_in,
> +			 NULL,
> +			 TPM_CC_PCR_Read,
> +			 TPM_RH_NULL, NULL, 0);
> +	if (rc != 0)
> +		goto end;
> +	/* nothing read, bank missing */
> +	if (pcr_read_out.pcrValues.count == 0) {
> +		ret = asprintf(errmsg, "tpm2_pcr_read: returned count 0 for %s",
> +			       algo_name);
> +		if (ret == -1) /* the contents of errmsg is undefined */
> +			*errmsg = NULL;
> +		rc = 1;
> +		goto end;
> +	}
> +	/* len parameter did not match the digest algorithm */
> +	else if (pcr_read_out.pcrValues.digests[0].t.size != len) {
> +		ret = asprintf(errmsg,
> +			       "tpm2_pcr_read: "
> +			       "expected length %d actual %u for %s",
> +			       len, pcr_read_out.pcrValues.digests[0].t.size,
> +			       algo_name);
> +		if (ret == -1)	/* the contents of errmsg is undefined */
> +			*errmsg = NULL;
> +		rc = 1;
> +		goto end;
> +	}
> +	else {
> +		memcpy(hwpcr,
> +		       pcr_read_out.pcrValues.digests[0].t.buffer,
> +		       pcr_read_out.pcrValues.digests[0].t.size);
> +	}
> + end:
> +	rc1 = TSS_Delete(tss_context);
> +	if (rc == 0)
> +		rc = rc1;
> +	/* map TCG return code to function return code */
> +	if (rc == 0)
> +		return 0;
> +	else
> +		return -1;
> +}
> +

"git am" complains about the trailing blank line.

I'll make these changes.

thanks,

Mimi


^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2021-08-11 10:58 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-08-03 20:40 [PATCH v5 ima-evm-utils 0/3] Add alternative calls to IBM TSS library Ken Goldman
2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 1/3] Expand the INSTALL instructions Ken Goldman
2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 2/3] Change PCR iterator from int to uint32_t Ken Goldman
2021-08-03 20:40 ` [PATCH v5 ima-evm-utils 3/3] Create alternative tpm2_pcr_read() that uses IBM TSS Ken Goldman
2021-08-11 10:57   ` Mimi Zohar

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.