Skip to content

Commit 66d19b2

Browse files
committed
Support for storage root key and primary key endorsement argument -s for "set key type", pk and srk types
1 parent 5f5bc63 commit 66d19b2

4 files changed

Lines changed: 136 additions & 88 deletions

File tree

README.md

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -529,10 +529,8 @@ fred-cert.der would be:
529529

530530
$ ./examples/client/client -u fred -J ./keys/fred-cert.der -i ./keys/fred-key.der
531531

532-
TPM
533-
===
534-
535-
wolfSSH now supports TPM public key authentication.
532+
TPM PUBLIC KEY AUTHENTICATION
533+
=============================
536534

537535
When using TPM for client side public key authentication wolfSSH has dependencies
538536
on wolfCrypt and wolfTPM. Youll also need to have a tpm simulator
@@ -560,9 +558,14 @@ simulator like `ibmswtpm2`. This can be done as followed:
560558
$ cd src
561559
$ ./tpm_server
562560

563-
Before starting the echoserver you need to run the keygen for keyblob in wolfTPM
564-
using:
561+
Before starting the echoserver you need to run the keygen for keyblob in wolfTPM.
562+
You must choose between using the primary/endorsement key (recommended) or the
563+
storage root key. The following commands will generate the keyblob:
565564

565+
For primary endorsement key:
566+
$ ./examples/keygen/keygen keyblob.bin -rsa -t -pem -eh
567+
568+
For storage root key:
566569
$ ./examples/keygen/keygen keyblob.bin -rsa -t -pem
567570

568571
This will produce a key.pem TPM public key which needs to be converted the to
@@ -576,9 +579,14 @@ server:
576579

577580
$ ./examples/echoserver/echoserver
578581

579-
From another terminal run the client with the keyblob:
582+
From another terminal run the client with the keyblob. You must specify which
583+
key type to use:
584+
585+
Using primary endorsement key (recommened)
586+
$ ./examples/client/client -i ../wolfTPM/keyblob.bin -u hansel -s pk
580587

581-
$ ./examples/client/client -i ../wolfTPM/keyblob.bin -u hansel
588+
Using storage root key
589+
$ ./examples/client/client -i ../wolfTPM/keyblob.bin -u hansel -s srk
582590

583591
For debuging run server like above then:
584592

examples/client/client.c

Lines changed: 32 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,9 @@ static void ShowUsage(void)
125125
printf(" -E List all possible algos\n");
126126
printf(" -k set the list of key algos to use\n");
127127
printf(" -q turn off debugging output\n");
128+
#ifdef WOLFSSH_TPM
129+
printf(" -s <type> TPM key type: pk (primary key) or srk (storage)\n");
130+
#endif
128131
}
129132

130133

@@ -640,6 +643,7 @@ THREAD_RETURN WOLFSSH_THREAD client_test(void* args)
640643
int ret = 0;
641644
int ch;
642645
int userEcc = 0;
646+
int useEndorsementKey = -1;
643647
word16 port = wolfSshPort;
644648
char* host = (char*)wolfSshIp;
645649
const char* username = NULL;
@@ -665,7 +669,8 @@ THREAD_RETURN WOLFSSH_THREAD client_test(void* args)
665669

666670
(void)keepOpen;
667671

668-
while ((ch = mygetopt(argc, argv, "?ac:h:i:j:p:tu:xzNP:RJ:A:XeEk:q")) != -1) {
672+
while ((ch = mygetopt(argc, argv,
673+
"?ac:h:i:j:p:tu:xzNP:RJ:A:XeEk:qs:")) != -1) {
669674
switch (ch) {
670675
case 'h':
671676
host = myoptarg;
@@ -769,6 +774,22 @@ THREAD_RETURN WOLFSSH_THREAD client_test(void* args)
769774
break;
770775
#endif
771776

777+
case 's':
778+
if (myoptarg == NULL) {
779+
err_sys("TPM key type cannot be NULL");
780+
}
781+
if (strcmp(myoptarg, "pk") == 0) {
782+
useEndorsementKey = 1; /* Use primary/endorsement key */
783+
}
784+
else if (strcmp(myoptarg, "srk") == 0) {
785+
useEndorsementKey = 0; /* Use storage key */
786+
}
787+
else {
788+
useEndorsementKey = -1;
789+
err_sys("Invalid TPM key type. Must be 'pk' or 'srk'");
790+
}
791+
break;
792+
772793
case '?':
773794
ShowUsage();
774795
exit(EXIT_SUCCESS);
@@ -798,7 +819,8 @@ THREAD_RETURN WOLFSSH_THREAD client_test(void* args)
798819
}
799820
#endif
800821
#endif
801-
ret = ClientSetPrivateKey(privKeyName, userEcc, NULL);
822+
ret = ClientSetPrivateKey(privKeyName, userEcc, NULL,
823+
useEndorsementKey);
802824
if (ret != 0) {
803825
err_sys("Error setting private key");
804826
}
@@ -853,7 +875,14 @@ THREAD_RETURN WOLFSSH_THREAD client_test(void* args)
853875
err_sys("Couldn't create wolfSSH session.");
854876

855877
#ifdef WOLFSSH_TPM
856-
CLientSetTpm(ssh);
878+
if (useEndorsementKey == -1) {
879+
ClientFreeBuffers(pubKeyName, privKeyName, NULL);
880+
wolfSSH_free(ssh);
881+
wolfSSH_CTX_free(ctx);
882+
err_sys("TPM key type must be specified as either 'pk' or 'srk'");
883+
} else {
884+
CLientSetTpm(ssh);
885+
}
857886
#endif
858887
#if defined(WOLFSSL_PTHREADS) && defined(WOLFSSL_TEST_GLOBAL_REQ)
859888
wolfSSH_SetGlobalReq(ctx, callbackGlobalReq);

examples/client/common.c

Lines changed: 86 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -771,19 +771,13 @@ int ClientUseCert(const char* certName, void* heap)
771771
#define WOLFSSH_TPM_KEY_AUTH "ThisIsMyKeyAuth"
772772
#endif
773773

774-
/* Enable use of endorsement key instead of storage key */
775-
#ifndef WOLFSSH_TPM_ENDORSEMENT_KEY
776-
#define WOLFSSH_TPM_ENDORSEMENT_KEY 1
777-
#endif
778-
779-
static const char gStorageKeyAuth[] = WOLFSSH_TPM_SRK_AUTH;
780774
static const char gKeyAuth[] = WOLFSSH_TPM_KEY_AUTH;
775+
static const char gStorageKeyAuth[] = WOLFSSH_TPM_SRK_AUTH;
781776

782777
#define TPM2_DEMO_STORAGE_KEY_HANDLE WOLFSSH_TPM_SRK_HANDLE
783778

784779
static int getPrimaryStoragekey(WOLFTPM2_DEV* pDev,
785-
WOLFTPM2_KEY* pStorageKey,
786-
TPM_ALG_ID alg)
780+
WOLFTPM2_KEY* pStorageKey, TPM_ALG_ID alg)
787781
{
788782
int rc;
789783

@@ -820,6 +814,37 @@ static int getPrimaryStoragekey(WOLFTPM2_DEV* pDev,
820814
return rc;
821815
}
822816

817+
/* move to wolfTPM */
818+
static int getPrimaryEndorsementKey(WOLFTPM2_DEV* pDev,
819+
WOLFTPM2_KEY* pEndorseKey, TPM_ALG_ID alg)
820+
{
821+
int rc;
822+
WOLFTPM2_SESSION tpmSession;
823+
824+
WLOG(WS_LOG_DEBUG, "Entering getPrimaryEndorsementKey()");
825+
826+
/* Create endorsement key (EK) */
827+
rc = wolfTPM2_CreateEK(pDev, pEndorseKey, alg);
828+
if (rc != 0) {
829+
WLOG(WS_LOG_DEBUG, "Creating EK failed, rc: %d", rc);
830+
return rc;
831+
}
832+
833+
/* EK requires Policy auth, not Password */
834+
pEndorseKey->handle.policyAuth = 1;
835+
836+
/* Create and set policy session */
837+
rc = wolfTPM2_CreateAuthSession_EkPolicy(pDev, &tpmSession);
838+
if (rc != 0) {
839+
WLOG(WS_LOG_DEBUG, "Creating EK policy session failed, rc: %d", rc);
840+
return rc;
841+
}
842+
843+
rc = wolfTPM2_SetAuthSession(pDev, 0, &tpmSession, 0);
844+
WLOG(WS_LOG_DEBUG, "Leaving getPrimaryEndorsementKey(), rc = %d", rc);
845+
return rc;
846+
}
847+
823848
static int readKeyBlob(const char* filename, WOLFTPM2_KEYBLOB* key)
824849
{
825850
int rc = 0;
@@ -904,81 +929,65 @@ static int readKeyBlob(const char* filename, WOLFTPM2_KEYBLOB* key)
904929
return rc;
905930
}
906931

907-
static int getPrimaryEndorsementKey(WOLFTPM2_DEV* pDev, WOLFTPM2_KEY* pEndorseKey, TPM_ALG_ID alg)
908-
{
909-
int rc;
910-
WOLFTPM2_SESSION tpmSession;
911-
912-
WLOG(WS_LOG_DEBUG, "Entering getPrimaryEndorsementKey()");
913-
914-
/* Create endorsement key (EK) */
915-
rc = wolfTPM2_CreateEK(pDev, pEndorseKey, alg);
916-
if (rc != 0) {
917-
WLOG(WS_LOG_DEBUG, "Creating EK failed, rc: %d", rc);
918-
return rc;
919-
}
920-
921-
/* EK requires Policy auth, not Password */
922-
pEndorseKey->handle.policyAuth = 1;
923-
924-
/* Create and set policy session */
925-
rc = wolfTPM2_CreateAuthSession_EkPolicy(pDev, &tpmSession);
926-
if (rc != 0) {
927-
WLOG(WS_LOG_DEBUG, "Creating EK policy session failed, rc: %d", rc);
928-
return rc;
929-
}
930-
931-
rc = wolfTPM2_SetAuthSession(pDev, 0, &tpmSession, 0);
932-
WLOG(WS_LOG_DEBUG, "Leaving getPrimaryEndorsementKey(), rc = %d", rc);
933-
return rc;
934-
}
935-
936932
static int wolfSSH_TPM_InitKey(WOLFTPM2_DEV* dev, const char* name,
937-
WOLFTPM2_KEY* pTpmKey)
933+
WOLFTPM2_KEY* pTpmKey, int useEndorsementKey)
938934
{
939935
int rc = 0;
940-
#if WOLFSSH_TPM_ENDORSEMENT_KEY
941936
WOLFTPM2_KEY endorse;
942-
#else
943937
WOLFTPM2_KEY storage;
944-
#endif
938+
WOLFTPM2_KEY* primary = NULL;
945939
WOLFTPM2_KEYBLOB tpmKeyBlob;
946940
byte* p = NULL;
947941

948942
WLOG(WS_LOG_DEBUG, "Entering wolfSSH_TPM_InitKey()");
949943

944+
/* Initialize structures */
945+
XMEMSET(&endorse, 0, sizeof(endorse));
946+
XMEMSET(&storage, 0, sizeof(storage));
947+
XMEMSET(&tpmKeyBlob, 0, sizeof(tpmKeyBlob));
948+
950949
/* Initialize the TPM 2.0 device */
951-
if (rc == 0) {
952-
rc = wolfTPM2_Init(dev, TPM2_IoCb, NULL);
953-
if (rc != 0) {
954-
WLOG(WS_LOG_DEBUG, "TPM 2.0 Device initialization failed, rc: %d", rc);
955-
}
950+
rc = wolfTPM2_Init(dev, TPM2_IoCb, NULL);
951+
if (rc != 0) {
952+
WLOG(WS_LOG_DEBUG,
953+
"TPM 2.0 Device initialization failed, rc: %d", rc);
954+
return rc;
956955
}
957956

958-
/* TPM 2.0 keys live under a Primary Key, acquire such key */
957+
/* Get primary key based on type */
959958
if (rc == 0) {
960-
#if WOLFSSH_TPM_ENDORSEMENT_KEY
961-
rc = getPrimaryEndorsementKey(dev, &endorse, TPM_ALG_RSA);
962-
if (rc != 0) {
963-
WLOG(WS_LOG_DEBUG, "Acquiring Primary Endorsement Key failed, rc: %d", rc);
964-
}
965-
#else
966-
rc = getPrimaryStoragekey(dev, &storage, TPM_ALG_RSA);
967-
if (rc != 0) {
968-
WLOG(WS_LOG_DEBUG, "Acquiring Primary Storage Key failed, rc: %d", rc);
959+
if (useEndorsementKey == 1) {
960+
rc = getPrimaryEndorsementKey(dev, &endorse, TPM_ALG_RSA);
961+
if (rc == 0) {
962+
primary = &endorse;
963+
WLOG(WS_LOG_DEBUG, "Using Endorsement Key");
964+
} else {
965+
WLOG(WS_LOG_DEBUG,
966+
"Getting Primary Endorsement Key failed, rc: %d", rc);
967+
}
968+
} else {
969+
rc = getPrimaryStoragekey(dev, &storage, TPM_ALG_RSA);
970+
if (rc == 0) {
971+
wolfTPM2_SetAuthHandle(dev, 0, &storage.handle);
972+
primary = &storage;
973+
WLOG(WS_LOG_DEBUG, "Using Storage Key");
974+
} else {
975+
WLOG(WS_LOG_DEBUG,
976+
"Getting Primary Storage Key failed, rc: %d", rc);
977+
}
969978
}
970-
#endif
971979
}
972980

973981
/* Load the TPM 2.0 key blob from disk */
974982
if (rc == 0) {
975983
rc = readKeyBlob(name, &tpmKeyBlob);
976984
if (rc != 0) {
977-
WLOG(WS_LOG_DEBUG, "Reading key blob from disk failed, rc: %d", rc);
985+
WLOG(WS_LOG_DEBUG,
986+
"Reading key blob from disk failed, rc: %d", rc);
978987
}
979988
}
980989

981-
/* set session for authorization key */
990+
/* Set auth for key */
982991
if (rc == 0) {
983992
tpmKeyBlob.handle.auth.size = (int)sizeof(gKeyAuth)-1;
984993
XMEMCPY(tpmKeyBlob.handle.auth.buffer, gKeyAuth,
@@ -987,15 +996,13 @@ static int wolfSSH_TPM_InitKey(WOLFTPM2_DEV* dev, const char* name,
987996

988997
/* Load the public key into the TPM device */
989998
if (rc == 0) {
990-
#if WOLFSSH_TPM_ENDORSEMENT_KEY
991-
rc = wolfTPM2_LoadKey(dev, &tpmKeyBlob, &endorse.handle);
992-
#else
993-
rc = wolfTPM2_LoadKey(dev, &tpmKeyBlob, &storage.handle);
994-
#endif
999+
rc = wolfTPM2_LoadKey(dev, &tpmKeyBlob, &primary->handle);
9951000
if (rc != 0) {
9961001
WLOG(WS_LOG_DEBUG, "wolfTPM2_LoadKey failed, rc: %d", rc);
1002+
} else {
1003+
WLOG(WS_LOG_DEBUG, "Loaded key to 0x%x\n",
1004+
(word32)tpmKeyBlob.handle.hndl);
9971005
}
998-
WLOG(WS_LOG_DEBUG, "Loaded key to 0x%x\n", (word32)tpmKeyBlob.handle.hndl);
9991006
}
10001007

10011008
/* Read the public key and extract the public key as a DER/ASN.1 */
@@ -1013,24 +1020,25 @@ static int wolfSSH_TPM_InitKey(WOLFTPM2_DEV* dev, const char* name,
10131020
rc = wolfSSH_ReadPublicKey_buffer(userPublicKey, userPublicKeySz,
10141021
WOLFSSH_FORMAT_ASN1, &p, &userPublicKeySz, &userPublicKeyType,
10151022
&userPublicKeyTypeSz, NULL);
1016-
if (rc != 0) {
1023+
if (rc == 0) {
1024+
userPublicKey = p;
1025+
} else {
10171026
WLOG(WS_LOG_DEBUG, "Reading public key failed, rc: %d", rc);
10181027
}
1019-
userPublicKey = p;
10201028
}
10211029

1022-
/* Unload primary key handle */
1030+
/* Copy key info */
10231031
if (rc == 0) {
10241032
XMEMCPY(&pTpmKey->handle, &tpmKeyBlob.handle, sizeof(pTpmKey->handle));
10251033
XMEMCPY(&pTpmKey->pub, &tpmKeyBlob.pub, sizeof(pTpmKey->pub));
1026-
#if WOLFSSH_TPM_ENDORSEMENT_KEY
1027-
wolfTPM2_UnloadHandle(dev, &endorse.handle);
1028-
#else
1029-
wolfTPM2_UnloadHandle(dev, &storage.handle);
1030-
#endif
10311034
}
10321035

1033-
WLOG(WS_LOG_DEBUG, "Leaving wolfSSH_TPM_InitKey()");
1036+
/* Cleanup */
1037+
if (primary != NULL) {
1038+
wolfTPM2_UnloadHandle(dev, &primary->handle);
1039+
}
1040+
1041+
WLOG(WS_LOG_DEBUG, "Leaving wolfSSH_TPM_InitKey(), rc = %d", rc);
10341042
return rc;
10351043
}
10361044

@@ -1063,7 +1071,8 @@ int CLientSetTpm(WOLFSSH* ssh)
10631071

10641072
/* Reads the private key to use from file name privKeyName.
10651073
* returns 0 on success */
1066-
int ClientSetPrivateKey(const char* privKeyName, int userEcc, void* heap)
1074+
int ClientSetPrivateKey(const char* privKeyName, int userEcc,
1075+
void* heap, int useEndorsementKey)
10671076
{
10681077
int ret = 0;
10691078

@@ -1099,7 +1108,8 @@ int ClientSetPrivateKey(const char* privKeyName, int userEcc, void* heap)
10991108
*/
11001109
WMEMSET(&tpmDev, 0, sizeof(tpmDev));
11011110
WMEMSET(&tpmKey, 0, sizeof(tpmKey));
1102-
ret = wolfSSH_TPM_InitKey(&tpmDev, privKeyName, &tpmKey);
1111+
ret = wolfSSH_TPM_InitKey(&tpmDev, privKeyName, &tpmKey,
1112+
useEndorsementKey);
11031113
#elif !defined(NO_FILESYSTEM)
11041114
userPrivateKey = NULL; /* create new buffer based on parsed input */
11051115
userPrivateKeyAlloc = 1;

examples/client/common.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,8 @@
2222
#define WOLFSSH_COMMON_H
2323
int ClientLoadCA(WOLFSSH_CTX* ctx, const char* caCert);
2424
int ClientUsePubKey(const char* pubKeyName, int userEcc, void* heap);
25-
int ClientSetPrivateKey(const char* privKeyName, int userEcc, void* heap);
25+
int ClientSetPrivateKey(const char* privKeyName, int userEcc, void* heap,
26+
int useEndorsementKey);
2627
int ClientUseCert(const char* certName, void* heap);
2728
int ClientSetEcho(int type);
2829
int ClientUserAuth(byte authType,

0 commit comments

Comments
 (0)