mirror of https://github.com/wolfSSL/wolfBoot.git
Measure wolfBoot, not application. Added TPM docs.
parent
d05672ea64
commit
b05c7ab980
|
@ -0,0 +1,31 @@
|
||||||
|
# wolfBoot TPM support
|
||||||
|
|
||||||
|
In wolfBoot we support TPM based root of trust, sealing/unsealing, cryptographic offloading and measured boot using a TPM.
|
||||||
|
|
||||||
|
## Build Options
|
||||||
|
|
||||||
|
| Config Option | Preprocessor Macro | Description |
|
||||||
|
| ------------- | ------------------ | ----------------------------------- |
|
||||||
|
| `WOLFTPM=1` | `WOLFBOOT_TPM` | Enables wolfTPM support and cryptographic offloading for RSA2048 and ECC256/384 |
|
||||||
|
| `WOLFBOOT_TPM_KEYSTORE=1` | `WOLFBOOT_TPM_KEYSTORE` | Enables TPM based root of trust. NV Index must store a hash of the trusted public key. |
|
||||||
|
| `WOLFBOOT_TPM_KEYSTORE_NV_INDEX=0x` | `WOLFBOOT_TPM_KEYSTORE_NV_INDEX=0x` | NV index in platform range 0x1400000 - 0x17FFFFF |
|
||||||
|
| `MEASURED_BOOT=1` | `WOLFBOOT_MEASURED_BOOT` | Enable measured boot. Extend PCR with wolfBoot hash. |
|
||||||
|
| `MEASURED_PCR_A=16` | `WOLFBOOT_MEASURED_PCR_A=16` | The PCR index to use. See [docs/measured_boot.md](/docs/measured_boot.md) |
|
||||||
|
|
||||||
|
## Root of Trust (ROT)
|
||||||
|
|
||||||
|
See wolfTPM Secure Root of Trust (ROT) example [here](https://github.com/wolfSSL/wolfTPM/tree/master/examples/boot).
|
||||||
|
|
||||||
|
The design uses a platform NV handle that has been locked. The NV stores a hash of the public key. It is recommended to supply a derived "authentication" value to prevent TPM tampering. This authentication value is encrypted on the bus.
|
||||||
|
|
||||||
|
## Cryptographic offloading
|
||||||
|
|
||||||
|
The RSA2048 and ECC256/384 bit verification can be offloaded to a TPM for code size reduction or performance improvement.
|
||||||
|
|
||||||
|
## Measured Boot
|
||||||
|
|
||||||
|
The wolfBoot image is hashed and extended to the indicated PCR. This can be used later in the application to prove the boot process was not tampered with.
|
||||||
|
|
||||||
|
## Sealing and Unsealing a secret
|
||||||
|
|
||||||
|
API's for this will be available soon.
|
|
@ -133,6 +133,7 @@ extern "C" {
|
||||||
# define WOLFBOOT_SHA_DIGEST_SIZE (32)
|
# define WOLFBOOT_SHA_DIGEST_SIZE (32)
|
||||||
# define image_hash image_sha256
|
# define image_hash image_sha256
|
||||||
# define key_hash key_sha256
|
# define key_hash key_sha256
|
||||||
|
# define self_hash self_sha256
|
||||||
#elif defined(WOLFBOOT_HASH_SHA384)
|
#elif defined(WOLFBOOT_HASH_SHA384)
|
||||||
# ifndef WOLFBOOT_SHA_BLOCK_SIZE
|
# ifndef WOLFBOOT_SHA_BLOCK_SIZE
|
||||||
# define WOLFBOOT_SHA_BLOCK_SIZE (256)
|
# define WOLFBOOT_SHA_BLOCK_SIZE (256)
|
||||||
|
@ -141,6 +142,7 @@ extern "C" {
|
||||||
# define WOLFBOOT_SHA_DIGEST_SIZE (48)
|
# define WOLFBOOT_SHA_DIGEST_SIZE (48)
|
||||||
# define image_hash image_sha384
|
# define image_hash image_sha384
|
||||||
# define key_hash key_sha384
|
# define key_hash key_sha384
|
||||||
|
# define self_hash self_sha384
|
||||||
#elif defined(WOLFBOOT_HASH_SHA3_384)
|
#elif defined(WOLFBOOT_HASH_SHA3_384)
|
||||||
# ifndef WOLFBOOT_SHA_BLOCK_SIZE
|
# ifndef WOLFBOOT_SHA_BLOCK_SIZE
|
||||||
# define WOLFBOOT_SHA_BLOCK_SIZE (128)
|
# define WOLFBOOT_SHA_BLOCK_SIZE (128)
|
||||||
|
|
71
src/image.c
71
src/image.c
|
@ -442,6 +442,30 @@ static uint8_t *get_img_hdr(struct wolfBoot_image *img)
|
||||||
|
|
||||||
#if defined(WOLFBOOT_HASH_SHA256)
|
#if defined(WOLFBOOT_HASH_SHA256)
|
||||||
#include <wolfssl/wolfcrypt/sha256.h>
|
#include <wolfssl/wolfcrypt/sha256.h>
|
||||||
|
|
||||||
|
#ifdef WOLFBOOT_MEASURED_BOOT
|
||||||
|
static int self_sha256(uint8_t *hash)
|
||||||
|
{
|
||||||
|
void *p = (void*)WOLFBOOT_PARTITION_BOOT_ADDRESS;
|
||||||
|
uint32_t sz = (uint32_t)WOLFBOOT_PARTITION_SIZE;
|
||||||
|
uint32_t blksz, position = 0;
|
||||||
|
wc_Sha256 sha256_ctx;
|
||||||
|
|
||||||
|
wc_InitSha256(&sha256_ctx);
|
||||||
|
do {
|
||||||
|
blksz = WOLFBOOT_SHA_BLOCK_SIZE;
|
||||||
|
if (position + blksz > sz)
|
||||||
|
blksz = sz - position;
|
||||||
|
wc_Sha256Update(&sha256_ctx, p, blksz);
|
||||||
|
position += blksz;
|
||||||
|
p += blksz;
|
||||||
|
} while (position < sz);
|
||||||
|
wc_Sha256Final(&sha256_ctx, hash);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif /* WOLFBOOT_MEASURED_BOOT */
|
||||||
|
|
||||||
static int image_sha256(struct wolfBoot_image *img, uint8_t *hash)
|
static int image_sha256(struct wolfBoot_image *img, uint8_t *hash)
|
||||||
{
|
{
|
||||||
uint8_t *stored_sha, *end_sha;
|
uint8_t *stored_sha, *end_sha;
|
||||||
|
@ -508,8 +532,31 @@ static void key_sha256(uint8_t key_slot, uint8_t *hash)
|
||||||
#endif /* SHA2-256 */
|
#endif /* SHA2-256 */
|
||||||
|
|
||||||
#if defined(WOLFBOOT_HASH_SHA384)
|
#if defined(WOLFBOOT_HASH_SHA384)
|
||||||
|
|
||||||
#include <wolfssl/wolfcrypt/sha512.h>
|
#include <wolfssl/wolfcrypt/sha512.h>
|
||||||
|
|
||||||
|
#ifdef WOLFBOOT_MEASURED_BOOT
|
||||||
|
static int self_sha384(uint8_t *hash)
|
||||||
|
{
|
||||||
|
void *p = (void*)WOLFBOOT_PARTITION_BOOT_ADDRESS;
|
||||||
|
uint32_t sz = (uint32_t)WOLFBOOT_PARTITION_SIZE;
|
||||||
|
uint32_t blksz, position = 0;
|
||||||
|
wc_Sha384 sha384_ctx;
|
||||||
|
|
||||||
|
wc_InitSha384(&sha384_ctx);
|
||||||
|
do {
|
||||||
|
blksz = WOLFBOOT_SHA_BLOCK_SIZE;
|
||||||
|
if (position + blksz > sz)
|
||||||
|
blksz = sz - position;
|
||||||
|
wc_Sha384Update(&sha384_ctx, p, blksz);
|
||||||
|
position += blksz;
|
||||||
|
p += blksz;
|
||||||
|
} while (position < sz);
|
||||||
|
wc_Sha384Final(&sha384_ctx, hash);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif /* WOLFBOOT_MEASURED_BOOT */
|
||||||
|
|
||||||
static int image_sha384(struct wolfBoot_image *img, uint8_t *hash)
|
static int image_sha384(struct wolfBoot_image *img, uint8_t *hash)
|
||||||
{
|
{
|
||||||
uint8_t *stored_sha, *end_sha;
|
uint8_t *stored_sha, *end_sha;
|
||||||
|
@ -782,7 +829,7 @@ static int TPM2_IoCb(TPM2_CTX* ctx, const byte* txBuf, byte* rxBuf,
|
||||||
}
|
}
|
||||||
#endif /* !ARCH_SIM */
|
#endif /* !ARCH_SIM */
|
||||||
|
|
||||||
#if defined(WOLFBOOT_TPM) && defined(WOLFBOOT_MEASURED_BOOT)
|
#ifdef WOLFBOOT_MEASURED_BOOT
|
||||||
#define measure_boot(hash) wolfBoot_tpm2_extend((hash), __LINE__)
|
#define measure_boot(hash) wolfBoot_tpm2_extend((hash), __LINE__)
|
||||||
static int wolfBoot_tpm2_extend(uint8_t* hash, int line)
|
static int wolfBoot_tpm2_extend(uint8_t* hash, int line)
|
||||||
{
|
{
|
||||||
|
@ -899,6 +946,17 @@ int wolfBoot_tpm2_init(void)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef WOLFBOOT_MEASURED_BOOT
|
||||||
|
/* hash wolfBoot and extend PCR */
|
||||||
|
rc = self_hash(digest);
|
||||||
|
if (rc == 0) {
|
||||||
|
rc = measure_boot(digest);
|
||||||
|
}
|
||||||
|
if (rc != 0) {
|
||||||
|
wolfBoot_printf("Error %d performing wolfBoot measurement!\n", rc);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1082,15 +1140,6 @@ int wolfBoot_verify_integrity(struct wolfBoot_image *img)
|
||||||
return -1;
|
return -1;
|
||||||
if (image_hash(img, digest) != 0)
|
if (image_hash(img, digest) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
#if defined(WOLFBOOT_TPM) && defined(WOLFBOOT_MEASURED_BOOT)
|
|
||||||
/*
|
|
||||||
* TPM measurement must be performed regardless of the
|
|
||||||
* verification outcome afterwards, because the purpose
|
|
||||||
* of a Measured Boot is to record the current boot state
|
|
||||||
*/
|
|
||||||
if (measure_boot(digest) != 0)
|
|
||||||
return -1;
|
|
||||||
#endif
|
|
||||||
if (memcmp(digest, stored_sha, stored_sha_len) != 0)
|
if (memcmp(digest, stored_sha, stored_sha_len) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
img->sha_ok = 1;
|
img->sha_ok = 1;
|
||||||
|
|
Loading…
Reference in New Issue