Added new wrapper API `wolfTPM2_OpenExisting` for accessing device that's already started. Added unit test framework.

pull/71/head
David Garske 2019-07-22 14:27:40 -07:00
parent 17bfd276b0
commit c6e45dc580
8 changed files with 218 additions and 27 deletions

View File

@ -36,6 +36,7 @@ include wolftpm/include.am
include examples/include.am
include IDE/include.am
include certs/include.am
include tests/include.am
EXTRA_DIST+= README.md
EXTRA_DIST+= ChangeLog.md

View File

@ -107,8 +107,6 @@ AC_ARG_ENABLE([examples],
[ ENABLED_EXAMPLES=yes ]
)
AM_CONDITIONAL([BUILD_EXAMPLES], [test "x$ENABLED_EXAMPLES" = "xyes"])
# Wrapper
AC_ARG_ENABLE([wrapper],
@ -122,8 +120,6 @@ then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM2_NO_WRAPPER"
fi
AM_CONDITIONAL([BUILD_WRAPPER], [test "x$ENABLED_WRAPPER" = "xyes"])
# wolfCrypt
AC_ARG_ENABLE([wolfcrypt],
@ -138,7 +134,6 @@ then
else
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM2_NO_WOLFCRYPT"
fi
AM_CONDITIONAL([HAVE_LIBWOLFSSL], [test "x$ENABLED_WOLFCRYPT" = "xyes"])
# I2C Support
@ -152,7 +147,6 @@ if test "x$ENABLED_I2C" = "xyes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_I2C"
fi
AM_CONDITIONAL([BUILD_I2C], [test "x$ENABLED_I2C" = "xyes"])
# Advanced IO
@ -166,7 +160,6 @@ if test "x$ENABLED_ADVIO" = "xyes" || test "x$ENABLED_I2C" = "xyes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_ADV_IO"
fi
AM_CONDITIONAL([BUILD_ADVIO], [test "x$ENABLED_ADVIO" = "xyes"])
# STM ST33 Support
@ -180,7 +173,6 @@ if test "x$ENABLED_ST33" = "xyes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_ST33"
fi
AM_CONDITIONAL([BUILD_ST33], [test "x$ENABLED_ST33" = "xyes"])
# Microchip ATTPM20 Support
@ -193,7 +185,7 @@ if test "x$ENABLED_MCHP" = "xyes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_MCHP"
fi
AM_CONDITIONAL([BUILD_MCHP], [test "x$ENABLED_MCHP" = "xyes"])
# Infineon SLB9670
ENABLED_INFINEON=no
@ -202,7 +194,7 @@ then
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_SLB9670"
ENABLED_INFINEON=yes
fi
AM_CONDITIONAL([BUILD_INFINEON], [test "x$ENABLED_INFINEON" = "xyes"])
# HARDEN FLAGS
AX_HARDEN_CC_COMPILER_FLAGS
@ -210,6 +202,19 @@ AX_HARDEN_CC_COMPILER_FLAGS
OPTION_FLAGS="$CFLAGS $CPPFLAGS $AM_CFLAGS"
# The following AM_CONDITIONAL statements set flags for use in the Makefiles.
AM_CONDITIONAL([BUILD_EXAMPLES], [test "x$ENABLED_EXAMPLES" = "xyes"])
AM_CONDITIONAL([BUILD_WRAPPER], [test "x$ENABLED_WRAPPER" = "xyes"])
AM_CONDITIONAL([HAVE_LIBWOLFSSL], [test "x$ENABLED_WOLFCRYPT" = "xyes"])
AM_CONDITIONAL([BUILD_I2C], [test "x$ENABLED_I2C" = "xyes"])
AM_CONDITIONAL([BUILD_ADVIO], [test "x$ENABLED_ADVIO" = "xyes"])
AM_CONDITIONAL([BUILD_ST33], [test "x$ENABLED_ST33" = "xyes"])
AM_CONDITIONAL([BUILD_MCHP], [test "x$ENABLED_MCHP" = "xyes"])
AM_CONDITIONAL([BUILD_INFINEON], [test "x$ENABLED_INFINEON" = "xyes"])
CREATE_HEX_VERSION
AC_SUBST([AM_CPPFLAGS])
AC_SUBST([AM_CFLAGS])

View File

@ -119,11 +119,6 @@ int TPM2_Wrapper_Test(void* userCtx)
printf("TPM2 Demo for Wrapper API's\n");
/* Demonstrate single-shot API to test and init TPM hardware */
rc = wolfTPM2_Test(TPM2_IoCb, userCtx, NULL);
if (rc != 0) goto exit;
/* Init the TPM2 device */
rc = wolfTPM2_Init(&dev, TPM2_IoCb, userCtx);
if (rc != 0) return rc;

View File

@ -353,8 +353,14 @@ TPM_RC TPM2_Init_ex(TPM2_CTX* ctx, TPM2HalIoCb ioCb, void* userCtx,
/* Set the active TPM global */
TPM2_SetActiveCtx(ctx);
/* Perform chip startup */
rc = TPM2_ChipStartup(ctx, timeoutTries);
if (timeoutTries > 0) {
/* Perform chip startup and assign locality */
rc = TPM2_ChipStartup(ctx, timeoutTries);
}
else {
/* use existing locality */
ctx->locality = WOLFTPM_LOCALITY_DEFAULT;
}
return rc;
}

View File

@ -124,6 +124,8 @@ int wolfTPM2_Init(WOLFTPM2_DEV* dev, TPM2HalIoCb ioCb, void* userCtx)
if (dev == NULL)
return BAD_FUNC_ARG;
XMEMSET(dev, 0, sizeof(WOLFTPM2_DEV));
rc = wolfTPM2_Init_NoDev(&dev->ctx, ioCb, userCtx, TPM_TIMEOUT_TRIES);
if (rc != TPM_RC_SUCCESS) {
return rc;
@ -136,6 +138,33 @@ int wolfTPM2_Init(WOLFTPM2_DEV* dev, TPM2HalIoCb ioCb, void* userCtx)
return rc;
}
/* Access already started TPM module */
int wolfTPM2_OpenExisting(WOLFTPM2_DEV* dev, TPM2HalIoCb ioCb, void* userCtx)
{
int rc;
if (dev == NULL) {
return BAD_FUNC_ARG;
}
XMEMSET(dev, 0, sizeof(WOLFTPM2_DEV));
/* The 0 startup indicates use existing locality */
rc = TPM2_Init_ex(&dev->ctx, ioCb, userCtx, 0);
if (rc != TPM_RC_SUCCESS) {
#ifdef DEBUG_WOLFTPM
printf("TPM2_Init failed %d: %s\n", rc, wolfTPM2_GetRCString(rc));
#endif
return rc;
}
/* define the default session auth */
XMEMSET(dev->session, 0, sizeof(dev->session));
wolfTPM2_SetAuth(dev, 0, TPM_RS_PW, NULL, 0);
return rc;
}
int wolfTPM2_GetTpmDevId(WOLFTPM2_DEV* dev)
{
if (dev == NULL) {
@ -326,10 +355,9 @@ int wolfTPM2_SetAuth(WOLFTPM2_DEV* dev, int index,
return 0;
}
int wolfTPM2_Cleanup(WOLFTPM2_DEV* dev)
int wolfTPM2_Cleanup_ex(WOLFTPM2_DEV* dev, int doShutdown)
{
int rc;
Shutdown_In shutdownIn;
int rc = 0;
if (dev == NULL) {
return BAD_FUNC_ARG;
@ -342,13 +370,17 @@ int wolfTPM2_Cleanup(WOLFTPM2_DEV* dev)
return rc;
#endif
shutdownIn.shutdownType = TPM_SU_CLEAR;
rc = TPM2_Shutdown(&shutdownIn);
if (rc != TPM_RC_SUCCESS) {
#ifdef DEBUG_WOLFTPM
printf("TPM2_Shutdown failed %d: %s\n", rc, wolfTPM2_GetRCString(rc));
#endif
return rc;
if (doShutdown) {
Shutdown_In shutdownIn;
XMEMSET(&shutdownIn, 0, sizeof(shutdownIn));
shutdownIn.shutdownType = TPM_SU_CLEAR;
rc = TPM2_Shutdown(&shutdownIn);
if (rc != TPM_RC_SUCCESS) {
#ifdef DEBUG_WOLFTPM
printf("TPM2_Shutdown failed %d: %s\n", rc, wolfTPM2_GetRCString(rc));
#endif
/* finish cleanup and return error */
}
}
TPM2_Cleanup(&dev->ctx);
@ -356,6 +388,11 @@ int wolfTPM2_Cleanup(WOLFTPM2_DEV* dev)
return rc;
}
int wolfTPM2_Cleanup(WOLFTPM2_DEV* dev)
{
return wolfTPM2_Cleanup_ex(dev, 1);
}
int wolfTPM2_StartSession(WOLFTPM2_DEV* dev, WOLFTPM2_SESSION* session,
WOLFTPM2_KEY* tpmKey, WOLFTPM2_HANDLE* bind, TPM_SE sesType,
@ -3495,6 +3532,7 @@ int wolfTPM2_ClearCryptoDevCb(WOLFTPM2_DEV* dev, int devId)
rc = wolfTPM2_GetTpmDevId(dev);
if (rc >= 0) {
devId = rc;
rc = 0;
}
}
if (devId != INVALID_DEVID) {

14
tests/include.am 100644
View File

@ -0,0 +1,14 @@
# vim:ft=automake
# included from Top Level Makefile.am
# All paths should be given relative to the root
if BUILD_EXAMPLES
check_PROGRAMS += tests/unit.test
noinst_PROGRAMS += tests/unit.test
tests_unit_test_SOURCES = \
tests/unit_tests.c \
examples/tpm_io.c
tests_unit_test_CFLAGS = $(AM_CFLAGS)
tests_unit_test_LDADD = src/libwolftpm.la $(LIB_STATIC_ADD)
tests_unit_test_DEPENDENCIES = src/libwolftpm.la
endif

130
tests/unit_tests.c 100644
View File

@ -0,0 +1,130 @@
/* unit_tests.c
*
* Copyright (C) 2006-2019 wolfSSL Inc.
*
* This file is part of wolfTPM.
*
* wolfTPM is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfTPM 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, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
/* wolfTPM 2.0 unit tests */
#include <wolftpm/tpm2.h>
#include <wolftpm/tpm2_wrap.h>
#include <examples/tpm_io.h>
#include <examples/tpm_test.h>
#include <examples/wrap/wrap_test.h>
#include <stdio.h>
/* Test Fail Helpers */
#ifndef XABORT
#define XABORT() abort()
#endif
#define Fail(description, result) do { \
printf("\nERROR - %s line %d failed with:", __FILE__, __LINE__); \
printf("\n expected: "); printf description; \
printf("\n result: "); printf result; printf("\n\n"); \
XABORT(); \
} while(0)
#define Assert(test, description, result) if (!(test)) Fail(description, result)
#define AssertTrue(x) Assert( (x), ("%s is true", #x), (#x " => FALSE"))
#define AssertFalse(x) Assert(!(x), ("%s is false", #x), (#x " => TRUE"))
#define AssertNotNull(x) Assert( (x), ("%s is not null", #x), (#x " => NULL"))
#define AssertNull(x) do { \
void* _x = (void *) (x); \
Assert(!_x, ("%s is null", #x), (#x " => %p", _x)); \
} while(0)
#define AssertInt(x, y, op, er) do { \
int _x = (int)x; \
int _y = (int)y; \
Assert(_x op _y, ("%s " #op " %s", #x, #y), ("%d " #er " %d", _x, _y)); \
} while(0)
#define AssertIntEQ(x, y) AssertInt(x, y, ==, !=)
#define AssertIntNE(x, y) AssertInt(x, y, !=, ==)
#define AssertIntGT(x, y) AssertInt(x, y, >, <=)
#define AssertIntLT(x, y) AssertInt(x, y, <, >=)
#define AssertIntGE(x, y) AssertInt(x, y, >=, <)
#define AssertIntLE(x, y) AssertInt(x, y, <=, >)
#define AssertStr(x, y, op, er) do { \
const char* _x = x; \
const char* _y = y; \
int _z = (_x && _y) ? strcmp(_x, _y) : -1; \
Assert(_z op 0, ("%s " #op " %s", #x, #y), \
("\"%s\" " #er " \"%s\"", _x, _y));\
} while(0)
#define AssertStrEQ(x, y) AssertStr(x, y, ==, !=)
#define AssertStrNE(x, y) AssertStr(x, y, !=, ==)
#define AssertStrGT(x, y) AssertStr(x, y, >, <=)
#define AssertStrLT(x, y) AssertStr(x, y, <, >=)
#define AssertStrGE(x, y) AssertStr(x, y, >=, <)
#define AssertStrLE(x, y) AssertStr(x, y, <=, >)
/* test for WOLFTPM2_DEV restore */
static void test_OpenExistingDev(void)
{
#ifndef WOLFTPM2_NO_WRAPPER
int rc;
WOLFTPM2_DEV dev;
WOLFTPM2_KEY storageKey;
/* Init the TPM2 device */
rc = wolfTPM2_Init(&dev, TPM2_IoCb, NULL);
AssertIntEQ(rc, 0);
/* Test access to TPM to read storage primary key */
rc = wolfTPM2_ReadPublicKey(&dev, &storageKey,
TPM2_DEMO_STORAGE_KEY_HANDLE);
if (rc != 0 && rc != TPM_RC_HANDLE) goto exit;
/* Perform cleanup, but don't shutdown TPM module */
rc = wolfTPM2_Cleanup_ex(&dev, 0);
if (rc != 0) goto exit;
/* Restore TPM access */
rc = wolfTPM2_OpenExisting(&dev, TPM2_IoCb, NULL);
if (rc != 0) goto exit;
/* Test access to TPM to read storage primary key */
rc = wolfTPM2_ReadPublicKey(&dev, &storageKey,
TPM2_DEMO_STORAGE_KEY_HANDLE);
if (rc != 0 && rc != TPM_RC_HANDLE) goto exit;
printf("TPM Open Existing Test Passed\n");
exit:
AssertIntEQ(rc, 0);
wolfTPM2_Cleanup(&dev);
#endif
}
#ifndef NO_MAIN_DRIVER
int main(int argc, char *argv[])
#else
int unit_tests(int argc, char *argv[])
#endif
{
(void)argc;
(void)argv;
test_OpenExistingDev();
return 0;
}

View File

@ -96,7 +96,9 @@ typedef struct WOLFTPM2_CAPS {
/* Wrapper API's to simplify TPM use */
WOLFTPM_API int wolfTPM2_Test(TPM2HalIoCb ioCb, void* userCtx, WOLFTPM2_CAPS* caps);
WOLFTPM_API int wolfTPM2_Init(WOLFTPM2_DEV* dev, TPM2HalIoCb ioCb, void* userCtx);
WOLFTPM_API int wolfTPM2_OpenExisting(WOLFTPM2_DEV* dev, TPM2HalIoCb ioCb, void* userCtx);
WOLFTPM_API int wolfTPM2_Cleanup(WOLFTPM2_DEV* dev);
WOLFTPM_API int wolfTPM2_Cleanup_ex(WOLFTPM2_DEV* dev, int doShutdown);
WOLFTPM_API int wolfTPM2_GetTpmDevId(WOLFTPM2_DEV* dev);