diff options
author | Vadim Bendebury <vbendeb@chromium.org> | 2019-02-28 20:05:27 -0800 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2019-04-05 09:21:44 -0700 |
commit | 1d6c7bb9773f76aa70ce65822fa001ff72892cd2 (patch) | |
tree | 3631462d9540df08d13cffa9a7f8e7e9bb3e7899 /fuzz | |
parent | 63bf8f8ba87b23378391b147f1b3e9fdcf3d8dc5 (diff) | |
download | chrome-ec-1d6c7bb9773f76aa70ce65822fa001ff72892cd2.tar.gz |
nvmem: test modifications to support the new scheme
This patch includes changes to support testing of the new nvmem
implementation.
Making fizz compatible required duplicating a lot of functionality
available in the test/ directory (fuzz/nvmem_tpm2_mock.c is very
similar to test/nvmem_tpm2_mock.c), but I could not find an easy way
to avoid it.
BRANCH=cr50, cr50-mp
BUG=b:69907320, b:129710256
CQ-DEPEND=CL:1496607
TEST=with the rest of the patches applied 'make buildall -j' succeeds,
which confirms both test and fuzz success.
Change-Id: Ife999b04d22f8ddbe9ea5d35f4c3e21f57592754
Signed-off-by: Vadim Bendebury <vbendeb@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1450278
Reviewed-by: Andrey Pronin <apronin@chromium.org>
Diffstat (limited to 'fuzz')
-rw-r--r-- | fuzz/build.mk | 5 | ||||
-rw-r--r-- | fuzz/cr50_fuzz.cc | 1 | ||||
-rw-r--r-- | fuzz/fuzz_config.h | 23 | ||||
-rw-r--r-- | fuzz/nvmem_tpm2_mock.c | 228 |
4 files changed, 251 insertions, 6 deletions
diff --git a/fuzz/build.mk b/fuzz/build.mk index fda788fd93..76d7d13f5b 100644 --- a/fuzz/build.mk +++ b/fuzz/build.mk @@ -25,7 +25,7 @@ endif # Does your object file need to link against cstdlib? # Yes -> use <obj_name>-rw # Otherwise use <obj_name>-y -cr50_fuzz-rw = cr50_fuzz.o pinweaver_model.o mem_hash_tree.o +cr50_fuzz-rw = cr50_fuzz.o pinweaver_model.o mem_hash_tree.o nvmem_tpm2_mock.o host_command_fuzz-y = host_command_fuzz.o usb_pd_fuzz-y = usb_pd_fuzz.o @@ -35,6 +35,9 @@ $(out)/RW/fuzz/pinweaver_model.o: ${CR50_PROTO_HEADERS} $(out)/RW/fuzz/cr50_fuzz.o: ${CR50_PROTO_HEADERS} $(out)/RW/fuzz/cr50_fuzz.o: CPPFLAGS+=${LIBPROTOBUF_MUTATOR_CFLAGS} +TPM2_LIB_ROOT := $(CROS_WORKON_SRCROOT)/src/third_party/tpm2 +$(out)/RW/fuzz/nvmem_tpm2_mock.o: CFLAGS += -I$(TPM2_LIB_ROOT) + $(out)/cr50_fuzz.exe: $(out)/cryptoc/libcryptoc.a \ $(out)/gen/fuzz/cr50_fuzz.pb.o \ $(out)/gen/fuzz/pinweaver/pinweaver.pb.o \ diff --git a/fuzz/cr50_fuzz.cc b/fuzz/cr50_fuzz.cc index e891ee5d85..186700f415 100644 --- a/fuzz/cr50_fuzz.cc +++ b/fuzz/cr50_fuzz.cc @@ -71,7 +71,6 @@ void InitializeFuzzerRun() { memset(__host_flash, 0xff, sizeof(__host_flash)); nvmem_init(); nvmem_enable_commits(); - initvars(); srand(0); } diff --git a/fuzz/fuzz_config.h b/fuzz/fuzz_config.h index 362df69c56..dd2cdc5ae9 100644 --- a/fuzz/fuzz_config.h +++ b/fuzz/fuzz_config.h @@ -17,6 +17,7 @@ #define CONFIG_PINWEAVER #define CONFIG_UPTO_SHA512 #define SHA512_SUPPORT +#define CONFIG_MALLOC /******************************************************************************/ /* From chip/g/config_chip.h */ @@ -29,6 +30,11 @@ /******************************************************************************/ /* From board/cr50/board.h */ /* Non-volatile counter storage for U2F */ +#define CONFIG_CRC8 +#define CONFIG_FLASH_ERASED_VALUE32 (-1U) +#define CONFIG_FLASH_LOG +#define CONFIG_FLASH_LOG_BASE CONFIG_PROGRAM_MEMORY_BASE +#define CONFIG_FLASH_LOG_SPACE 0x800 #define CONFIG_FLASH_NVCOUNTER #define CONFIG_FLASH_NVCTR_SIZE CONFIG_FLASH_BANK_SIZE #define CONFIG_FLASH_NVCTR_BASE_A (CONFIG_PROGRAM_MEMORY_BASE + \ @@ -41,14 +47,23 @@ #define CONFIG_FLASH_NVMEM_OFFSET_A (CFG_TOP_A_OFF + CONFIG_FLASH_NVCTR_SIZE) #define CONFIG_FLASH_NVMEM_OFFSET_B (CFG_TOP_B_OFF + CONFIG_FLASH_NVCTR_SIZE) /* Address of start of Nvmem area */ -#define CONFIG_FLASH_NVMEM_BASE_A (CONFIG_PROGRAM_MEMORY_BASE + \ - CONFIG_FLASH_NVMEM_OFFSET_A) -#define CONFIG_FLASH_NVMEM_BASE_B (CONFIG_PROGRAM_MEMORY_BASE + \ - CONFIG_FLASH_NVMEM_OFFSET_B) +#define CONFIG_FLASH_NVMEM_BASE_A \ + (CONFIG_PROGRAM_MEMORY_BASE + CONFIG_FLASH_NVMEM_OFFSET_A) +#define CONFIG_FLASH_NVMEM_BASE_B \ + (CONFIG_PROGRAM_MEMORY_BASE + CONFIG_FLASH_NVMEM_OFFSET_B) +#define CONFIG_FLASH_NEW_NVMEM_BASE_A \ + (CONFIG_FLASH_NVMEM_BASE_A + CONFIG_FLASH_BANK_SIZE) +#define CONFIG_FLASH_NEW_NVMEM_BASE_B \ + (CONFIG_FLASH_NVMEM_BASE_B + CONFIG_FLASH_BANK_SIZE) /* Size partition in NvMem */ #define NVMEM_PARTITION_SIZE (CFG_TOP_SIZE - CONFIG_FLASH_NVCTR_SIZE) /* Size in bytes of NvMem area */ #define CONFIG_FLASH_NVMEM_SIZE (NVMEM_PARTITION_SIZE * NVMEM_NUM_PARTITIONS) + +#define NEW_NVMEM_PARTITION_SIZE (NVMEM_PARTITION_SIZE - CONFIG_FLASH_BANK_SIZE) +#define NEW_NVMEM_TOTAL_PAGES \ + (2 * NEW_NVMEM_PARTITION_SIZE / CONFIG_FLASH_BANK_SIZE) + /* Enable <key, value> variable support. */ #define CONFIG_FLASH_NVMEM_VARS #define NVMEM_CR50_SIZE 272 diff --git a/fuzz/nvmem_tpm2_mock.c b/fuzz/nvmem_tpm2_mock.c new file mode 100644 index 0000000000..5fac9674a2 --- /dev/null +++ b/fuzz/nvmem_tpm2_mock.c @@ -0,0 +1,228 @@ +/* Copyright 2019 The Chromium OS Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ +/* Stuff from tpm2 directory. */ +#define NV_C +#include "Global.h" +#undef NV_C +#include "NV_fp.h" +#include "tpm_generated.h" + +#include "nvmem.h" +#include "util.h" + +#define NVMEM_CR50_SIZE 272 + +#ifndef TEST_FUZZ +uint32_t nvmem_user_sizes[NVMEM_NUM_USERS] = {MOCK_NV_MEMORY_SIZE, + NVMEM_CR50_SIZE}; +#endif + +uint32_t s_evictNvStart; +uint32_t s_evictNvEnd; + +/* Calculate size of TPM NVMEM. */ +#define MOCK_NV_MEMORY_SIZE \ + (NVMEM_PARTITION_SIZE - sizeof(struct nvmem_tag) - NVMEM_CR50_SIZE) + +/* + * Sizes of the reserved objects stored in the TPM NVMEM. Note that the second + * last object is in fact a variable size field starting with 4 bytes of size + * and then up to 512 bytes of actual index data. The array below assumes that + * the full 512 bytes of the index space are used. + */ +const uint16_t res_sizes[] = {4, 2, 2, 2, 66, 66, 66, 66, 66, 66, + 34, 34, 34, 66, 66, 66, 8, 4, 134, 28, + 3, 4, 4, 4, 4, 4, 2, 15, 2, 8, + 4, 4, 4, 96, 2844, 424, 516, 8}; + +static uint16_t res_addrs[ARRAY_SIZE(res_sizes)]; + +BOOL NvEarlyStageFindHandle(TPM_HANDLE handle) +{ + size_t i; + + res_addrs[0] = 0; + + for (i = 1; i < ARRAY_SIZE(res_addrs); i++) + res_addrs[i] = res_addrs[i - 1] + res_sizes[i - 1]; + + s_evictNvStart = res_addrs[i - 1] + res_sizes[i - 1]; + + s_evictNvEnd = MOCK_NV_MEMORY_SIZE; + return 0; +} + +void NvGetReserved(UINT32 index, NV_RESERVED_ITEM *ri) +{ + if (index < ARRAY_SIZE(res_sizes)) { + ri->size = res_sizes[index]; + ri->offset = res_addrs[index]; + } else { + ri->size = 0; + } +} + +UINT16 UINT16_Marshal(UINT16 *source, BYTE **buffer, INT32 *size) +{ + uint16_t value; + + if (!size || (*size < sizeof(value))) + return 0; + + value = htobe16(*source); + + memcpy(*buffer, &value, sizeof(value)); + *buffer += sizeof(value); + *size -= sizeof(value); + + return sizeof(value); +} + +UINT16 UINT32_Marshal(UINT32 *source, BYTE **buffer, INT32 *size) +{ + uint32_t value; + + if (!size || (*size < sizeof(value))) + return 0; + + value = htobe32(*source); + + memcpy(*buffer, &value, sizeof(value)); + *buffer += sizeof(value); + *size -= sizeof(value); + + return sizeof(value); +} + +UINT16 UINT64_Marshal(UINT64 *source, BYTE **buffer, INT32 *size) +{ + uint64_t value; + + if (!size || (*size < sizeof(value))) + return 0; + + value = htobe64(*source); + + memcpy(*buffer, &value, sizeof(value)); + *buffer += sizeof(value); + *size -= sizeof(value); + + return sizeof(value); +} + +UINT16 TPM2B_DIGEST_Marshal(TPM2B_DIGEST *source, BYTE **buffer, INT32 *size) +{ + UINT16 total_size; + INT32 i; + uint8_t *p; + + total_size = UINT16_Marshal(&source->t.size, buffer, size); + p = *buffer; + + for (i = 0; (i < source->t.size) && *size; ++i) { + *p++ = source->t.buffer[i]; + *size -= 1; + } + + total_size += i; + *buffer = p; + + return total_size; +} + +uint16_t TPM2B_AUTH_Marshal(TPM2B_AUTH *source, BYTE **buffer, INT32 *size) +{ + return TPM2B_DIGEST_Marshal(source, buffer, size); +} + +uint16_t TPM2B_NONCE_Marshal(TPM2B_AUTH *source, BYTE **buffer, INT32 *size) +{ + return TPM2B_DIGEST_Marshal(source, buffer, size); +} + +TPM_RC UINT16_Unmarshal(UINT16 *target, BYTE **buffer, INT32 *size) +{ + uint16_t value; + + if (!size || *size < sizeof(value)) + return TPM_RC_INSUFFICIENT; + + memcpy(&value, *buffer, sizeof(value)); + *target = be16toh(value); + + *buffer += sizeof(value); + *size -= sizeof(value); + + return TPM_RC_SUCCESS; +} + +TPM_RC UINT32_Unmarshal(UINT32 *target, BYTE **buffer, INT32 *size) +{ + uint32_t value; + + if (!size || *size < sizeof(value)) + return TPM_RC_INSUFFICIENT; + + memcpy(&value, *buffer, sizeof(value)); + *target = be32toh(value); + + *buffer += sizeof(value); + *size -= sizeof(value); + + return TPM_RC_SUCCESS; +} + +TPM_RC UINT64_Unmarshal(UINT64 *target, BYTE **buffer, INT32 *size) +{ + uint64_t value; + + if (!size || *size < sizeof(value)) + return TPM_RC_INSUFFICIENT; + + memcpy(&value, *buffer, sizeof(value)); + *target = be64toh(value); + + *buffer += sizeof(value); + *size -= sizeof(value); + + return TPM_RC_SUCCESS; +} + +TPM_RC TPM2B_DIGEST_Unmarshal(TPM2B_DIGEST *target, BYTE **buffer, INT32 *size) +{ + TPM_RC result; + INT32 i; + uint8_t *p; + + result = UINT16_Unmarshal(&target->t.size, buffer, size); + + if (result != TPM_RC_SUCCESS) + return result; + + if (target->t.size == 0) + return TPM_RC_SUCCESS; + + if ((target->t.size > sizeof(TPMU_HA)) || (target->t.size > *size)) + return TPM_RC_SIZE; + + p = *buffer; + for (i = 0; i < target->t.size; ++i) + target->t.buffer[i] = *p++; + + *buffer = p; + *size -= i; + + return TPM_RC_SUCCESS; +} + +TPM_RC TPM2B_AUTH_Unmarshal(TPM2B_AUTH *target, BYTE **buffer, INT32 *size) +{ + return TPM2B_DIGEST_Unmarshal(target, buffer, size); +} + +TPM_RC TPM2B_NONCE_Unmarshal(TPM2B_AUTH *target, BYTE **buffer, INT32 *size) +{ + return TPM2B_DIGEST_Unmarshal(target, buffer, size); +} |