diff options
author | Daisuke Nojiri <dnojiri@chromium.org> | 2016-09-12 12:47:14 -0700 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2016-10-01 00:01:10 -0700 |
commit | 626e0b034db4c3c395cc5eb716d8725b4f030fe0 (patch) | |
tree | 2597a16d9d3f60a3b82b18d90b72f99544510177 /firmware | |
parent | 01fb293825877edb83e8ddb9555733876f7556ea (diff) | |
download | vboot-626e0b034db4c3c395cc5eb716d8725b4f030fe0.tar.gz |
bdb: Add secret deriving code for SP-RO
This patch adds code which dervies secrets from BDS. It's supposed to be
done by SP-RO, hence the code is mostly useful for testing (or emulation).
vba_extend_secrets_ro takes a function pointer to a hash extend
function. It'll be used to try different sha256 extend algorithms.
BUG=chromium:649555
BRANCH=none
TEST=make runtests
Change-Id: I8fef6b851fb84686d8bcdd948b36160016687c51
Signed-off-by: Daisuke Nojiri <dnojiri@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/384354
Reviewed-by: Randall Spangler <rspangler@chromium.org>
Diffstat (limited to 'firmware')
-rw-r--r-- | firmware/bdb/bdb_api.h | 18 | ||||
-rw-r--r-- | firmware/bdb/bdb_flag.h | 5 | ||||
-rw-r--r-- | firmware/bdb/nvm.c | 18 | ||||
-rw-r--r-- | firmware/bdb/secrets.c | 273 | ||||
-rw-r--r-- | firmware/bdb/secrets.h | 59 |
5 files changed, 282 insertions, 91 deletions
diff --git a/firmware/bdb/bdb_api.h b/firmware/bdb/bdb_api.h index 6c2e2a46..c0e850f9 100644 --- a/firmware/bdb/bdb_api.h +++ b/firmware/bdb/bdb_api.h @@ -23,8 +23,7 @@ struct vba_context { uint8_t *bdb; /* Secrets */ - struct bdb_ro_secrets *ro_secrets; - struct bdb_rw_secrets *rw_secrets; + struct bdb_secrets *secrets; /* NVM-RW buffer */ struct nvmrw nvmrw; @@ -92,7 +91,7 @@ int vba_update_buc(struct vba_context *ctx, uint8_t *new_buc); * @return BDB_SUCCESS or BDB_ERROR_* */ int vba_derive_secret(struct vba_context *ctx, enum bdb_secret_type type, - const uint8_t *buf, uint32_t buf_size); + uint8_t *wsr, const uint8_t *buf, uint32_t buf_size); /** * Clear a secret @@ -104,6 +103,19 @@ int vba_derive_secret(struct vba_context *ctx, enum bdb_secret_type type, int vba_clear_secret(struct vba_context *ctx, enum bdb_secret_type type); /** + * Extend secrets for SP-RO + * + * @param ctx struct vba_context + * @param bdb BDB + * @param wsr Pointer to working secret register contents + * @param extend Function to be called for extending a secret + * @return BDB_SUCCESS or BDB_ERROR_* + */ +typedef void (*f_extend)(const uint8_t *from, const uint8_t *by, uint8_t *to); +int vba_extend_secrets_ro(struct vba_context *ctx, const uint8_t *bdb, + uint8_t *wsr, f_extend extend); + +/** * Get vboot register value * * Implemented by each chip diff --git a/firmware/bdb/bdb_flag.h b/firmware/bdb/bdb_flag.h index 45f57567..a7bd8574 100644 --- a/firmware/bdb/bdb_flag.h +++ b/firmware/bdb/bdb_flag.h @@ -6,7 +6,10 @@ #ifndef VBOOT_REFERENCE_FIRMWARE_BDB_BDB_FLAG_H #define VBOOT_REFERENCE_FIRMWARE_BDB_BDB_FLAG_H +/* Indicate whether BDB key is verified */ +#define VBA_CONTEXT_FLAG_BDB_KEY_EFUSED (1 << 0) + /* Indicate whether kernel data key is verified */ -#define VBA_CONTEXT_FLAG_KERNEL_DATA_KEY_VERIFIED (1 << 0) +#define VBA_CONTEXT_FLAG_KERNEL_DATA_KEY_VERIFIED (1 << 1) #endif diff --git a/firmware/bdb/nvm.c b/firmware/bdb/nvm.c index 9c40ea55..85c301a2 100644 --- a/firmware/bdb/nvm.c +++ b/firmware/bdb/nvm.c @@ -39,7 +39,7 @@ static int nvmrw_validate(const void *buf, uint32_t size) return BDB_SUCCESS; } -static int nvmrw_verify(const struct bdb_ro_secrets *secrets, +static int nvmrw_verify(const struct bdb_secrets *secrets, const struct nvmrw *nvm, uint32_t size) { uint8_t mac[NVM_HMAC_SIZE]; @@ -72,7 +72,7 @@ int nvmrw_write(struct vba_context *ctx, enum nvm_type type) if (!ctx) return BDB_ERROR_NVM_INVALID_PARAMETER; - if (!ctx->ro_secrets) + if (!ctx->secrets) return BDB_ERROR_NVM_INVALID_SECRET; rv = nvmrw_validate(nvm, sizeof(*nvm)); @@ -80,7 +80,7 @@ int nvmrw_write(struct vba_context *ctx, enum nvm_type type) return rv; /* Update HMAC */ - hmac(VB2_HASH_SHA256, ctx->ro_secrets->nvm_rw, BDB_SECRET_SIZE, + hmac(VB2_HASH_SHA256, ctx->secrets->nvm_rw, BDB_SECRET_SIZE, nvm, nvm->struct_size - sizeof(nvm->hmac), nvm->hmac, sizeof(nvm->hmac)); @@ -101,7 +101,7 @@ int nvmrw_write(struct vba_context *ctx, enum nvm_type type) } static int read_verify_nvmrw(enum nvm_type type, - const struct bdb_ro_secrets *secrets, + const struct bdb_secrets *secrets, uint8_t *buf, uint32_t buf_size) { struct nvmrw *nvm = (struct nvmrw *)buf; @@ -136,11 +136,11 @@ int nvmrw_read(struct vba_context *ctx) int rv1, rv2; /* Read and verify the 1st copy */ - rv1 = read_verify_nvmrw(NVM_TYPE_RW_PRIMARY, ctx->ro_secrets, + rv1 = read_verify_nvmrw(NVM_TYPE_RW_PRIMARY, ctx->secrets, buf1, sizeof(buf1)); /* Read and verify the 2nd copy */ - rv2 = read_verify_nvmrw(NVM_TYPE_RW_SECONDARY, ctx->ro_secrets, + rv2 = read_verify_nvmrw(NVM_TYPE_RW_SECONDARY, ctx->secrets, buf2, sizeof(buf2)); if (rv1 == BDB_SUCCESS && rv2 == BDB_SUCCESS) { @@ -204,7 +204,7 @@ int vba_update_kernel_version(struct vba_context *ctx, { struct nvmrw *nvm = &ctx->nvmrw; - if (nvmrw_verify(ctx->ro_secrets, nvm, sizeof(*nvm))) { + if (nvmrw_verify(ctx->secrets, nvm, sizeof(*nvm))) { if (nvmrw_init(ctx)) return BDB_ERROR_NVM_INIT; } @@ -236,7 +236,7 @@ int vba_update_buc(struct vba_context *ctx, uint8_t *new_buc) uint8_t buc[BUC_ENC_DIGEST_SIZE]; int rv1, rv2; - if (nvmrw_verify(ctx->ro_secrets, nvm, sizeof(*nvm))) { + if (nvmrw_verify(ctx->secrets, nvm, sizeof(*nvm))) { if (nvmrw_init(ctx)) return BDB_ERROR_NVM_INIT; } @@ -245,7 +245,7 @@ int vba_update_buc(struct vba_context *ctx, uint8_t *new_buc) * Note that we do not need to decide whether we should use hardware * crypto or not because this is supposed to be running in RW code. */ if (vbe_aes256_encrypt(new_buc, BUC_ENC_DIGEST_SIZE, - ctx->rw_secrets->buc, buc)) + ctx->secrets->buc, buc)) return BDB_ERROR_ENCRYPT_BUC; /* Return if new BUC is same as current one. */ diff --git a/firmware/bdb/secrets.c b/firmware/bdb/secrets.c index 08bca5f5..bd6c6fcf 100644 --- a/firmware/bdb/secrets.c +++ b/firmware/bdb/secrets.c @@ -11,8 +11,137 @@ #include "bdb.h" #include "secrets.h" -static int get_constant(const uint8_t *buf, uint32_t buf_size, - const uint8_t *constant, uint8_t *out) +const uint8_t secret_constant_a[] = { + 0xad, 0xf8, 0xd1, 0xd9, 0x48, 0xe6, 0xb3, 0xe4, 0xe0, 0xc4, + 0xd8, 0x66, 0x97, 0x95, 0x71, 0xa8, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x01}; + +const uint8_t secret_constant_b[] = { + 0xba, 0x9d, 0x1d, 0x8b, 0x12, 0xbd, 0x8d, 0xcd, 0x4c, 0x89, + 0xd8, 0x18, 0x72, 0x98, 0xb5, 0x18, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x02}; + +const uint8_t secret_constant_x[] = { + 0xfd, 0xc1, 0xe5, 0x57, 0x34, 0xf4, 0xf6, 0x89, 0x6d, 0x1b, + 0x6f, 0xf2, 0xd0, 0x36, 0xdb, 0xf4, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x09}; + +const uint8_t secret_constant_y[] = { + 0x18, 0xef, 0x01, 0x8e, 0xcd, 0x62, 0xf1, 0xb0, 0x2d, 0xd4, + 0x11, 0xa4, 0xb5, 0x6e, 0x38, 0xf6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x0a}; + +const uint8_t secret_constant_c[] = { + 0x46, 0xda, 0x52, 0x8d, 0x08, 0x56, 0x14, 0xde, 0x75, 0x9c, + 0x9a, 0xeb, 0x08, 0x93, 0x3d, 0xd6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x0b}; + +const uint8_t secret_constant_fv0[] = { + 0x93, 0x32, 0xf7, 0x8d, 0xec, 0x4b, 0x26, 0x2e, 0xb3, 0x5c, + 0x39, 0xd7, 0xfc, 0xc6, 0x9f, 0x09, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x05}; + +const uint8_t secret_constant_fv1[] = { + 0x60, 0x8d, 0x96, 0x35, 0xdf, 0xf6, 0x31, 0x67, 0xab, 0xb8, + 0x9f, 0x50, 0x81, 0x28, 0x82, 0xec, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x06}; + +const uint8_t secret_constant_kv0[] = { + 0x46, 0x6d, 0xef, 0x2c, 0x05, 0xc9, 0xbf, 0xa9, 0x6b, 0xee, + 0xaa, 0x6c, 0xb9, 0xb4, 0x6d, 0x37, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x07}; + +const uint8_t secret_constant_kv1[] = { + 0x0a, 0x9e, 0xc9, 0x20, 0x29, 0xa3, 0x5d, 0xd7, 0x27, 0x55, + 0xb6, 0xa6, 0xb4, 0x80, 0x7c, 0x73, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x08}; + +const uint8_t secret_constant_k[] = { + /* + * Digest of kernel data key struct fills first 32 bytes + */ + 0x1e, 0x1d, 0xec, 0xf2, 0x6d, 0x27, 0xa6, 0xd9, + 0x67, 0x0f, 0x34, 0xc5, 0xfa, 0x01, 0x68, 0xf6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x03}; + +const uint8_t secret_constant_l[] = { + /* + * Digest of kernel data key struct fills first 32 bytes + */ + 0x9b, 0xc0, 0x29, 0xd3, 0xc3, 0x90, 0x7f, 0x82, + 0x56, 0xe2, 0x67, 0x79, 0x11, 0x74, 0xbe, 0xd0, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x04}; + +const uint8_t secret_constant_p[] = { + /* + * Digest of KDB key struct fills first 32 bytes + */ + 0xfe, 0x31, 0xed, 0xed, 0x45, 0xfd, 0x8a, 0x5d, + 0x87, 0x90, 0xac, 0x17, 0x02, 0x89, 0x2c, 0xba, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x0c}; + +const uint8_t secret_constant_q[] = { + /* + * Digest of KDB key struct fills first 32 bytes + */ + 0xc7, 0x60, 0x83, 0x0f, 0x20, 0x44, 0x5d, 0x9c, + 0x70, 0x96, 0x05, 0x2d, 0x51, 0x4b, 0x15, 0x99, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0x0d}; + +/** + * Get constant with digest + * + * This function computes a digest of the given buffer and concatenates it + * to the given constant. + * + * @param buf Data from which a digest is computed + * @param buf_size Size of <buf> + * @param constant Buffer containing constant + * @param out Buffer where the result is stored + * @return BDB_SUCCESS on success or !BDB_SUCCESS otherwise + */ +static int get_constant_with_digest(const uint8_t *buf, uint32_t buf_size, + const uint8_t *constant, uint8_t *out) { int digest_size = vb2_digest_size(VB2_HASH_SHA256); const struct bdb_key *key = (const struct bdb_key *)buf; @@ -32,42 +161,120 @@ static int get_constant(const uint8_t *buf, uint32_t buf_size, return BDB_SUCCESS; } +/** + * Derive secrets for SP-RO + * + * This function extends a BDS to derive secrets as done by SP-RO (a.k.a. mask + * rom). + * + * @param ctx VBoot context + * @param type Type of secret to derive + * @param wsr Work secret register + * @param buf Data from which a digest is computed + * @param buf_size Size of <buf> + * @param extend sha256 extension function to be used + * @return BDB_SUCCESS on success or BDB_ERROR_* otherwise + */ +static int derive_secret_ro(struct vba_context *ctx, enum bdb_secret_type type, + uint8_t *wsr, const uint8_t *buf, uint32_t buf_size, + f_extend extend) +{ + uint8_t c[BDB_CONSTANT_BLOCK_SIZE]; + uint8_t *from; + const uint8_t *by = (const uint8_t *)c; + uint8_t *to; + + switch (type) { + case BDB_SECRET_TYPE_WSR: + from = to = wsr; + by = secret_constant_x; + break; + case BDB_SECRET_TYPE_BDB: + from = wsr; + to = ctx->secrets->bdb; + if (get_constant_with_digest(buf, buf_size, + secret_constant_p, c)) + return BDB_ERROR_SECRET_BDB; + break; + case BDB_SECRET_TYPE_BOOT_PATH: + from = wsr; + to = ctx->secrets->boot_path; + if (get_constant_with_digest(buf, buf_size, + secret_constant_k, c)) + return BDB_ERROR_SECRET_BOOT_PATH; + break; + case BDB_SECRET_TYPE_BOOT_VERIFIED: + from = wsr; + to = ctx->secrets->boot_verified; + if (ctx->flags & VBA_CONTEXT_FLAG_BDB_KEY_EFUSED) + by = secret_constant_fv0; + else + by = secret_constant_fv1; + break; + case BDB_SECRET_TYPE_NVM_WP: + from = wsr; + by = secret_constant_a; + to = ctx->secrets->nvm_wp; + break; + case BDB_SECRET_TYPE_NVM_RW: + from = ctx->secrets->nvm_wp; + by = secret_constant_b; + to = ctx->secrets->nvm_rw; + break; + default: + return BDB_ERROR_SECRET_TYPE; + } + + if (extend) + extend(from, by, to); + else + vb2_sha256_extend(from, by, to); + + return BDB_SUCCESS; +} + int vba_derive_secret(struct vba_context *ctx, enum bdb_secret_type type, - const uint8_t *buf, uint32_t buf_size) + uint8_t *wsr, const uint8_t *buf, uint32_t buf_size) { uint8_t c[BDB_CONSTANT_BLOCK_SIZE]; - const uint8_t *b = (const uint8_t *)c; - uint8_t *s; - uint8_t *o; + uint8_t *from; + const uint8_t *by = (const uint8_t *)c; + uint8_t *to; switch (type) { + case BDB_SECRET_TYPE_WSR: + from = to = wsr; + by = secret_constant_y; + break; case BDB_SECRET_TYPE_BDB: - s = o = ctx->ro_secrets->bdb; - if (get_constant(buf, buf_size, secret_constant_q, c)) + from = to = ctx->secrets->bdb; + if (get_constant_with_digest(buf, buf_size, + secret_constant_q, c)) return BDB_ERROR_SECRET_BDB; break; case BDB_SECRET_TYPE_BOOT_PATH: - s = o = ctx->ro_secrets->boot_path; - if (get_constant(buf, buf_size, secret_constant_l, c)) + from = to = ctx->secrets->boot_path; + if (get_constant_with_digest(buf, buf_size, + secret_constant_l, c)) return BDB_ERROR_SECRET_BOOT_PATH; break; case BDB_SECRET_TYPE_BOOT_VERIFIED: - s = o = ctx->ro_secrets->boot_verified; + from = to = ctx->secrets->boot_verified; if (ctx->flags & VBA_CONTEXT_FLAG_KERNEL_DATA_KEY_VERIFIED) - b = secret_constant_kv1; + by = secret_constant_kv1; else - b = secret_constant_kv0; + by = secret_constant_kv0; break; case BDB_SECRET_TYPE_BUC: - s = ctx->ro_secrets->boot_verified; - b = secret_constant_c; - o = ctx->rw_secrets->buc; + from = ctx->secrets->boot_verified; + by = secret_constant_c; + to = ctx->secrets->buc; break; default: return BDB_ERROR_SECRET_TYPE; } - vb2_sha256_extend(s, b, o); + vb2_sha256_extend(from, by, to); return BDB_SUCCESS; } @@ -78,19 +285,19 @@ int vba_clear_secret(struct vba_context *ctx, enum bdb_secret_type type) switch (type) { case BDB_SECRET_TYPE_NVM_RW: - s = ctx->ro_secrets->nvm_rw; + s = ctx->secrets->nvm_rw; break; case BDB_SECRET_TYPE_BDB: - s = ctx->ro_secrets->bdb; + s = ctx->secrets->bdb; break; case BDB_SECRET_TYPE_BOOT_PATH: - s = ctx->ro_secrets->boot_path; + s = ctx->secrets->boot_path; break; case BDB_SECRET_TYPE_BOOT_VERIFIED: - s = ctx->ro_secrets->boot_verified; + s = ctx->secrets->boot_verified; break; case BDB_SECRET_TYPE_BUC: - s = ctx->rw_secrets->buc; + s = ctx->secrets->buc; break; default: return BDB_ERROR_SECRET_TYPE; @@ -99,3 +306,25 @@ int vba_clear_secret(struct vba_context *ctx, enum bdb_secret_type type) memset(s, 0, BDB_SECRET_SIZE); return BDB_SUCCESS; } + +int vba_extend_secrets_ro(struct vba_context *ctx, const uint8_t *bdb, + uint8_t *wsr, f_extend extend) +{ + const struct bdb_key *bdbkey = bdb_get_bdbkey(bdb); + const struct bdb_key *datakey = bdb_get_datakey(bdb); + + derive_secret_ro(ctx, BDB_SECRET_TYPE_BDB, wsr, (const uint8_t *)bdbkey, + bdbkey->struct_size, extend); + derive_secret_ro(ctx, BDB_SECRET_TYPE_BOOT_PATH, wsr, + (const uint8_t *)datakey, datakey->struct_size, + extend); + derive_secret_ro(ctx, BDB_SECRET_TYPE_BOOT_VERIFIED, wsr, NULL, 0, + extend); + derive_secret_ro(ctx, BDB_SECRET_TYPE_NVM_WP, wsr, NULL, 0, extend); + /* Deriving NVM-RW has to be done after NVM-WP */ + derive_secret_ro(ctx, BDB_SECRET_TYPE_NVM_RW, wsr, NULL, 0, extend); + /* Extending WSR has to be done last. */ + derive_secret_ro(ctx, BDB_SECRET_TYPE_WSR, wsr, NULL, 0, extend); + + return BDB_SUCCESS; +} diff --git a/firmware/bdb/secrets.h b/firmware/bdb/secrets.h index ed8973f2..59c27cf6 100644 --- a/firmware/bdb/secrets.h +++ b/firmware/bdb/secrets.h @@ -9,51 +9,6 @@ #define BDB_SECRET_SIZE 32 #define BDB_CONSTANT_BLOCK_SIZE 64 -const uint8_t secret_constant_c[] = { - 0x46, 0xda, 0x52, 0x8d, 0x08, 0x56, 0x14, 0xde, 0x75, 0x9c, - 0x9a, 0xeb, 0x08, 0x93, 0x3d, 0xd6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0x0b}; - -const uint8_t secret_constant_kv1[] = { - 0x0a, 0x9e, 0xc9, 0x20, 0x29, 0xa3, 0x5d, 0xd7, 0x27, 0x55, - 0xb6, 0xa6, 0xb4, 0x80, 0x7c, 0x73, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0x08}; - -const uint8_t secret_constant_kv0[] = { - 0x46, 0x6d, 0xef, 0x2c, 0x05, 0xc9, 0xbf, 0xa9, 0x6b, 0xee, - 0xaa, 0x6c, 0xb9, 0xb4, 0x6d, 0x37, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0x07}; - -const uint8_t secret_constant_l[] = { - /* - * Digest of kernel data key struct fills first 32 bytes - */ - 0x9b, 0xc0, 0x29, 0xd3, 0xc3, 0x90, 0x7f, 0x82, - 0x56, 0xe2, 0x67, 0x79, 0x11, 0x74, 0xbe, 0xd0, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0x04}; - -const uint8_t secret_constant_q[] = { - /* - * Digest of KDB key struct fills first 32 bytes - */ - 0xc7, 0x60, 0x83, 0x0f, 0x20, 0x44, 0x5d, 0x9c, - 0x70, 0x96, 0x05, 0x2d, 0x51, 0x4b, 0x15, 0x99, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, - 0xc6, 0xc6, 0xc6, 0x0d}; - enum bdb_secret_type { BDB_SECRET_TYPE_WSR, BDB_SECRET_TYPE_NVM_WP, @@ -66,22 +21,14 @@ enum bdb_secret_type { }; /* - * Secrets passed to SP-RW by SP-RO. How it's passed depends on chips. - * These are hash-extended by SP-RW. + * Struct storing BDB secrets passed between SP-RO and SP-RW. */ -struct bdb_ro_secrets { - uint8_t nvm_wp[BDB_SECRET_SIZE]; +struct bdb_secrets { uint8_t nvm_rw[BDB_SECRET_SIZE]; uint8_t bdb[BDB_SECRET_SIZE]; uint8_t boot_verified[BDB_SECRET_SIZE]; uint8_t boot_path[BDB_SECRET_SIZE]; -}; - -/* - * Additional secrets SP-RW derives from RO secrets. This can be independently - * updated as more secrets are needed. - */ -struct bdb_rw_secrets { + uint8_t nvm_wp[BDB_SECRET_SIZE]; uint8_t buc[BDB_SECRET_SIZE]; }; |