Skip to content

Commit 758eda1

Browse files
dgarskedanielinux
authored andcommitted
Add support for sealing/unsealing a secret with auth.
1 parent 0f5b5ab commit 758eda1

File tree

7 files changed

+105
-29
lines changed

7 files changed

+105
-29
lines changed

.github/workflows/test-build-sim-tpm.yml

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,10 @@ on:
1616
rot-args:
1717
required: false
1818
type: string
19-
authstr:
19+
keyauthstr:
20+
required: false
21+
type: string
22+
sealauthstr:
2023
required: false
2124
type: string
2225

@@ -59,7 +62,7 @@ jobs:
5962
6063
- name: Write TPM ROT to TPM
6164
run: |
62-
./tools/tpm/rot -write ${{inputs.rot-args}} -auth="${{inputs.authstr}}"
65+
./tools/tpm/rot -write ${{inputs.rot-args}} -auth="${{inputs.keyauthstr}}"
6366
6467
- name: Create a PCR Policy
6568
run: |
@@ -69,7 +72,7 @@ jobs:
6972
7073
- name: Build wolfboot
7174
run: |
72-
make ${{inputs.make-args}} WOLFBOOT_TPM_KEYSTORE_AUTH="${{inputs.authstr}}"
75+
make ${{inputs.make-args}} WOLFBOOT_TPM_KEYSTORE_AUTH="${{inputs.keykeyauthstr}}" WOLFBOOT_TPM_SEAL_AUTH="${{inputs.sealauthstr}}"
7376
7477
- name: Run wolfBoot
7578
run: |

.github/workflows/test-tpm.yml

Lines changed: 36 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ jobs:
6565
arch: host
6666
config-file: ./config/examples/sim-tpm-keystore.config
6767
make-args: SIGN=ECC256 HASH=SHA256
68-
authstr: TestAuth
68+
keyauthstr: TestAuth
6969

7070
sim_tpm_keystore_ecc384:
7171
uses: ./.github/workflows/test-build-sim-tpm.yml
@@ -74,15 +74,15 @@ jobs:
7474
config-file: ./config/examples/sim-tpm-keystore.config
7575
make-args: SIGN=ECC384 HASH=SHA384
7676
rot-args: -sha384
77-
authstr: TestAuth
77+
keyauthstr: TestAuth
7878

7979
sim_tpm_keystore_rsa2048:
8080
uses: ./.github/workflows/test-build-sim-tpm.yml
8181
with:
8282
arch: host
8383
config-file: ./config/examples/sim-tpm-keystore.config
8484
make-args: SIGN=RSA2048 HASH=SHA256
85-
authstr: TestAuth
85+
keyauthstr: TestAuth
8686

8787

8888
sim_tpm_keystore_noauth_ecc256:
@@ -114,7 +114,8 @@ jobs:
114114
arch: host
115115
config-file: ./config/examples/sim-tpm-seal.config
116116
make-args: SIGN=ECC256 HASH=SHA256 POLICY_FILE=policy.bin
117-
authstr: TestAuth
117+
keyauthstr: TestAuth
118+
sealauthstr: SealAuth
118119

119120
sim_tpm_seal_ecc384:
120121
uses: ./.github/workflows/test-build-sim-tpm.yml
@@ -123,7 +124,8 @@ jobs:
123124
config-file: ./config/examples/sim-tpm-seal.config
124125
make-args: SIGN=ECC384 HASH=SHA384 POLICY_FILE=policy.bin
125126
rot-args: -sha384
126-
authstr: TestAuth
127+
keyauthstr: TestAuth
128+
sealauthstr: SealAuth
127129

128130
sim_tpm_seal_rsa2048:
129131
uses: ./.github/workflows/test-build-sim-tpm.yml
@@ -132,4 +134,32 @@ jobs:
132134
config-file: ./config/examples/sim-tpm-seal.config
133135
# use larger image header size for two 2048-bit signatures
134136
make-args: SIGN=RSA2048ENC HASH=SHA256 POLICY_FILE=policy.bin IMAGE_HEADER_SIZE=1024
135-
authstr: TestAuth
137+
keyauthstr: TestAuth
138+
sealauthstr: SealAuth
139+
140+
141+
sim_tpm_seal_noauth_ecc256:
142+
uses: ./.github/workflows/test-build-sim-tpm.yml
143+
with:
144+
arch: host
145+
config-file: ./config/examples/sim-tpm-seal.config
146+
make-args: SIGN=ECC256 HASH=SHA256 POLICY_FILE=policy.bin
147+
keyauthstr: TestAuth
148+
149+
sim_tpm_seal_noauth_ecc384:
150+
uses: ./.github/workflows/test-build-sim-tpm.yml
151+
with:
152+
arch: host
153+
config-file: ./config/examples/sim-tpm-seal.config
154+
make-args: SIGN=ECC384 HASH=SHA384 POLICY_FILE=policy.bin
155+
rot-args: -sha384
156+
keyauthstr: TestAuth
157+
158+
sim_tpm_seal_noauth_rsa2048:
159+
uses: ./.github/workflows/test-build-sim-tpm.yml
160+
with:
161+
arch: host
162+
config-file: ./config/examples/sim-tpm-seal.config
163+
# use larger image header size for two 2048-bit signatures
164+
make-args: SIGN=RSA2048ENC HASH=SHA256 POLICY_FILE=policy.bin IMAGE_HEADER_SIZE=1024
165+
keyauthstr: TestAuth

config/examples/sim-tpm-seal.config

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ MEASURED_PCR_A?=16
2929
# Sealing a secret into TPM based on external PCR policy signed by the sign tool
3030
WOLFBOOT_TPM_SEAL?=1
3131
WOLFBOOT_TPM_SEAL_NV_BASE=0x01400300
32+
#WOLFBOOT_TPM_SEAL_AUTH?=SealAuth
3233

3334
# TPM Logging
3435
#CFLAGS_EXTRA+=-DDEBUG_WOLFTPM

docs/TPM.md

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ In wolfBoot we support TPM based root of trust, sealing/unsealing, cryptographic
1515
| `MEASURED_PCR_A=16` | `WOLFBOOT_MEASURED_PCR_A=16` | The PCR index to use. See [docs/measured_boot.md](/docs/measured_boot.md). |
1616
| `WOLFBOOT_TPM_SEAL=1` | `WOLFBOOT_TPM_SEAL` | Enables support for sealing/unsealing based on PCR policy signed externally. |
1717
| `WOLFBOOT_TPM_SEAL_NV_BASE=0x01400300` | `WOLFBOOT_TPM_SEAL_NV_BASE` | To override the default sealed blob storage location in the platform hierarchy. |
18+
| `WOLFBOOT_TPM_SEAL_AUTH=secret` | `WOLFBOOT_TPM_SEAL_AUTH` | Password for sealing/unsealing secrets |
1819

1920
## Root of Trust (ROT)
2021

@@ -36,14 +37,14 @@ The wolfBoot image is hashed and extended to the indicated PCR. This can be used
3637
See the wolfTPM Sealing/Unsealing example [here](https://github.com/wolfSSL/wolfTPM/tree/secret_seal/examples/boot#secure-boot-encryption-key-storage)
3738

3839
Known PCR values must be signed to seal/unseal a secret. The signature for the authorization policy resides in the signed header using the `--policy` argument.
39-
If a signed policy is not in the header then a value cannot be sealed. Instead the PCR(s) and a digest to sign will be printed for use with the sign tool.
40+
If a signed policy is not in the header then a value cannot be sealed. Instead the PCR(s) values and a PCR policy digest will be printed to sign. You can use `./tools/keytools/sign` or `./tools/tpm/policy_sign` to sign the policy externally.
4041

4142
This exposes two new wolfBoot API's for sealing and unsealing data with blob stored to NV index:
4243
```c
43-
int wolfBoot_seal(uint8_t* pubkey_hint, uint8_t* policy, uint16_t policySz,
44-
int index, const uint8_t* secret, int secret_sz);
45-
int wolfBoot_unseal(uint8_t* pubkey_hint, uint8_t* policy, uint16_t policySz,
46-
int index, uint8_t* secret, int* secret_sz);
44+
int wolfBoot_seal_auth(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
45+
int index, const uint8_t* secret, int secret_sz, const byte* auth, int authSz);
46+
int wolfBoot_unseal_auth(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
47+
int index, uint8_t* secret, int* secret_sz, const byte* auth, int authSz);
4748
```
4849
4950
By default this index will be based on an NV Index at `(0x01400300 + index)`.
@@ -62,7 +63,8 @@ NOTE: The TPM's RSA verify requires ASN.1 encoding, so use SIGN=RSA2048ENC
6263
% ./tools/tpm/policy_create -pcr=0
6364
# if ROT enabled
6465
% ./tools/tpm/rot -write [-auth=TestAuth]
65-
% make clean && make POLICY_FILE=policy.bin
66+
% make clean
67+
$ make POLICY_FILE=policy.bin [WOLFBOOT_TPM_KEYSTORE_AUTH=TestAuth] [WOLFBOOT_TPM_SEAL_AUTH=SealAuth]
6668
6769
% ./wolfboot.elf get_version
6870
Simulator assigned ./internal_flash.dd to base 0x103378000

include/tpm.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,10 +72,14 @@ int wolfBoot_get_policy(struct wolfBoot_image* img,
7272

7373
int wolfBoot_seal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
7474
int index, const uint8_t* secret, int secret_sz);
75+
int wolfBoot_seal_auth(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
76+
int index, const uint8_t* secret, int secret_sz, const uint8_t* auth, int authSz);
7577
int wolfBoot_seal_blob(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
7678
WOLFTPM2_KEYBLOB* seal_blob, const uint8_t* secret, int secret_sz);
7779
int wolfBoot_unseal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
7880
int index, uint8_t* secret, int* secret_sz);
81+
int wolfBoot_unseal_auth(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
82+
int index, uint8_t* secret, int* secret_sz, const uint8_t* auth, int authSz);
7983
int wolfBoot_unseal_blob(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
8084
WOLFTPM2_KEYBLOB* seal_blob, uint8_t* secret, int* secret_sz);
8185

@@ -102,7 +106,7 @@ int wolfBoot_tpm2_extend(uint8_t pcrIndex, uint8_t* hash, int line);
102106
/* debugging */
103107
void wolfBoot_print_hexstr(const unsigned char* bin, unsigned long sz,
104108
unsigned long maxLine);
105-
void wolfBoot_print_bin(const byte* buffer, word32 length);
109+
void wolfBoot_print_bin(const uint8_t* buffer, uint32_t length);
106110

107111

108112
#else

options.mk

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,9 @@ endif
2828
ifeq ($(WOLFBOOT_TPM_SEAL),1)
2929
WOLFTPM:=1
3030
CFLAGS+=-D"WOLFBOOT_TPM_SEAL"
31+
ifneq ($(WOLFBOOT_TPM_SEAL_AUTH),)
32+
CFLAGS+=-DWOLFBOOT_TPM_SEAL_AUTH='"$(WOLFBOOT_TPM_SEAL_AUTH)"'
33+
endif
3134
ifneq ($(WOLFBOOT_TPM_SEAL_NV_BASE),)
3235
CFLAGS+=-D"WOLFBOOT_TPM_SEAL_NV_BASE=$(WOLFBOOT_TPM_SEAL_NV_BASE)"
3336
endif

src/tpm.c

Lines changed: 46 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -605,9 +605,9 @@ int wolfBoot_store_blob(TPMI_RH_NV_AUTH authHandle, uint32_t nvIndex,
605605
nvSz = (uint32_t)sizeof(blob->pub.size) + blob->pub.size;
606606
nvSz += (uint32_t)sizeof(blob->priv.size) + blob->priv.size;
607607

608-
/* Create NV - no auth required, blob encrypted by TPM already */
608+
/* Create NV */
609609
rc = wolfTPM2_NVCreateAuth(&wolftpm_dev, &parent, &nv,
610-
nv.handle.hndl, nvAttributes, nvSz, NULL, 0);
610+
nv.handle.hndl, nvAttributes, nvSz, auth, authSz);
611611
if (rc == TPM_RC_NV_DEFINED) {
612612
/* allow use of existing handle - ignore this error */
613613
rc = 0;
@@ -739,7 +739,8 @@ int wolfBoot_delete_blob(TPMI_RH_NV_AUTH authHandle, uint32_t nvIndex,
739739
}
740740

741741
/* The secret is sealed based on a policy authorization from a public key. */
742-
int wolfBoot_seal_blob(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
742+
int wolfBoot_seal_blob(const uint8_t* pubkey_hint,
743+
const uint8_t* policy, uint16_t policySz,
743744
WOLFTPM2_KEYBLOB* seal_blob, const uint8_t* secret, int secret_sz)
744745
{
745746
int rc;
@@ -801,8 +802,9 @@ int wolfBoot_seal_blob(const uint8_t* pubkey_hint, const uint8_t* policy, uint16
801802
/* Create a new key for sealing using external signing auth */
802803
wolfTPM2_GetKeyTemplate_KeySeal(&template, pcrAlg);
803804
rc = wolfTPM2_CreateKeySeal_ex(&wolftpm_dev, seal_blob,
804-
&wolftpm_srk.handle, &template, NULL, 0, pcrAlg, NULL, 0,
805-
secret, secret_sz);
805+
&wolftpm_srk.handle, &template,
806+
seal_blob->handle.auth.buffer, seal_blob->handle.auth.size,
807+
pcrAlg, NULL, 0, secret, secret_sz);
806808
}
807809

808810
wolfTPM2_UnloadHandle(&wolftpm_dev, &policy_session.handle);
@@ -813,15 +815,20 @@ int wolfBoot_seal_blob(const uint8_t* pubkey_hint, const uint8_t* policy, uint16
813815

814816
/* Index (0-X) determines location in NV from WOLFBOOT_TPM_SEAL_NV_BASE to
815817
* store sealed blob */
816-
int wolfBoot_seal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
817-
int index, const uint8_t* secret, int secret_sz)
818+
int wolfBoot_seal_auth(const uint8_t* pubkey_hint,
819+
const uint8_t* policy, uint16_t policySz,
820+
int index, const uint8_t* secret, int secret_sz,
821+
const uint8_t* auth, int authSz)
818822
{
819823
int rc;
820824
WOLFTPM2_KEYBLOB seal_blob;
821825
word32 nvAttributes;
822826

823827
memset(&seal_blob, 0, sizeof(seal_blob));
824828

829+
seal_blob.handle.auth.size = authSz;
830+
XMEMCPY(seal_blob.handle.auth.buffer, auth, authSz);
831+
825832
/* creates a sealed keyed hash object (not loaded to TPM) */
826833
rc = wolfBoot_seal_blob(pubkey_hint, policy, policySz, &seal_blob,
827834
secret, secret_sz);
@@ -841,8 +848,7 @@ int wolfBoot_seal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t po
841848

842849
rc = wolfBoot_store_blob(TPM_RH_PLATFORM,
843850
WOLFBOOT_TPM_SEAL_NV_BASE + index,
844-
nvAttributes, &seal_blob,
845-
NULL, 0 /* auth is not required as blob is already encrypted */
851+
nvAttributes, &seal_blob, auth, authSz
846852
);
847853
}
848854
if (rc != 0) {
@@ -851,6 +857,19 @@ int wolfBoot_seal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t po
851857
}
852858
return rc;
853859
}
860+
int wolfBoot_seal(const uint8_t* pubkey_hint,
861+
const uint8_t* policy, uint16_t policySz,
862+
int index, const uint8_t* secret, int secret_sz)
863+
{
864+
const char* auth = NULL;
865+
int authSz = 0;
866+
#ifdef WOLFBOOT_TPM_SEAL_AUTH
867+
auth = WOLFBOOT_TPM_SEAL_AUTH;
868+
authSz = (int)strlen(auth);
869+
#endif
870+
return wolfBoot_seal_auth(pubkey_hint, policy, policySz, index,
871+
secret, secret_sz, (const uint8_t*)auth, authSz);
872+
}
854873

855874
/* The unseal requires a signed policy from HDR_POLICY_SIGNATURE */
856875
int wolfBoot_unseal_blob(const uint8_t* pubkey_hint,
@@ -999,17 +1018,18 @@ int wolfBoot_unseal_blob(const uint8_t* pubkey_hint,
9991018
return rc;
10001019
}
10011020

1002-
int wolfBoot_unseal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t policySz,
1003-
int index, uint8_t* secret, int* secret_sz)
1021+
int wolfBoot_unseal_auth(const uint8_t* pubkey_hint,
1022+
const uint8_t* policy, uint16_t policySz,
1023+
int index, uint8_t* secret, int* secret_sz,
1024+
const uint8_t* auth, int authSz)
10041025
{
10051026
int rc;
10061027
WOLFTPM2_KEYBLOB seal_blob;
10071028

10081029
memset(&seal_blob, 0, sizeof(seal_blob));
10091030

10101031
rc = wolfBoot_read_blob(WOLFBOOT_TPM_SEAL_NV_BASE + index, &seal_blob,
1011-
NULL, 0 /* auth is not required as sealed blob is already encrypted */
1012-
);
1032+
auth, authSz);
10131033
if (rc == 0) {
10141034
rc = wolfBoot_unseal_blob(pubkey_hint, policy, policySz, &seal_blob,
10151035
secret, secret_sz);
@@ -1026,6 +1046,19 @@ int wolfBoot_unseal(const uint8_t* pubkey_hint, const uint8_t* policy, uint16_t
10261046
}
10271047
return rc;
10281048
}
1049+
int wolfBoot_unseal(const uint8_t* pubkey_hint,
1050+
const uint8_t* policy, uint16_t policySz,
1051+
int index, uint8_t* secret, int* secret_sz)
1052+
{
1053+
const char* auth = NULL;
1054+
int authSz = 0;
1055+
#ifdef WOLFBOOT_TPM_SEAL_AUTH
1056+
auth = WOLFBOOT_TPM_SEAL_AUTH;
1057+
authSz = (int)strlen(auth);
1058+
#endif
1059+
return wolfBoot_unseal_auth(pubkey_hint, policy, policySz, index,
1060+
secret, secret_sz, (const uint8_t*)auth, authSz);
1061+
}
10291062
#endif /* WOLFBOOT_TPM_SEAL */
10301063

10311064
#if (defined(WOLFBOOT_TPM_KEYSTORE) || defined(WOLFBOOT_TPM_SEAL)) && \

0 commit comments

Comments
 (0)