Merge commit '5c0fcf0f8725b98043a4b18f36e21489375d133a' into cros_sdk
Updated vboot_reference to CrOS version 14056.0.0
BUG=b/192265868
TEST=local BE run
RELEASE_NOTE=Updated ChromeOS base to ChromeOS version 14056.0.0.
Signed-off-by: Robert Kolchmeyer <rkolchmeyer@google.com>
Change-Id: I60a04a25a1dad1b0a9508acdc912a2344deabf2b
diff --git a/Android.mk b/Android.mk
index 64d89e1..c54a3b7 100644
--- a/Android.mk
+++ b/Android.mk
@@ -54,7 +54,6 @@
firmware/lib/gpt_misc.c \
firmware/lib/utility_string.c \
firmware/lib/vboot_api_kernel.c \
- firmware/lib/vboot_audio.c \
firmware/lib/vboot_display.c \
firmware/lib/vboot_kernel.c \
firmware/lib/region-kernel.c \
@@ -62,7 +61,6 @@
VBINIT_SRCS += \
firmware/stub/tpm_lite_stub.c \
firmware/stub/utility_stub.c \
- firmware/stub/vboot_api_stub_init.c \
firmware/stub/vboot_api_stub_region.c
VBSF_SRCS += \
diff --git a/Makefile b/Makefile
index 3a72d3d..327b753 100644
--- a/Makefile
+++ b/Makefile
@@ -187,6 +187,12 @@
CFLAGS += -DTPM2_MODE
endif
+# Support devices with GPT in SPI-NOR (for nand device)
+# TODO(b:184812319): Consider removing this code if nobody uses it.
+ifneq (${GPT_SPI_NOR},)
+CFLAGS += -DGPT_SPI_NOR
+endif
+
# Enable boot from external disk when switching to dev mode
ifneq ($(filter-out 0,${BOOT_EXTERNAL_ON_DEV}),)
CFLAGS += -DBOOT_EXTERNAL_ON_DEV=1
@@ -213,6 +219,15 @@
CFLAGS += -DTPM2_SIMULATOR=0
endif
+# VTPM_PROXY indicates whether the TPM driver simulator feature
+# is enable or not.
+# This flag only takes effect when TPM2_SIMULATOR is enabled.
+ifneq ($(filter-out 0,${VTPM_PROXY}),)
+CFLAGS += -DVTPM_PROXY=1
+else
+CFLAGS += -DVTPM_PROXY=0
+endif
+
# DETACHABLE indicates whether the device is a detachable or not.
ifneq ($(filter-out 0,${DETACHABLE}),)
CFLAGS += -DDETACHABLE=1
@@ -358,6 +373,9 @@
ifeq (${FIRMWARE_ARCH},)
INCLUDES += -Ihost/include -Ihost/lib/include
INCLUDES += -Ihost/lib21/include
+ifeq ($(shell uname -s), OpenBSD)
+INCLUDES += -I/usr/local/include
+endif
endif
# Firmware library, used by the other firmware components (depthcharge,
@@ -376,11 +394,13 @@
firmware/2lib/2crc8.c \
firmware/2lib/2crypto.c \
firmware/2lib/2ec_sync.c \
+ firmware/2lib/2firmware.c \
firmware/2lib/2gbb.c \
firmware/2lib/2hmac.c \
firmware/2lib/2kernel.c \
firmware/2lib/2misc.c \
firmware/2lib/2nvstorage.c \
+ firmware/2lib/2packed_key.c \
firmware/2lib/2recovery_reasons.c \
firmware/2lib/2rsa.c \
firmware/2lib/2secdata_firmware.c \
@@ -390,6 +410,7 @@
firmware/2lib/2sha256.c \
firmware/2lib/2sha512.c \
firmware/2lib/2sha_utility.c \
+ firmware/2lib/2struct.c \
firmware/2lib/2stub_hwcrypto.c \
firmware/2lib/2tpm_bootmode.c \
firmware/lib/cgptlib/cgptlib.c \
@@ -399,16 +420,13 @@
firmware/lib/vboot_api_kernel.c \
firmware/lib/vboot_kernel.c \
firmware/lib20/api_kernel.c \
- firmware/lib20/kernel.c \
- firmware/lib20/misc.c \
- firmware/lib20/packed_key.c
+ firmware/lib20/kernel.c
# Only add these to firmware and test builds,
# as regular host builds don't need them
$(if ${FIRMWARE_ARCH},FWLIB_SRCS,TESTLIB_SRCS) += \
firmware/2lib/2ui.c \
firmware/2lib/2ui_screens.c \
- firmware/lib/vboot_audio.c
# TPM lightweight command library
ifeq (${TPM2_MODE},)
@@ -434,7 +452,6 @@
firmware/stub/tpm_lite_stub.c \
firmware/stub/vboot_api_stub.c \
firmware/stub/vboot_api_stub_disk.c \
- firmware/stub/vboot_api_stub_init.c \
firmware/stub/vboot_api_stub_stream.c \
firmware/2lib/2stub.c
endif
@@ -491,7 +508,6 @@
cgpt/cgpt_create.c \
cgpt/cgpt_edit.c \
cgpt/cgpt_find.c \
- cgpt/cgpt_nor.c \
cgpt/cgpt_prioritize.c \
cgpt/cgpt_show.c \
firmware/2lib/2common.c \
@@ -507,6 +523,7 @@
firmware/2lib/2sha256.c \
firmware/2lib/2sha512.c \
firmware/2lib/2sha_utility.c \
+ firmware/2lib/2struct.c \
firmware/2lib/2stub.c \
firmware/2lib/2stub_hwcrypto.c \
firmware/lib/cgptlib/cgptlib_internal.c \
@@ -515,7 +532,6 @@
firmware/stub/tpm_lite_stub.c \
firmware/stub/vboot_api_stub.c \
firmware/stub/vboot_api_stub_disk.c \
- firmware/stub/vboot_api_stub_init.c \
futility/dump_kernel_config_lib.c \
$(CROSSYSTEM_ARCH_C) \
host/lib/chromeos_config.c \
@@ -529,6 +545,10 @@
host/lib21/host_misc.c \
${TLCL_SRCS}
+ifneq (${GPT_SPI_NOR},)
+HOSTLIB_SRCS += cgpt/cgpt_nor.c
+endif
+
HOSTLIB_OBJS = ${HOSTLIB_SRCS:%.c=${BUILD}/%.o}
ALL_OBJS += ${HOSTLIB_OBJS}
@@ -546,7 +566,6 @@
cgpt/cgpt_edit.c \
cgpt/cgpt_find.c \
cgpt/cgpt_legacy.c \
- cgpt/cgpt_nor.c \
cgpt/cgpt_prioritize.c \
cgpt/cgpt_repair.c \
cgpt/cgpt_show.c \
@@ -560,6 +579,10 @@
cgpt/cmd_repair.c \
cgpt/cmd_show.c
+ifneq (${GPT_SPI_NOR},)
+CGPT_SRCS += cgpt/cgpt_nor.c
+endif
+
CGPT_OBJS = ${CGPT_SRCS:%.c=${BUILD}/%.o}
ALL_OBJS += ${CGPT_OBJS}
@@ -653,7 +676,6 @@
futility/file_type_rwsig.c \
futility/file_type_usbpd1.c \
futility/misc.c \
- futility/ryu_root_header.c \
futility/updater.c \
futility/updater_archive.c \
futility/updater_quirks.c \
@@ -716,6 +738,7 @@
tests/vb2_common3_tests \
tests/vb2_crypto_tests \
tests/vb2_ec_sync_tests \
+ tests/vb2_firmware_tests \
tests/vb2_gbb_tests \
tests/vb2_host_flashrom_tests \
tests/vb2_host_key_tests \
@@ -739,7 +762,6 @@
tests/vb20_api_kernel_tests \
tests/vb20_verify_fw.c \
tests/vb20_kernel_tests \
- tests/vb20_misc_tests \
tests/vb20_rsa_padding_tests \
tests/vb20_verify_fw
@@ -942,10 +964,12 @@
${Q}${LD} -o ${CGPT_WRAPPER} ${LDFLAGS} $^ ${LDLIBS}
.PHONY: cgpt
-cgpt: ${CGPT} ${CGPT_WRAPPER}
+cgpt: ${CGPT} $(if ${GPT_SPI_NOR},cgpt_wrapper)
# on FreeBSD: install misc/e2fsprogs-libuuid from ports,
# or e2fsprogs-libuuid from its binary package system.
+# on OpenBSD: install sysutils/e2fsprogs from ports,
+# or e2fsprogs from its binary package system, to install uuid/uid.h
${CGPT}: LDLIBS += -luuid
${CGPT}: ${CGPT_OBJS} ${UTILLIB}
@@ -1121,6 +1145,9 @@
ifeq ($(shell uname -s), FreeBSD)
CRYPTO_LIBS += -lcrypto
endif
+ifeq ($(shell uname -s), OpenBSD)
+LDFLAGS += -Wl,-z,notext
+endif
${BUILD}/utility/dumpRSAPublicKey: LDLIBS += ${CRYPTO_LIBS}
${BUILD}/utility/pad_digest_utility: LDLIBS += ${CRYPTO_LIBS}
@@ -1246,6 +1273,7 @@
${RUNTEST} ${BUILD_RUN}/tests/vb2_common3_tests ${TEST_KEYS}
${RUNTEST} ${BUILD_RUN}/tests/vb2_crypto_tests
${RUNTEST} ${BUILD_RUN}/tests/vb2_ec_sync_tests
+ ${RUNTEST} ${BUILD_RUN}/tests/vb2_firmware_tests
${RUNTEST} ${BUILD_RUN}/tests/vb2_gbb_tests
${RUNTEST} ${BUILD_RUN}/tests/vb2_host_key_tests
${RUNTEST} ${BUILD_RUN}/tests/vb2_kernel_tests
@@ -1262,7 +1290,6 @@
${RUNTEST} ${BUILD_RUN}/tests/vb2_ui_utility_tests
${RUNTEST} ${BUILD_RUN}/tests/vb20_api_kernel_tests
${RUNTEST} ${BUILD_RUN}/tests/vb20_kernel_tests
- ${RUNTEST} ${BUILD_RUN}/tests/vb20_misc_tests
${RUNTEST} ${BUILD_RUN}/tests/vb21_host_common_tests
${RUNTEST} ${BUILD_RUN}/tests/vb21_host_common2_tests ${TEST_KEYS}
${RUNTEST} ${BUILD_RUN}/tests/vb21_host_key_tests ${TEST_KEYS} ${BUILD}
diff --git a/cgpt/cgpt.h b/cgpt/cgpt.h
index 0747b5c..89c357e 100644
--- a/cgpt/cgpt.h
+++ b/cgpt/cgpt.h
@@ -7,7 +7,7 @@
#define VBOOT_REFERENCE_CGPT_H_
#include <fcntl.h>
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
#include <features.h>
#endif
#include <stdint.h>
diff --git a/cgpt/cgpt_common.c b/cgpt/cgpt_common.c
index 426be3b..c3edd0f 100644
--- a/cgpt/cgpt_common.c
+++ b/cgpt/cgpt_common.c
@@ -9,7 +9,7 @@
#include <errno.h>
#include <fcntl.h>
#include <getopt.h>
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
#include <linux/major.h>
#include <mtd/mtd-user.h>
#endif
@@ -295,7 +295,7 @@
if (fstat(fd, &stat) == -1) {
return -1;
}
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
if ((stat.st_mode & S_IFMT) != S_IFREG) {
if (ioctl(fd, BLKGETSIZE64, size) < 0) {
return -1;
@@ -325,7 +325,7 @@
memset(drive, 0, sizeof(struct drive));
drive->fd = open(drive_path, mode |
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
O_LARGEFILE |
#endif
O_NOFOLLOW);
diff --git a/cgpt/cgpt_find.c b/cgpt/cgpt_find.c
index 6f4bbae..8046aad 100644
--- a/cgpt/cgpt_find.c
+++ b/cgpt/cgpt_find.c
@@ -96,19 +96,6 @@
EntryDetails(entry, partnum - 1, params->numeric);
}
-// This handles the MTD devices. ChromeOS uses /dev/mtdX for kernel partitions,
-// /dev/ubiblockX_0 for root partitions, and /dev/ubiX for stateful partition.
-static void chromeos_mtd_show(CgptFindParams *params, const char *filename,
- int partnum, GptEntry *entry) {
- if (GuidEqual(&guid_chromeos_kernel, &entry->type)) {
- printf("/dev/mtd%d\n", partnum);
- } else if (GuidEqual(&guid_chromeos_rootfs, &entry->type)) {
- printf("/dev/ubiblock%d_0\n", partnum);
- } else {
- printf("/dev/ubi%d_0\n", partnum);
- }
-}
-
// This returns true if a GPT partition matches the search criteria. If a match
// isn't found (or if the file doesn't contain a GPT), it returns false. The
// filename and partition number that matched is left in a global, since we
@@ -214,6 +201,76 @@
return 0;
}
+#ifdef GPT_SPI_NOR
+// This handles the MTD devices. ChromeOS uses /dev/mtdX for kernel partitions,
+// /dev/ubiblockX_0 for root partitions, and /dev/ubiX for stateful partition.
+static void chromeos_mtd_show(CgptFindParams *params, const char *filename,
+ int partnum, GptEntry *entry) {
+ if (GuidEqual(&guid_chromeos_kernel, &entry->type)) {
+ printf("/dev/mtd%d\n", partnum);
+ } else if (GuidEqual(&guid_chromeos_rootfs, &entry->type)) {
+ printf("/dev/ubiblock%d_0\n", partnum);
+ } else {
+ printf("/dev/ubi%d_0\n", partnum);
+ }
+}
+
+static int scan_spi_gpt(CgptFindParams *params) {
+ int found = 0;
+ char partname[MAX_PARTITION_NAME_LEN];
+ FILE *fp;
+ size_t line_length = 0;
+ char *line = NULL;
+
+ fp = fopen(PROC_MTD, "re");
+ if (!fp) {
+ return found;
+ }
+
+ while (getline(&line, &line_length, fp) != -1) {
+ uint64_t sz;
+ uint32_t erasesz;
+ char name[128];
+ // dev: size erasesize name
+ if (sscanf(line, "%64[^:]: %" PRIx64 " %x \"%127[^\"]\"",
+ partname, &sz, &erasesz, name) != 4)
+ continue;
+ if (strcmp(partname, "mtd0") == 0) {
+ char temp_dir[] = "/tmp/cgpt_find.XXXXXX";
+ if (params->drive_size == 0) {
+ if (GetMtdSize("/dev/mtd0", ¶ms->drive_size) != 0) {
+ perror("GetMtdSize");
+ goto cleanup;
+ }
+ }
+ if (ReadNorFlash(temp_dir) != 0) {
+ perror("ReadNorFlash");
+ goto cleanup;
+ }
+ char nor_file[64];
+ if (snprintf(nor_file, sizeof(nor_file), "%s/rw_gpt", temp_dir) > 0) {
+ params->show_fn = chromeos_mtd_show;
+ if (do_search(params, nor_file)) {
+ found++;
+ }
+ params->show_fn = NULL;
+ }
+ RemoveDir(temp_dir);
+ break;
+ }
+ }
+cleanup:
+ fclose(fp);
+ free(line);
+ return found;
+}
+#else
+// Stub
+static int scan_spi_gpt(CgptFindParams *params) {
+ return 0;
+}
+#endif
+
// This scans all the physical devices it can find, looking for a match. It
// returns true if any matches were found, false otherwise.
static int scan_real_devs(CgptFindParams *params) {
@@ -255,48 +312,10 @@
}
fclose(fp);
-
- fp = fopen(PROC_MTD, "re");
- if (!fp) {
- free(line);
- return found;
- }
-
- while (getline(&line, &line_length, fp) != -1) {
- uint64_t sz;
- uint32_t erasesz;
- char name[128];
- // dev: size erasesize name
- if (sscanf(line, "%64[^:]: %" PRIx64 " %x \"%127[^\"]\"",
- partname, &sz, &erasesz, name) != 4)
- continue;
- if (strcmp(partname, "mtd0") == 0) {
- char temp_dir[] = "/tmp/cgpt_find.XXXXXX";
- if (params->drive_size == 0) {
- if (GetMtdSize("/dev/mtd0", ¶ms->drive_size) != 0) {
- perror("GetMtdSize");
- goto cleanup;
- }
- }
- if (ReadNorFlash(temp_dir) != 0) {
- perror("ReadNorFlash");
- goto cleanup;
- }
- char nor_file[64];
- if (snprintf(nor_file, sizeof(nor_file), "%s/rw_gpt", temp_dir) > 0) {
- params->show_fn = chromeos_mtd_show;
- if (do_search(params, nor_file)) {
- found++;
- }
- params->show_fn = NULL;
- }
- RemoveDir(temp_dir);
- break;
- }
- }
-cleanup:
- fclose(fp);
free(line);
+
+ found += scan_spi_gpt(params);
+
return found;
}
diff --git a/cgpt/cgpt_nor.c b/cgpt/cgpt_nor.c
index fd18446..2e43918 100644
--- a/cgpt/cgpt_nor.c
+++ b/cgpt/cgpt_nor.c
@@ -24,6 +24,7 @@
#include "cgpt.h"
#include "cgpt_nor.h"
+#include "subprocess.h"
static const char FLASHROM_PATH[] = "/usr/sbin/flashrom";
@@ -48,6 +49,7 @@
return ret;
}
+// TODO(b:184812319): Remove these functions and use subprocess_run everywhere.
int ForkExecV(const char *cwd, const char *const argv[]) {
pid_t pid = fork();
if (pid == -1) {
@@ -200,6 +202,7 @@
// Read RW_GPT from NOR flash to "rw_gpt" in a temp dir |temp_dir_template|.
// |temp_dir_template| is passed to mkdtemp() so it must satisfy all
// requirements by mkdtemp.
+// TODO(b:184812319): Replace this function with flashrom_read.
int ReadNorFlash(char *temp_dir_template) {
int ret = 0;
@@ -212,27 +215,40 @@
// Read RW_GPT section from NOR flash to "rw_gpt".
ret++;
- int fd_flags = fcntl(1, F_GETFD);
- // Close stdout on exec so that flashrom does not muck up cgpt's output.
- if (0 != fcntl(1, F_SETFD, FD_CLOEXEC))
- Warning("Can't stop flashrom from mucking up our output\n");
- if (ForkExecL(temp_dir_template, FLASHROM_PATH, "-i", "RW_GPT:rw_gpt", "-r",
- NULL) != 0) {
+
+ char *cwd = getcwd(NULL, 0);
+ if (!cwd) {
+ Error("Cannot get current directory.\n");
+ return ret;
+ }
+ if (chdir(temp_dir_template) < 0) {
+ Error("Cannot change directory.\n");
+ goto out_free;
+ }
+ const char *const argv[] = {FLASHROM_PATH, "-i", "RW_GPT:rw_gpt", "-r"};
+ // Redirect stdout to /dev/null so that flashrom does not muck up cgpt's
+ // output.
+ if (subprocess_run(argv, &subprocess_null, &subprocess_null, NULL) != 0) {
Error("Cannot exec flashrom to read from RW_GPT section.\n");
RemoveDir(temp_dir_template);
} else {
ret = 0;
}
+ if (chdir(cwd) < 0) {
+ Error("Cannot change directory back to original.\n");
+ goto out_free;
+ }
- // Restore stdout flags
- if (0 != fcntl(1, F_SETFD, fd_flags))
- Warning("Can't restore stdout flags\n");
+out_free:
+ free(cwd);
return ret;
}
// Write "rw_gpt" back to NOR flash. We write the file in two parts for safety.
+// TODO(b:184812319): Replace this function with flashrom_write.
int WriteNorFlash(const char *dir) {
int ret = 0;
+
ret++;
if (split_gpt(dir, "rw_gpt") != 0) {
Error("Cannot split rw_gpt in two.\n");
@@ -240,26 +256,43 @@
}
ret++;
int nr_fails = 0;
- int fd_flags = fcntl(1, F_GETFD);
- // Close stdout on exec so that flashrom does not muck up cgpt's output.
- if (0 != fcntl(1, F_SETFD, FD_CLOEXEC))
- Warning("Can't stop flashrom from mucking up our output\n");
- if (ForkExecL(dir, FLASHROM_PATH, "-i", "RW_GPT_PRIMARY:rw_gpt_1",
- "-w", "--fast-verify", NULL) != 0) {
+
+ char *cwd = getcwd(NULL, 0);
+ if (!cwd) {
+ Error("Cannot get current directory.\n");
+ return ret;
+ }
+ if (chdir(dir) < 0) {
+ Error("Cannot change directory.\n");
+ goto out_free;
+ }
+ const char *const argv1[] = {FLASHROM_PATH, "-i", "RW_GPT_PRIMARY:rw_gpt_1",
+ "-w", "--noverify-all"};
+ // Redirect stdout to /dev/null so that flashrom does not muck up cgpt's
+ // output.
+ if (subprocess_run(argv1, &subprocess_null, &subprocess_null, NULL) != 0) {
Warning("Cannot write the 1st half of rw_gpt back with flashrom.\n");
nr_fails++;
}
- if (ForkExecL(dir, FLASHROM_PATH, "-i", "RW_GPT_SECONDARY:rw_gpt_2",
- "-w", "--fast-verify", NULL) != 0) {
+ const char *const argv2[] = {FLASHROM_PATH, "-i", "RW_GPT_SECONDARY:rw_gpt_2",
+ "-w", "--noverify-all"};
+ // Redirect stdout to /dev/null so that flashrom does not muck up cgpt's
+ // output.
+ if (subprocess_run(argv2, &subprocess_null, &subprocess_null, NULL) != 0) {
Warning("Cannot write the 2nd half of rw_gpt back with flashrom.\n");
nr_fails++;
}
- if (0 != fcntl(1, F_SETFD, fd_flags))
- Warning("Can't restore stdout flags\n");
+ if (chdir(cwd) < 0) {
+ Error("Cannot change directory back to original.\n");
+ goto out_free;
+ }
switch (nr_fails) {
case 0: ret = 0; break;
case 1: Warning("It might still be okay.\n"); break;
case 2: Error("Cannot write both parts back with flashrom.\n"); break;
}
+
+out_free:
+ free(cwd);
return ret;
}
diff --git a/firmware/2lib/2api.c b/firmware/2lib/2api.c
index 2beb9ed..aa1d25d 100644
--- a/firmware/2lib/2api.c
+++ b/firmware/2lib/2api.c
@@ -15,7 +15,6 @@
#include "2sha.h"
#include "2sysincludes.h"
#include "2tpm_bootmode.h"
-#include "vb2_common.h"
vb2_error_t vb2api_fw_phase1(struct vb2_context *ctx)
{
diff --git a/firmware/2lib/2common.c b/firmware/2lib/2common.c
index a88bc2e..fa0585e 100644
--- a/firmware/2lib/2common.c
+++ b/firmware/2lib/2common.c
@@ -8,8 +8,6 @@
#include "2common.h"
#include "2rsa.h"
-#include "2sha.h"
-#include "2sysincludes.h"
vb2_error_t vb2_safe_memcmp(const void *s1, const void *s2, size_t size)
{
@@ -190,9 +188,9 @@
const struct vb2_workbuf *wb)
{
struct vb2_workbuf wblocal = *wb;
- struct vb2_digest_context *dc;
uint8_t *digest;
uint32_t digest_size;
+ vb2_error_t rv;
if (sig->data_size > size) {
VB2_DEBUG("Data buffer smaller than length of signed data.\n");
@@ -208,164 +206,26 @@
if (!digest)
return VB2_ERROR_VDATA_WORKBUF_DIGEST;
- /* Hashing requires temp space for the context */
- dc = vb2_workbuf_alloc(&wblocal, sizeof(*dc));
- if (!dc)
- return VB2_ERROR_VDATA_WORKBUF_HASHING;
-
- VB2_TRY(vb2_digest_init(dc, key->hash_alg));
- VB2_TRY(vb2_digest_extend(dc, data, sig->data_size));
- VB2_TRY(vb2_digest_finalize(dc, digest, digest_size));
-
- vb2_workbuf_free(&wblocal, sizeof(*dc));
+ if (key->allow_hwcrypto) {
+ rv = vb2ex_hwcrypto_digest_init(key->hash_alg, sig->data_size);
+ if (rv == VB2_SUCCESS) {
+ VB2_DEBUG("Using HW crypto engine for hash_alg %d\n", key->hash_alg);
+ VB2_TRY(vb2ex_hwcrypto_digest_extend(data, sig->data_size));
+ VB2_TRY(vb2ex_hwcrypto_digest_finalize(digest, digest_size));
+ } else if (rv == VB2_ERROR_EX_HWCRYPTO_UNSUPPORTED) {
+ VB2_DEBUG("HW crypto for hash_alg %d not supported, using SW\n",
+ key->hash_alg);
+ VB2_TRY(vb2_digest_buffer(data, sig->data_size, key->hash_alg,
+ digest, digest_size));
+ } else {
+ VB2_DEBUG("HW crypto init error : %d\n", rv);
+ return rv;
+ }
+ } else {
+ VB2_DEBUG("HW crypto forbidden by TPM flag, using SW\n");
+ VB2_TRY(vb2_digest_buffer(data, sig->data_size, key->hash_alg,
+ digest, digest_size));
+ }
return vb2_verify_digest(key, sig, digest, &wblocal);
}
-
-vb2_error_t vb2_check_keyblock(const struct vb2_keyblock *block, uint32_t size,
- const struct vb2_signature *sig)
-{
- if(size < sizeof(*block)) {
- VB2_DEBUG("Not enough space for keyblock header.\n");
- return VB2_ERROR_KEYBLOCK_TOO_SMALL_FOR_HEADER;
- }
-
- if (memcmp(block->magic, VB2_KEYBLOCK_MAGIC, VB2_KEYBLOCK_MAGIC_SIZE)) {
- VB2_DEBUG("Not a valid verified boot keyblock.\n");
- return VB2_ERROR_KEYBLOCK_MAGIC;
- }
-
- if (block->header_version_major != VB2_KEYBLOCK_VERSION_MAJOR) {
- VB2_DEBUG("Incompatible keyblock header version.\n");
- return VB2_ERROR_KEYBLOCK_HEADER_VERSION;
- }
-
- if (size < block->keyblock_size) {
- VB2_DEBUG("Not enough data for keyblock.\n");
- return VB2_ERROR_KEYBLOCK_SIZE;
- }
-
- if (vb2_verify_signature_inside(block, block->keyblock_size, sig)) {
- VB2_DEBUG("Keyblock signature off end of block\n");
- return VB2_ERROR_KEYBLOCK_SIG_OUTSIDE;
- }
-
- /* Make sure advertised signature data sizes are valid. */
- if (block->keyblock_size < sig->data_size) {
- VB2_DEBUG("Signature calculated past end of block\n");
- return VB2_ERROR_KEYBLOCK_SIGNED_TOO_MUCH;
- }
-
- /* Verify we signed enough data */
- if (sig->data_size < sizeof(struct vb2_keyblock)) {
- VB2_DEBUG("Didn't sign enough data\n");
- return VB2_ERROR_KEYBLOCK_SIGNED_TOO_LITTLE;
- }
-
- /* Verify data key is inside the block and inside signed data */
- if (vb2_verify_packed_key_inside(block, block->keyblock_size,
- &block->data_key)) {
- VB2_DEBUG("Data key off end of keyblock\n");
- return VB2_ERROR_KEYBLOCK_DATA_KEY_OUTSIDE;
- }
- if (vb2_verify_packed_key_inside(block, sig->data_size,
- &block->data_key)) {
- VB2_DEBUG("Data key off end of signed data\n");
- return VB2_ERROR_KEYBLOCK_DATA_KEY_UNSIGNED;
- }
-
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2_verify_keyblock(struct vb2_keyblock *block, uint32_t size,
- const struct vb2_public_key *key,
- const struct vb2_workbuf *wb)
-{
- struct vb2_signature *sig = &block->keyblock_signature;
- vb2_error_t rv;
-
- /* Validity check keyblock before attempting signature check of data */
- VB2_TRY(vb2_check_keyblock(block, size, sig));
-
- VB2_DEBUG("Checking keyblock signature...\n");
- rv = vb2_verify_data((const uint8_t *)block, size, sig, key, wb);
- if (rv) {
- VB2_DEBUG("Invalid keyblock signature.\n");
- return VB2_ERROR_KEYBLOCK_SIG_INVALID;
- }
-
- /* Success */
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2_verify_fw_preamble(struct vb2_fw_preamble *preamble,
- uint32_t size,
- const struct vb2_public_key *key,
- const struct vb2_workbuf *wb)
-{
- struct vb2_signature *sig = &preamble->preamble_signature;
-
- VB2_DEBUG("Verifying preamble.\n");
-
- /* Validity checks before attempting signature of data */
- if(size < sizeof(*preamble)) {
- VB2_DEBUG("Not enough data for preamble header\n");
- return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
- }
- if (preamble->header_version_major !=
- VB2_FIRMWARE_PREAMBLE_HEADER_VERSION_MAJOR) {
- VB2_DEBUG("Incompatible firmware preamble header version.\n");
- return VB2_ERROR_PREAMBLE_HEADER_VERSION;
- }
-
- if (preamble->header_version_minor < 1) {
- VB2_DEBUG("Only preamble header 2.1+ supported\n");
- return VB2_ERROR_PREAMBLE_HEADER_OLD;
- }
-
- if (size < preamble->preamble_size) {
- VB2_DEBUG("Not enough data for preamble.\n");
- return VB2_ERROR_PREAMBLE_SIZE;
- }
-
- /* Check signature */
- if (vb2_verify_signature_inside(preamble, preamble->preamble_size,
- sig)) {
- VB2_DEBUG("Preamble signature off end of preamble\n");
- return VB2_ERROR_PREAMBLE_SIG_OUTSIDE;
- }
-
- /* Make sure advertised signature data sizes are valid. */
- if (preamble->preamble_size < sig->data_size) {
- VB2_DEBUG("Signature calculated past end of the block\n");
- return VB2_ERROR_PREAMBLE_SIGNED_TOO_MUCH;
- }
-
- if (vb2_verify_data((const uint8_t *)preamble, size, sig, key, wb)) {
- VB2_DEBUG("Preamble signature validation failed\n");
- return VB2_ERROR_PREAMBLE_SIG_INVALID;
- }
-
- /* Verify we signed enough data */
- if (sig->data_size < sizeof(struct vb2_fw_preamble)) {
- VB2_DEBUG("Didn't sign enough data\n");
- return VB2_ERROR_PREAMBLE_SIGNED_TOO_LITTLE;
- }
-
- /* Verify body signature is inside the signed data */
- if (vb2_verify_signature_inside(preamble, sig->data_size,
- &preamble->body_signature)) {
- VB2_DEBUG("Firmware body signature off end of preamble\n");
- return VB2_ERROR_PREAMBLE_BODY_SIG_OUTSIDE;
- }
-
- /* Verify kernel subkey is inside the signed data */
- if (vb2_verify_packed_key_inside(preamble, sig->data_size,
- &preamble->kernel_subkey)) {
- VB2_DEBUG("Kernel subkey off end of preamble\n");
- return VB2_ERROR_PREAMBLE_KERNEL_SUBKEY_OUTSIDE;
- }
-
- /* Success */
- return VB2_SUCCESS;
-}
diff --git a/firmware/lib20/misc.c b/firmware/2lib/2firmware.c
similarity index 98%
rename from firmware/lib20/misc.c
rename to firmware/2lib/2firmware.c
index bc8e995..bc708dc 100644
--- a/firmware/lib20/misc.c
+++ b/firmware/2lib/2firmware.c
@@ -6,13 +6,13 @@
*/
#include "2api.h"
+#include "2common.h"
#include "2misc.h"
#include "2nvstorage.h"
#include "2rsa.h"
#include "2secdata.h"
#include "2sha.h"
#include "2sysincludes.h"
-#include "vb2_common.h"
vb2_error_t vb2_load_fw_keyblock(struct vb2_context *ctx)
{
diff --git a/firmware/2lib/2kernel.c b/firmware/2lib/2kernel.c
index 8c6d191..763214d 100644
--- a/firmware/2lib/2kernel.c
+++ b/firmware/2lib/2kernel.c
@@ -11,7 +11,6 @@
#include "2nvstorage.h"
#include "2rsa.h"
#include "2secdata.h"
-#include "vb2_common.h"
#include "vboot_kernel.h"
/**
diff --git a/firmware/2lib/2misc.c b/firmware/2lib/2misc.c
index 7c4ca26..75a9f36 100644
--- a/firmware/2lib/2misc.c
+++ b/firmware/2lib/2misc.c
@@ -15,7 +15,6 @@
#include "2sha.h"
#include "2struct.h"
#include "2sysincludes.h"
-#include "vb2_common.h"
#include "vboot_api.h"
#include "vboot_struct.h"
@@ -251,7 +250,7 @@
* developer mode.
*/
vb2_nv_set(ctx, VB2_NV_DEV_BOOT_EXTERNAL, 0);
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 0);
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 0);
vb2_nv_set(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY, 0);
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT, 0);
}
@@ -409,7 +408,7 @@
* return false (=RW). That's ok because if recovery is manual, we will
* get the right signal and that's the case we care about.
*/
- if (!vb2ex_ec_trusted())
+ if (!(ctx->flags & VB2_CONTEXT_EC_TRUSTED) && !vb2ex_ec_trusted())
return 0;
/* Now we confidently check the recovery switch state at boot */
@@ -528,8 +527,8 @@
{
struct vb2_gbb_header *gbb = vb2_get_gbb(ctx);
- if (gbb->flags & VB2_GBB_FLAG_DEFAULT_DEV_BOOT_LEGACY)
- return VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY;
+ if (gbb->flags & VB2_GBB_FLAG_DEFAULT_DEV_BOOT_ALTFW)
+ return VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW;
switch (vb2_nv_get(ctx, VB2_NV_DEV_DEFAULT_BOOT)) {
case VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL:
@@ -537,9 +536,9 @@
return VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL;
break;
- case VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY:
- if (vb2_dev_boot_legacy_allowed(ctx))
- return VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY;
+ case VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW:
+ if (vb2_dev_boot_altfw_allowed(ctx))
+ return VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW;
break;
}
@@ -556,14 +555,14 @@
return 1;
}
-int vb2_dev_boot_legacy_allowed(struct vb2_context *ctx)
+int vb2_dev_boot_altfw_allowed(struct vb2_context *ctx)
{
struct vb2_gbb_header *gbb = vb2_get_gbb(ctx);
- return vb2_nv_get(ctx, VB2_NV_DEV_BOOT_LEGACY) ||
- (gbb->flags & VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY) ||
+ return vb2_nv_get(ctx, VB2_NV_DEV_BOOT_ALTFW) ||
+ (gbb->flags & VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW) ||
vb2_secdata_fwmp_get_flag(ctx,
- VB2_SECDATA_FWMP_DEV_ENABLE_LEGACY);
+ VB2_SECDATA_FWMP_DEV_ENABLE_ALTFW);
}
int vb2_dev_boot_external_allowed(struct vb2_context *ctx)
@@ -661,9 +660,9 @@
i = vb2_nv_get(ctx, VB2_NV_DEV_BOOT_EXTERNAL);
DEBUG_INFO_APPEND("\ndev_boot_usb: %d", i);
- /* Add dev_boot_legacy flag */
- i = vb2_nv_get(ctx, VB2_NV_DEV_BOOT_LEGACY);
- DEBUG_INFO_APPEND("\ndev_boot_legacy: %d", i);
+ /* Add dev_boot_altfw flag */
+ i = vb2_nv_get(ctx, VB2_NV_DEV_BOOT_ALTFW);
+ DEBUG_INFO_APPEND("\ndev_boot_altfw: %d", i);
/* Add dev_default_boot flag */
i = vb2_nv_get(ctx, VB2_NV_DEV_DEFAULT_BOOT);
diff --git a/firmware/2lib/2nvstorage.c b/firmware/2lib/2nvstorage.c
index c3cdca5..1cd5ba2 100644
--- a/firmware/2lib/2nvstorage.c
+++ b/firmware/2lib/2nvstorage.c
@@ -145,7 +145,7 @@
case VB2_NV_DEV_BOOT_EXTERNAL:
return GETBIT(VB2_NV_OFFS_DEV, VB2_NV_DEV_FLAG_EXTERNAL);
- case VB2_NV_DEV_BOOT_LEGACY:
+ case VB2_NV_DEV_BOOT_ALTFW:
return GETBIT(VB2_NV_OFFS_DEV, VB2_NV_DEV_FLAG_LEGACY);
case VB2_NV_DEV_BOOT_SIGNED_ONLY:
@@ -331,7 +331,7 @@
SETBIT(VB2_NV_OFFS_DEV, VB2_NV_DEV_FLAG_EXTERNAL);
break;
- case VB2_NV_DEV_BOOT_LEGACY:
+ case VB2_NV_DEV_BOOT_ALTFW:
SETBIT(VB2_NV_OFFS_DEV, VB2_NV_DEV_FLAG_LEGACY);
break;
diff --git a/firmware/lib20/packed_key.c b/firmware/2lib/2packed_key.c
similarity index 98%
rename from firmware/lib20/packed_key.c
rename to firmware/2lib/2packed_key.c
index 3870288..4e2c654 100644
--- a/firmware/lib20/packed_key.c
+++ b/firmware/2lib/2packed_key.c
@@ -6,9 +6,9 @@
*/
#include "2common.h"
+#include "2packed_key.h"
#include "2rsa.h"
#include "2sysincludes.h"
-#include "vb2_common.h"
test_mockable
vb2_error_t vb2_unpack_key_buffer(struct vb2_public_key *key,
diff --git a/firmware/2lib/2recovery_reasons.c b/firmware/2lib/2recovery_reasons.c
index 093ef86..8c43dce 100644
--- a/firmware/2lib/2recovery_reasons.c
+++ b/firmware/2lib/2recovery_reasons.c
@@ -152,8 +152,8 @@
return "Recovery hash space lock error in RO firmware";
/* 0x60 */ case VB2_RECOVERY_TPM_DISABLE_FAILED:
return "Failed to disable TPM before running untrusted code";
- /* 0x61 */ case VB2_RECOVERY_ALTFW_HASH_FAILED:
- return "Verification of alternative firmware payload failed";
+ /* 0x61 */ case VB2_RECOVERY_ALTFW_HASH_MISMATCH:
+ return "Verification of alternate bootloader payload failed";
/* 0x62 */ case VB2_RECOVERY_SECDATA_FWMP_INIT:
return "FWMP secure NVRAM (TPM) initialization error";
/* 0x63 */ case VB2_RECOVERY_CR50_BOOT_MODE:
diff --git a/firmware/2lib/2rsa.c b/firmware/2lib/2rsa.c
index 962558d..dcd8bad 100644
--- a/firmware/2lib/2rsa.c
+++ b/firmware/2lib/2rsa.c
@@ -11,6 +11,7 @@
#include "2common.h"
#include "2rsa.h"
+#include "2rsa_private.h"
#include "2sha.h"
#include "2sysincludes.h"
#include "vboot_test.h"
diff --git a/firmware/2lib/2secdata_fwmp.c b/firmware/2lib/2secdata_fwmp.c
index a28b5bb..cec2481 100644
--- a/firmware/2lib/2secdata_fwmp.c
+++ b/firmware/2lib/2secdata_fwmp.c
@@ -60,6 +60,25 @@
return VB2_SUCCESS;
}
+uint32_t vb2api_secdata_fwmp_create(struct vb2_context *ctx)
+{
+ struct vb2_secdata_fwmp *sec = (void *)&ctx->secdata_fwmp;
+
+ /* Clear the entire struct */
+ memset(sec, 0, sizeof(*sec));
+
+ /* Set to current version */
+ sec->struct_version = VB2_SECDATA_FWMP_VERSION;
+
+ /* Set the structure size */
+ sec->struct_size = sizeof(*sec);
+
+ /* Calculate initial CRC */
+ sec->crc8 = vb2_secdata_fwmp_crc(sec);
+
+ return sizeof(*sec);
+}
+
vb2_error_t vb2_secdata_fwmp_init(struct vb2_context *ctx)
{
struct vb2_shared_data *sd = vb2_get_sd(ctx);
diff --git a/firmware/2lib/2secdata_kernel.c b/firmware/2lib/2secdata_kernel.c
index de12ca0..0d4208f 100644
--- a/firmware/2lib/2secdata_kernel.c
+++ b/firmware/2lib/2secdata_kernel.c
@@ -22,7 +22,13 @@
return MAJOR_VER(sec->struct_version) == 0;
}
-uint8_t vb2_secdata_kernel_crc(struct vb2_context *ctx)
+/**
+ * Calculate crc8 of kernel secure storage.
+ *
+ * @param ctx Context pointer
+ * @return Calculated crc8 value.
+ */
+static uint8_t secdata_kernel_crc(struct vb2_context *ctx)
{
size_t offset, size;
@@ -54,7 +60,7 @@
*size = VB2_SECDATA_KERNEL_SIZE_V02;
/* Verify CRC */
- if (sec->crc8 != vb2_secdata_kernel_crc(ctx)) {
+ if (sec->crc8 != secdata_kernel_crc(ctx)) {
VB2_DEBUG("secdata_kernel: bad CRC\n");
return VB2_ERROR_SECDATA_KERNEL_CRC;
}
@@ -101,7 +107,7 @@
*size = sec->struct_size;
/* Verify CRC */
- if (sec->crc8 != vb2_secdata_kernel_crc(ctx)) {
+ if (sec->crc8 != secdata_kernel_crc(ctx)) {
VB2_DEBUG("secdata_kernel: bad CRC\n");
return VB2_ERROR_SECDATA_KERNEL_CRC;
}
@@ -131,7 +137,7 @@
memset(sec, 0, sizeof(*sec));
sec->struct_version = VB2_SECDATA_KERNEL_VERSION_LATEST;
sec->struct_size = sizeof(*sec);
- sec->crc8 = vb2_secdata_kernel_crc(ctx);
+ sec->crc8 = secdata_kernel_crc(ctx);
/* Mark as changed */
ctx->flags |= VB2_CONTEXT_SECDATA_KERNEL_CHANGED;
@@ -256,9 +262,9 @@
}
if (is_v0(ctx))
- v0->crc8 = vb2_secdata_kernel_crc(ctx);
+ v0->crc8 = secdata_kernel_crc(ctx);
else
- v1->crc8 = vb2_secdata_kernel_crc(ctx);
+ v1->crc8 = secdata_kernel_crc(ctx);
ctx->flags |= VB2_CONTEXT_SECDATA_KERNEL_CHANGED;
return;
@@ -300,7 +306,7 @@
}
memcpy(sec->ec_hash, sha256, sizeof(sec->ec_hash));
- sec->crc8 = vb2_secdata_kernel_crc(ctx);
+ sec->crc8 = secdata_kernel_crc(ctx);
ctx->flags |= VB2_CONTEXT_SECDATA_KERNEL_CHANGED;
diff --git a/firmware/2lib/2struct.c b/firmware/2lib/2struct.c
new file mode 100644
index 0000000..a16f869
--- /dev/null
+++ b/firmware/2lib/2struct.c
@@ -0,0 +1,317 @@
+/* Copyright 2021 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.
+ *
+ * Functions for reading, checking and verifying firmware and
+ * kernel data structures.
+ */
+
+#include "2common.h"
+
+vb2_error_t vb2_check_keyblock(const struct vb2_keyblock *block, uint32_t size,
+ const struct vb2_signature *sig)
+{
+ if(size < sizeof(*block)) {
+ VB2_DEBUG("Not enough space for keyblock header.\n");
+ return VB2_ERROR_KEYBLOCK_TOO_SMALL_FOR_HEADER;
+ }
+
+ if (memcmp(block->magic, VB2_KEYBLOCK_MAGIC, VB2_KEYBLOCK_MAGIC_SIZE)) {
+ VB2_DEBUG("Not a valid verified boot keyblock.\n");
+ return VB2_ERROR_KEYBLOCK_MAGIC;
+ }
+
+ if (block->header_version_major != VB2_KEYBLOCK_VERSION_MAJOR) {
+ VB2_DEBUG("Incompatible keyblock header version.\n");
+ return VB2_ERROR_KEYBLOCK_HEADER_VERSION;
+ }
+
+ if (size < block->keyblock_size) {
+ VB2_DEBUG("Not enough data for keyblock.\n");
+ return VB2_ERROR_KEYBLOCK_SIZE;
+ }
+
+ if (vb2_verify_signature_inside(block, block->keyblock_size, sig)) {
+ VB2_DEBUG("Keyblock signature off end of block\n");
+ return VB2_ERROR_KEYBLOCK_SIG_OUTSIDE;
+ }
+
+ /* Make sure advertised signature data sizes are valid. */
+ if (block->keyblock_size < sig->data_size) {
+ VB2_DEBUG("Signature calculated past end of block\n");
+ return VB2_ERROR_KEYBLOCK_SIGNED_TOO_MUCH;
+ }
+
+ /* Verify we signed enough data */
+ if (sig->data_size < sizeof(struct vb2_keyblock)) {
+ VB2_DEBUG("Didn't sign enough data\n");
+ return VB2_ERROR_KEYBLOCK_SIGNED_TOO_LITTLE;
+ }
+
+ /* Verify data key is inside the block and inside signed data */
+ if (vb2_verify_packed_key_inside(block, block->keyblock_size,
+ &block->data_key)) {
+ VB2_DEBUG("Data key off end of keyblock\n");
+ return VB2_ERROR_KEYBLOCK_DATA_KEY_OUTSIDE;
+ }
+ if (vb2_verify_packed_key_inside(block, sig->data_size,
+ &block->data_key)) {
+ VB2_DEBUG("Data key off end of signed data\n");
+ return VB2_ERROR_KEYBLOCK_DATA_KEY_UNSIGNED;
+ }
+
+ return VB2_SUCCESS;
+}
+
+vb2_error_t vb2_verify_keyblock(struct vb2_keyblock *block, uint32_t size,
+ const struct vb2_public_key *key,
+ const struct vb2_workbuf *wb)
+{
+ struct vb2_signature *sig = &block->keyblock_signature;
+ vb2_error_t rv;
+
+ /* Validity check keyblock before attempting signature check of data */
+ VB2_TRY(vb2_check_keyblock(block, size, sig));
+
+ VB2_DEBUG("Checking keyblock signature...\n");
+ rv = vb2_verify_data((const uint8_t *)block, size, sig, key, wb);
+ if (rv) {
+ VB2_DEBUG("Invalid keyblock signature.\n");
+ return VB2_ERROR_KEYBLOCK_SIG_INVALID;
+ }
+
+ /* Success */
+ return VB2_SUCCESS;
+}
+
+vb2_error_t vb2_verify_fw_preamble(struct vb2_fw_preamble *preamble,
+ uint32_t size,
+ const struct vb2_public_key *key,
+ const struct vb2_workbuf *wb)
+{
+ struct vb2_signature *sig = &preamble->preamble_signature;
+
+ VB2_DEBUG("Verifying preamble.\n");
+
+ /* Validity checks before attempting signature of data */
+ if(size < sizeof(*preamble)) {
+ VB2_DEBUG("Not enough data for preamble header\n");
+ return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
+ }
+ if (preamble->header_version_major !=
+ VB2_FIRMWARE_PREAMBLE_HEADER_VERSION_MAJOR) {
+ VB2_DEBUG("Incompatible firmware preamble header version.\n");
+ return VB2_ERROR_PREAMBLE_HEADER_VERSION;
+ }
+
+ if (preamble->header_version_minor < 1) {
+ VB2_DEBUG("Only preamble header 2.1+ supported\n");
+ return VB2_ERROR_PREAMBLE_HEADER_OLD;
+ }
+
+ if (size < preamble->preamble_size) {
+ VB2_DEBUG("Not enough data for preamble.\n");
+ return VB2_ERROR_PREAMBLE_SIZE;
+ }
+
+ /* Check signature */
+ if (vb2_verify_signature_inside(preamble, preamble->preamble_size,
+ sig)) {
+ VB2_DEBUG("Preamble signature off end of preamble\n");
+ return VB2_ERROR_PREAMBLE_SIG_OUTSIDE;
+ }
+
+ /* Make sure advertised signature data sizes are valid. */
+ if (preamble->preamble_size < sig->data_size) {
+ VB2_DEBUG("Signature calculated past end of the block\n");
+ return VB2_ERROR_PREAMBLE_SIGNED_TOO_MUCH;
+ }
+
+ if (vb2_verify_data((const uint8_t *)preamble, size, sig, key, wb)) {
+ VB2_DEBUG("Preamble signature validation failed\n");
+ return VB2_ERROR_PREAMBLE_SIG_INVALID;
+ }
+
+ /* Verify we signed enough data */
+ if (sig->data_size < sizeof(struct vb2_fw_preamble)) {
+ VB2_DEBUG("Didn't sign enough data\n");
+ return VB2_ERROR_PREAMBLE_SIGNED_TOO_LITTLE;
+ }
+
+ /* Verify body signature is inside the signed data */
+ if (vb2_verify_signature_inside(preamble, sig->data_size,
+ &preamble->body_signature)) {
+ VB2_DEBUG("Firmware body signature off end of preamble\n");
+ return VB2_ERROR_PREAMBLE_BODY_SIG_OUTSIDE;
+ }
+
+ /* Verify kernel subkey is inside the signed data */
+ if (vb2_verify_packed_key_inside(preamble, sig->data_size,
+ &preamble->kernel_subkey)) {
+ VB2_DEBUG("Kernel subkey off end of preamble\n");
+ return VB2_ERROR_PREAMBLE_KERNEL_SUBKEY_OUTSIDE;
+ }
+
+ /* Success */
+ return VB2_SUCCESS;
+}
+
+uint32_t vb2_kernel_get_flags(const struct vb2_kernel_preamble *preamble)
+{
+ if (preamble->header_version_minor < 2)
+ return 0;
+
+ return preamble->flags;
+}
+
+test_mockable
+vb2_error_t vb2_verify_keyblock_hash(const struct vb2_keyblock *block,
+ uint32_t size,
+ const struct vb2_workbuf *wb)
+{
+ const struct vb2_signature *sig = &block->keyblock_hash;
+ struct vb2_workbuf wblocal = *wb;
+ struct vb2_digest_context *dc;
+ uint8_t *digest;
+ uint32_t digest_size;
+
+ /* Validity check keyblock before attempting hash check of data */
+ VB2_TRY(vb2_check_keyblock(block, size, sig));
+
+ VB2_DEBUG("Checking keyblock hash...\n");
+
+ /* Digest goes at start of work buffer */
+ digest_size = vb2_digest_size(VB2_HASH_SHA512);
+ digest = vb2_workbuf_alloc(&wblocal, digest_size);
+ if (!digest)
+ return VB2_ERROR_VDATA_WORKBUF_DIGEST;
+
+ /* Hashing requires temp space for the context */
+ dc = vb2_workbuf_alloc(&wblocal, sizeof(*dc));
+ if (!dc)
+ return VB2_ERROR_VDATA_WORKBUF_HASHING;
+
+ VB2_TRY(vb2_digest_init(dc, VB2_HASH_SHA512));
+
+ VB2_TRY(vb2_digest_extend(dc, (const uint8_t *)block, sig->data_size));
+
+ VB2_TRY(vb2_digest_finalize(dc, digest, digest_size));
+
+ if (vb2_safe_memcmp(vb2_signature_data(sig), digest,
+ digest_size) != 0) {
+ VB2_DEBUG("Invalid keyblock hash.\n");
+ return VB2_ERROR_KEYBLOCK_HASH_INVALID_IN_DEV_MODE;
+ }
+
+ /* Success */
+ return VB2_SUCCESS;
+}
+
+test_mockable
+vb2_error_t vb2_verify_kernel_preamble(struct vb2_kernel_preamble *preamble,
+ uint32_t size,
+ const struct vb2_public_key *key,
+ const struct vb2_workbuf *wb)
+{
+ struct vb2_signature *sig = &preamble->preamble_signature;
+ uint32_t min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_0_SIZE;
+
+ VB2_DEBUG("Verifying kernel preamble.\n");
+
+ /* Make sure it's even safe to look at the struct */
+ if(size < min_size) {
+ VB2_DEBUG("Not enough data for preamble header.\n");
+ return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
+ }
+ if (preamble->header_version_major !=
+ VB2_KERNEL_PREAMBLE_HEADER_VERSION_MAJOR) {
+ VB2_DEBUG("Incompatible kernel preamble header version.\n");
+ return VB2_ERROR_PREAMBLE_HEADER_VERSION;
+ }
+
+ if (preamble->header_version_minor >= 2)
+ min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_2_SIZE;
+ else if (preamble->header_version_minor == 1)
+ min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_1_SIZE;
+ if(preamble->preamble_size < min_size) {
+ VB2_DEBUG("Preamble size too small for header.\n");
+ return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
+ }
+ if (size < preamble->preamble_size) {
+ VB2_DEBUG("Not enough data for preamble.\n");
+ return VB2_ERROR_PREAMBLE_SIZE;
+ }
+
+ /* Check signature */
+ if (vb2_verify_signature_inside(preamble, preamble->preamble_size,
+ sig)) {
+ VB2_DEBUG("Preamble signature off end of preamble\n");
+ return VB2_ERROR_PREAMBLE_SIG_OUTSIDE;
+ }
+
+ /* Make sure advertised signature data sizes are valid. */
+ if (preamble->preamble_size < sig->data_size) {
+ VB2_DEBUG("Signature calculated past end of the block\n");
+ return VB2_ERROR_PREAMBLE_SIGNED_TOO_MUCH;
+ }
+
+ if (vb2_verify_data((const uint8_t *)preamble, size, sig, key, wb)) {
+ VB2_DEBUG("Preamble signature validation failed\n");
+ return VB2_ERROR_PREAMBLE_SIG_INVALID;
+ }
+
+ /* Verify we signed enough data */
+ if (sig->data_size < sizeof(struct vb2_fw_preamble)) {
+ VB2_DEBUG("Didn't sign enough data\n");
+ return VB2_ERROR_PREAMBLE_SIGNED_TOO_LITTLE;
+ }
+
+ /* Verify body signature is inside the signed data */
+ if (vb2_verify_signature_inside(preamble, sig->data_size,
+ &preamble->body_signature)) {
+ VB2_DEBUG("Body signature off end of preamble\n");
+ return VB2_ERROR_PREAMBLE_BODY_SIG_OUTSIDE;
+ }
+
+ /*
+ * If bootloader is present, verify it's covered by the body
+ * signature.
+ */
+ if (preamble->bootloader_size) {
+ const void *body_ptr =
+ (const void *)(uintptr_t)preamble->body_load_address;
+ const void *bootloader_ptr =
+ (const void *)(uintptr_t)preamble->bootloader_address;
+ if (vb2_verify_member_inside(body_ptr,
+ preamble->body_signature.data_size,
+ bootloader_ptr,
+ preamble->bootloader_size,
+ 0, 0)) {
+ VB2_DEBUG("Bootloader off end of signed data\n");
+ return VB2_ERROR_PREAMBLE_BOOTLOADER_OUTSIDE;
+ }
+ }
+
+ /*
+ * If vmlinuz header is present, verify it's covered by the body
+ * signature.
+ */
+ if (preamble->header_version_minor >= 1 &&
+ preamble->vmlinuz_header_size) {
+ const void *body_ptr =
+ (const void *)(uintptr_t)preamble->body_load_address;
+ const void *vmlinuz_header_ptr = (const void *)
+ (uintptr_t)preamble->vmlinuz_header_address;
+ if (vb2_verify_member_inside(body_ptr,
+ preamble->body_signature.data_size,
+ vmlinuz_header_ptr,
+ preamble->vmlinuz_header_size,
+ 0, 0)) {
+ VB2_DEBUG("Vmlinuz header off end of signed data\n");
+ return VB2_ERROR_PREAMBLE_VMLINUZ_HEADER_OUTSIDE;
+ }
+ }
+
+ /* Success */
+ return VB2_SUCCESS;
+}
diff --git a/firmware/2lib/2stub.c b/firmware/2lib/2stub.c
index 782ad42..7cec2e5 100644
--- a/firmware/2lib/2stub.c
+++ b/firmware/2lib/2stub.c
@@ -8,10 +8,15 @@
#include <stdarg.h>
#include <stdlib.h>
#include <stdio.h>
+#include <sys/time.h>
#include "2api.h"
+#include "2common.h"
#include "2sysincludes.h"
+/*****************************************************************************/
+/* General utility stubs */
+
__attribute__((weak))
void vb2ex_printf(const char *func, const char *fmt, ...)
{
@@ -26,10 +31,18 @@
}
__attribute__((weak))
-vb2_error_t vb2ex_tpm_clear_owner(struct vb2_context *ctx)
+void vb2ex_abort(void)
{
- fprintf(stderr, "%s: function not implemented\n", __func__);
- return VB2_ERROR_EX_UNIMPLEMENTED;
+ /* Stub simply exits. */
+ abort();
+}
+
+__attribute__((weak))
+uint32_t vb2ex_mtime(void)
+{
+ struct timeval tv;
+ gettimeofday(&tv, NULL);
+ return tv.tv_sec * VB2_MSEC_PER_SEC + tv.tv_usec / VB2_USEC_PER_MSEC;
}
__attribute__((weak))
@@ -41,6 +54,16 @@
return VB2_ERROR_EX_UNIMPLEMENTED;
}
+/*****************************************************************************/
+/* TPM-related stubs */
+
+__attribute__((weak))
+vb2_error_t vb2ex_tpm_clear_owner(struct vb2_context *ctx)
+{
+ fprintf(stderr, "%s: function not implemented\n", __func__);
+ return VB2_ERROR_EX_UNIMPLEMENTED;
+}
+
__attribute__((weak))
vb2_error_t vb2ex_tpm_set_mode(enum vb2_tpm_mode mode_val)
{
@@ -48,6 +71,80 @@
return VB2_ERROR_EX_UNIMPLEMENTED;
}
+/*****************************************************************************/
+/* auxfw and EC-related stubs */
+
+__attribute__((weak))
+int vb2ex_ec_trusted(void)
+{
+ return 1;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_running_rw(int *in_rw)
+{
+ *in_rw = 0;
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_jump_to_rw(void)
+{
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_disable_jump(void)
+{
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_hash_image(enum vb2_firmware_selection select,
+ const uint8_t **hash, int *hash_size)
+{
+ static const uint8_t fake_hash[32] = {1, 2, 3, 4};
+
+ *hash = fake_hash;
+ *hash_size = sizeof(fake_hash);
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_get_expected_image_hash(enum vb2_firmware_selection select,
+ const uint8_t **hash, int *hash_size)
+{
+ static const uint8_t fake_hash[32] = {1, 2, 3, 4};
+
+ *hash = fake_hash;
+ *hash_size = sizeof(fake_hash);
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_update_image(enum vb2_firmware_selection select)
+{
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_protect(enum vb2_firmware_selection select)
+{
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_vboot_done(struct vb2_context *ctx)
+{
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_ec_battery_cutoff(void)
+{
+ return VB2_SUCCESS;
+}
+
__attribute__((weak))
vb2_error_t vb2ex_auxfw_check(enum vb2_auxfw_update_severity *severity)
{
@@ -67,12 +164,8 @@
return VB2_SUCCESS;
}
-__attribute__((weak))
-void vb2ex_abort(void)
-{
- /* Stub simply exits. */
- abort();
-}
+/*****************************************************************************/
+/* UI-related stubs */
__attribute__((weak))
const char *vb2ex_get_debug_info(struct vb2_context *ctx)
@@ -94,9 +187,23 @@
}
__attribute__((weak))
-const char *vb2ex_get_diagnostic_storage(void)
+vb2_error_t vb2ex_diag_get_storage_health(const char **out)
{
- return "mock";
+ *out = "mock";
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_diag_get_storage_test_log(const char **out)
+{
+ *out = "mock";
+ return VB2_SUCCESS;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_diag_storage_test_control(enum vb2_diag_storage_test ops)
+{
+ return VB2_SUCCESS;
}
__attribute__((weak))
@@ -112,3 +219,40 @@
*out = "mock";
return VB2_SUCCESS;
}
+
+__attribute__((weak))
+void vb2ex_msleep(uint32_t msec)
+{
+}
+
+__attribute__((weak))
+void vb2ex_beep(uint32_t msec, uint32_t frequency)
+{
+}
+
+__attribute__((weak))
+uint32_t vb2ex_get_locale_count(void)
+{
+ return 0;
+}
+
+__attribute__((weak))
+uint32_t vb2ex_get_altfw_count(void)
+{
+ return 0;
+}
+
+__attribute__((weak))
+int vb2ex_physical_presence_pressed(void)
+{
+ return 0;
+}
+
+__attribute__((weak))
+vb2_error_t vb2ex_commit_data(struct vb2_context *ctx)
+{
+ ctx->flags &= ~VB2_CONTEXT_SECDATA_FIRMWARE_CHANGED;
+ ctx->flags &= ~VB2_CONTEXT_SECDATA_KERNEL_CHANGED;
+ ctx->flags &= ~VB2_CONTEXT_NVDATA_CHANGED;
+ return VB2_SUCCESS;
+}
diff --git a/firmware/2lib/2ui.c b/firmware/2lib/2ui.c
index 10de176..7173450 100644
--- a/firmware/2lib/2ui.c
+++ b/firmware/2lib/2ui.c
@@ -24,7 +24,7 @@
* shutdown is required.
*
* @param ui UI context pointer
- * @return VB2_REQUEST_SHUTDOWN if shutdown needed, or VB2_REQUEST_UI_CONTINUE
+ * @return VB2_REQUEST_SHUTDOWN if shutdown needed, or VB2_SUCCESS
*/
vb2_error_t check_shutdown_request(struct vb2_ui_context *ui)
{
@@ -64,7 +64,7 @@
if (shutdown_request)
return VB2_REQUEST_SHUTDOWN;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
@@ -81,7 +81,7 @@
ui->error_code = VB2_UI_ERROR_NONE;
ui->key = 0;
}
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
@@ -131,7 +131,7 @@
ui->key, ui->key_trusted);
}
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
vb2_error_t vb2_ui_menu_prev(struct vb2_ui_context *ui)
@@ -139,7 +139,7 @@
int item;
if (!DETACHABLE && ui->key == VB_BUTTON_VOL_UP_SHORT_PRESS)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
item = ui->state->selected_item - 1;
while (item >= 0 && VB2_GET_BIT(ui->state->hidden_item_mask, item))
@@ -148,7 +148,7 @@
if (item >= 0)
ui->state->selected_item = item;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
vb2_error_t vb2_ui_menu_next(struct vb2_ui_context *ui)
@@ -157,7 +157,7 @@
const struct vb2_menu *menu;
if (!DETACHABLE && ui->key == VB_BUTTON_VOL_DOWN_SHORT_PRESS)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
menu = get_menu(ui);
item = ui->state->selected_item + 1;
@@ -168,7 +168,7 @@
if (item < menu->num_items)
ui->state->selected_item = item;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
vb2_error_t vb2_ui_menu_select(struct vb2_ui_context *ui)
@@ -177,11 +177,11 @@
const struct vb2_menu_item *menu_item;
if (!DETACHABLE && ui->key == VB_BUTTON_POWER_SHORT_PRESS)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
menu = get_menu(ui);
if (menu->num_items == 0)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
menu_item = &menu->items[ui->state->selected_item];
@@ -190,7 +190,7 @@
ui->state->selected_item)) {
VB2_DEBUG("Menu item <%s> disabled; ignoring\n",
menu_item->text);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
if (menu_item->action) {
@@ -204,7 +204,7 @@
VB2_DEBUG("Menu item <%s> no action or target screen\n",
menu_item->text);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
@@ -219,7 +219,7 @@
free(ui->state);
ui->state = tmp;
if (ui->state->screen->reinit)
- return ui->state->screen->reinit(ui);
+ VB2_TRY(ui->state->screen->reinit(ui));
} else {
VB2_DEBUG("ERROR: No previous screen; ignoring\n");
}
@@ -233,7 +233,7 @@
ui->state->selected_item = 0;
if (menu->num_items > 1 && menu->items[0].is_language_select)
ui->state->selected_item = 1;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
vb2_error_t vb2_ui_screen_change(struct vb2_ui_context *ui, enum vb2_screen id)
@@ -266,7 +266,7 @@
free(cur_state);
}
if (ui->state->screen->reinit)
- return ui->state->screen->reinit(ui);
+ VB2_TRY(ui->state->screen->reinit(ui));
} else {
/* Allocate the requested screen on top of the stack. */
cur_state = malloc(sizeof(*ui->state));
@@ -279,9 +279,9 @@
cur_state->screen = new_screen_info;
ui->state = cur_state;
if (ui->state->screen->init)
- return ui->state->screen->init(ui);
+ VB2_TRY(ui->state->screen->init(ui));
else
- return default_screen_init(ui);
+ VB2_TRY(default_screen_init(ui));
}
return VB2_REQUEST_UI_CONTINUE;
@@ -290,8 +290,9 @@
/*****************************************************************************/
/* Core UI loop */
-vb2_error_t ui_loop(struct vb2_context *ctx, enum vb2_screen root_screen_id,
- vb2_error_t (*global_action)(struct vb2_ui_context *ui))
+static vb2_error_t ui_loop_impl(
+ struct vb2_context *ctx, enum vb2_screen root_screen_id,
+ vb2_error_t (*global_action)(struct vb2_ui_context *ui))
{
struct vb2_ui_context ui;
struct vb2_screen_state prev_state;
@@ -309,9 +310,11 @@
if (root_info == NULL)
VB2_DIE("Root screen not found.\n");
ui.locale_id = vb2_nv_get(ctx, VB2_NV_LOCALIZATION_INDEX);
+
rv = vb2_ui_screen_change(&ui, root_screen_id);
- if (rv != VB2_REQUEST_UI_CONTINUE)
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE)
return rv;
+
memset(&prev_state, 0, sizeof(prev_state));
prev_disable_timer = 0;
prev_error_code = VB2_UI_ERROR_NONE;
@@ -365,32 +368,32 @@
/* Check for shutdown request. */
rv = check_shutdown_request(&ui);
- if (rv != VB2_REQUEST_UI_CONTINUE) {
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE) {
VB2_DEBUG("Shutdown requested!\n");
return rv;
}
/* Check if we need to exit an error box. */
rv = error_exit_action(&ui);
- if (rv != VB2_REQUEST_UI_CONTINUE)
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE)
return rv;
/* Run screen action. */
if (ui.state->screen->action) {
rv = ui.state->screen->action(&ui);
- if (rv != VB2_REQUEST_UI_CONTINUE)
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE)
return rv;
}
/* Run menu navigation action. */
rv = menu_navigation_action(&ui);
- if (rv != VB2_REQUEST_UI_CONTINUE)
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE)
return rv;
/* Run global action function if available. */
if (global_action) {
rv = global_action(&ui);
- if (rv != VB2_REQUEST_UI_CONTINUE)
+ if (rv && rv != VB2_REQUEST_UI_CONTINUE)
return rv;
}
@@ -403,17 +406,38 @@
return VB2_SUCCESS;
}
+vb2_error_t ui_loop(struct vb2_context *ctx, enum vb2_screen root_screen_id,
+ vb2_error_t (*global_action)(struct vb2_ui_context *ui))
+{
+ vb2_error_t rv = ui_loop_impl(ctx, root_screen_id, global_action);
+ if (rv == VB2_REQUEST_UI_EXIT)
+ return VB2_SUCCESS;
+ return rv;
+}
+
/*****************************************************************************/
/* Developer mode */
vb2_error_t vb2_developer_menu(struct vb2_context *ctx)
{
- return ui_loop(ctx, VB2_SCREEN_DEVELOPER_MODE, developer_action);
+ enum vb2_screen root_screen_id = VB2_SCREEN_DEVELOPER_MODE;
+ if (!vb2_dev_boot_allowed(ctx)) {
+ VB2_DEBUG("WARNING: Dev boot not allowed; forcing to-norm\n");
+ root_screen_id = VB2_SCREEN_DEVELOPER_TO_NORM;
+ }
+ return ui_loop(ctx, root_screen_id, developer_action);
}
vb2_error_t developer_action(struct vb2_ui_context *ui)
{
/* Developer mode keyboard shortcuts */
+ if (ui->key == '\t')
+ return vb2_ui_screen_change(ui, VB2_SCREEN_DEBUG_INFO);
+
+ /* Ignore other shortcuts */
+ if (!vb2_dev_boot_allowed(ui->ctx))
+ return VB2_REQUEST_UI_CONTINUE;
+
if (ui->key == VB_KEY_CTRL('S'))
return vb2_ui_screen_change(ui, VB2_SCREEN_DEVELOPER_TO_NORM);
if (ui->key == VB_KEY_CTRL('U') ||
@@ -422,12 +446,10 @@
if (ui->key == VB_KEY_CTRL('D') ||
(DETACHABLE && ui->key == VB_BUTTON_VOL_DOWN_LONG_PRESS))
return vb2_ui_developer_mode_boot_internal_action(ui);
- if (ui->key == VB_KEY_CTRL('L'))
- return vb2_ui_developer_mode_boot_alternate_action(ui);
- if (ui->key == '\t')
- return vb2_ui_screen_change(ui, VB2_SCREEN_DEBUG_INFO);
+ if (ui->key == VB_KEY_CTRL('L')) /* L for aLtfw (formerly Legacy) */
+ return vb2_ui_developer_mode_boot_altfw_action(ui);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
@@ -444,7 +466,7 @@
if (ui->key == '\t')
return vb2_ui_screen_change(ui, VB2_SCREEN_DEBUG_INFO);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
@@ -460,7 +482,7 @@
/* See if we have a recovery kernel available yet. */
vb2_error_t rv = VbTryLoadKernel(ui->ctx, VB_DISK_FLAG_REMOVABLE);
if (rv == VB2_SUCCESS)
- return rv;
+ return VB2_REQUEST_UI_EXIT;
/* If disk validity state changed, switch to appropriate screen. */
if (ui->recovery_rv != rv) {
@@ -481,7 +503,7 @@
if (ui->key == '\t')
return vb2_ui_screen_change(ui, VB2_SCREEN_DEBUG_INFO);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/*****************************************************************************/
diff --git a/firmware/2lib/2ui_screens.c b/firmware/2lib/2ui_screens.c
index 4aeeda1..a9359b5 100644
--- a/firmware/2lib/2ui_screens.c
+++ b/firmware/2lib/2ui_screens.c
@@ -53,6 +53,32 @@
/******************************************************************************/
/*
+ * Functions for ui error handling
+ */
+
+static vb2_error_t set_ui_error(struct vb2_ui_context *ui,
+ enum vb2_ui_error error_code)
+{
+ /* Keep the first occurring error. */
+ if (ui->error_code)
+ VB2_DEBUG("When handling ui error %#x, another ui error "
+ "occurred: %#x",
+ ui->error_code, error_code);
+ else
+ ui->error_code = error_code;
+ /* Return to the ui loop to show the error code. */
+ return VB2_REQUEST_UI_CONTINUE;
+}
+
+static vb2_error_t set_ui_error_and_go_back(struct vb2_ui_context *ui,
+ enum vb2_ui_error error_code)
+{
+ set_ui_error(ui, error_code);
+ return vb2_ui_screen_back(ui);
+}
+
+/******************************************************************************/
+/*
* Functions used for log screens
*
* Expects that the page_count is valid and page_up_item and page_down_item are
@@ -60,73 +86,83 @@
* current_page is valid in prev and next actions, and the back_item is assigned
* to a correct menu item index.
*/
-/* TODO(b/174127808): Split out enabling/disabling buttons. */
-static vb2_error_t log_page_init(struct vb2_ui_context *ui)
+static vb2_error_t log_page_update(struct vb2_ui_context *ui,
+ const char *new_log_string)
+{
+ const struct vb2_screen_info *screen = ui->state->screen;
+
+ if (new_log_string) {
+ ui->state->page_count = vb2ex_prepare_log_screen(
+ screen->id, ui->locale_id, new_log_string);
+ if (ui->state->page_count == 0) {
+ VB2_DEBUG("vb2ex_prepare_log_screen failed");
+ return VB2_ERROR_UI_LOG_INIT;
+ }
+ if (ui->state->current_page >= ui->state->page_count)
+ ui->state->current_page = ui->state->page_count - 1;
+ ui->force_display = 1;
+ }
+ VB2_CLR_BIT(ui->state->disabled_item_mask, screen->page_up_item);
+ VB2_CLR_BIT(ui->state->disabled_item_mask, screen->page_down_item);
+ if (ui->state->current_page == 0)
+ VB2_SET_BIT(ui->state->disabled_item_mask,
+ screen->page_up_item);
+ if (ui->state->current_page == ui->state->page_count - 1)
+ VB2_SET_BIT(ui->state->disabled_item_mask,
+ screen->page_down_item);
+
+ return VB2_SUCCESS;
+}
+
+static vb2_error_t log_page_reset_to_top(struct vb2_ui_context *ui)
{
const struct vb2_screen_info *screen = ui->state->screen;
ui->state->current_page = 0;
+ ui->state->selected_item = ui->state->page_count > 1
+ ? screen->page_down_item
+ : screen->back_item;
+ return log_page_update(ui, NULL);
+}
- if (ui->state->page_count == 1) {
- VB2_SET_BIT(ui->state->disabled_item_mask,
- screen->page_up_item);
- VB2_SET_BIT(ui->state->disabled_item_mask,
- screen->page_down_item);
- ui->state->selected_item = screen->back_item;
+static vb2_error_t log_page_show_back_or_cancel(struct vb2_ui_context *ui,
+ int is_show_cancel)
+{
+ int back_item = ui->state->screen->back_item;
+ int cancel_item = ui->state->screen->cancel_item;
+ VB2_CLR_BIT(ui->state->hidden_item_mask, back_item);
+ VB2_CLR_BIT(ui->state->hidden_item_mask, cancel_item);
+ if (is_show_cancel) {
+ VB2_SET_BIT(ui->state->hidden_item_mask, back_item);
+ if (ui->state->selected_item == back_item)
+ ui->state->selected_item = cancel_item;
} else {
- VB2_SET_BIT(ui->state->disabled_item_mask,
- screen->page_up_item);
- ui->state->selected_item = screen->page_down_item;
+ VB2_SET_BIT(ui->state->hidden_item_mask, cancel_item);
+ if (ui->state->selected_item == cancel_item)
+ ui->state->selected_item = back_item;
}
-
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static vb2_error_t log_page_prev_action(struct vb2_ui_context *ui)
{
- const struct vb2_screen_info *screen = ui->state->screen;
-
/* Validity check. */
if (ui->state->current_page == 0)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
ui->state->current_page--;
-
- /* Clear bits of page down. */
- if (ui->state->current_page != ui->state->page_count - 1)
- VB2_CLR_BIT(ui->state->disabled_item_mask,
- screen->page_down_item);
-
- /* Disable page up at the first page. */
- if (ui->state->current_page == 0)
- VB2_SET_BIT(ui->state->disabled_item_mask,
- screen->page_up_item);
-
- return VB2_REQUEST_UI_CONTINUE;
+ return log_page_update(ui, NULL);
}
static vb2_error_t log_page_next_action(struct vb2_ui_context *ui)
{
- const struct vb2_screen_info *screen = ui->state->screen;
-
/* Validity check. */
if (ui->state->current_page == ui->state->page_count - 1)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
ui->state->current_page++;
-
- /* Clear bits of page up. */
- if (ui->state->current_page != 0)
- VB2_CLR_BIT(ui->state->disabled_item_mask,
- screen->page_up_item);
-
- /* Disable page down at the last page. */
- if (ui->state->current_page == ui->state->page_count - 1)
- VB2_SET_BIT(ui->state->disabled_item_mask,
- screen->page_down_item);
-
- return VB2_REQUEST_UI_CONTINUE;
+ return log_page_update(ui, NULL);
}
#define PAGE_UP_ITEM ((struct vb2_menu_item){ \
@@ -140,14 +176,6 @@
})
/******************************************************************************/
-/* VB2_SCREEN_BLANK */
-
-static const struct vb2_screen_info blank_screen = {
- .id = VB2_SCREEN_BLANK,
- .name = "Blank",
-};
-
-/******************************************************************************/
/* VB2_SCREEN_LANGUAGE_SELECT */
static vb2_error_t language_select_action(struct vb2_ui_context *ui)
@@ -214,7 +242,7 @@
"initializing selected_item to 0\n");
ui->state->selected_item = 0;
}
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static const struct vb2_screen_info language_select_screen = {
@@ -255,7 +283,7 @@
ui->state->selected_item = ADVANCED_OPTIONS_ITEM_DEBUG_INFO;
}
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static const struct vb2_menu_item advanced_options_items[] = {
@@ -290,42 +318,27 @@
#define DEBUG_INFO_ITEM_PAGE_DOWN 2
#define DEBUG_INFO_ITEM_BACK 3
-static vb2_error_t debug_info_init(struct vb2_ui_context *ui)
+static vb2_error_t debug_info_set_content(struct vb2_ui_context *ui)
{
const char *log_string = vb2ex_get_debug_info(ui->ctx);
- if (!log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve debug info\n");
- ui->error_code = VB2_UI_ERROR_DEBUG_LOG;
- return vb2_ui_screen_back(ui);
- }
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare debug info screen\n");
- ui->error_code = VB2_UI_ERROR_DEBUG_LOG;
- return vb2_ui_screen_back(ui);
- }
+ if (!log_string)
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DEBUG_LOG);
+ if (vb2_is_error(log_page_update(ui, log_string)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DEBUG_LOG);
+ return VB2_SUCCESS;
+}
- return log_page_init(ui);
+static vb2_error_t debug_info_init(struct vb2_ui_context *ui)
+{
+ VB2_TRY(debug_info_set_content(ui));
+ if (vb2_is_error(log_page_reset_to_top(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DEBUG_LOG);
+ return VB2_SUCCESS;
}
static vb2_error_t debug_info_reinit(struct vb2_ui_context *ui)
{
- const char *log_string = vb2ex_get_debug_info(ui->ctx);
- if (!log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve debug info\n");
- ui->error_code = VB2_UI_ERROR_DEBUG_LOG;
- return vb2_ui_screen_back(ui);
- }
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare debug info screen\n");
- ui->error_code = VB2_UI_ERROR_DEBUG_LOG;
- return vb2_ui_screen_back(ui);
- }
-
- return VB2_REQUEST_UI_CONTINUE;
+ return debug_info_set_content(ui);
}
static const struct vb2_menu_item debug_info_items[] = {
@@ -354,42 +367,28 @@
#define FIRMWARE_LOG_ITEM_PAGE_DOWN 2
#define FIRMWARE_LOG_ITEM_BACK 3
+static vb2_error_t firmware_log_set_content(struct vb2_ui_context *ui,
+ int reset)
+{
+ const char *log_string = vb2ex_get_firmware_log(reset);
+ if (!log_string)
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_FIRMWARE_LOG);
+ if (vb2_is_error(log_page_update(ui, log_string)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_FIRMWARE_LOG);
+ return VB2_SUCCESS;
+}
+
static vb2_error_t firmware_log_init(struct vb2_ui_context *ui)
{
- const char *log_string = vb2ex_get_firmware_log(1);
- if (!log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve firmware log\n");
- ui->error_code = VB2_UI_ERROR_FIRMWARE_LOG;
- return vb2_ui_screen_back(ui);
- }
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare firmware log screen\n");
- ui->error_code = VB2_UI_ERROR_FIRMWARE_LOG;
- return vb2_ui_screen_back(ui);
- }
-
- return log_page_init(ui);
+ VB2_TRY(firmware_log_set_content(ui, 1));
+ if (vb2_is_error(log_page_reset_to_top(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_FIRMWARE_LOG);
+ return VB2_SUCCESS;
}
static vb2_error_t firmware_log_reinit(struct vb2_ui_context *ui)
{
- const char *log_string = vb2ex_get_firmware_log(0);
- if (!log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve firmware log\n");
- ui->error_code = VB2_UI_ERROR_FIRMWARE_LOG;
- return vb2_ui_screen_back(ui);
- }
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare firmware log screen\n");
- ui->error_code = VB2_UI_ERROR_FIRMWARE_LOG;
- return vb2_ui_screen_back(ui);
- }
-
- return VB2_REQUEST_UI_CONTINUE;
+ return firmware_log_set_content(ui, 0);
}
static const struct vb2_menu_item firmware_log_items[] = {
@@ -440,7 +439,7 @@
VB2_SET_BIT(ui->state->hidden_item_mask,
RECOVERY_SELECT_ITEM_DIAGNOSTICS);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static const struct vb2_menu_item recovery_select_items[] = {
@@ -490,11 +489,10 @@
vb2_error_t recovery_to_dev_init(struct vb2_ui_context *ui)
{
- if (vb2_get_sd(ui->ctx)->flags & VB2_SD_FLAG_DEV_MODE_ENABLED) {
+ if (vb2_get_sd(ui->ctx)->flags & VB2_SD_FLAG_DEV_MODE_ENABLED)
/* We're in dev mode, so let user know they can't transition */
- ui->error_code = VB2_UI_ERROR_DEV_MODE_ALREADY_ENABLED;
- return vb2_ui_screen_back(ui);
- }
+ return set_ui_error_and_go_back(
+ ui, VB2_UI_ERROR_DEV_MODE_ALREADY_ENABLED);
if (!PHYSICAL_PRESENCE_KEYBOARD && vb2ex_physical_presence_pressed()) {
VB2_DEBUG("Presence button stuck?\n");
@@ -512,7 +510,7 @@
ui->physical_presence_button_pressed = 0;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static vb2_error_t recovery_to_dev_finalize(struct vb2_ui_context *ui)
@@ -524,7 +522,7 @@
(vb2_get_sd(ui->ctx)->flags & VB2_SD_FLAG_DEV_MODE_ENABLED) ||
!vb2_allow_recovery(ui->ctx)) {
VB2_DEBUG("ERROR: Dev transition validity check failed\n");
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
VB2_DEBUG("Enabling dev mode and rebooting...\n");
@@ -543,8 +541,9 @@
* from an untrusted keyboard.
*/
if (PHYSICAL_PRESENCE_KEYBOARD && ui->key == VB_KEY_ENTER)
- ui->error_code = VB2_UI_ERROR_UNTRUSTED_CONFIRMATION;
- return VB2_REQUEST_UI_CONTINUE;
+ return set_ui_error(
+ ui, VB2_UI_ERROR_UNTRUSTED_CONFIRMATION);
+ return VB2_SUCCESS;
}
return recovery_to_dev_finalize(ui);
}
@@ -560,17 +559,17 @@
/* Keyboard physical presence case covered by "Confirm" action. */
if (PHYSICAL_PRESENCE_KEYBOARD)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
pressed = vb2ex_physical_presence_pressed();
if (pressed) {
VB2_DEBUG("Physical presence button pressed, "
"awaiting release\n");
ui->physical_presence_button_pressed = 1;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
if (!ui->physical_presence_button_pressed)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
VB2_DEBUG("Physical presence button released\n");
return recovery_to_dev_finalize(ui);
@@ -681,17 +680,13 @@
#define DEVELOPER_MODE_ITEM_RETURN_TO_SECURE 1
#define DEVELOPER_MODE_ITEM_BOOT_INTERNAL 2
#define DEVELOPER_MODE_ITEM_BOOT_EXTERNAL 3
-#define DEVELOPER_MODE_ITEM_SELECT_BOOTLOADER 4
+#define DEVELOPER_MODE_ITEM_SELECT_ALTFW 4
vb2_error_t developer_mode_init(struct vb2_ui_context *ui)
{
enum vb2_dev_default_boot_target default_boot =
vb2api_get_dev_default_boot_target(ui->ctx);
- /* TODO(b/159579189): Split this case into a separate root screen */
- if (!vb2_dev_boot_allowed(ui->ctx))
- vb2_ui_screen_change(ui, VB2_SCREEN_DEVELOPER_TO_NORM);
-
/* Don't show "Return to secure mode" button if GBB forces dev mode. */
if (vb2_get_gbb(ui->ctx)->flags & VB2_GBB_FLAG_FORCE_DEV_SWITCH_ON)
VB2_SET_BIT(ui->state->hidden_item_mask,
@@ -703,18 +698,18 @@
DEVELOPER_MODE_ITEM_BOOT_EXTERNAL);
/* Don't show "Select alternate bootloader" button if not allowed. */
- if (!vb2_dev_boot_legacy_allowed(ui->ctx))
+ if (!vb2_dev_boot_altfw_allowed(ui->ctx))
VB2_SET_BIT(ui->state->hidden_item_mask,
- DEVELOPER_MODE_ITEM_SELECT_BOOTLOADER);
+ DEVELOPER_MODE_ITEM_SELECT_ALTFW);
/* Choose the default selection. */
switch (default_boot) {
case VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL:
ui->state->selected_item = DEVELOPER_MODE_ITEM_BOOT_EXTERNAL;
break;
- case VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY:
+ case VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW:
ui->state->selected_item =
- DEVELOPER_MODE_ITEM_SELECT_BOOTLOADER;
+ DEVELOPER_MODE_ITEM_SELECT_ALTFW;
break;
default:
ui->state->selected_item = DEVELOPER_MODE_ITEM_BOOT_INTERNAL;
@@ -723,7 +718,7 @@
ui->start_time_ms = vb2ex_mtime();
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
vb2_error_t vb2_ui_developer_mode_boot_internal_action(
@@ -732,11 +727,11 @@
if (!(ui->ctx->flags & VB2_CONTEXT_DEVELOPER_MODE) ||
!vb2_dev_boot_allowed(ui->ctx)) {
VB2_DEBUG("ERROR: Dev mode internal boot not allowed\n");
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
VB2_TRY(VbTryLoadKernel(ui->ctx, VB_DISK_FLAG_FIXED));
- return VB2_SUCCESS;
+ return VB2_REQUEST_UI_EXIT;
}
vb2_error_t vb2_ui_developer_mode_boot_external_action(
@@ -750,13 +745,12 @@
!vb2_dev_boot_external_allowed(ui->ctx)) {
VB2_DEBUG("ERROR: Dev mode external boot not allowed\n");
ui->error_beep = 1;
- ui->error_code = VB2_UI_ERROR_EXTERNAL_BOOT_NOT_ENABLED;
- return VB2_REQUEST_UI_CONTINUE;
+ return set_ui_error(ui, VB2_UI_ERROR_EXTERNAL_BOOT_DISABLED);
}
rv = VbTryLoadKernel(ui->ctx, VB_DISK_FLAG_REMOVABLE);
if (rv == VB2_SUCCESS) {
- return VB2_SUCCESS;
+ return VB2_REQUEST_UI_EXIT;
} else if (rv == VB2_ERROR_LK_NO_DISK_FOUND) {
if (ui->state->screen->id !=
VB2_SCREEN_DEVELOPER_BOOT_EXTERNAL) {
@@ -781,15 +775,11 @@
const int use_short = vb2api_use_short_dev_screen_delay(ui->ctx);
uint64_t elapsed_ms;
- /* TODO(b/159579189): Split this case into a separate root screen */
- if (!vb2_dev_boot_allowed(ui->ctx))
- vb2_ui_screen_change(ui, VB2_SCREEN_DEVELOPER_TO_NORM);
-
/* Once any user interaction occurs, stop the timer. */
if (ui->key)
ui->disable_timer = 1;
if (ui->disable_timer)
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
elapsed_ms = vb2ex_mtime() - ui->start_time_ms;
@@ -814,7 +804,7 @@
return vb2_ui_menu_select(ui);
}
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
static const struct vb2_menu_item developer_mode_items[] = {
@@ -831,9 +821,9 @@
.text = "Boot from external disk",
.action = vb2_ui_developer_mode_boot_external_action,
},
- [DEVELOPER_MODE_ITEM_SELECT_BOOTLOADER] = {
+ [DEVELOPER_MODE_ITEM_SELECT_ALTFW] = {
.text = "Select alternate bootloader",
- .target = VB2_SCREEN_DEVELOPER_SELECT_BOOTLOADER,
+ .target = VB2_SCREEN_DEVELOPER_SELECT_ALTFW,
},
ADVANCED_OPTIONS_ITEM,
POWER_OFF_ITEM,
@@ -851,24 +841,29 @@
/* VB2_SCREEN_DEVELOPER_TO_NORM */
#define DEVELOPER_TO_NORM_ITEM_CONFIRM 1
+#define DEVELOPER_TO_NORM_ITEM_CANCEL 2
static vb2_error_t developer_to_norm_init(struct vb2_ui_context *ui)
{
/* Don't allow to-norm if GBB forces dev mode */
if (vb2_get_gbb(ui->ctx)->flags & VB2_GBB_FLAG_FORCE_DEV_SWITCH_ON) {
VB2_DEBUG("ERROR: to-norm not allowed\n");
- ui->error_code = VB2_UI_ERROR_TO_NORM_NOT_ALLOWED;
- return vb2_ui_screen_back(ui);
+ return set_ui_error_and_go_back(
+ ui, VB2_UI_ERROR_TO_NORM_NOT_ALLOWED);
}
ui->state->selected_item = DEVELOPER_TO_NORM_ITEM_CONFIRM;
- return VB2_REQUEST_UI_CONTINUE;
+ /* Hide "Cancel" button if dev boot is not allowed */
+ if (!vb2_dev_boot_allowed(ui->ctx))
+ VB2_SET_BIT(ui->state->hidden_item_mask,
+ DEVELOPER_TO_NORM_ITEM_CANCEL);
+ return VB2_SUCCESS;
}
vb2_error_t developer_to_norm_action(struct vb2_ui_context *ui)
{
if (vb2_get_gbb(ui->ctx)->flags & VB2_GBB_FLAG_FORCE_DEV_SWITCH_ON) {
VB2_DEBUG("ERROR: dev mode forced by GBB flag\n");
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
VB2_DEBUG("Leaving dev mode\n");
@@ -878,11 +873,11 @@
static const struct vb2_menu_item developer_to_norm_items[] = {
LANGUAGE_SELECT_ITEM,
- {
+ [DEVELOPER_TO_NORM_ITEM_CONFIRM] = {
.text = "Confirm",
.action = developer_to_norm_action,
},
- {
+ [DEVELOPER_TO_NORM_ITEM_CANCEL] = {
.text = "Cancel",
.action = vb2_ui_screen_back,
},
@@ -929,7 +924,7 @@
};
/******************************************************************************/
-/* VB2_SCREEN_DEVELOPER_SELECT_BOOTLOADER */
+/* VB2_SCREEN_DEVELOPER_SELECT_ALTFW */
static const struct vb2_menu_item developer_select_bootloader_items_before[] = {
LANGUAGE_SELECT_ITEM,
@@ -942,51 +937,46 @@
static vb2_error_t developer_select_bootloader_init(struct vb2_ui_context *ui)
{
- if (get_menu(ui)->num_items == 0) {
- ui->error_code = VB2_UI_ERROR_NO_BOOTLOADER;
- return vb2_ui_screen_back(ui);
- }
+ if (get_menu(ui)->num_items == 0)
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_ALTFW_EMPTY);
/* Select the first bootloader. */
ui->state->selected_item =
ARRAY_SIZE(developer_select_bootloader_items_before);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
-vb2_error_t vb2_ui_developer_mode_boot_alternate_action(
+vb2_error_t vb2_ui_developer_mode_boot_altfw_action(
struct vb2_ui_context *ui)
{
- uint32_t altfw_num;
+ uint32_t altfw_id;
const size_t menu_before_len =
ARRAY_SIZE(developer_select_bootloader_items_before);
if (!(ui->ctx->flags & VB2_CONTEXT_DEVELOPER_MODE) ||
!vb2_dev_boot_allowed(ui->ctx) ||
- !vb2_dev_boot_legacy_allowed(ui->ctx)) {
+ !vb2_dev_boot_altfw_allowed(ui->ctx)) {
VB2_DEBUG("ERROR: Dev mode alternate bootloader not allowed\n");
- ui->error_code = VB2_UI_ERROR_ALTERNATE_BOOT_DISABLED;
- return VB2_REQUEST_UI_CONTINUE;
+ return set_ui_error(ui, VB2_UI_ERROR_ALTFW_DISABLED);
}
- if (vb2ex_get_bootloader_count() == 0) {
+ if (vb2ex_get_altfw_count() == 0) {
VB2_DEBUG("ERROR: No alternate bootloader was found\n");
- ui->error_code = VB2_UI_ERROR_NO_BOOTLOADER;
- return VB2_REQUEST_UI_CONTINUE;
+ return set_ui_error(ui, VB2_UI_ERROR_ALTFW_EMPTY);
}
if (ui->key == VB_KEY_CTRL('L')) {
- altfw_num = 0;
+ altfw_id = 0;
VB2_DEBUG("Try booting from default bootloader\n");
} else {
- altfw_num = ui->state->selected_item - menu_before_len + 1;
- VB2_DEBUG("Try booting from bootloader #%u\n", altfw_num);
+ altfw_id = ui->state->selected_item - menu_before_len + 1;
+ VB2_DEBUG("Try booting from bootloader #%u\n", altfw_id);
}
- /* VbExLegacy will not return if successful */
- VbExLegacy(altfw_num);
+ /* vb2ex_run_altfw will not return if successful */
+ vb2ex_run_altfw(altfw_id);
VB2_DEBUG("ERROR: Alternate bootloader failed\n");
- ui->error_code = VB2_UI_ERROR_ALTERNATE_BOOT_FAILED;
- return VB2_REQUEST_UI_CONTINUE;
+ return set_ui_error(ui, VB2_UI_ERROR_ALTFW_FAILED);
}
static const struct vb2_menu *get_bootloader_menu(struct vb2_ui_context *ui)
@@ -1002,7 +992,7 @@
if (ui->bootloader_menu.num_items > 0)
return &ui->bootloader_menu;
- num_bootloaders = vb2ex_get_bootloader_count();
+ num_bootloaders = vb2ex_get_altfw_count();
if (num_bootloaders == 0) {
VB2_DEBUG("ERROR: No bootloader was found\n");
return NULL;
@@ -1024,7 +1014,7 @@
for (i = 0; i < num_bootloaders; i++) {
items[i + menu_before_len].text = "Some bootloader";
items[i + menu_before_len].action =
- vb2_ui_developer_mode_boot_alternate_action;
+ vb2_ui_developer_mode_boot_altfw_action;
}
/* Copy postfix items to the end. */
@@ -1039,7 +1029,7 @@
}
static const struct vb2_screen_info developer_select_bootloader_screen = {
- .id = VB2_SCREEN_DEVELOPER_SELECT_BOOTLOADER,
+ .id = VB2_SCREEN_DEVELOPER_SELECT_ALTFW,
.name = "Select alternate bootloader",
.init = developer_select_bootloader_init,
.get_menu = get_bootloader_menu,
@@ -1048,18 +1038,44 @@
/******************************************************************************/
/* VB2_SCREEN_DIAGNOSTICS */
+#define DIAGNOSTICS_ITEM_STORAGE_HEALTH 1
+#define DIAGNOSTICS_ITEM_STORAGE_TEST_SHORT 2
+#define DIAGNOSTICS_ITEM_STORAGE_TEST_EXTENDED 3
+
+static vb2_error_t diagnostics_init(struct vb2_ui_context *ui)
+{
+ const char *unused_log_string;
+ vb2_error_t rv = vb2ex_diag_get_storage_test_log(&unused_log_string);
+ if (rv == VB2_ERROR_EX_UNIMPLEMENTED) {
+ VB2_SET_BIT(ui->state->disabled_item_mask,
+ DIAGNOSTICS_ITEM_STORAGE_TEST_SHORT);
+ VB2_SET_BIT(ui->state->disabled_item_mask,
+ DIAGNOSTICS_ITEM_STORAGE_TEST_EXTENDED);
+ }
+ ui->state->selected_item = DIAGNOSTICS_ITEM_STORAGE_HEALTH;
+ return VB2_SUCCESS;
+}
+
static const struct vb2_menu_item diagnostics_items[] = {
LANGUAGE_SELECT_ITEM,
- {
- .text = "Storage",
- .target = VB2_SCREEN_DIAGNOSTICS_STORAGE,
+ [DIAGNOSTICS_ITEM_STORAGE_HEALTH] = {
+ .text = "Storage health info",
+ .target = VB2_SCREEN_DIAGNOSTICS_STORAGE_HEALTH,
+ },
+ [DIAGNOSTICS_ITEM_STORAGE_TEST_SHORT] = {
+ .text = "Storage self-test (short)",
+ .target = VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_SHORT,
+ },
+ [DIAGNOSTICS_ITEM_STORAGE_TEST_EXTENDED] = {
+ .text = "Storage self-test (Extended)",
+ .target = VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_EXTENDED,
},
{
- .text = "Quick memory check",
+ .text = "Memory check (quick)",
.target = VB2_SCREEN_DIAGNOSTICS_MEMORY_QUICK,
},
{
- .text = "Full memory check",
+ .text = "Memory check (full)",
.target = VB2_SCREEN_DIAGNOSTICS_MEMORY_FULL,
},
POWER_OFF_ITEM,
@@ -1068,50 +1084,167 @@
static const struct vb2_screen_info diagnostics_screen = {
.id = VB2_SCREEN_DIAGNOSTICS,
.name = "Diagnostic tools",
+ .init = diagnostics_init,
.menu = MENU_ITEMS(diagnostics_items),
};
/******************************************************************************/
-/* VB2_SCREEN_DIAGNOSTICS_STORAGE */
+/* VB2_SCREEN_DIAGNOSTICS_STORAGE_HEALTH */
-#define DIAGNOSTICS_STORAGE_ITEM_PAGE_UP 0
-#define DIAGNOSTICS_STORAGE_ITEM_PAGE_DOWN 1
-#define DIAGNOSTICS_STORAGE_ITEM_BACK 2
+#define DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_UP 0
+#define DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_DOWN 1
+#define DIAGNOSTICS_STORAGE_HEALTH_ITEM_BACK 2
-static vb2_error_t diagnostics_storage_init(struct vb2_ui_context *ui)
+static vb2_error_t diagnostics_storage_health_init_impl(
+ struct vb2_ui_context *ui)
{
- const char *log_string = vb2ex_get_diagnostic_storage();
- if (!log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve storage log message\n");
- ui->error_code = VB2_UI_ERROR_DIAGNOSTICS;
- return vb2_ui_screen_back(ui);
- }
-
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare storage log screen\n");
- ui->error_code = VB2_UI_ERROR_DIAGNOSTICS;
- return vb2_ui_screen_back(ui);
- }
- return log_page_init(ui);
+ const char *log_string;
+ VB2_TRY(vb2ex_diag_get_storage_health(&log_string));
+ VB2_TRY(log_page_update(ui, log_string));
+ return log_page_reset_to_top(ui);
}
-static const struct vb2_menu_item diagnostics_storage_items[] = {
- [DIAGNOSTICS_STORAGE_ITEM_PAGE_UP] = PAGE_UP_ITEM,
- [DIAGNOSTICS_STORAGE_ITEM_PAGE_DOWN] = PAGE_DOWN_ITEM,
- [DIAGNOSTICS_STORAGE_ITEM_BACK] = BACK_ITEM,
+static vb2_error_t diagnostics_storage_health_init(struct vb2_ui_context *ui)
+{
+ if (vb2_is_error(diagnostics_storage_health_init_impl(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
+}
+
+static const struct vb2_menu_item diagnostics_storage_health_items[] = {
+ [DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_UP] = PAGE_UP_ITEM,
+ [DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_DOWN] = PAGE_DOWN_ITEM,
+ [DIAGNOSTICS_STORAGE_HEALTH_ITEM_BACK] = BACK_ITEM,
POWER_OFF_ITEM,
};
-static const struct vb2_screen_info diagnostics_storage_screen = {
- .id = VB2_SCREEN_DIAGNOSTICS_STORAGE,
- .name = "Storage",
- .init = diagnostics_storage_init,
- .menu = MENU_ITEMS(diagnostics_storage_items),
- .page_up_item = DIAGNOSTICS_STORAGE_ITEM_PAGE_UP,
- .page_down_item = DIAGNOSTICS_STORAGE_ITEM_PAGE_DOWN,
- .back_item = DIAGNOSTICS_STORAGE_ITEM_BACK,
+static const struct vb2_screen_info diagnostics_storage_health_screen = {
+ .id = VB2_SCREEN_DIAGNOSTICS_STORAGE_HEALTH,
+ .name = "Storage health info",
+ .init = diagnostics_storage_health_init,
+ .menu = MENU_ITEMS(diagnostics_storage_health_items),
+ .page_up_item = DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_UP,
+ .page_down_item = DIAGNOSTICS_STORAGE_HEALTH_ITEM_PAGE_DOWN,
+ .back_item = DIAGNOSTICS_STORAGE_HEALTH_ITEM_BACK,
+};
+
+/******************************************************************************/
+/* VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST */
+
+#define DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_UP 0
+#define DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_DOWN 1
+#define DIAGNOSTICS_STORAGE_TEST_ITEM_BACK 2
+#define DIAGNOSTICS_STORAGE_TEST_ITEM_CANCEL 3
+
+static vb2_error_t diagnostics_storage_test_update_impl(
+ struct vb2_ui_context *ui)
+{
+ const char *log_string;
+ int is_test_running = 0;
+
+ /* Early return if the test is done. */
+ if (ui->state->test_finished)
+ return VB2_SUCCESS;
+
+ vb2_error_t rv = vb2ex_diag_get_storage_test_log(&log_string);
+ switch (rv) {
+ case VB2_ERROR_EX_DIAG_TEST_RUNNING:
+ is_test_running = 1;
+ break;
+ case VB2_SUCCESS:
+ ui->state->test_finished = 1;
+ break;
+ default:
+ VB2_DEBUG("vb2ex_diag_get_storage_test_log returned %#x\n", rv);
+ return rv;
+ }
+ VB2_TRY(log_page_show_back_or_cancel(ui, is_test_running));
+ return log_page_update(ui, log_string);
+}
+
+static vb2_error_t diagnostics_storage_test_update(struct vb2_ui_context *ui)
+{
+ if (vb2_is_error(diagnostics_storage_test_update_impl(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
+}
+
+static vb2_error_t diagnostics_storage_test_control(
+ struct vb2_ui_context *ui, enum vb2_diag_storage_test op)
+{
+ if (vb2_is_error(vb2ex_diag_storage_test_control(op)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
+}
+
+static vb2_error_t diagnostics_storage_test_init(struct vb2_ui_context *ui)
+{
+ VB2_TRY(diagnostics_storage_test_update(ui));
+ if (vb2_is_error(log_page_reset_to_top(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
+}
+
+static vb2_error_t diagnostics_storage_test_short_init(
+ struct vb2_ui_context *ui)
+{
+ VB2_TRY(diagnostics_storage_test_control(ui,
+ VB2_DIAG_STORAGE_TEST_STOP));
+ VB2_TRY(diagnostics_storage_test_control(ui,
+ VB2_DIAG_STORAGE_TEST_SHORT));
+ return diagnostics_storage_test_init(ui);
+}
+
+static vb2_error_t diagnostics_storage_test_extended_init(
+ struct vb2_ui_context *ui)
+{
+ VB2_TRY(diagnostics_storage_test_control(ui,
+ VB2_DIAG_STORAGE_TEST_STOP));
+ VB2_TRY(diagnostics_storage_test_control(
+ ui, VB2_DIAG_STORAGE_TEST_EXTENDED));
+ return diagnostics_storage_test_init(ui);
+}
+
+static vb2_error_t diagnostics_storage_test_cancel(struct vb2_ui_context *ui)
+{
+ VB2_TRY(diagnostics_storage_test_control(ui,
+ VB2_DIAG_STORAGE_TEST_STOP));
+ return vb2_ui_screen_back(ui);
+}
+
+static const struct vb2_menu_item diagnostics_storage_test_items[] = {
+ [DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_UP] = PAGE_UP_ITEM,
+ [DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_DOWN] = PAGE_DOWN_ITEM,
+ [DIAGNOSTICS_STORAGE_TEST_ITEM_BACK] = BACK_ITEM,
+ [DIAGNOSTICS_STORAGE_TEST_ITEM_CANCEL] = {
+ .text = "Cancel",
+ .action = diagnostics_storage_test_cancel,
+ },
+ POWER_OFF_ITEM,
+};
+
+static const struct vb2_screen_info diagnostics_storage_test_short_screen = {
+ .id = VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_SHORT,
+ .name = "Storage self-test (short)",
+ .init = diagnostics_storage_test_short_init,
+ .action = diagnostics_storage_test_update,
+ .menu = MENU_ITEMS(diagnostics_storage_test_items),
+ .page_up_item = DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_UP,
+ .page_down_item = DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_DOWN,
+ .back_item = DIAGNOSTICS_STORAGE_TEST_ITEM_BACK,
+ .cancel_item = DIAGNOSTICS_STORAGE_TEST_ITEM_CANCEL,
+};
+
+static const struct vb2_screen_info diagnostics_storage_test_extended_screen = {
+ .id = VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_EXTENDED,
+ .name = "Storage self-test (extended)",
+ .init = diagnostics_storage_test_extended_init,
+ .action = diagnostics_storage_test_update,
+ .menu = MENU_ITEMS(diagnostics_storage_test_items),
+ .page_up_item = DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_UP,
+ .page_down_item = DIAGNOSTICS_STORAGE_TEST_ITEM_PAGE_DOWN,
+ .back_item = DIAGNOSTICS_STORAGE_TEST_ITEM_BACK,
+ .cancel_item = DIAGNOSTICS_STORAGE_TEST_ITEM_CANCEL,
};
/******************************************************************************/
@@ -1120,88 +1253,65 @@
#define DIAGNOSTICS_MEMORY_ITEM_PAGE_UP 0
#define DIAGNOSTICS_MEMORY_ITEM_PAGE_DOWN 1
-#define DIAGNOSTICS_MEMORY_ITEM_CANCEL 2
-#define DIAGNOSTICS_MEMORY_ITEM_BACK 3
+#define DIAGNOSTICS_MEMORY_ITEM_BACK 2
+#define DIAGNOSTICS_MEMORY_ITEM_CANCEL 3
typedef vb2_error_t (*memory_test_op_t)(int reset, const char **out);
+static vb2_error_t diagnostics_memory_update_screen_impl(
+ struct vb2_ui_context *ui, memory_test_op_t op, int reset)
+{
+ const char *log_string = NULL;
+ vb2_error_t rv;
+ int is_test_running = 0;
+
+ /* Early return if the memory test is done. */
+ if (ui->state->test_finished)
+ return VB2_SUCCESS;
+
+ rv = op(reset, &log_string);
+ switch (rv) {
+ /* The test is still running but the output buffer was unchanged. */
+ case VB2_ERROR_EX_DIAG_TEST_RUNNING:
+ return VB2_SUCCESS;
+ case VB2_ERROR_EX_DIAG_TEST_UPDATED:
+ is_test_running = 1;
+ break;
+ case VB2_SUCCESS:
+ ui->state->test_finished = 1;
+ break;
+ default:
+ VB2_DEBUG("memory_test_op returned %#x\n", rv);
+ return rv;
+ }
+ VB2_TRY(log_page_show_back_or_cancel(ui, is_test_running));
+ return log_page_update(ui, log_string);
+}
+
static vb2_error_t diagnostics_memory_update_screen(struct vb2_ui_context *ui,
memory_test_op_t op,
int reset)
{
- const char *log_string = NULL;
-
- /* Early return if the memory test is done. */
- if (ui->state->test_finished)
- return VB2_REQUEST_UI_CONTINUE;
-
- vb2_error_t rv = op(reset, &log_string);
-
- /* The test is still running but the output buffer was unchanged. */
- if (rv == VB2_ERROR_EX_DIAG_TEST_RUNNING)
- return VB2_REQUEST_UI_CONTINUE;
-
- if ((rv && rv != VB2_ERROR_EX_DIAG_TEST_UPDATED) || !log_string) {
- VB2_DEBUG("ERROR: Failed to retrieve memory test status\n");
- ui->error_code = VB2_UI_ERROR_DIAGNOSTICS;
- return vb2_ui_screen_back(ui);
- }
-
- ui->state->page_count = vb2ex_prepare_log_screen(
- ui->state->screen->id, ui->locale_id, log_string);
- if (ui->state->page_count == 0) {
- VB2_DEBUG("ERROR: Failed to prepare memory log screen, error: "
- "%#x\n", rv);
- ui->error_code = VB2_UI_ERROR_DIAGNOSTICS;
- return vb2_ui_screen_back(ui);
- }
- /* TODO(b/174127808): Integrate this into a new log_page_* function. */
- if (ui->state->current_page >= ui->state->page_count)
- ui->state->current_page = ui->state->page_count - 1;
-
- ui->force_display = 1;
-
- /* Show cancel button when the test is running, otherwise show the back
- * button. VB2_SUCCESS indicates the test is finished. */
- VB2_CLR_BIT(ui->state->hidden_item_mask,
- DIAGNOSTICS_MEMORY_ITEM_CANCEL);
- VB2_CLR_BIT(ui->state->hidden_item_mask, DIAGNOSTICS_MEMORY_ITEM_BACK);
- if (rv == VB2_ERROR_EX_DIAG_TEST_UPDATED) {
- VB2_SET_BIT(ui->state->hidden_item_mask,
- DIAGNOSTICS_MEMORY_ITEM_BACK);
- if (ui->state->selected_item == DIAGNOSTICS_MEMORY_ITEM_BACK)
- ui->state->selected_item =
- DIAGNOSTICS_MEMORY_ITEM_CANCEL;
- } else {
- VB2_SET_BIT(ui->state->hidden_item_mask,
- DIAGNOSTICS_MEMORY_ITEM_CANCEL);
- if (ui->state->selected_item == DIAGNOSTICS_MEMORY_ITEM_CANCEL)
- ui->state->selected_item = DIAGNOSTICS_MEMORY_ITEM_BACK;
- ui->state->test_finished = 1;
- }
-
- return VB2_REQUEST_UI_CONTINUE;
+ if (vb2_is_error(diagnostics_memory_update_screen_impl(ui, op, reset)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
}
static vb2_error_t diagnostics_memory_init_quick(struct vb2_ui_context *ui)
{
- vb2_error_t rv;
- rv = diagnostics_memory_update_screen(
- ui, &vb2ex_diag_memory_quick_test, 1);
-
- if (rv != VB2_REQUEST_UI_CONTINUE)
- return rv;
- return log_page_init(ui);
+ VB2_TRY(diagnostics_memory_update_screen(
+ ui, &vb2ex_diag_memory_quick_test, 1));
+ if (vb2_is_error(log_page_reset_to_top(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
}
static vb2_error_t diagnostics_memory_init_full(struct vb2_ui_context *ui)
{
- vb2_error_t rv;
- rv = diagnostics_memory_update_screen(
- ui, &vb2ex_diag_memory_full_test, 1);
-
- if (rv != VB2_REQUEST_UI_CONTINUE)
- return rv;
- return log_page_init(ui);
+ VB2_TRY(diagnostics_memory_update_screen(
+ ui, &vb2ex_diag_memory_full_test, 1));
+ if (vb2_is_error(log_page_reset_to_top(ui)))
+ return set_ui_error_and_go_back(ui, VB2_UI_ERROR_DIAGNOSTICS);
+ return VB2_SUCCESS;
}
static vb2_error_t diagnostics_memory_update_quick(struct vb2_ui_context *ui)
@@ -1219,34 +1329,36 @@
static const struct vb2_menu_item diagnostics_memory_items[] = {
[DIAGNOSTICS_MEMORY_ITEM_PAGE_UP] = PAGE_UP_ITEM,
[DIAGNOSTICS_MEMORY_ITEM_PAGE_DOWN] = PAGE_DOWN_ITEM,
+ [DIAGNOSTICS_MEMORY_ITEM_BACK] = BACK_ITEM,
[DIAGNOSTICS_MEMORY_ITEM_CANCEL] = {
- .text = "Cancel and go back",
+ .text = "Cancel",
.action = vb2_ui_screen_back,
},
- [DIAGNOSTICS_MEMORY_ITEM_BACK] = BACK_ITEM,
POWER_OFF_ITEM,
};
static const struct vb2_screen_info diagnostics_memory_quick_screen = {
.id = VB2_SCREEN_DIAGNOSTICS_MEMORY_QUICK,
- .name = "Quick memory check",
+ .name = "Memory check (quick)",
.init = diagnostics_memory_init_quick,
.action = diagnostics_memory_update_quick,
.menu = MENU_ITEMS(diagnostics_memory_items),
.page_up_item = DIAGNOSTICS_MEMORY_ITEM_PAGE_UP,
.page_down_item = DIAGNOSTICS_MEMORY_ITEM_PAGE_DOWN,
- .back_item = DIAGNOSTICS_MEMORY_ITEM_CANCEL,
+ .back_item = DIAGNOSTICS_MEMORY_ITEM_BACK,
+ .cancel_item = DIAGNOSTICS_MEMORY_ITEM_CANCEL,
};
static const struct vb2_screen_info diagnostics_memory_full_screen = {
.id = VB2_SCREEN_DIAGNOSTICS_MEMORY_FULL,
- .name = "Full memory check",
+ .name = "Memory check (full)",
.init = diagnostics_memory_init_full,
.action = diagnostics_memory_update_full,
.menu = MENU_ITEMS(diagnostics_memory_items),
.page_up_item = DIAGNOSTICS_MEMORY_ITEM_PAGE_UP,
.page_down_item = DIAGNOSTICS_MEMORY_ITEM_PAGE_DOWN,
- .back_item = DIAGNOSTICS_MEMORY_ITEM_CANCEL,
+ .back_item = DIAGNOSTICS_MEMORY_ITEM_BACK,
+ .cancel_item = DIAGNOSTICS_MEMORY_ITEM_CANCEL,
};
/******************************************************************************/
@@ -1258,7 +1370,6 @@
* screen, based on the menu information passed from vboot.
*/
static const struct vb2_screen_info *screens[] = {
- &blank_screen,
&language_select_screen,
&recovery_broken_screen,
&advanced_options_screen,
@@ -1278,7 +1389,9 @@
&developer_invalid_disk_screen,
&developer_select_bootloader_screen,
&diagnostics_screen,
- &diagnostics_storage_screen,
+ &diagnostics_storage_health_screen,
+ &diagnostics_storage_test_short_screen,
+ &diagnostics_storage_test_extended_screen,
&diagnostics_memory_quick_screen,
&diagnostics_memory_full_screen,
};
diff --git a/firmware/2lib/include/2api.h b/firmware/2lib/include/2api.h
index 94f0df5..fb656da 100644
--- a/firmware/2lib/include/2api.h
+++ b/firmware/2lib/include/2api.h
@@ -64,6 +64,17 @@
*/
#define VB2_TRY(expr, ...) _VB2_TRY_IMPL(expr, ##__VA_ARGS__, NULL, 0)
+/**
+ * Check if the return value is an error.
+ *
+ * @param rv The return value.
+ * @return True if the value is an error.
+ */
+static inline int vb2_is_error(vb2_error_t rv)
+{
+ return rv >= VB2_ERROR_BASE && rv <= VB2_ERROR_MAX;
+}
+
/* Flags for vb2_context.
*
* Unless otherwise noted, flags are set by verified boot and may be read (but
@@ -222,6 +233,13 @@
* NO_BOOT means the OS is not allowed to boot. Only relevant for EFS2.
*/
VB2_CONTEXT_NO_BOOT = (1 << 23),
+
+ /*
+ * TRUSTED means EC is running an RO copy and PD isn't enabled. At
+ * least that was last known to the GSC. If EC RO is correctly behaving,
+ * it doesn't jump to RW when this flag is set.
+ */
+ VB2_CONTEXT_EC_TRUSTED = (1 << 24),
};
/* Helper for aligning fields in vb2_context. */
@@ -567,6 +585,15 @@
uint32_t vb2api_secdata_kernel_create_v0(struct vb2_context *ctx);
/**
+ * Create an empty Firmware Management Parameters (FWMP) in secure storage
+ * context.
+ *
+ * @param ctx Context pointer
+ * @return size of created FWMP secure storage data in bytes
+ */
+uint32_t vb2api_secdata_fwmp_create(struct vb2_context *ctx);
+
+/**
* Check the validity of firmware management parameters (FWMP) space.
*
* Checks size, version, and CRC. If the struct size is larger than the size
@@ -875,8 +902,8 @@
/* Default to boot from external disk. */
VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL = 1,
- /* Default to boot legacy OS. */
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY = 2,
+ /* Default to boot altfw. */
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW = 2,
};
/**
@@ -1005,7 +1032,7 @@
* caller may not get a chance to commit this data.
*
* @param ctx Vboot context
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2ex_commit_data(struct vb2_context *ctx);
@@ -1015,7 +1042,7 @@
/**
* Initialize the TPM.
*
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2ex_tpm_init(void);
@@ -1026,7 +1053,7 @@
* TPM_TakeOwnership, since the TPM device can be opened only by one process at
* a time.
*
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2ex_tpm_close(void);
vb2_error_t vb2ex_tpm_open(void);
@@ -1061,7 +1088,7 @@
* the TPM RNG directly. Otherwise, an attacker with communication interception
* abilities could launch replay attacks by reusing previous nonces.
*
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2ex_tpm_get_random(uint8_t *buf, uint32_t length);
@@ -1093,7 +1120,7 @@
*
* @param mode_val Desired TPM mode to set. May be one of ENABLED
* or DISABLED from vb2_tpm_mode enum.
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2ex_tpm_set_mode(enum vb2_tpm_mode mode_val);
@@ -1304,8 +1331,6 @@
/* Screens. */
enum vb2_screen {
- /* Blank screen */
- VB2_SCREEN_BLANK = 0x0,
/* Wait screen for EC sync and AUXFW sync */
VB2_SCREEN_FIRMWARE_SYNC = 0x100,
/* Broken screen */
@@ -1339,12 +1364,14 @@
VB2_SCREEN_DEVELOPER_BOOT_EXTERNAL = 0x320,
/* Invalid external disk inserted */
VB2_SCREEN_DEVELOPER_INVALID_DISK = 0x330,
- /* Select alternate bootloader ("legacy boot") */
- VB2_SCREEN_DEVELOPER_SELECT_BOOTLOADER = 0x340,
+ /* Select alternate bootloader ("altfw") */
+ VB2_SCREEN_DEVELOPER_SELECT_ALTFW = 0x340,
/* Diagnostic tools */
VB2_SCREEN_DIAGNOSTICS = 0x400,
/* Storage diagnostic screen */
- VB2_SCREEN_DIAGNOSTICS_STORAGE = 0x410,
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_HEALTH = 0x410,
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_SHORT = 0x411,
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_EXTENDED = 0x412,
/* Memory diagnostic screens */
VB2_SCREEN_DIAGNOSTICS_MEMORY_QUICK = 0x420,
VB2_SCREEN_DIAGNOSTICS_MEMORY_FULL = 0x421,
@@ -1355,22 +1382,22 @@
VB2_UI_ERROR_NONE = 0,
/* Dev mode already enabled */
VB2_UI_ERROR_DEV_MODE_ALREADY_ENABLED,
- /* To-norm not allowed */
- VB2_UI_ERROR_TO_NORM_NOT_ALLOWED,
- /* Debug info screen initialization failed */
- VB2_UI_ERROR_DEBUG_LOG,
- /* External boot not enabled */
- VB2_UI_ERROR_EXTERNAL_BOOT_NOT_ENABLED,
- /* Firmware log screen initialization failed */
- VB2_UI_ERROR_FIRMWARE_LOG,
/* Untrusted confirmation */
VB2_UI_ERROR_UNTRUSTED_CONFIRMATION,
+ /* To-norm not allowed */
+ VB2_UI_ERROR_TO_NORM_NOT_ALLOWED,
+ /* External boot is disabled */
+ VB2_UI_ERROR_EXTERNAL_BOOT_DISABLED,
/* Alternate bootloader is disabled */
- VB2_UI_ERROR_ALTERNATE_BOOT_DISABLED,
- /* No bootloader was found */
- VB2_UI_ERROR_NO_BOOTLOADER,
+ VB2_UI_ERROR_ALTFW_DISABLED,
+ /* No alternate bootloader was found */
+ VB2_UI_ERROR_ALTFW_EMPTY,
/* Alternate bootloader failed */
- VB2_UI_ERROR_ALTERNATE_BOOT_FAILED,
+ VB2_UI_ERROR_ALTFW_FAILED,
+ /* Debug info screen initialization failed */
+ VB2_UI_ERROR_DEBUG_LOG,
+ /* Firmware log screen initialization failed */
+ VB2_UI_ERROR_FIRMWARE_LOG,
/* Diagnostics internal failure */
VB2_UI_ERROR_DIAGNOSTICS,
};
@@ -1410,23 +1437,34 @@
/**
* Check that physical presence button is currently pressed by the user.
*
- * @returns 1 for pressed, 0 for not.
+ * @return 1 for pressed, 0 for not.
*/
int vb2ex_physical_presence_pressed(void);
/**
* Get the number of supported locales.
*
- * @returns Number of locales. 0 if none or on error.
+ * @return Number of locales. 0 if none or on error.
*/
uint32_t vb2ex_get_locale_count(void);
/**
* Return the number of available alternate bootloaders.
*
- * @returns Number of alternate bootloaders. 0 if none or on error.
+ * @return Number of alternate bootloaders. 0 if none or on error.
*/
-uint32_t vb2ex_get_bootloader_count(void);
+uint32_t vb2ex_get_altfw_count(void);
+
+/**
+ * Run alternate bootloader.
+ *
+ * @param altfw_id ID of alternate bootloader to run, where
+ * altfw_id <= vb2ex_get_altfw_count(). 0 for default,
+ * which corresponds to an alternate bootloader in
+ * the range 1 <= altfw_id <= vb2ex_getfw_count().
+ * @return VB2_SUCCESS, or error code on error.
+ */
+vb2_error_t vb2ex_run_altfw(uint32_t altfw_id);
/**
* Delay for at least the specified number of milliseconds.
@@ -1504,16 +1542,30 @@
const char *str);
/**
- * Get the full storage diagnostic log.
+ * Get the health info of the storage.
*
- * Return a pointer of full log string which is guaranteed to be
- * null-terminated. The function implementation should manage string memory
- * internally. Subsequent calls may update the string and/or may return a new
- * pointer.
- *
- * @return The pointer to the full debug info string. NULL on error.
+ * @param out For returning a read-only pointer of full log string which is
+ * guaranteed to be null-terminated. The function will manage
+ * memory internally, so the returned pointer will only be valid
+ * until next call.
+ * @return VB2_SUCCESS, or error code on error.
*/
-const char *vb2ex_get_diagnostic_storage(void);
+vb2_error_t vb2ex_diag_get_storage_health(const char **out);
+
+/**
+ * Get the storage self-test log.
+ *
+ * @param out For returning a read-only pointer of full log string which is
+ * guaranteed to be null-terminated. The function will manage
+ * memory internally, so the returned pointer will only be valid
+ * until next call.
+ * @return The status of storage test. VB2_SUCCESS means the test is finished,
+ * regardless of passing or failing. VB2_ERROR_EX_DIAG_TEST_RUNNING means
+ * the test is still running. VB2_ERROR_EX_UNIMPLEMENTED means the storage
+ * self-test is not supported on this device. Other non-zero codes for internal
+ * errors.
+ */
+vb2_error_t vb2ex_diag_get_storage_test_log(const char **out);
/**
* Get the memory diagnostic status. When it is called, it will take over the
@@ -1537,6 +1589,17 @@
vb2_error_t vb2ex_diag_memory_full_test(int reset, const char **out);
/*****************************************************************************/
+/* Functions for diagnostics control. */
+
+enum vb2_diag_storage_test {
+ VB2_DIAG_STORAGE_TEST_STOP = 0,
+ VB2_DIAG_STORAGE_TEST_SHORT,
+ VB2_DIAG_STORAGE_TEST_EXTENDED,
+};
+
+vb2_error_t vb2ex_diag_storage_test_control(enum vb2_diag_storage_test ops);
+
+/*****************************************************************************/
/* Timer. */
/**
diff --git a/firmware/2lib/include/2common.h b/firmware/2lib/include/2common.h
index e610093..918c50d 100644
--- a/firmware/2lib/include/2common.h
+++ b/firmware/2lib/include/2common.h
@@ -10,6 +10,7 @@
#include "2api.h"
#include "2gbb.h"
+#include "2packed_key.h"
#include "2return_codes.h"
#include "2sha.h"
#include "2struct.h"
@@ -427,4 +428,44 @@
const struct vb2_public_key *key,
const struct vb2_workbuf *wb);
+/**
+ * Get the flags for the kernel preamble.
+ *
+ * @param preamble Preamble to check
+ * @return Flags for the preamble. Old preamble versions (<2.2) return 0.
+ */
+uint32_t vb2_kernel_get_flags(const struct vb2_kernel_preamble *preamble);
+
+/**
+ * Verify a keyblock using its hash.
+ *
+ * Header fields are also checked for validity. Does not verify key index or key
+ * block flags. Use this for self-signed keyblocks in developer mode.
+ *
+ * @param block Keyblock to verify
+ * @param size Size of keyblock buffer
+ * @param key Key to use to verify block
+ * @param wb Work buffer
+ * @return VB2_SUCCESS, or non-zero error code if error.
+ */
+vb2_error_t vb2_verify_keyblock_hash(const struct vb2_keyblock *block,
+ uint32_t size,
+ const struct vb2_workbuf *wb);
+
+/**
+ * Check the validity of a kernel preamble using a public key.
+ *
+ * The signature in the preamble is destroyed during the check.
+ *
+ * @param preamble Preamble to verify
+ * @param size Size of preamble buffer
+ * @param key Key to use to verify preamble
+ * @param wb Work buffer
+ * @return VB2_SUCCESS, or non-zero error code if error.
+ */
+vb2_error_t vb2_verify_kernel_preamble(struct vb2_kernel_preamble *preamble,
+ uint32_t size,
+ const struct vb2_public_key *key,
+ const struct vb2_workbuf *wb);
+
#endif /* VBOOT_REFERENCE_2COMMON_H_ */
diff --git a/firmware/2lib/include/2gbb_flags.h b/firmware/2lib/include/2gbb_flags.h
index c1c937c..0eff7f7 100644
--- a/firmware/2lib/include/2gbb_flags.h
+++ b/firmware/2lib/include/2gbb_flags.h
@@ -53,8 +53,8 @@
/* Allow Enter key to trigger dev->tonorm screen transition */
VB2_GBB_FLAG_ENTER_TRIGGERS_TONORM = 1 << 6,
- /* Allow booting Legacy OSes in dev mode even if dev_boot_legacy=0. */
- VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY = 1 << 7,
+ /* Allow booting Legacy OSes in dev mode even if dev_boot_altfw=0. */
+ VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW = 1 << 7,
/*
* Currently running FAFT tests. May be used as a hint to disable
@@ -69,7 +69,7 @@
VB2_GBB_FLAG_DISABLE_EC_SOFTWARE_SYNC = 1 << 9,
/* Default to booting legacy OS when dev screen times out */
- VB2_GBB_FLAG_DEFAULT_DEV_BOOT_LEGACY = 1 << 10,
+ VB2_GBB_FLAG_DEFAULT_DEV_BOOT_ALTFW = 1 << 10,
/* Disable auxiliary firmware (auxfw) software sync */
VB2_GBB_FLAG_DISABLE_AUXFW_SOFTWARE_SYNC = 1 << 11,
diff --git a/firmware/2lib/include/2misc.h b/firmware/2lib/include/2misc.h
index 334b148..3d96293 100644
--- a/firmware/2lib/include/2misc.h
+++ b/firmware/2lib/include/2misc.h
@@ -224,13 +224,13 @@
* Determine if booting from legacy BIOS is allowed.
*
* Legacy BIOS is allowed if any of these flags are set:
- * VB2_NV_DEV_BOOT_LEGACY, VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY, and
- * VB2_SECDATA_FWMP_DEV_ENABLE_LEGACY.
+ * VB2_NV_DEV_BOOT_ALTFW, VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW, and
+ * VB2_SECDATA_FWMP_DEV_ENABLE_ALTFW.
*
* @param ctx Vboot context
* @return 1 if allowed, or 0 otherwise.
*/
-int vb2_dev_boot_legacy_allowed(struct vb2_context *ctx);
+int vb2_dev_boot_altfw_allowed(struct vb2_context *ctx);
/**
* Determine if booting from external disk is allowed.
diff --git a/firmware/2lib/include/2nvstorage.h b/firmware/2lib/include/2nvstorage.h
index 9de8056..2f40b23 100644
--- a/firmware/2lib/include/2nvstorage.h
+++ b/firmware/2lib/include/2nvstorage.h
@@ -49,7 +49,7 @@
/* Allow booting from external disk in developer mode. 0=no, 1=yes. */
VB2_NV_DEV_BOOT_EXTERNAL,
/* Allow booting of legacy OSes in developer mode. 0=no, 1=yes. */
- VB2_NV_DEV_BOOT_LEGACY,
+ VB2_NV_DEV_BOOT_ALTFW,
/* Only boot Google-signed images in developer mode. 0=no, 1=yes. */
VB2_NV_DEV_BOOT_SIGNED_ONLY,
/*
diff --git a/firmware/2lib/include/2packed_key.h b/firmware/2lib/include/2packed_key.h
new file mode 100644
index 0000000..09c7355
--- /dev/null
+++ b/firmware/2lib/include/2packed_key.h
@@ -0,0 +1,39 @@
+/* Copyright 2021 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.
+ *
+ * Functions related to unpacking keys and key buffers.
+ */
+
+#ifndef VBOOT_REFERENCE_2PACKED_KEY_H_
+#define VBOOT_REFERENCE_2PACKED_KEY_H_
+
+/**
+ * Unpack a vboot1-format key buffer for use in verification
+ *
+ * The elements of the unpacked key will point into the source buffer, so don't
+ * free the source buffer until you're done with the key.
+ *
+ * @param key Destintion for unpacked key
+ * @param buf Source buffer containing packed key
+ * @param size Size of buffer in bytes
+ * @return VB2_SUCCESS, or non-zero error code if error.
+ */
+vb2_error_t vb2_unpack_key_buffer(struct vb2_public_key *key,
+ const uint8_t *buf, uint32_t size);
+
+/**
+ * Unpack a vboot1-format key for use in verification
+ *
+ * The elements of the unpacked key will point into the source packed key, so
+ * don't free the source until you're done with the public key.
+ *
+ * @param key Destintion for unpacked key
+ * @param packed_key Source packed key
+ * @param size Size of buffer in bytes
+ * @return VB2_SUCCESS, or non-zero error code if error.
+ */
+vb2_error_t vb2_unpack_key(struct vb2_public_key *key,
+ const struct vb2_packed_key *packed_key);
+
+#endif /* VBOOT_REFERENCE_2PACKED_KEY_H_ */
diff --git a/firmware/2lib/include/2recovery_reasons.h b/firmware/2lib/include/2recovery_reasons.h
index 514ee4f..30dbd2e 100644
--- a/firmware/2lib/include/2recovery_reasons.h
+++ b/firmware/2lib/include/2recovery_reasons.h
@@ -14,7 +14,7 @@
* Return a description of the recovery reason code.
*
* @param recovery reason code
- * @returns A string literal with English description of the recovery reason
+ * @return A string literal with English description of the recovery reason
*/
const char *vb2_get_recovery_reason_string(uint8_t code);
@@ -265,8 +265,8 @@
/* Failed to disable the TPM [prior to running untrusted code] */
VB2_RECOVERY_TPM_DISABLE_FAILED = 0x60,
- /* Alt FW Failed hash verification */
- VB2_RECOVERY_ALTFW_HASH_FAILED = 0x61,
+ /* Verification of altfw payload failed (deprecated) */
+ VB2_RECOVERY_ALTFW_HASH_MISMATCH = 0x61,
/* FWMP secure data initialization error */
VB2_RECOVERY_SECDATA_FWMP_INIT = 0x62,
diff --git a/firmware/2lib/include/2return_codes.h b/firmware/2lib/include/2return_codes.h
index 49f9935..4512ff8 100644
--- a/firmware/2lib/include/2return_codes.h
+++ b/firmware/2lib/include/2return_codes.h
@@ -44,6 +44,9 @@
/* Continue in the UI loop. This is used in UI internal functions. */
VB2_REQUEST_UI_CONTINUE = 0x1005,
+ /* Break from the UI loop. This is used in UI internal functions. */
+ VB2_REQUEST_UI_EXIT = 0x1006,
+
/* End of VB2_REQUEST_* */
VB2_REQUEST_END = 0x5000,
@@ -395,6 +398,9 @@
/* No signature matching key ID */
VB2_ERROR_KEYBLOCK_SIG_ID,
+ /* Invalid keyblock hash in dev mode (self-signed kernel) */
+ VB2_ERROR_KEYBLOCK_HASH_INVALID_IN_DEV_MODE,
+
/**********************************************************************
* Preamble verification errors (all in vb2_verify_preamble())
*/
@@ -538,23 +544,27 @@
/* Kernel preamble not loaded before calling vb2api_get_kernel_size() */
VB2_ERROR_API_GET_KERNEL_SIZE_PREAMBLE,
- /* Unable to unpack kernel subkey in vb2_verify_vblock() */
- VB2_ERROR_VBLOCK_KERNEL_SUBKEY,
+ /* Unable to unpack kernel subkey in vb2_verify_vblock();
+ * deprecated and replaced with VB2_ERROR_UNPACK_KEY_* */
+ VB2_ERROR_DEPRECATED_VBLOCK_KERNEL_SUBKEY,
/*
* Got a self-signed kernel in vb2_verify_vblock(), but need an
- * officially signed one.
+ * officially signed one; deprecated and replaced with
+ * VB2_ERROR_KERNEL_KEYBLOCK_*.
*/
- VB2_ERROR_VBLOCK_SELF_SIGNED,
+ VB2_ERROR_DEPRECATED_VBLOCK_SELF_SIGNED,
- /* Invalid keyblock hash in vb2_verify_vblock() */
- VB2_ERROR_VBLOCK_KEYBLOCK_HASH,
+ /* Invalid keyblock hash in vb2_verify_vblock();
+ * deprecated and replaced with VB2_ERROR_KERNEL_KEYBLOCK_* */
+ VB2_ERROR_DEPRECATED_VBLOCK_KEYBLOCK_HASH,
- /* Invalid keyblock in vb2_verify_vblock() */
- VB2_ERROR_VBLOCK_KEYBLOCK,
+ /* Invalid keyblock in vb2_verify_vblock();
+ * deprecated and replaced with VB2_ERROR_KERNEL_KEYBLOCK_* */
+ VB2_ERROR_DEPRECATED_VBLOCK_KEYBLOCK,
- /* Wrong developer key hash in vb2_verify_vblock() */
- VB2_ERROR_VBLOCK_DEV_KEY_HASH,
+ /* Wrong dev key hash in vb2_verify_kernel_vblock_dev_key_hash() */
+ VB2_ERROR_KERNEL_KEYBLOCK_DEV_KEY_HASH,
/* Work buffer too small in vb2_load_partition() */
VB2_ERROR_LOAD_PARTITION_WORKBUF,
diff --git a/firmware/2lib/include/2rsa_private.h b/firmware/2lib/include/2rsa_private.h
new file mode 100644
index 0000000..23a2aac
--- /dev/null
+++ b/firmware/2lib/include/2rsa_private.h
@@ -0,0 +1,21 @@
+/* Copyright 2021 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.
+ *
+ * Internal functions from 2rsa.c that have error conditions we can't trigger
+ * from the public APIs. These include checks for bad algorithms where the
+ * next call level up already checks for bad algorithms, etc.
+ *
+ * These functions aren't in 2rsa.h because they're not part of the public
+ * APIs.
+ */
+
+#ifndef VBOOT_REFERENCE_2RSA_PRIVATE_H_
+#define VBOOT_REFERENCE_2RSA_PRIVATE_H_
+
+struct vb2_public_key;
+int vb2_mont_ge(const struct vb2_public_key *key, uint32_t *a);
+vb2_error_t vb2_check_padding(const uint8_t *sig,
+ const struct vb2_public_key *key);
+
+#endif /* VBOOT_REFERENCE_2RSA_PRIVATE_H_ */
diff --git a/firmware/2lib/include/2secdata.h b/firmware/2lib/include/2secdata.h
index 5e41934..f9a0e30 100644
--- a/firmware/2lib/include/2secdata.h
+++ b/firmware/2lib/include/2secdata.h
@@ -181,7 +181,7 @@
VB2_SECDATA_FWMP_DEV_DISABLE_BOOT = (1 << 0),
VB2_SECDATA_FWMP_DEV_DISABLE_RECOVERY = (1 << 1),
VB2_SECDATA_FWMP_DEV_ENABLE_EXTERNAL = (1 << 2),
- VB2_SECDATA_FWMP_DEV_ENABLE_LEGACY = (1 << 3),
+ VB2_SECDATA_FWMP_DEV_ENABLE_ALTFW = (1 << 3),
VB2_SECDATA_FWMP_DEV_ENABLE_OFFICIAL_ONLY = (1 << 4),
VB2_SECDATA_FWMP_DEV_USE_KEY_HASH = (1 << 5),
/* CCD = case-closed debugging on cr50; flag implemented on cr50 */
diff --git a/firmware/2lib/include/2struct.h b/firmware/2lib/include/2struct.h
index e0ef606..b79bbd0 100644
--- a/firmware/2lib/include/2struct.h
+++ b/firmware/2lib/include/2struct.h
@@ -304,43 +304,6 @@
/****************************************************************************/
-/*
- * Root key hash for Ryu devices only. Contains the hash of the root key.
- * This will be embedded somewhere inside the RO part of the firmware, so that
- * it can verify the GBB contains only the official root key.
- */
-#define RYU_ROOT_KEY_HASH_MAGIC "RtKyHash"
-#define RYU_ROOT_KEY_HASH_MAGIC_INVCASE "rTkYhASH"
-#define RYU_ROOT_KEY_HASH_MAGIC_SIZE 8
-
-#define RYU_ROOT_KEY_HASH_VERSION_MAJOR 1
-#define RYU_ROOT_KEY_HASH_VERSION_MINOR 0
-
-struct vb2_ryu_root_key_hash {
- /* Magic number (RYU_ROOT_KEY_HASH_MAGIC) */
- uint8_t magic[RYU_ROOT_KEY_HASH_MAGIC_SIZE];
-
- /* Version of this struct */
- uint16_t header_version_major;
- uint16_t header_version_minor;
-
- /*
- * Length of this struct, in bytes, including any variable length data
- * which follows (there is none, yet).
- */
- uint32_t struct_size;
-
- /*
- * SHA-256 hash digest of the entire root key section from the GBB. If
- * all 0 bytes, all root keys will be treated as if matching.
- */
- uint8_t root_key_hash_digest[32];
-};
-
-#define EXPECTED_VB2_RYU_ROOT_KEY_HASH_SIZE 48
-
-/****************************************************************************/
-
/* Packed public key data */
struct vb2_packed_key {
/* Offset of key data from start of this struct */
diff --git a/firmware/2lib/include/2ui.h b/firmware/2lib/include/2ui.h
index 77c5acf..bfb2b8b 100644
--- a/firmware/2lib/include/2ui.h
+++ b/firmware/2lib/include/2ui.h
@@ -66,6 +66,7 @@
uint32_t page_up_item;
uint32_t page_down_item;
uint32_t back_item;
+ uint32_t cancel_item;
};
struct vb2_screen_state {
@@ -78,7 +79,7 @@
uint32_t page_count;
uint32_t current_page;
- /* For memory check screen. */
+ /* For minidiag test screens. */
int test_finished; /* Do not update screen if the content is done */
struct vb2_screen_state *prev;
@@ -132,13 +133,13 @@
struct vb2_ui_context *ui);
vb2_error_t vb2_ui_developer_mode_boot_external_action(
struct vb2_ui_context *ui);
-vb2_error_t vb2_ui_developer_mode_boot_alternate_action(
+vb2_error_t vb2_ui_developer_mode_boot_altfw_action(
struct vb2_ui_context *ui);
/**
* Get info struct of a screen.
*
- * @param screen Screen from enum vb2_screen
+ * @param id Screen from enum vb2_screen
*
* @return screen info struct on success, NULL on error.
*/
@@ -155,7 +156,7 @@
* on 0 when we hit the start of the menu.
*
* @param ui UI context pointer
- * @return VB2_REQUEST_UI_CONTINUE, or error code on error.
+ * @return VB2_SUCCESS, or error code on error.
*/
vb2_error_t vb2_ui_menu_prev(struct vb2_ui_context *ui);
@@ -167,29 +168,43 @@
* on the max index when we hit the end of the menu.
*
* @param ui UI context pointer
- * @return VB2_REQUEST_UI_CONTINUE, or error code on error.
+ * @return VB2_SUCCESS, or error code on error.
*/
vb2_error_t vb2_ui_menu_next(struct vb2_ui_context *ui);
/**
* Select the current menu item.
*
+ * The caller should take care of returning after this function, and should not
+ * continue executing under the assumption that the screen has *not* changed.
+ *
* If the current menu item has an action associated with it, run the action.
* Otherwise, navigate to the target screen. If neither of these are set, then
* selecting the menu item is a no-op.
*
* @param ui UI context pointer
- * @return VB2_REQUEST_UI_CONTINUE, or error code on error.
+ * @return VB2_SUCCESS, or error code on error.
*/
vb2_error_t vb2_ui_menu_select(struct vb2_ui_context *ui);
/*****************************************************************************/
/* Screen navigation functions */
-
+/**
+ * After these functions are called, no assumptions may be made about which
+ * screen is currently displayed, and thus execution should return to ui_loop.
+ * VB2_REQUEST_UI_CONTINUE is returned rather than VB2_SUCCESS, so VB2_TRY can
+ * be used to wrapped to these functions and the callers of these functions.
+ */
/**
* Return back to the previous screen.
*
- * If the current screen is already the root scren, the request is ignored.
+ * The caller should take care of returning after this function, and should not
+ * continue executing under the assumption that the screen has *not* changed.
+ *
+ * If the current screen is already the root screen, the request is ignored.
+ *
+ * TODO(b/157625765): Consider falling into recovery mode (BROKEN screen) when
+ * the current screen is already the root screen.
*
* @param ui UI context pointer
* @return VB2_REQUEST_UI_CONTINUE, or error code on error.
@@ -199,9 +214,16 @@
/**
* Change to the given screen.
*
+ * The caller should take care of returning after this function, and should not
+ * continue executing under the assumption that the screen has *not* changed.
+ *
* If the screen is not found, the request is ignored.
*
+ * TODO(b/157625765): Consider falling into recovery mode (BROKEN screen) when
+ * the target screen is not found.
+ *
* @param ui UI context pointer
+ * @param id Screen from enum vb2_screen
* @return VB2_REQUEST_UI_CONTINUE, or error code on error.
*/
vb2_error_t vb2_ui_screen_change(struct vb2_ui_context *ui, enum vb2_screen id);
@@ -219,7 +241,7 @@
* If a timeout occurs, take the default boot action.
*
* @param ctx Vboot context
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2_developer_menu(struct vb2_context *ctx);
@@ -230,7 +252,7 @@
* encountered last boot. Wait for the user to physically reset or shut down.
*
* @param ctx Vboot context
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2_broken_recovery_menu(struct vb2_context *ctx);
@@ -241,7 +263,7 @@
* navigate the step-by-step recovery, or enter developer mode if allowed.
*
* @param ctx Vboot context
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2_manual_recovery_menu(struct vb2_context *ctx);
@@ -252,7 +274,7 @@
* diagnostic tests of various hardware components.
*
* @param ctx Vboot context
- * @returns VB2_SUCCESS, or non-zero error code.
+ * @return VB2_SUCCESS, or non-zero error code.
*/
vb2_error_t vb2_diagnostic_menu(struct vb2_context *ctx);
diff --git a/firmware/include/tpm2_tss_constants.h b/firmware/include/tpm2_tss_constants.h
index 7374735..becd710 100644
--- a/firmware/include/tpm2_tss_constants.h
+++ b/firmware/include/tpm2_tss_constants.h
@@ -34,9 +34,13 @@
#define TPM2_NV_ReadPublic ((TPM_CC)0x00000169)
#define TPM2_GetCapability ((TPM_CC)0x0000017A)
#define TPM2_GetRandom ((TPM_CC)0x0000017B)
+#define TPM2_PCR_Extend ((TPM_CC)0x00000182)
+
+#define TPM_HT_PCR 0x00
+#define TPM_HT_NV_INDEX 0x01
#define HR_SHIFT 24
-#define TPM_HT_NV_INDEX 0x01
+#define HR_PCR (TPM_HT_PCR << HR_SHIFT)
#define HR_NV_INDEX (TPM_HT_NV_INDEX << HR_SHIFT)
#define TPM_RH_OWNER 0x40000001
#define TPM_RH_PLATFORM 0x4000000C
@@ -110,9 +114,15 @@
#define TPMI_RH_NV_INDEX_TCG_WG_START ((TPMI_RH_NV_INDEX)0x01C40000)
#define TPMI_RH_NV_INDEX_RESERVED_START ((TPMI_RH_NV_INDEX)0x01C90000)
+#define HASH_COUNT 1 /* Only SHA-256 is supported */
+
+/* Table 206 - Defines for SHA256 Hash Values */
+#define SHA256_DIGEST_SIZE 32
+
typedef uint8_t TPMI_YES_NO;
typedef uint32_t TPM_CC;
typedef uint32_t TPM_HANDLE;
+typedef TPM_HANDLE TPMI_DH_PCR;
typedef TPM_HANDLE TPMI_RH_NV_INDEX;
typedef TPM_HANDLE TPMI_RH_ENABLES;
typedef uint32_t TPM_CAP;
@@ -146,6 +156,20 @@
} TPML_TAGGED_TPM_PROPERTY;
typedef union {
+ uint8_t sha256[SHA256_DIGEST_SIZE];
+} TPMU_HA;
+
+typedef struct {
+ TPMI_ALG_HASH hashAlg;
+ TPMU_HA digest;
+} TPMT_HA;
+
+typedef struct {
+ uint32_t count;
+ TPMT_HA digests[HASH_COUNT];
+} TPML_DIGEST_VALUES;
+
+typedef union {
TPML_TAGGED_TPM_PROPERTY tpm_properties;
} TPMU_CAPABILITIES;
@@ -223,6 +247,11 @@
TPM_SU shutdown_type;
};
+struct tpm2_pcr_extend_cmd {
+ TPMI_DH_PCR pcrHandle;
+ TPML_DIGEST_VALUES digests;
+};
+
/* Common command/response header. */
struct tpm_header {
uint16_t tpm_tag;
diff --git a/firmware/include/vboot_api.h b/firmware/include/vboot_api.h
index 739019a..2b1d838 100644
--- a/firmware/include/vboot_api.h
+++ b/firmware/include/vboot_api.h
@@ -44,7 +44,6 @@
*/
typedef void *VbExDiskHandle_t;
-/* Data used only by VbSelectAndLoadKernel() */
typedef struct VbSelectAndLoadKernelParams {
/* Inputs to VbSelectAndLoadKernel() */
/* Destination buffer for kernel (normally at 0x100000 on x86) */
@@ -68,12 +67,6 @@
uint8_t partition_guid[16];
/* Flags set by signer */
uint32_t flags;
- /*
- * TODO: in H2C, all that pretty much just gets passed to the
- * bootloader as KernelBootloaderOptions, though the disk handle is
- * passed as an index instead of a handle. Is that used anymore now
- * that we're passing partition_guid?
- */
} VbSelectAndLoadKernelParams;
/**
@@ -88,13 +81,22 @@
/* Disk access (previously in boot_device.h) */
/* Flags for VbDisk APIs */
+
+/*
+ * Disk selection in the lower 16 bits (where the disk lives), and disk
+ * attributes in the higher 16 bits (extra information about the disk
+ * needed to access it correctly).
+ */
+#define VB_DISK_FLAG_SELECT_MASK 0xffff
+#define VB_DISK_FLAG_ATTRIBUTE_MASK (0xffff << 16)
+
/* Disk is removable. Example removable disks: SD cards, USB keys. */
-#define VB_DISK_FLAG_REMOVABLE 0x00000001
+#define VB_DISK_FLAG_REMOVABLE (1 << 0)
/*
* Disk is fixed. If this flag is present, disk is internal to the system and
* not removable. Example fixed disks: internal SATA SSD, eMMC.
*/
-#define VB_DISK_FLAG_FIXED 0x00000002
+#define VB_DISK_FLAG_FIXED (1 << 1)
/*
* Note that VB_DISK_FLAG_REMOVABLE and VB_DISK_FLAG_FIXED are
* mutually-exclusive for a single disk. VbExDiskGetInfo() may specify both
@@ -130,7 +132,7 @@
* streaming aspects of the disk. If a disk is random-access (i.e.
* not raw NAND) then these fields are equal.
*/
-#define VB_DISK_FLAG_EXTERNAL_GPT 0x00000004
+#define VB_DISK_FLAG_EXTERNAL_GPT (1 << 16)
/* Information on a single disk */
typedef struct VbDiskInfo {
@@ -355,33 +357,6 @@
/* Shutdown requested due to a power button being pressed. */
#define VB_SHUTDOWN_REQUEST_POWER_BUTTON 0x00000004
-enum VbAltFwIndex_t {
- VB_ALTFW_DIAGNOSTIC = -1,
- VB_ALTFW_DEFAULT = 0,
- VB_ALTFW_FIRST = 1,
- VB_ALTFW_SECOND,
- VB_ALTFW_THIRD,
- VB_ALTFW_FOURTH,
- VB_ALTFW_FIFTH,
- VB_ALTFW_SIXTH,
- VB_ALTFW_SEVENTH,
- VB_ALTFW_EIGHTH,
- VB_ALTFW_NINTH,
-};
-
-/**
- * Execute legacy boot option.
- *
- * @param altfw_num Bootloader sequence number to execute. Use
- * 0 to boot the default payload, if any
- * >0 (i.e., positive #) run a payload by # based in altfw/list file
- * <0 (i.e., negative #) run a specific payload by name without using
- * the altfw/list file. Typically payloads in this category will be
- * verified before they are run. Currently these #s are defined:
- * -1 diagnostic payload
- */
-vb2_error_t VbExLegacy(enum VbAltFwIndex_t altfw_num);
-
#ifdef __cplusplus
}
#endif /* __cplusplus */
diff --git a/firmware/lib/include/load_kernel_fw.h b/firmware/lib/include/load_kernel_fw.h
index 9e4db8e..96c8f86 100644
--- a/firmware/lib/include/load_kernel_fw.h
+++ b/firmware/lib/include/load_kernel_fw.h
@@ -11,47 +11,6 @@
#include "vboot_api.h"
-struct vb2_context;
-
-/* Interface provided by verified boot library to BDS */
-
-/* Boot flags for LoadKernel().boot_flags */
-/* GPT is external */
-#define BOOT_FLAG_EXTERNAL_GPT (0x04ULL)
-
-typedef struct LoadKernelParams {
- /* Inputs to LoadKernel() */
- /* Disk handle for current device */
- VbExDiskHandle_t disk_handle;
- /* Bytes per lba sector on current device */
- uint64_t bytes_per_lba;
- /* Number of LBA-addressable sectors on the main device */
- uint64_t streaming_lba_count;
- /* Random-access GPT size */
- uint64_t gpt_lba_count;
- /* Destination buffer for kernel (normally at 0x100000) */
- void *kernel_buffer;
- /* Size of kernel buffer in bytes */
- uint64_t kernel_buffer_size;
- /* Boot flags */
- uint64_t boot_flags;
-
- /*
- * Outputs from LoadKernel(); valid only if LoadKernel() returns
- * LOAD_KERNEL_SUCCESS
- */
- /* Partition number to boot on current device (1...M) */
- uint32_t partition_number;
- /* Address of bootloader image in RAM */
- uint64_t bootloader_address;
- /* Size of bootloader image in bytes */
- uint32_t bootloader_size;
- /* UniquePartitionGuid for boot partition */
- uint8_t partition_guid[16];
- /* Flags passed in by signer */
- uint32_t flags;
-} LoadKernelParams;
-
/**
* Attempt to load the kernel from the current device.
*
@@ -60,6 +19,8 @@
*
* Returns VB2_SUCCESS if successful. If unsuccessful, returns an error code.
*/
-vb2_error_t LoadKernel(struct vb2_context *ctx, LoadKernelParams *params);
+vb2_error_t LoadKernel(struct vb2_context *ctx,
+ VbSelectAndLoadKernelParams *params,
+ VbDiskInfo *disk_info);
#endif /* VBOOT_REFERENCE_LOAD_KERNEL_FW_H_ */
diff --git a/firmware/lib/include/vboot_audio.h b/firmware/lib/include/vboot_audio.h
deleted file mode 100644
index 64cf0a7..0000000
--- a/firmware/lib/include/vboot_audio.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Copyright (c) 2013 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.
- *
- * Delay/beep functions used in dev-mode kernel selection.
- */
-
-#ifndef VBOOT_REFERENCE_VBOOT_AUDIO_H_
-#define VBOOT_REFERENCE_VBOOT_AUDIO_H_
-
-#include "vboot_api.h"
-
-/**
- * Initialization function.
- */
-void vb2_audio_start(struct vb2_context *ctx);
-
-/**
- * Caller should loop without extra delay until this returns false.
- */
-int vb2_audio_looping(void);
-
-#endif /* VBOOT_REFERENCE_VBOOT_AUDIO_H_ */
diff --git a/firmware/lib/include/vboot_kernel.h b/firmware/lib/include/vboot_kernel.h
index 661f0c4..a9dc824 100644
--- a/firmware/lib/include/vboot_kernel.h
+++ b/firmware/lib/include/vboot_kernel.h
@@ -16,84 +16,6 @@
struct vb2_context;
-/* Flags for VbSharedDataKernelPart.flags */
-#define VBSD_LKP_FLAG_KEYBLOCK_VALID 0x01
-
-/* Result codes for VbSharedDataKernelPart.check_result */
-#define VBSD_LKP_CHECK_NOT_DONE 0
-#define VBSD_LKP_CHECK_TOO_SMALL 1
-#define VBSD_LKP_CHECK_READ_START 2
-#define VBSD_LKP_CHECK_KEYBLOCK_SIG 3
-#define VBSD_LKP_CHECK_KEYBLOCK_HASH 4
-#define VBSD_LKP_CHECK_DEV_MISMATCH 5
-#define VBSD_LKP_CHECK_REC_MISMATCH 6
-#define VBSD_LKP_CHECK_KEY_ROLLBACK 7
-#define VBSD_LKP_CHECK_DATA_KEY_PARSE 8
-#define VBSD_LKP_CHECK_VERIFY_PREAMBLE 9
-#define VBSD_LKP_CHECK_KERNEL_ROLLBACK 10
-#define VBSD_LKP_CHECK_PREAMBLE_VALID 11
-/*
- * Body load address check is omitted; this result code is deprecated and not
- * used anywhere in the codebase.
- */
-#define VBSD_LKP_CHECK_BODY_ADDRESS 12
-#define VBSD_LKP_CHECK_BODY_OFFSET 13
-#define VBSD_LKP_CHECK_SELF_SIGNED 14
-#define VBSD_LKP_CHECK_BODY_EXCEEDS_MEM 15
-#define VBSD_LKP_CHECK_BODY_EXCEEDS_PART 16
-#define VBSD_LKP_CHECK_READ_DATA 17
-#define VBSD_LKP_CHECK_VERIFY_DATA 18
-#define VBSD_LKP_CHECK_KERNEL_GOOD 19
-
-/* Information about a single kernel partition check in LoadKernel() */
-typedef struct VbSharedDataKernelPart {
- uint64_t sector_start; /* Start sector of partition */
- uint64_t sector_count; /* Sector count of partition */
- uint32_t combined_version; /* Combined key+kernel version */
- uint8_t gpt_index; /* Index of partition in GPT */
- uint8_t check_result; /* Check result; see VBSD_LKP_CHECK_* */
- uint8_t flags; /* Flags (see VBSD_LKP_FLAG_* */
- uint8_t reserved0; /* Reserved for padding */
-} VbSharedDataKernelPart;
-
-/* Number of kernel partitions to track per call. Must be power of 2. */
-#define VBSD_MAX_KERNEL_PARTS 8
-
-/* Result codes for VbSharedDataKernelCall.check_result */
-#define VBSD_LKC_CHECK_NOT_DONE 0
-#define VBSD_LKC_CHECK_DEV_SWITCH_MISMATCH 1
-#define VBSD_LKC_CHECK_GPT_READ_ERROR 2
-#define VBSD_LKC_CHECK_GPT_PARSE_ERROR 3
-#define VBSD_LKC_CHECK_GOOD_PARTITION 4
-#define VBSD_LKC_CHECK_INVALID_PARTITIONS 5
-#define VBSD_LKC_CHECK_NO_PARTITIONS 6
-
-/* Information about a single call to LoadKernel() */
-typedef struct VbSharedDataKernelCall {
- /* Bottom 32 bits of flags passed in LoadKernelParams.boot_flags */
- uint32_t boot_flags;
- /* Debug flags; see VBSD_LK_FLAG_* */
- uint32_t flags;
- /* Number of sectors on drive */
- uint64_t sector_count;
- /* Sector size in bytes */
- uint32_t sector_size;
- /* Check result; see VBSD_LKC_CHECK_* */
- uint8_t check_result;
- /* Boot mode for LoadKernel(); see VBSD_LK_BOOT_MODE_* constants */
- uint8_t boot_mode;
- /* Test error number, if non-zero */
- uint8_t test_error_num;
- /* Return code from LoadKernel() */
- uint8_t return_code;
- /* Number of kernel partitions found */
- uint8_t kernel_parts_found;
- /* Reserved for padding */
- uint8_t reserved0[7];
- /* Data on kernels */
- VbSharedDataKernelPart parts[VBSD_MAX_KERNEL_PARTS];
-} VbSharedDataKernelCall;
-
/**
* Attempt loading a kernel from the specified type(s) of disks.
*
@@ -101,9 +23,9 @@
* VB2_SUCCESS.
*
* @param ctx Vboot context
- * @param get_info_flags Flags to pass to VbExDiskGetInfo()
+ * @param disk_flags Flags to pass to VbExDiskGetInfo()
* @return VB2_SUCCESS or the most specific VB2_ERROR_LK error.
*/
-vb2_error_t VbTryLoadKernel(struct vb2_context *ctx, uint32_t get_info_flags);
+vb2_error_t VbTryLoadKernel(struct vb2_context *ctx, uint32_t disk_flags);
#endif /* VBOOT_REFERENCE_VBOOT_KERNEL_H_ */
diff --git a/firmware/lib/include/vboot_struct.h b/firmware/lib/include/vboot_struct.h
index caca1f2..8a06892 100644
--- a/firmware/lib/include/vboot_struct.h
+++ b/firmware/lib/include/vboot_struct.h
@@ -53,9 +53,6 @@
/* NvStorage uses 64-byte record, not 16-byte */
#define VBSD_NVDATA_V2 0x00100000
-/* Number of kernel calls to track. Must be power of 2. */
-#define VBSD_MAX_KERNEL_CALLS 4
-
/* Data shared to OS. */
typedef struct VbSharedDataHeader {
/* Fields present in version 1 */
@@ -117,8 +114,8 @@
/* Debugging information from LoadKernel() */
/* Number of times LoadKernel() called */
uint32_t lk_call_count;
- /* Info on calls */
- VbSharedDataKernelCall lk_calls[VBSD_MAX_KERNEL_CALLS];
+ /* Reserved for padding */
+ uint8_t reserved3[896];
/*
* Offset and size of supplemental kernel data. Reserve space for
@@ -137,7 +134,7 @@
/* Recovery reason for current boot */
uint8_t recovery_reason;
/* Reserved for padding */
- uint8_t reserved3[7];
+ uint8_t reserved4[7];
/* Flags from firmware keyblock */
uint64_t fw_keyblock_flags;
/* Kernel TPM version at start of VbSelectAndLoadKernel() */
diff --git a/firmware/lib/include/vboot_test.h b/firmware/lib/include/vboot_test.h
index 9c84909..41e8e5d 100644
--- a/firmware/lib/include/vboot_test.h
+++ b/firmware/lib/include/vboot_test.h
@@ -9,35 +9,9 @@
#define VBOOT_REFERENCE_TEST_API_H_
/****************************************************************************
- * 2rsa.c
- *
- * Internal functions from 2rsa.c that have error conditions we can't trigger
- * from the public APIs. These include checks for bad algorithms where the
- * next call level up already checks for bad algorithms, etc.
- *
- * These functions aren't in 2rsa.h because they're not part of the public
- * APIs.
- */
-struct vb2_public_key;
-int vb2_mont_ge(const struct vb2_public_key *key, uint32_t *a);
-vb2_error_t vb2_check_padding(const uint8_t *sig,
- const struct vb2_public_key *key);
-
-/****************************************************************************
* vboot_api_kernel.c */
-struct LoadKernelParams;
-struct LoadKernelParams *VbApiKernelGetParams(void);
-
-/****************************************************************************
- * 2secdata_kernel.c */
-
-/**
- * Calculate crc8 of kernel secure storage.
- *
- * @param ctx Context pointer
- * @return Calculated crc8 value.
- */
-uint8_t vb2_secdata_kernel_crc(struct vb2_context *ctx);
+struct VbSelectAndLoadKernelParams;
+struct VbSelectAndLoadKernelParams *VbApiKernelGetParams(void);
#endif /* VBOOT_REFERENCE_TEST_API_H_ */
diff --git a/firmware/lib/tpm2_lite/marshaling.c b/firmware/lib/tpm2_lite/marshaling.c
index ef3606b..b9857d4 100644
--- a/firmware/lib/tpm2_lite/marshaling.c
+++ b/firmware/lib/tpm2_lite/marshaling.c
@@ -283,7 +283,7 @@
}
memcpy(*buffer, blob, blob_size);
- buffer_space -= blob_size;
+ *buffer_space -= blob_size;
*buffer = (void *)((uintptr_t)(*buffer) + blob_size);
}
@@ -327,6 +327,7 @@
#define marshal_TPM_HANDLE(a, b, c) marshal_u32(a, b, c)
#define marshal_TPM_SU(a, b, c) marshal_u16(a, b, c)
#define marshal_ALG_ID(a, b, c) marshal_u16(a, b, c)
+#define marshal_TPMI_ALG_HASH(a, b, c) marshal_u16(a, b, c)
/*
* For TPM2B* structures the size field (16 or 32 bits) goes before the data.
@@ -671,6 +672,48 @@
marshal_TPM_SU(buffer, command_body->shutdown_type, buffer_space);
}
+static void marshal_TPMT_HA(void **buffer,
+ TPMT_HA *data,
+ int *buffer_space)
+{
+ if (data->hashAlg != TPM_ALG_SHA256)
+ {
+ VB2_DEBUG("Unsupported TPMT_HA hash algorithm: %#x\n",
+ data->hashAlg);
+ *buffer_space = -1;
+ return;
+ }
+ marshal_TPMI_ALG_HASH(buffer, data->hashAlg, buffer_space);
+ /* We only support SHA256 now. */
+ marshal_blob(buffer, data->digest.sha256,
+ SHA256_DIGEST_SIZE, buffer_space);
+}
+
+static void marshal_TPML_DIGEST_VALUES(void **buffer,
+ TPML_DIGEST_VALUES *data,
+ int *buffer_space)
+{
+ int i;
+
+ marshal_u32(buffer, data->count, buffer_space);
+ for (i = 0; i < data->count; i++)
+ marshal_TPMT_HA(buffer, &data->digests[i], buffer_space);
+}
+
+static void marshal_pcr_extend(void **buffer,
+ struct tpm2_pcr_extend_cmd *command_body,
+ int *buffer_space)
+{
+ struct tpm2_session_header session_header;
+
+ tpm_tag = TPM_ST_SESSIONS;
+ marshal_TPM_HANDLE(buffer, command_body->pcrHandle, buffer_space);
+ memset(&session_header, 0, sizeof(session_header));
+ session_header.session_handle = TPM_RS_PW;
+ marshal_session_header(buffer, &session_header, buffer_space);
+ marshal_TPML_DIGEST_VALUES(buffer, &command_body->digests, buffer_space);
+}
+
int tpm_marshal_command(TPM_CC command, void *tpm_command_body,
void *buffer, int buffer_size)
{
@@ -740,6 +783,10 @@
marshal_shutdown(&cmd_body, tpm_command_body, &body_size);
break;
+ case TPM2_PCR_Extend:
+ marshal_pcr_extend(&cmd_body, tpm_command_body, &body_size);
+ break;
+
default:
body_size = -1;
VB2_DEBUG("Request to marshal unsupported command %#x\n",
@@ -811,6 +858,7 @@
case TPM2_Shutdown:
case TPM2_NV_DefineSpace:
case TPM2_NV_UndefineSpace:
+ case TPM2_PCR_Extend:
/* Session data included in response can be safely ignored. */
cr_size = 0;
break;
diff --git a/firmware/lib/tpm2_lite/tlcl.c b/firmware/lib/tpm2_lite/tlcl.c
index e4695d1..b91119b 100644
--- a/firmware/lib/tpm2_lite/tlcl.c
+++ b/firmware/lib/tpm2_lite/tlcl.c
@@ -314,8 +314,15 @@
uint32_t TlclExtend(int pcr_num, const uint8_t *in_digest, uint8_t *out_digest)
{
- VB2_DEBUG("NOT YET IMPLEMENTED\n");
- return TPM_SUCCESS;
+ struct tpm2_pcr_extend_cmd pcr_ext_cmd;
+
+ pcr_ext_cmd.pcrHandle = HR_PCR + pcr_num;
+ pcr_ext_cmd.digests.count = 1;
+ pcr_ext_cmd.digests.digests[0].hashAlg = TPM_ALG_SHA256;
+ memcpy(pcr_ext_cmd.digests.digests[0].digest.sha256, in_digest,
+ sizeof(pcr_ext_cmd.digests.digests[0].digest.sha256));
+
+ return tpm_get_response_code(TPM2_PCR_Extend, &pcr_ext_cmd);
}
diff --git a/firmware/lib/vboot_api_kernel.c b/firmware/lib/vboot_api_kernel.c
index e2d1431..93de040 100644
--- a/firmware/lib/vboot_api_kernel.c
+++ b/firmware/lib/vboot_api_kernel.c
@@ -15,18 +15,17 @@
#include "2sysincludes.h"
#include "2ui.h"
#include "load_kernel_fw.h"
-#include "vb2_common.h"
#include "vboot_api.h"
#include "vboot_kernel.h"
#include "vboot_struct.h"
#include "vboot_test.h"
/* Global variables */
-static LoadKernelParams lkp;
+static VbSelectAndLoadKernelParams lkp;
#ifdef CHROMEOS_ENVIRONMENT
/* Global variable accessor for unit tests */
-struct LoadKernelParams *VbApiKernelGetParams(void)
+struct VbSelectAndLoadKernelParams *VbApiKernelGetParams(void)
{
return &lkp;
}
@@ -54,8 +53,18 @@
return VB2_SUCCESS;
}
+static int is_valid_disk(VbDiskInfo *info, uint32_t disk_flags)
+{
+ return info->bytes_per_lba >= 512 &&
+ (info->bytes_per_lba & (info->bytes_per_lba - 1)) == 0 &&
+ info->lba_count >= 16 &&
+ (info->flags & disk_flags & VB_DISK_FLAG_SELECT_MASK) &&
+ ((info->flags & VB_DISK_FLAG_SELECT_MASK) &
+ ((info->flags & VB_DISK_FLAG_SELECT_MASK) - 1)) == 0;
+}
+
test_mockable
-vb2_error_t VbTryLoadKernel(struct vb2_context *ctx, uint32_t get_info_flags)
+vb2_error_t VbTryLoadKernel(struct vb2_context *ctx, uint32_t disk_flags)
{
vb2_error_t rv = VB2_ERROR_LK_NO_DISK_FOUND;
VbDiskInfo* disk_info = NULL;
@@ -65,26 +74,14 @@
lkp.disk_handle = NULL;
/* Find disks */
- if (VB2_SUCCESS != VbExDiskGetInfo(&disk_info, &disk_count,
- get_info_flags))
+ if (VB2_SUCCESS != VbExDiskGetInfo(&disk_info, &disk_count, disk_flags))
disk_count = 0;
/* Loop over disks */
for (i = 0; i < disk_count; i++) {
VB2_DEBUG("trying disk %d\n", (int)i);
- /*
- * Validity-check what we can. FWIW, VbTryLoadKernel() is always
- * called with only a single bit set in get_info_flags.
- *
- * Ensure that we got a partition with only the flags we asked
- * for.
- */
- if (disk_info[i].bytes_per_lba < 512 ||
- (disk_info[i].bytes_per_lba &
- (disk_info[i].bytes_per_lba - 1)) != 0 ||
- 16 > disk_info[i].lba_count ||
- get_info_flags != (disk_info[i].flags &
- ~VB_DISK_FLAG_EXTERNAL_GPT)) {
+
+ if (!is_valid_disk(&disk_info[i], disk_flags)) {
VB2_DEBUG(" skipping: bytes_per_lba=%" PRIu64
" lba_count=%" PRIu64 " flags=%#x\n",
disk_info[i].bytes_per_lba,
@@ -92,20 +89,14 @@
disk_info[i].flags);
continue;
}
- lkp.disk_handle = disk_info[i].handle;
- lkp.bytes_per_lba = disk_info[i].bytes_per_lba;
- lkp.gpt_lba_count = disk_info[i].lba_count;
- lkp.streaming_lba_count = disk_info[i].streaming_lba_count
- ?: lkp.gpt_lba_count;
- lkp.boot_flags |= disk_info[i].flags & VB_DISK_FLAG_EXTERNAL_GPT
- ? BOOT_FLAG_EXTERNAL_GPT : 0;
- vb2_error_t new_rv = LoadKernel(ctx, &lkp);
+ lkp.disk_handle = disk_info[i].handle;
+ vb2_error_t new_rv = LoadKernel(ctx, &lkp, &disk_info[i]);
VB2_DEBUG("LoadKernel() = %#x\n", new_rv);
/* Stop now if we found a kernel. */
if (VB2_SUCCESS == new_rv) {
- VbExDiskFreeInfo(disk_info, lkp.disk_handle);
+ VbExDiskFreeInfo(disk_info, disk_info[i].handle);
return VB2_SUCCESS;
}
@@ -115,7 +106,8 @@
}
/* If we drop out of the loop, we didn't find any usable kernel. */
- if (get_info_flags & VB_DISK_FLAG_FIXED) {
+ if (!(ctx->flags & VB2_CONTEXT_RECOVERY_MODE) &&
+ !(ctx->flags & VB2_CONTEXT_DEVELOPER_MODE)) {
switch (rv) {
case VB2_ERROR_LK_INVALID_KERNEL_FOUND:
vb2api_fail(ctx, VB2_RECOVERY_RW_INVALID_OS, rv);
@@ -236,7 +228,13 @@
VB2_TRY(vb2_broken_recovery_menu(ctx));
} else if (DIAGNOSTIC_UI && vb2api_diagnostic_ui_enabled(ctx) &&
vb2_nv_get(ctx, VB2_NV_DIAG_REQUEST)) {
+ /*
+ * Need to clear the request flag and commit nvdata changes
+ * immediately to avoid booting back into diagnostic tool when a
+ * forced system reset occurs.
+ */
vb2_nv_set(ctx, VB2_NV_DIAG_REQUEST, 0);
+ vb2ex_commit_data(ctx);
/* Diagnostic boot. This has UI. */
VB2_TRY(vb2_diagnostic_menu(ctx));
diff --git a/firmware/lib/vboot_audio.c b/firmware/lib/vboot_audio.c
deleted file mode 100644
index c2c599b..0000000
--- a/firmware/lib/vboot_audio.c
+++ /dev/null
@@ -1,57 +0,0 @@
-/* Copyright (c) 2013 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.
- *
- * Delay/beep functions used in dev-mode kernel selection.
- */
-
-#include "2api.h"
-#include "2common.h"
-#include "2misc.h"
-#include "2sysincludes.h"
-#include "vboot_api.h"
-#include "vboot_audio.h"
-
-int audio_open_count = 0; /* Times audio has been opened */
-static int audio_use_short; /* Use short delay? */
-static uint32_t open_time; /* Time of last open */
-static int beep_count; /* Number of beeps so far */
-
-/**
- * Initialization function.
- */
-void vb2_audio_start(struct vb2_context *ctx)
-{
- open_time = vb2ex_mtime(); /* "zero" starts now */
- beep_count = 0;
-
- if (vb2api_use_short_dev_screen_delay(ctx) &&
- (audio_open_count++ == 0)) {
- VB2_DEBUG("vb2_audio_start() - using short dev screen delay\n");
- audio_use_short = 1;
- } else {
- audio_use_short = 0;
- }
-}
-
-/**
- * Caller should loop without extra delay until this returns false.
- */
-int vb2_audio_looping(void)
-{
- uint32_t now = vb2ex_mtime() - open_time;
-
- /* If we're using short delay, wait 2 seconds and don't beep */
- if (audio_use_short)
- return now < 2 * VB2_MSEC_PER_SEC;
-
- /* Otherwise, beep at 20 and 20.5 seconds */
- if ((beep_count == 0 && now > 20 * VB2_MSEC_PER_SEC) ||
- (beep_count == 1 && now > 20 * VB2_MSEC_PER_SEC + 500)) {
- vb2ex_beep(250, 400);
- beep_count++;
- }
-
- /* Stop after 30 seconds */
- return (now < 30 * VB2_MSEC_PER_SEC);
-}
diff --git a/firmware/lib/vboot_kernel.c b/firmware/lib/vboot_kernel.c
index 6a0b0f3..05458b0 100644
--- a/firmware/lib/vboot_kernel.c
+++ b/firmware/lib/vboot_kernel.c
@@ -9,64 +9,68 @@
#include "2common.h"
#include "2misc.h"
#include "2nvstorage.h"
-#include "2rsa.h"
-#include "2sha.h"
+#include "2packed_key.h"
#include "2secdata.h"
#include "2sysincludes.h"
#include "cgptlib.h"
#include "cgptlib_internal.h"
#include "gpt_misc.h"
#include "load_kernel_fw.h"
-#include "vb2_common.h"
#include "vboot_api.h"
-#include "vboot_kernel.h"
-#include "vboot_struct.h"
#define LOWEST_TPM_VERSION 0xffffffff
-enum vboot_mode {
- kBootRecovery = 0, /* Recovery firmware, any dev switch position */
- kBootNormal = 1, /* Normal boot - kernel must be verified */
- kBootDev = 2 /* Developer boot - self-signed kernel ok */
+enum vb2_boot_mode {
+ /* Normal boot: kernel must be verified. */
+ VB2_BOOT_MODE_NORMAL = 0,
+
+ /* Recovery boot, regardless of dev mode state. */
+ VB2_BOOT_MODE_RECOVERY = 1,
+
+ /* Developer boot: self-signed kernel okay. */
+ VB2_BOOT_MODE_DEVELOPER = 2,
};
/**
- * Return the boot mode based on the parameters.
+ * Return the current boot mode (normal, recovery, or dev).
*
- * @param params Load kernel parameters
- * @return The current boot mode.
+ * @param ctx Vboot context
+ * @return Current boot mode (see vb2_boot_mode enum).
*/
-static enum vboot_mode get_kernel_boot_mode(struct vb2_context *ctx)
+static enum vb2_boot_mode get_boot_mode(struct vb2_context *ctx)
{
if (ctx->flags & VB2_CONTEXT_RECOVERY_MODE)
- return kBootRecovery;
+ return VB2_BOOT_MODE_RECOVERY;
if (ctx->flags & VB2_CONTEXT_DEVELOPER_MODE)
- return kBootDev;
+ return VB2_BOOT_MODE_DEVELOPER;
- return kBootNormal;
-};
+ return VB2_BOOT_MODE_NORMAL;
+}
/**
- * Check if the parameters require an officially signed OS.
+ * Check if a valid keyblock is required.
*
- * @param params Load kernel parameters
- * @return 1 if official OS required; 0 if self-signed kernels are ok
+ * @param ctx Vboot context
+ * @return 1 if valid keyblock required (officially signed kernel);
+ * 0 if valid hash is enough (self-signed kernel).
*/
-static int require_official_os(struct vb2_context *ctx,
- const LoadKernelParams *params)
+static int need_valid_keyblock(struct vb2_context *ctx)
{
/* Normal and recovery modes always require official OS */
- if (get_kernel_boot_mode(ctx) != kBootDev)
+ if (get_boot_mode(ctx) != VB2_BOOT_MODE_DEVELOPER)
return 1;
- /* FWMP can require developer mode to use official OS */
+ /* FWMP can require developer mode to use signed kernels */
if (vb2_secdata_fwmp_get_flag(
ctx, VB2_SECDATA_FWMP_DEV_ENABLE_OFFICIAL_ONLY))
return 1;
- /* Developer can request official OS via nvstorage */
- return vb2_nv_get(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY);
+ /* Developers may require signed kernels */
+ if (vb2_nv_get(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY))
+ return 1;
+
+ return 0;
}
/**
@@ -111,53 +115,109 @@
}
/**
+ * Verify developer mode key hash.
+ *
+ * @param ctx Vboot context
+ * @param keyblock Keyblock to verify
+ * @return VB2_SUCCESS, or non-zero error code.
+ */
+static vb2_error_t vb2_verify_kernel_dev_key_hash(
+ struct vb2_context *ctx, struct vb2_keyblock *keyblock)
+{
+ struct vb2_packed_key *key = &keyblock->data_key;
+ uint8_t *buf = ((uint8_t *)key) + key->key_offset;
+ uint32_t buflen = key->key_size;
+ uint8_t digest[VB2_SHA256_DIGEST_SIZE];
+
+ VB2_DEBUG("Checking developer key hash.\n");
+ VB2_TRY(vb2_digest_buffer(buf, buflen, VB2_HASH_SHA256, digest,
+ sizeof(digest)));
+
+ uint8_t *fwmp_dev_key_hash =
+ vb2_secdata_fwmp_get_dev_key_hash(ctx);
+ if (fwmp_dev_key_hash == NULL) {
+ VB2_DEBUG("Couldn't retrieve developer key hash.\n");
+ return VB2_ERROR_KERNEL_KEYBLOCK_DEV_KEY_HASH;
+ }
+
+ if (vb2_safe_memcmp(digest, fwmp_dev_key_hash,
+ VB2_SHA256_DIGEST_SIZE)) {
+ int i;
+
+ VB2_DEBUG("Wrong developer key hash.\n");
+ VB2_DEBUG("Want: ");
+ for (i = 0; i < VB2_SHA256_DIGEST_SIZE; i++)
+ VB2_DEBUG_RAW("%02x ", fwmp_dev_key_hash[i]);
+ VB2_DEBUG_RAW("\n");
+ VB2_DEBUG("Got: ");
+ for (i = 0; i < VB2_SHA256_DIGEST_SIZE; i++)
+ VB2_DEBUG_RAW("%02x ", digest[i]);
+ VB2_DEBUG_RAW("\n");
+
+ return VB2_ERROR_KERNEL_KEYBLOCK_DEV_KEY_HASH;
+ }
+
+ return VB2_SUCCESS;
+}
+
+/**
* Verify a kernel vblock.
*
* @param kbuf Buffer containing the vblock
* @param kbuf_size Size of the buffer in bytes
- * @param kernel_subkey Packed kernel subkey to use in validating keyblock
- * @param params Load kernel parameters
- * @param min_version Minimum kernel version
- * @param shpart Destination for verification results
* @param wb Work buffer. Must be at least
* VB2_VERIFY_KERNEL_PREAMBLE_WORKBUF_BYTES bytes.
* @return VB2_SUCCESS, or non-zero error code.
*/
static vb2_error_t vb2_verify_kernel_vblock(
struct vb2_context *ctx, uint8_t *kbuf, uint32_t kbuf_size,
- const struct vb2_packed_key *kernel_subkey,
- const LoadKernelParams *params, uint32_t min_version,
- VbSharedDataKernelPart *shpart, struct vb2_workbuf *wb)
+ struct vb2_workbuf *wb)
{
- /* Unpack kernel subkey */
- struct vb2_public_key kernel_subkey2;
- if (VB2_SUCCESS != vb2_unpack_key(&kernel_subkey2, kernel_subkey)) {
- VB2_DEBUG("Unable to unpack kernel subkey\n");
- return VB2_ERROR_VBLOCK_KERNEL_SUBKEY;
- }
+ struct vb2_shared_data *sd = vb2_get_sd(ctx);
+
+ uint8_t *key_data;
+ uint32_t key_size;
+ struct vb2_public_key kernel_key;
+
+ int need_keyblock_valid = need_valid_keyblock(ctx);
+ int keyblock_valid = 1; /* Assume valid */
+
+ vb2_error_t rv;
+
+ /* Locate key to verify kernel. This will either be a recovery key, or
+ a kernel subkey passed from firmware verification. */
+ key_data = vb2_member_of(sd, sd->kernel_key_offset);
+ key_size = sd->kernel_key_size;
+ VB2_TRY(vb2_unpack_key_buffer(&kernel_key, key_data, key_size));
+
+ if (vb2_hwcrypto_allowed(ctx))
+ kernel_key.allow_hwcrypto = 1;
+
+ /*
+ * Clear any previous keyblock-valid flag (for example, from a previous
+ * kernel where the keyblock was signed but the preamble failed
+ * verification).
+ */
+ sd->flags &= ~VB2_SD_FLAG_KERNEL_SIGNED;
/* Verify the keyblock. */
- int keyblock_valid = 1; /* Assume valid */
struct vb2_keyblock *keyblock = get_keyblock(kbuf);
- if (VB2_SUCCESS != vb2_verify_keyblock(keyblock, kbuf_size,
- &kernel_subkey2, wb)) {
+ rv = vb2_verify_keyblock(keyblock, kbuf_size, &kernel_key, wb);
+ if (rv) {
VB2_DEBUG("Verifying keyblock signature failed.\n");
- shpart->check_result = VBSD_LKP_CHECK_KEYBLOCK_SIG;
keyblock_valid = 0;
/* Check if we must have an officially signed kernel */
- if (require_official_os(ctx, params)) {
+ if (need_keyblock_valid) {
VB2_DEBUG("Self-signed kernels not enabled.\n");
- shpart->check_result = VBSD_LKP_CHECK_SELF_SIGNED;
- return VB2_ERROR_VBLOCK_SELF_SIGNED;
+ return rv;
}
/* Otherwise, allow the kernel if the keyblock hash is valid */
- if (VB2_SUCCESS !=
- vb2_verify_keyblock_hash(keyblock, kbuf_size, wb)) {
+ rv = vb2_verify_keyblock_hash(keyblock, kbuf_size, wb);
+ if (rv) {
VB2_DEBUG("Verifying keyblock hash failed.\n");
- shpart->check_result = VBSD_LKP_CHECK_KEYBLOCK_HASH;
- return VB2_ERROR_VBLOCK_KEYBLOCK_HASH;
+ return rv;
}
}
@@ -167,126 +227,97 @@
VB2_KEYBLOCK_FLAG_DEVELOPER_1 :
VB2_KEYBLOCK_FLAG_DEVELOPER_0))) {
VB2_DEBUG("Keyblock developer flag mismatch.\n");
- shpart->check_result = VBSD_LKP_CHECK_DEV_MISMATCH;
keyblock_valid = 0;
+ if (need_keyblock_valid)
+ return VB2_ERROR_KERNEL_KEYBLOCK_DEV_FLAG;
}
if (!(keyblock->keyblock_flags &
((ctx->flags & VB2_CONTEXT_RECOVERY_MODE) ?
VB2_KEYBLOCK_FLAG_RECOVERY_1 :
VB2_KEYBLOCK_FLAG_RECOVERY_0))) {
VB2_DEBUG("Keyblock recovery flag mismatch.\n");
- shpart->check_result = VBSD_LKP_CHECK_REC_MISMATCH;
keyblock_valid = 0;
+ if (need_keyblock_valid)
+ return VB2_ERROR_KERNEL_KEYBLOCK_REC_FLAG;
}
/* Check for rollback of key version except in recovery mode. */
- enum vboot_mode boot_mode = get_kernel_boot_mode(ctx);
+ enum vb2_boot_mode boot_mode = get_boot_mode(ctx);
uint32_t key_version = keyblock->data_key.key_version;
- if (kBootRecovery != boot_mode) {
- if (key_version < (min_version >> 16)) {
- VB2_DEBUG("Key version too old.\n");
- shpart->check_result = VBSD_LKP_CHECK_KEY_ROLLBACK;
+ if (boot_mode != VB2_BOOT_MODE_RECOVERY) {
+ if (key_version < (sd->kernel_version_secdata >> 16)) {
keyblock_valid = 0;
+ if (need_keyblock_valid) {
+ VB2_DEBUG("Key version too old.\n");
+ return VB2_ERROR_KERNEL_KEYBLOCK_VERSION_ROLLBACK;
+ }
}
- if (key_version > 0xFFFF) {
+ if (key_version > VB2_MAX_KEY_VERSION) {
/*
* Key version is stored in 16 bits in the TPM, so key
* versions greater than 0xFFFF can't be stored
* properly.
*/
VB2_DEBUG("Key version > 0xFFFF.\n");
- shpart->check_result = VBSD_LKP_CHECK_KEY_ROLLBACK;
keyblock_valid = 0;
+ if (need_keyblock_valid)
+ return VB2_ERROR_KERNEL_KEYBLOCK_VERSION_RANGE;
}
}
- /* If not in developer mode, keyblock required to be valid. */
- if (kBootDev != boot_mode && !keyblock_valid) {
- VB2_DEBUG("Keyblock is invalid.\n");
- return VB2_ERROR_VBLOCK_KEYBLOCK;
- }
-
- /* If in developer mode and using key hash, check it */
- if ((kBootDev == boot_mode) &&
+ /* If in developer mode and using key hash, check it. */
+ if (boot_mode == VB2_BOOT_MODE_DEVELOPER &&
vb2_secdata_fwmp_get_flag(ctx, VB2_SECDATA_FWMP_DEV_USE_KEY_HASH)) {
- struct vb2_packed_key *key = &keyblock->data_key;
- uint8_t *buf = ((uint8_t *)key) + key->key_offset;
- uint32_t buflen = key->key_size;
- uint8_t digest[VB2_SHA256_DIGEST_SIZE];
-
- VB2_DEBUG("Checking developer key hash.\n");
- vb2_digest_buffer(buf, buflen, VB2_HASH_SHA256,
- digest, sizeof(digest));
-
- uint8_t *fwmp_dev_key_hash =
- vb2_secdata_fwmp_get_dev_key_hash(ctx);
- if (fwmp_dev_key_hash == NULL) {
- VB2_DEBUG("Couldn't retrieve developer key hash.\n");
- return VB2_ERROR_VBLOCK_DEV_KEY_HASH;
- }
-
- if (0 != vb2_safe_memcmp(digest, fwmp_dev_key_hash,
- VB2_SHA256_DIGEST_SIZE)) {
- int i;
-
- VB2_DEBUG("Wrong developer key hash.\n");
- VB2_DEBUG("Want: ");
- for (i = 0; i < VB2_SHA256_DIGEST_SIZE; i++)
- VB2_DEBUG("%02x", fwmp_dev_key_hash[i]);
- VB2_DEBUG("\nGot: ");
- for (i = 0; i < VB2_SHA256_DIGEST_SIZE; i++)
- VB2_DEBUG("%02x", digest[i]);
- VB2_DEBUG("\n");
-
- return VB2_ERROR_VBLOCK_DEV_KEY_HASH;
- }
+ VB2_TRY(vb2_verify_kernel_dev_key_hash(ctx, keyblock));
}
+ /*
+ * At this point, we've checked everything. The kernel keyblock is at
+ * least self-consistent, and has either a valid signature or a valid
+ * hash. Track if it had a valid signature (that is, would we have
+ * been willing to boot it even if developer mode was off).
+ */
+ if (keyblock_valid)
+ sd->flags |= VB2_SD_FLAG_KERNEL_SIGNED;
+
/* Get key for preamble verification from the keyblock. */
struct vb2_public_key data_key;
- if (VB2_SUCCESS != vb2_unpack_key(&data_key, &keyblock->data_key)) {
+ rv = vb2_unpack_key(&data_key, &keyblock->data_key);
+ if (rv) {
VB2_DEBUG("Unable to unpack kernel data key\n");
- shpart->check_result = VBSD_LKP_CHECK_DATA_KEY_PARSE;
- return VB2_ERROR_UNKNOWN;
+ return rv;
}
/* Verify the preamble, which follows the keyblock */
struct vb2_kernel_preamble *preamble = get_preamble(kbuf);
- if (VB2_SUCCESS !=
- vb2_verify_kernel_preamble(preamble,
- kbuf_size - keyblock->keyblock_size,
- &data_key,
- wb)) {
+ rv = vb2_verify_kernel_preamble(preamble,
+ kbuf_size - keyblock->keyblock_size,
+ &data_key,
+ wb);
+ if (rv) {
VB2_DEBUG("Preamble verification failed.\n");
- shpart->check_result = VBSD_LKP_CHECK_VERIFY_PREAMBLE;
- return VB2_ERROR_UNKNOWN;
+ return rv;
}
/*
- * If the keyblock is valid and we're not in recovery mode, check for
- * rollback of the kernel version.
+ * Kernel preamble version is the lower 16 bits of the composite
+ * kernel version.
*/
- uint32_t combined_version = (key_version << 16) |
- (preamble->kernel_version & 0xFFFF);
- shpart->combined_version = combined_version;
- if (keyblock_valid && kBootRecovery != boot_mode) {
- if (combined_version < min_version) {
- VB2_DEBUG("Kernel version too low.\n");
- shpart->check_result = VBSD_LKP_CHECK_KERNEL_ROLLBACK;
- /*
- * If not in developer mode, kernel version
- * must be valid.
- */
- if (kBootDev != boot_mode)
- return VB2_ERROR_UNKNOWN;
- }
+ if (preamble->kernel_version > VB2_MAX_PREAMBLE_VERSION)
+ return VB2_ERROR_KERNEL_PREAMBLE_VERSION_RANGE;
+
+ /* Combine with the key version. */
+ sd->kernel_version = key_version << 16 | preamble->kernel_version;
+
+ /* If not in recovery mode, check for rollback of the kernel version. */
+ if (need_keyblock_valid &&
+ boot_mode != VB2_BOOT_MODE_RECOVERY &&
+ sd->kernel_version < sd->kernel_version_secdata) {
+ VB2_DEBUG("Kernel version too low.\n");
+ return VB2_ERROR_KERNEL_PREAMBLE_VERSION_ROLLBACK;
}
VB2_DEBUG("Kernel preamble is good.\n");
- shpart->check_result = VBSD_LKP_CHECK_PREAMBLE_VALID;
- if (keyblock_valid)
- shpart->flags |= VBSD_LKP_FLAG_KEYBLOCK_VALID;
-
return VB2_SUCCESS;
}
@@ -306,39 +337,32 @@
*
* @param ctx Vboot context
* @param stream Stream to load kernel from
- * @param kernel_subkey Key to use to verify vblock
* @param flags Flags (one or more of vb2_load_partition_flags)
* @param params Load-kernel parameters
- * @param min_version Minimum kernel version from TPM
- * @param shpart Destination for verification results
- * @param wb Workbuf for data storage
* @return VB2_SUCCESS, or non-zero error code.
*/
static vb2_error_t vb2_load_partition(
- struct vb2_context *ctx, VbExStream_t stream,
- const struct vb2_packed_key *kernel_subkey, uint32_t flags,
- LoadKernelParams *params, uint32_t min_version,
- VbSharedDataKernelPart *shpart, struct vb2_workbuf *wb)
+ struct vb2_context *ctx, VbExStream_t stream, uint32_t flags,
+ VbSelectAndLoadKernelParams *params)
{
uint32_t read_ms = 0, start_ts;
- struct vb2_workbuf wblocal = *wb;
+ struct vb2_workbuf wb;
+
+ vb2_workbuf_from_ctx(ctx, &wb);
/* Allocate kernel header buffer in workbuf */
- uint8_t *kbuf = vb2_workbuf_alloc(&wblocal, KBUF_SIZE);
+ uint8_t *kbuf = vb2_workbuf_alloc(&wb, KBUF_SIZE);
if (!kbuf)
return VB2_ERROR_LOAD_PARTITION_WORKBUF;
start_ts = vb2ex_mtime();
if (VbExStreamRead(stream, KBUF_SIZE, kbuf)) {
VB2_DEBUG("Unable to read start of partition.\n");
- shpart->check_result = VBSD_LKP_CHECK_READ_START;
return VB2_ERROR_LOAD_PARTITION_READ_VBLOCK;
}
read_ms += vb2ex_mtime() - start_ts;
- if (VB2_SUCCESS !=
- vb2_verify_kernel_vblock(ctx, kbuf, KBUF_SIZE, kernel_subkey,
- params, min_version, shpart, &wblocal)) {
+ if (vb2_verify_kernel_vblock(ctx, kbuf, KBUF_SIZE, &wb)) {
return VB2_ERROR_LOAD_PARTITION_VERIFY_VBLOCK;
}
@@ -357,7 +381,6 @@
*/
uint32_t body_offset = get_body_offset(kbuf);
if (body_offset > KBUF_SIZE) {
- shpart->check_result = VBSD_LKP_CHECK_BODY_OFFSET;
VB2_DEBUG("Kernel body offset is %u > 64KB.\n", body_offset);
return VB2_ERROR_LOAD_PARTITION_BODY_OFFSET;
}
@@ -370,7 +393,6 @@
kernbuf_size = preamble->body_signature.data_size;
} else if (preamble->body_signature.data_size > kernbuf_size) {
VB2_DEBUG("Kernel body doesn't fit in memory.\n");
- shpart->check_result = VBSD_LKP_CHECK_BODY_EXCEEDS_MEM;
return VB2_ERROR_LOAD_PARTITION_BODY_SIZE;
}
@@ -392,7 +414,6 @@
start_ts = vb2ex_mtime();
if (body_toread && VbExStreamRead(stream, body_toread, body_readptr)) {
VB2_DEBUG("Unable to read kernel data.\n");
- shpart->check_result = VBSD_LKP_CHECK_READ_DATA;
return VB2_ERROR_LOAD_PARTITION_READ_BODY;
}
read_ms += vb2ex_mtime() - start_ts;
@@ -405,24 +426,23 @@
/* Get key for preamble/data verification from the keyblock. */
struct vb2_public_key data_key;
- if (VB2_SUCCESS != vb2_unpack_key(&data_key, &keyblock->data_key)) {
+ if (vb2_unpack_key(&data_key, &keyblock->data_key)) {
VB2_DEBUG("Unable to unpack kernel data key\n");
- shpart->check_result = VBSD_LKP_CHECK_DATA_KEY_PARSE;
return VB2_ERROR_LOAD_PARTITION_DATA_KEY;
}
+ if (vb2_hwcrypto_allowed(ctx))
+ data_key.allow_hwcrypto = 1;
+
/* Verify kernel data */
- if (VB2_SUCCESS != vb2_verify_data(kernbuf, kernbuf_size,
- &preamble->body_signature,
- &data_key, &wblocal)) {
+ if (vb2_verify_data(kernbuf, kernbuf_size, &preamble->body_signature,
+ &data_key, &wb)) {
VB2_DEBUG("Kernel data verification failed.\n");
- shpart->check_result = VBSD_LKP_CHECK_VERIFY_DATA;
return VB2_ERROR_LOAD_PARTITION_VERIFY_BODY;
}
/* If we're still here, the kernel is valid */
VB2_DEBUG("Partition is good.\n");
- shpart->check_result = VBSD_LKP_CHECK_KERNEL_GOOD;
/* Save kernel data back to parameters */
params->bootloader_address = preamble->bootloader_address;
@@ -436,94 +456,57 @@
return VB2_SUCCESS;
}
-vb2_error_t LoadKernel(struct vb2_context *ctx, LoadKernelParams *params)
+vb2_error_t LoadKernel(struct vb2_context *ctx,
+ VbSelectAndLoadKernelParams *params,
+ VbDiskInfo *disk_info)
{
struct vb2_shared_data *sd = vb2_get_sd(ctx);
- struct vb2_workbuf wb;
- VbSharedDataKernelCall shcall;
int found_partitions = 0;
uint32_t lowest_version = LOWEST_TPM_VERSION;
vb2_error_t rv;
- vb2_workbuf_from_ctx(ctx, &wb);
-
/* Clear output params in case we fail */
params->partition_number = 0;
params->bootloader_address = 0;
params->bootloader_size = 0;
params->flags = 0;
- /*
- * Set up tracking for this call. This wraps around if called many
- * times, so we need to initialize the call entry each time.
- */
- memset(&shcall, 0, sizeof(shcall));
- shcall.boot_flags = (uint32_t)params->boot_flags;
- shcall.boot_mode = get_kernel_boot_mode(ctx);
- shcall.sector_size = (uint32_t)params->bytes_per_lba;
- shcall.sector_count = params->streaming_lba_count;
-
- /* Locate key to verify kernel. This will either be a recovery key, or
- a kernel subkey passed from firmware verification. */
- struct vb2_packed_key *kernel_subkey =
- vb2_member_of(sd, sd->kernel_key_offset);
-
/* Read GPT data */
GptData gpt;
- gpt.sector_bytes = (uint32_t)params->bytes_per_lba;
- gpt.streaming_drive_sectors = params->streaming_lba_count;
- gpt.gpt_drive_sectors = params->gpt_lba_count;
- gpt.flags = params->boot_flags & BOOT_FLAG_EXTERNAL_GPT
+ gpt.sector_bytes = (uint32_t)disk_info->bytes_per_lba;
+ gpt.streaming_drive_sectors = disk_info->streaming_lba_count
+ ?: disk_info->lba_count;
+ gpt.gpt_drive_sectors = disk_info->lba_count;
+ gpt.flags = disk_info->flags & VB_DISK_FLAG_EXTERNAL_GPT
? GPT_FLAG_EXTERNAL : 0;
- if (0 != AllocAndReadGptData(params->disk_handle, &gpt)) {
+ if (AllocAndReadGptData(disk_info->handle, &gpt)) {
VB2_DEBUG("Unable to read GPT data\n");
- shcall.check_result = VBSD_LKC_CHECK_GPT_READ_ERROR;
goto gpt_done;
}
/* Initialize GPT library */
- if (GPT_SUCCESS != GptInit(&gpt)) {
+ if (GptInit(&gpt)) {
VB2_DEBUG("Error parsing GPT\n");
- shcall.check_result = VBSD_LKC_CHECK_GPT_PARSE_ERROR;
goto gpt_done;
}
/* Loop over candidate kernel partitions */
uint64_t part_start, part_size;
- while (GPT_SUCCESS ==
- GptNextKernelEntry(&gpt, &part_start, &part_size)) {
+ while (GptNextKernelEntry(&gpt, &part_start, &part_size) ==
+ GPT_SUCCESS) {
VB2_DEBUG("Found kernel entry at %"
PRIu64 " size %" PRIu64 "\n",
part_start, part_size);
- /*
- * Set up tracking for this partition. This wraps around if
- * called many times, so initialize the partition entry each
- * time.
- */
- VbSharedDataKernelPart *shpart =
- shcall.parts + (shcall.kernel_parts_found
- & (VBSD_MAX_KERNEL_PARTS - 1));
- memset(shpart, 0, sizeof(VbSharedDataKernelPart));
- shpart->sector_start = part_start;
- shpart->sector_count = part_size;
- /*
- * TODO: GPT partitions start at 1, but cgptlib starts them at
- * 0. Adjust here, until cgptlib is fixed.
- */
- shpart->gpt_index = (uint8_t)(gpt.current_kernel + 1);
- shcall.kernel_parts_found++;
-
/* Found at least one kernel partition. */
found_partitions++;
/* Set up the stream */
VbExStream_t stream = NULL;
- if (VbExStreamOpen(params->disk_handle,
+ if (VbExStreamOpen(disk_info->handle,
part_start, part_size, &stream)) {
VB2_DEBUG("Partition error getting stream.\n");
- shpart->check_result = VBSD_LKP_CHECK_TOO_SMALL;
VB2_DEBUG("Marking kernel as invalid.\n");
GptUpdateKernelEntry(&gpt, GPT_UPDATE_ENTRY_BAD);
continue;
@@ -538,32 +521,22 @@
lpflags |= VB2_LOAD_PARTITION_VBLOCK_ONLY;
}
- rv = vb2_load_partition(ctx,
- stream,
- kernel_subkey,
- lpflags,
- params,
- sd->kernel_version,
- shpart,
- &wb);
+ rv = vb2_load_partition(ctx, stream, lpflags, params);
VbExStreamClose(stream);
- if (rv != VB2_SUCCESS) {
+ if (rv) {
VB2_DEBUG("Marking kernel as invalid.\n");
GptUpdateKernelEntry(&gpt, GPT_UPDATE_ENTRY_BAD);
continue;
}
- int keyblock_valid = (shpart->flags &
- VBSD_LKP_FLAG_KEYBLOCK_VALID);
- if (keyblock_valid) {
- sd->flags |= VB2_SD_FLAG_KERNEL_SIGNED;
- /* Track lowest version from a valid header. */
- if (lowest_version > shpart->combined_version)
- lowest_version = shpart->combined_version;
+ int keyblock_valid = sd->flags & VB2_SD_FLAG_KERNEL_SIGNED;
+ /* Track lowest version from a valid header. */
+ if (keyblock_valid && lowest_version > sd->kernel_version) {
+ lowest_version = sd->kernel_version;
}
VB2_DEBUG("Keyblock valid: %d\n", keyblock_valid);
- VB2_DEBUG("Combined version: %u\n", shpart->combined_version);
+ VB2_DEBUG("Combined version: %u\n", sd->kernel_version);
/*
* If we're only looking at headers, we're done with this
@@ -599,7 +572,8 @@
* non-officially-signed kernel, there's no rollback
* protection, so we can stop at the first valid kernel.
*/
- if (kBootRecovery == shcall.boot_mode || !keyblock_valid) {
+ if (get_boot_mode(ctx) == VB2_BOOT_MODE_RECOVERY ||
+ !keyblock_valid) {
VB2_DEBUG("In recovery mode or dev-signed kernel\n");
break;
}
@@ -611,7 +585,7 @@
* Otherwise, we'll check all the other headers to see if they
* contain a newer key.
*/
- if (shpart->combined_version == sd->kernel_version) {
+ if (sd->kernel_version == sd->kernel_version_secdata) {
VB2_DEBUG("Same kernel version\n");
break;
}
@@ -619,12 +593,11 @@
gpt_done:
/* Write and free GPT data */
- WriteAndFreeGptData(params->disk_handle, &gpt);
+ WriteAndFreeGptData(disk_info->handle, &gpt);
/* Handle finding a good partition */
if (params->partition_number > 0) {
VB2_DEBUG("Good partition %d\n", params->partition_number);
- shcall.check_result = VBSD_LKC_CHECK_GOOD_PARTITION;
/*
* Validity check - only store a new TPM version if we found
* one. If lowest_version is still at its initial value, we
@@ -632,19 +605,16 @@
* just didn't look.
*/
if (lowest_version != LOWEST_TPM_VERSION &&
- lowest_version > sd->kernel_version)
+ lowest_version > sd->kernel_version_secdata)
sd->kernel_version = lowest_version;
/* Success! */
rv = VB2_SUCCESS;
} else if (found_partitions > 0) {
- shcall.check_result = VBSD_LKC_CHECK_INVALID_PARTITIONS;
rv = VB2_ERROR_LK_INVALID_KERNEL_FOUND;
} else {
- shcall.check_result = VBSD_LKC_CHECK_NO_PARTITIONS;
rv = VB2_ERROR_LK_NO_KERNEL_FOUND;
}
- shcall.return_code = (uint8_t)rv;
return rv;
}
diff --git a/firmware/lib20/api_kernel.c b/firmware/lib20/api_kernel.c
index 9ab8522..403e932 100644
--- a/firmware/lib20/api_kernel.c
+++ b/firmware/lib20/api_kernel.c
@@ -7,14 +7,13 @@
*/
#include "2api.h"
+#include "2common.h"
#include "2misc.h"
#include "2nvstorage.h"
#include "2rsa.h"
#include "2secdata.h"
#include "2sha.h"
#include "2sysincludes.h"
-#include "vb2_common.h"
-#include "vboot_struct.h"
vb2_error_t vb2api_load_kernel_vblock(struct vb2_context *ctx)
{
diff --git a/firmware/lib20/include/vb2_common.h b/firmware/lib20/include/vb2_common.h
deleted file mode 100644
index 53a077f..0000000
--- a/firmware/lib20/include/vb2_common.h
+++ /dev/null
@@ -1,102 +0,0 @@
-/* Copyright (c) 2014 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.
- *
- * Common functions between firmware and kernel verified boot.
- */
-
-#ifndef VBOOT_REFERENCE_VB2_COMMON_H_
-#define VBOOT_REFERENCE_VB2_COMMON_H_
-
-#include "2api.h"
-#include "2common.h"
-#include "2return_codes.h"
-#include "2sha.h"
-#include "2struct.h"
-#include "2sysincludes.h"
-
-struct vb2_public_key;
-
-/**
- * Unpack a vboot1-format key buffer for use in verification
- *
- * The elements of the unpacked key will point into the source buffer, so don't
- * free the source buffer until you're done with the key.
- *
- * @param key Destintion for unpacked key
- * @param buf Source buffer containing packed key
- * @param size Size of buffer in bytes
- * @return VB2_SUCCESS, or non-zero error code if error.
- */
-vb2_error_t vb2_unpack_key_buffer(struct vb2_public_key *key,
- const uint8_t *buf, uint32_t size);
-
-/**
- * Unpack a vboot1-format key for use in verification
- *
- * The elements of the unpacked key will point into the source packed key, so
- * don't free the source until you're done with the public key.
- *
- * @param key Destintion for unpacked key
- * @param packed_key Source packed key
- * @param size Size of buffer in bytes
- * @return VB2_SUCCESS, or non-zero error code if error.
- */
-vb2_error_t vb2_unpack_key(struct vb2_public_key *key,
- const struct vb2_packed_key *packed_key);
-
-/**
- * Verify a keyblock using its hash.
- *
- * Header fields are also checked for validity. Does not verify key index or key
- * block flags. Use this for self-signed keyblocks in developer mode.
- *
- * @param block Keyblock to verify
- * @param size Size of keyblock buffer
- * @param key Key to use to verify block
- * @param wb Work buffer
- * @return VB2_SUCCESS, or non-zero error code if error.
- */
-vb2_error_t vb2_verify_keyblock_hash(const struct vb2_keyblock *block,
- uint32_t size,
- const struct vb2_workbuf *wb);
-
-/**
- * Check the validity of a kernel preamble using a public key.
- *
- * The signature in the preamble is destroyed during the check.
- *
- * @param preamble Preamble to verify
- * @param size Size of preamble buffer
- * @param key Key to use to verify preamble
- * @param wb Work buffer
- * @return VB2_SUCCESS, or non-zero error code if error.
- */
-vb2_error_t vb2_verify_kernel_preamble(struct vb2_kernel_preamble *preamble,
- uint32_t size,
- const struct vb2_public_key *key,
- const struct vb2_workbuf *wb);
-
-/**
- * Retrieve the 16-bit vmlinuz header address and size from the preamble.
- *
- * Size 0 means there is no 16-bit vmlinuz header present. Old preamble
- * versions (<2.1) return 0 for both fields.
- *
- * @param preamble Preamble to check
- * @param vmlinuz_header_address Destination for header address
- * @param vmlinuz_header_size Destination for header size
- */
-void vb2_kernel_get_vmlinuz_header(const struct vb2_kernel_preamble *preamble,
- uint64_t *vmlinuz_header_address,
- uint32_t *vmlinuz_header_size);
-
-/**
- * Get the flags for the kernel preamble.
- *
- * @param preamble Preamble to check
- * @return Flags for the preamble. Old preamble versions (<2.2) return 0.
- */
-uint32_t vb2_kernel_get_flags(const struct vb2_kernel_preamble *preamble);
-
-#endif /* VBOOT_REFERENCE_VB2_COMMON_H_ */
diff --git a/firmware/lib20/kernel.c b/firmware/lib20/kernel.c
index 298b14f..81ded65 100644
--- a/firmware/lib20/kernel.c
+++ b/firmware/lib20/kernel.c
@@ -12,7 +12,6 @@
#include "2secdata.h"
#include "2sha.h"
#include "2sysincludes.h"
-#include "vb2_common.h"
/**
* Returns non-zero if the kernel needs to have a valid signature, instead of
@@ -35,49 +34,6 @@
return 0;
}
-test_mockable
-vb2_error_t vb2_verify_keyblock_hash(const struct vb2_keyblock *block,
- uint32_t size,
- const struct vb2_workbuf *wb)
-{
- const struct vb2_signature *sig = &block->keyblock_hash;
- struct vb2_workbuf wblocal = *wb;
- struct vb2_digest_context *dc;
- uint8_t *digest;
- uint32_t digest_size;
-
- /* Validity check keyblock before attempting hash check of data */
- VB2_TRY(vb2_check_keyblock(block, size, sig));
-
- VB2_DEBUG("Checking keyblock hash...\n");
-
- /* Digest goes at start of work buffer */
- digest_size = vb2_digest_size(VB2_HASH_SHA512);
- digest = vb2_workbuf_alloc(&wblocal, digest_size);
- if (!digest)
- return VB2_ERROR_VDATA_WORKBUF_DIGEST;
-
- /* Hashing requires temp space for the context */
- dc = vb2_workbuf_alloc(&wblocal, sizeof(*dc));
- if (!dc)
- return VB2_ERROR_VDATA_WORKBUF_HASHING;
-
- VB2_TRY(vb2_digest_init(dc, VB2_HASH_SHA512));
-
- VB2_TRY(vb2_digest_extend(dc, (const uint8_t *)block, sig->data_size));
-
- VB2_TRY(vb2_digest_finalize(dc, digest, digest_size));
-
- if (vb2_safe_memcmp(vb2_signature_data(sig), digest,
- digest_size) != 0) {
- VB2_DEBUG("Invalid keyblock hash.\n");
- return VB2_ERROR_KEYBLOCK_SIG_INVALID;
- }
-
- /* Success */
- return VB2_SUCCESS;
-}
-
vb2_error_t vb2_load_kernel_keyblock(struct vb2_context *ctx)
{
struct vb2_shared_data *sd = vb2_get_sd(ctx);
@@ -223,115 +179,6 @@
return VB2_SUCCESS;
}
-test_mockable
-vb2_error_t vb2_verify_kernel_preamble(struct vb2_kernel_preamble *preamble,
- uint32_t size,
- const struct vb2_public_key *key,
- const struct vb2_workbuf *wb)
-{
- struct vb2_signature *sig = &preamble->preamble_signature;
- uint32_t min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_0_SIZE;
-
- VB2_DEBUG("Verifying kernel preamble.\n");
-
- /* Make sure it's even safe to look at the struct */
- if(size < min_size) {
- VB2_DEBUG("Not enough data for preamble header.\n");
- return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
- }
- if (preamble->header_version_major !=
- VB2_KERNEL_PREAMBLE_HEADER_VERSION_MAJOR) {
- VB2_DEBUG("Incompatible kernel preamble header version.\n");
- return VB2_ERROR_PREAMBLE_HEADER_VERSION;
- }
-
- if (preamble->header_version_minor >= 2)
- min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_2_SIZE;
- else if (preamble->header_version_minor == 1)
- min_size = EXPECTED_VB2_KERNEL_PREAMBLE_2_1_SIZE;
- if(preamble->preamble_size < min_size) {
- VB2_DEBUG("Preamble size too small for header.\n");
- return VB2_ERROR_PREAMBLE_TOO_SMALL_FOR_HEADER;
- }
- if (size < preamble->preamble_size) {
- VB2_DEBUG("Not enough data for preamble.\n");
- return VB2_ERROR_PREAMBLE_SIZE;
- }
-
- /* Check signature */
- if (vb2_verify_signature_inside(preamble, preamble->preamble_size,
- sig)) {
- VB2_DEBUG("Preamble signature off end of preamble\n");
- return VB2_ERROR_PREAMBLE_SIG_OUTSIDE;
- }
-
- /* Make sure advertised signature data sizes are valid. */
- if (preamble->preamble_size < sig->data_size) {
- VB2_DEBUG("Signature calculated past end of the block\n");
- return VB2_ERROR_PREAMBLE_SIGNED_TOO_MUCH;
- }
-
- if (vb2_verify_data((const uint8_t *)preamble, size, sig, key, wb)) {
- VB2_DEBUG("Preamble signature validation failed\n");
- return VB2_ERROR_PREAMBLE_SIG_INVALID;
- }
-
- /* Verify we signed enough data */
- if (sig->data_size < sizeof(struct vb2_fw_preamble)) {
- VB2_DEBUG("Didn't sign enough data\n");
- return VB2_ERROR_PREAMBLE_SIGNED_TOO_LITTLE;
- }
-
- /* Verify body signature is inside the signed data */
- if (vb2_verify_signature_inside(preamble, sig->data_size,
- &preamble->body_signature)) {
- VB2_DEBUG("Body signature off end of preamble\n");
- return VB2_ERROR_PREAMBLE_BODY_SIG_OUTSIDE;
- }
-
- /*
- * If bootloader is present, verify it's covered by the body
- * signature.
- */
- if (preamble->bootloader_size) {
- const void *body_ptr =
- (const void *)(uintptr_t)preamble->body_load_address;
- const void *bootloader_ptr =
- (const void *)(uintptr_t)preamble->bootloader_address;
- if (vb2_verify_member_inside(body_ptr,
- preamble->body_signature.data_size,
- bootloader_ptr,
- preamble->bootloader_size,
- 0, 0)) {
- VB2_DEBUG("Bootloader off end of signed data\n");
- return VB2_ERROR_PREAMBLE_BOOTLOADER_OUTSIDE;
- }
- }
-
- /*
- * If vmlinuz header is present, verify it's covered by the body
- * signature.
- */
- if (preamble->header_version_minor >= 1 &&
- preamble->vmlinuz_header_size) {
- const void *body_ptr =
- (const void *)(uintptr_t)preamble->body_load_address;
- const void *vmlinuz_header_ptr = (const void *)
- (uintptr_t)preamble->vmlinuz_header_address;
- if (vb2_verify_member_inside(body_ptr,
- preamble->body_signature.data_size,
- vmlinuz_header_ptr,
- preamble->vmlinuz_header_size,
- 0, 0)) {
- VB2_DEBUG("Vmlinuz header off end of signed data\n");
- return VB2_ERROR_PREAMBLE_VMLINUZ_HEADER_OUTSIDE;
- }
- }
-
- /* Success */
- return VB2_SUCCESS;
-}
-
vb2_error_t vb2_load_kernel_preamble(struct vb2_context *ctx)
{
struct vb2_shared_data *sd = vb2_get_sd(ctx);
@@ -421,30 +268,3 @@
return VB2_SUCCESS;
}
-
-void vb2_kernel_get_vmlinuz_header(const struct vb2_kernel_preamble *preamble,
- uint64_t *vmlinuz_header_address,
- uint32_t *vmlinuz_header_size)
-{
- if (preamble->header_version_minor < 1) {
- *vmlinuz_header_address = 0;
- *vmlinuz_header_size = 0;
- } else {
- /*
- * Set header and size only if the preamble header version is >
- * 2.1 as they don't exist in version 2.0 (Note that we don't
- * need to check header_version_major; if that's not 2 then
- * vb2_verify_kernel_preamble() would have already failed.
- */
- *vmlinuz_header_address = preamble->vmlinuz_header_address;
- *vmlinuz_header_size = preamble->vmlinuz_header_size;
- }
-}
-
-uint32_t vb2_kernel_get_flags(const struct vb2_kernel_preamble *preamble)
-{
- if (preamble->header_version_minor < 2)
- return 0;
-
- return preamble->flags;
-}
diff --git a/firmware/stub/vboot_api_stub.c b/firmware/stub/vboot_api_stub.c
index fe1c13d..bc5f2fe 100644
--- a/firmware/stub/vboot_api_stub.c
+++ b/firmware/stub/vboot_api_stub.c
@@ -18,117 +18,26 @@
#include "vboot_api.h"
#include "vboot_test.h"
-void vb2ex_msleep(uint32_t msec)
-{
-}
-
-void vb2ex_beep(uint32_t msec, uint32_t frequency)
-{
-}
-
-uint32_t vb2ex_get_locale_count(void)
-{
- return 0;
-}
-
-uint32_t vb2ex_get_bootloader_count(void)
-{
- return 0;
-}
-
+__attribute__((weak))
uint32_t VbExKeyboardRead(void)
{
return 0;
}
+__attribute__((weak))
uint32_t VbExKeyboardReadWithFlags(uint32_t *flags_ptr)
{
return 0;
}
-int vb2ex_physical_presence_pressed(void)
-{
- return 0;
-}
-
+__attribute__((weak))
uint32_t VbExIsShutdownRequested(void)
{
return 0;
}
-int vb2ex_ec_trusted(void)
-{
- return 1;
-}
-
-vb2_error_t vb2ex_ec_running_rw(int *in_rw)
-{
- *in_rw = 0;
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_jump_to_rw(void)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_disable_jump(void)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_hash_image(enum vb2_firmware_selection select,
- const uint8_t **hash, int *hash_size)
-{
- static const uint8_t fake_hash[32] = {1, 2, 3, 4};
-
- *hash = fake_hash;
- *hash_size = sizeof(fake_hash);
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_get_expected_image_hash(enum vb2_firmware_selection select,
- const uint8_t **hash, int *hash_size)
-{
- static const uint8_t fake_hash[32] = {1, 2, 3, 4};
-
- *hash = fake_hash;
- *hash_size = sizeof(fake_hash);
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_update_image(enum vb2_firmware_selection select)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_protect(enum vb2_firmware_selection select)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_vboot_done(struct vb2_context *ctx)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_ec_battery_cutoff(void)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_auxfw_check(enum vb2_auxfw_update_severity *severity)
-{
- *severity = VB2_AUXFW_NO_UPDATE;
- return VB2_SUCCESS;
-}
-
-vb2_error_t vb2ex_auxfw_update(void)
-{
- return VB2_SUCCESS;
-}
-
-vb2_error_t VbExLegacy(enum VbAltFwIndex_t altfw_num)
+__attribute__((weak))
+vb2_error_t vb2ex_run_altfw(uint32_t altfw_id)
{
return VB2_SUCCESS;
}
diff --git a/firmware/stub/vboot_api_stub_disk.c b/firmware/stub/vboot_api_stub_disk.c
index 7dc413f..3244dc6 100644
--- a/firmware/stub/vboot_api_stub_disk.c
+++ b/firmware/stub/vboot_api_stub_disk.c
@@ -16,6 +16,7 @@
#include "vboot_api.h"
+__attribute__((weak))
vb2_error_t VbExDiskGetInfo(VbDiskInfo** infos_ptr, uint32_t* count,
uint32_t disk_flags)
{
@@ -25,6 +26,7 @@
}
+__attribute__((weak))
vb2_error_t VbExDiskFreeInfo(VbDiskInfo* infos_ptr,
VbExDiskHandle_t preserve_handle)
{
@@ -32,6 +34,7 @@
}
+__attribute__((weak))
vb2_error_t VbExDiskRead(VbExDiskHandle_t handle, uint64_t lba_start,
uint64_t lba_count, void* buffer)
{
@@ -39,6 +42,7 @@
}
+__attribute__((weak))
vb2_error_t VbExDiskWrite(VbExDiskHandle_t handle, uint64_t lba_start,
uint64_t lba_count, const void* buffer)
{
diff --git a/firmware/stub/vboot_api_stub_init.c b/firmware/stub/vboot_api_stub_init.c
deleted file mode 100644
index bd5c0c2..0000000
--- a/firmware/stub/vboot_api_stub_init.c
+++ /dev/null
@@ -1,29 +0,0 @@
-/* Copyright (c) 2013 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.
- *
- * Stub implementations of firmware-provided API functions.
- */
-
-#include <stdarg.h>
-#include <stdint.h>
-#include <stdlib.h>
-#include <sys/time.h>
-
-#include "2common.h"
-#include "vboot_api.h"
-
-uint32_t vb2ex_mtime(void)
-{
- struct timeval tv;
- gettimeofday(&tv, NULL);
- return tv.tv_sec * VB2_MSEC_PER_SEC + tv.tv_usec / VB2_USEC_PER_MSEC;
-}
-
-vb2_error_t vb2ex_commit_data(struct vb2_context *ctx)
-{
- ctx->flags &= ~VB2_CONTEXT_SECDATA_FIRMWARE_CHANGED;
- ctx->flags &= ~VB2_CONTEXT_SECDATA_KERNEL_CHANGED;
- ctx->flags &= ~VB2_CONTEXT_NVDATA_CHANGED;
- return VB2_SUCCESS;
-}
diff --git a/firmware/stub/vboot_api_stub_stream.c b/firmware/stub/vboot_api_stub_stream.c
index ae0a674..68e7ec7 100644
--- a/firmware/stub/vboot_api_stub_stream.c
+++ b/firmware/stub/vboot_api_stub_stream.c
@@ -25,6 +25,7 @@
uint64_t sectors_left;
};
+__attribute__((weak))
vb2_error_t VbExStreamOpen(VbExDiskHandle_t handle, uint64_t lba_start,
uint64_t lba_count, VbExStream_t *stream)
{
@@ -45,6 +46,7 @@
return VB2_SUCCESS;
}
+__attribute__((weak))
vb2_error_t VbExStreamRead(VbExStream_t stream, uint32_t bytes, void *buffer)
{
struct disk_stream *s = (struct disk_stream *)stream;
@@ -73,6 +75,7 @@
return VB2_SUCCESS;
}
+__attribute__((weak))
void VbExStreamClose(VbExStream_t stream)
{
struct disk_stream *s = (struct disk_stream *)stream;
diff --git a/futility/cmd_create.c b/futility/cmd_create.c
index aca1d4c..16a3733 100644
--- a/futility/cmd_create.c
+++ b/futility/cmd_create.c
@@ -22,7 +22,6 @@
#include "host_misc21.h"
#include "openssl_compat.h"
#include "util_misc.h"
-#include "vb2_common.h"
#include "vboot_host.h"
/* Command line options */
diff --git a/futility/cmd_gbb_utility.c b/futility/cmd_gbb_utility.c
index 2a76ecb..8f21eee 100644
--- a/futility/cmd_gbb_utility.c
+++ b/futility/cmd_gbb_utility.c
@@ -29,7 +29,6 @@
" --hwid \tReport hardware id (default).\n"
" --flags \tReport header flags.\n"
" --digest \tReport digest of hwid (>= v1.2)\n"
- " --roothash \tCheck ryu root key hash\n"
" -k, --rootkey=FILE \tFile name to export Root Key.\n"
" -b, --bmpfv=FILE \tFile name to export Bitmap FV.\n"
" -r --recoverykey=FILE\tFile name to export Recovery Key.\n"
@@ -61,7 +60,6 @@
OPT_FLAGS,
OPT_DIGEST,
OPT_HELP,
- OPT_ROOTHASH,
};
/* Command line options */
@@ -78,7 +76,6 @@
{"flags", 0, NULL, OPT_FLAGS},
{"digest", 0, NULL, OPT_DIGEST},
{"help", 0, NULL, OPT_HELP},
- {"roothash", 0, NULL, OPT_ROOTHASH},
{NULL, 0, NULL, 0},
};
@@ -367,7 +364,6 @@
int sel_hwid = 0;
int sel_digest = 0;
int sel_flags = 0;
- int sel_roothash = 0;
uint8_t *inbuf = NULL;
off_t filesize;
uint8_t *outbuf = NULL;
@@ -417,9 +413,6 @@
case OPT_DIGEST:
sel_digest = 1;
break;
- case OPT_ROOTHASH:
- sel_roothash = 1;
- break;
case OPT_HELP:
print_help(argc, argv);
return !!errorcnt;
@@ -498,9 +491,6 @@
if (sel_digest)
print_hwid_digest(gbb, "digest: ", "\n");
- if (sel_roothash)
- verify_ryu_root_header(inbuf, filesize, gbb);
-
if (sel_flags)
printf("flags: 0x%08x\n", gbb->flags);
if (opt_rootkey)
@@ -606,9 +596,6 @@
read_from_file("root_key", opt_rootkey,
gbb_base + gbb->rootkey_offset,
gbb->rootkey_size);
-
- if (fill_ryu_root_header(outbuf, filesize, gbb))
- errorcnt++;
}
if (opt_bmpfv)
read_from_file("bmp_fv", opt_bmpfv,
diff --git a/futility/cmd_show.c b/futility/cmd_show.c
index f3b9163..716b2b2 100644
--- a/futility/cmd_show.c
+++ b/futility/cmd_show.c
@@ -31,7 +31,6 @@
#include "host_key21.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Options */
struct show_option_s show_option = {
diff --git a/futility/cmd_sign.c b/futility/cmd_sign.c
index 6243e3a..9bfa7fd 100644
--- a/futility/cmd_sign.c
+++ b/futility/cmd_sign.c
@@ -29,7 +29,6 @@
#include "kernel_blob.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Options */
struct sign_option_s sign_option = {
diff --git a/futility/cmd_update.c b/futility/cmd_update.c
index 3d99664..57fa083 100644
--- a/futility/cmd_update.c
+++ b/futility/cmd_update.c
@@ -31,6 +31,7 @@
OPT_QUIRKS_LIST,
OPT_REPACK,
OPT_SERVO,
+ OPT_SERVO_NORESET,
OPT_SERVO_PORT,
OPT_SIGNATURE,
OPT_SYS_PROPS,
@@ -54,6 +55,7 @@
{"ccd", 0, NULL, OPT_CCD},
{"servo", 0, NULL, OPT_SERVO},
+ {"servo_noreset", 0, NULL, OPT_SERVO_NORESET},
{"servo_port", 1, NULL, OPT_SERVO_PORT},
{"emulate", 1, NULL, OPT_EMULATE},
{"factory", 0, NULL, OPT_FACTORY},
@@ -130,6 +132,7 @@
" --gbb_flags=FLAG\tOverride new GBB flags\n"
" --ccd \tDo fast,force,wp=0,p=raiden_debug_spi\n"
" --servo \tFlash using Servo (v2, v4, micro, ...)\n"
+ " --servo_noreset \tLike servo but with 'custom_rst=true'\n"
" --servo_port=PRT\tOverride servod port, implies --servo\n"
" --signature_id=S\tOverride signature ID for key files\n"
" --sys_props=LIST\tList of system properties to override\n"
@@ -139,12 +142,29 @@
argv[0]);
}
+static char *add_servo_noreset(char *programmer)
+{
+ char *ret;
+
+ if (strstr(programmer, "raiden_debug_spi:target=AP") == NULL) {
+ ERROR("servo_noreset only works for AP flashing over CCD.\n");
+ free(programmer);
+
+ return NULL;
+ }
+
+ ASPRINTF(&ret, "%s,custom_rst=true", programmer);
+ free(programmer);
+
+ return ret;
+}
+
static int do_update(int argc, char *argv[])
{
struct updater_config *cfg;
struct updater_config_arguments args = {0};
int i, errorcnt = 0, do_update = 1;
- int detect_servo = 0, do_servo_cpu_fw_spi = 0;
+ int detect_servo = 0, do_servo_cpu_fw_spi = 0, servo_noreset = 0;
char *servo_programmer = NULL;
char *endptr;
@@ -255,6 +275,14 @@
args.host_only = 1;
detect_servo = 1;
break;
+ case OPT_SERVO_NORESET:
+ args.fast_update = 1;
+ args.force_update = 1;
+ args.write_protection = "0";
+ args.host_only = 1;
+ detect_servo = 1;
+ servo_noreset = 1;
+ break;
case OPT_SERVO_PORT:
setenv(ENV_SERVOD_PORT, optarg, 1);
args.fast_update = 1;
@@ -289,6 +317,10 @@
if (!errorcnt && detect_servo) {
servo_programmer = host_detect_servo(&do_servo_cpu_fw_spi);
+
+ if (servo_programmer && servo_noreset)
+ servo_programmer = add_servo_noreset(servo_programmer);
+
if (!servo_programmer)
errorcnt++;
else if (!args.programmer)
diff --git a/futility/cmd_vbutil_firmware.c b/futility/cmd_vbutil_firmware.c
index 7659ed2..b7155f7 100644
--- a/futility/cmd_vbutil_firmware.c
+++ b/futility/cmd_vbutil_firmware.c
@@ -22,7 +22,6 @@
#include "kernel_blob.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Command line options */
enum {
diff --git a/futility/cmd_vbutil_kernel.c b/futility/cmd_vbutil_kernel.c
index 83a76f8..7268bee 100644
--- a/futility/cmd_vbutil_kernel.c
+++ b/futility/cmd_vbutil_kernel.c
@@ -9,7 +9,7 @@
#include <fcntl.h>
#include <getopt.h>
#include <inttypes.h> /* For PRIu64 */
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
#include <linux/fs.h> /* For BLKGETSIZE64 */
#endif
#include <stdarg.h>
@@ -26,7 +26,6 @@
#include "host_common.h"
#include "kernel_blob.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Global opts */
static int opt_verbose;
@@ -173,7 +172,7 @@
FATAL("Unable to stat %s: %s\n", filename, strerror(errno));
if (S_ISBLK(statbuf.st_mode)) {
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
int fd = open(filename, O_RDONLY);
if (fd >= 0) {
ioctl(fd, BLKGETSIZE64, &file_size);
diff --git a/futility/cmd_vbutil_key.c b/futility/cmd_vbutil_key.c
index 0d81254..d26df3f 100644
--- a/futility/cmd_vbutil_key.c
+++ b/futility/cmd_vbutil_key.c
@@ -17,7 +17,6 @@
#include "host_key21.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Command line options */
enum {
diff --git a/futility/cmd_vbutil_keyblock.c b/futility/cmd_vbutil_keyblock.c
index 977b4aa..bec23c3 100644
--- a/futility/cmd_vbutil_keyblock.c
+++ b/futility/cmd_vbutil_keyblock.c
@@ -19,7 +19,6 @@
#include "host_key21.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/* Command line options */
enum {
diff --git a/futility/dump_kernel_config_lib.c b/futility/dump_kernel_config_lib.c
index 4240e5e..ff39c41 100644
--- a/futility/dump_kernel_config_lib.c
+++ b/futility/dump_kernel_config_lib.c
@@ -10,7 +10,7 @@
#include <string.h>
#include <sys/mman.h>
#include <sys/stat.h>
-#if !defined (__FreeBSD__)
+#if !defined (__FreeBSD__) && !defined(__OpenBSD__)
#include <sys/sysmacros.h>
#endif
#include <sys/types.h>
@@ -125,7 +125,7 @@
char *newstr = NULL;
int fd = open(infile, O_RDONLY | O_CLOEXEC
-#if !defined(__FreeBSD__)
+#if !defined(__FreeBSD__) && !defined(__OpenBSD__)
| O_LARGEFILE
#endif
);
diff --git a/futility/file_type_bios.c b/futility/file_type_bios.c
index 7e805f5..fe0b223 100644
--- a/futility/file_type_bios.c
+++ b/futility/file_type_bios.c
@@ -16,7 +16,6 @@
#include "futility_options.h"
#include "host_common.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
static const char * const fmap_name[] = {
"GBB", /* BIOS_FMAP_GBB */
diff --git a/futility/futility.h b/futility/futility.h
index 881189c..1f34713 100644
--- a/futility/futility.h
+++ b/futility/futility.h
@@ -116,14 +116,6 @@
/* Copies a file or dies with an error message */
void futil_copy_file_or_die(const char *infile, const char *outfile);
-/* Update ryu root key header in the image */
-int fill_ryu_root_header(uint8_t *ptr, size_t size,
- const struct vb2_gbb_header *gbb);
-
-/* Verify ryu root key header */
-int verify_ryu_root_header(uint8_t *ptr, size_t size,
- const struct vb2_gbb_header *gbb);
-
/* Possible file operation errors */
enum futil_file_err {
FILE_ERR_NONE,
diff --git a/futility/misc.c b/futility/misc.c
index 0c8a0e7..f3e7748 100644
--- a/futility/misc.c
+++ b/futility/misc.c
@@ -5,7 +5,7 @@
#include <assert.h>
#include <errno.h>
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
#include <linux/fs.h> /* For BLKGETSIZE64 */
#endif
#include <stdarg.h>
@@ -272,7 +272,7 @@
return FILE_ERR_STAT;
}
-#if !defined(HAVE_MACOS) && !defined(__FreeBSD__)
+#if !defined(HAVE_MACOS) && !defined(__FreeBSD__) && !defined(__OpenBSD__)
if (S_ISBLK(sb.st_mode))
ioctl(fd, BLKGETSIZE64, &sb.st_size);
#endif
diff --git a/futility/ryu_root_header.c b/futility/ryu_root_header.c
deleted file mode 100644
index ef00531..0000000
--- a/futility/ryu_root_header.c
+++ /dev/null
@@ -1,165 +0,0 @@
-/* Copyright 2015 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.
- */
-
-#include <errno.h>
-#include <getopt.h>
-#include <inttypes.h>
-#include <stddef.h>
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <sys/stat.h>
-#include <sys/types.h>
-#include <unistd.h>
-
-#include "2common.h"
-#include "2sha.h"
-#include "2sysincludes.h"
-#include "futility.h"
-
-#define SEARCH_STRIDE 4
-
-/**
- * Check if the pointer contains the magic string. We need to use a
- * case-swapped version, so that the actual magic string doesn't appear in the
- * code, to avoid falsely finding it when searching for the struct.
- */
-static int is_magic(const void *ptr)
-{
- const char magic_inv[RYU_ROOT_KEY_HASH_MAGIC_SIZE] =
- RYU_ROOT_KEY_HASH_MAGIC_INVCASE;
- const char *magic = ptr;
- int i;
-
- for (i = 0; i < RYU_ROOT_KEY_HASH_MAGIC_SIZE; i++) {
- if (magic[i] != (magic_inv[i] ^ 0x20))
- return 0;
- }
-
- return 1;
-}
-
-static int valid_ryu_root_header(struct vb2_ryu_root_key_hash *hash,
- size_t size)
-{
- if (!is_magic(hash->magic))
- return 0; /* Wrong magic */
-
- if (hash->header_version_major != RYU_ROOT_KEY_HASH_VERSION_MAJOR)
- return 0; /* Version we can't parse */
-
- if (hash->struct_size < EXPECTED_VB2_RYU_ROOT_KEY_HASH_SIZE)
- return 0; /* Header too small */
-
- if (hash->struct_size > size)
- return 0; /* Claimed size doesn't fit in buffer */
-
- return 1;
-}
-
-/**
- * Find the root key hash struct and return it or NULL if error.
- */
-static struct vb2_ryu_root_key_hash *find_ryu_root_header(uint8_t *ptr,
- size_t size)
-{
- size_t i;
- struct vb2_ryu_root_key_hash *tmp, *hash = NULL;
- int count = 0;
-
- /* Look for the ryu root key hash header */
- for (i = 0; i <= size - SEARCH_STRIDE; i += SEARCH_STRIDE) {
- if (!is_magic(ptr + i))
- continue;
-
- /* Found something. See if it's any good. */
- tmp = (struct vb2_ryu_root_key_hash *) (ptr + i);
- if (valid_ryu_root_header(tmp, size - i))
- if (!count++)
- hash = tmp;
- }
-
- switch (count) {
- case 0:
- return NULL;
- case 1:
- return hash;
- default:
- fprintf(stderr,
- "WARNING: multiple ryu root hash headers found\n");
- /* But hey, it's only a warning. Use the first one. */
- return hash;
- }
-}
-
-static void calculate_root_key_hash(uint8_t *digest, size_t digest_size,
- const struct vb2_gbb_header *gbb)
-{
- const uint8_t *gbb_base = (const uint8_t *)gbb;
-
- vb2_digest_buffer(gbb_base + gbb->rootkey_offset,
- gbb->rootkey_size,
- VB2_HASH_SHA256,
- digest,
- digest_size);
-}
-
-int fill_ryu_root_header(uint8_t *ptr, size_t size,
- const struct vb2_gbb_header *gbb)
-{
- struct vb2_ryu_root_key_hash *hash;
-
- /*
- * Find the ryu root header. If not found, nothing we can do, but
- * that's ok because most images don't have the header.
- */
- hash = find_ryu_root_header(ptr, size);
- if (!hash)
- return 0;
-
- /* Update the hash stored in the header based on the root key */
- calculate_root_key_hash(hash->root_key_hash_digest,
- sizeof(hash->root_key_hash_digest),
- gbb);
-
- printf(" - calculate ryu root hash: success\n");
- return 0;
-}
-
-int verify_ryu_root_header(uint8_t *ptr, size_t size,
- const struct vb2_gbb_header *gbb)
-{
- uint8_t digest[VB2_SHA256_DIGEST_SIZE] = {0};
-
- struct vb2_ryu_root_key_hash *hash;
-
- /*
- * Find the ryu root header. If not found, nothing we can do, but
- * that's ok because most images don't have the header.
- */
- hash = find_ryu_root_header(ptr, size);
- if (!hash) {
- printf(" - ryu root hash not found\n");
- return 0;
- }
-
- /* Check for all 0's, which means hash hasn't been set */
- if (0 == memcmp(digest, hash->root_key_hash_digest, sizeof(digest))) {
- printf(" - ryu root hash is unset\n");
- return 0;
- }
-
- /* Update the hash stored in the header based on the root key */
- calculate_root_key_hash(digest, sizeof(digest), gbb);
-
- if (0 == memcmp(digest, hash->root_key_hash_digest, sizeof(digest))) {
- printf(" - ryu root hash verified\n");
- return 0;
- } else {
- printf(" - ryu root hash does not verify\n");
- return -1;
- }
-}
diff --git a/futility/updater.c b/futility/updater.c
index fa00854..87ac6fd 100644
--- a/futility/updater.c
+++ b/futility/updater.c
@@ -14,7 +14,6 @@
#include "host_misc.h"
#include "updater.h"
#include "util_misc.h"
-#include "vb2_common.h"
#define REMOVE_WP_URL "https://goo.gl/ces83U"
diff --git a/futility/updater_archive.c b/futility/updater_archive.c
index 218499e..4ad5287 100644
--- a/futility/updater_archive.c
+++ b/futility/updater_archive.c
@@ -8,6 +8,9 @@
#include <assert.h>
#include <ctype.h>
#include <errno.h>
+#if defined(__OpenBSD__)
+#include <sys/types.h>
+#endif
#include <fts.h>
#include <string.h>
#include <stdio.h>
@@ -30,7 +33,6 @@
#include "host_misc.h"
#include "updater.h"
#include "util_misc.h"
-#include "vb2_common.h"
/*
* A firmware update package (archive) is a file packed by either shar(1) or
@@ -1058,16 +1060,16 @@
return;
if (load_firmware_image(&image, fpath, archive))
return;
- if (is_host)
- gbb = find_gbb(&image);
- else
+ if (!is_host)
printf(",\n");
printf("%*s\"%s\": { \"versions\": { \"ro\": \"%s\", \"rw\": \"%s\" },",
indent, "", name, image.ro_version, image.rw_version_a);
indent += 2;
- if (is_host && patch_image_by_model(&image, m, archive) != 0) {
+ if (!is_host) {
+ /* No extra information to be printed */
+ } else if (patch_image_by_model(&image, m, archive) != 0) {
ERROR("Failed to patch images by model: %s\n", m->name);
- } else if (gbb) {
+ } else if (NULL != (gbb = find_gbb(&image))) {
printf("\n%*s\"keys\": { \"root\": \"%s\", ",
indent, "",
get_gbb_key_hash(gbb, gbb->rootkey_offset,
diff --git a/futility/updater_quirks.c b/futility/updater_quirks.c
index b9bdb2c..1d1ba62 100644
--- a/futility/updater_quirks.c
+++ b/futility/updater_quirks.c
@@ -46,7 +46,7 @@
{ .match = "Google_Poppy.", .quirks = "min_platform_version=6" },
{ .match = "Google_Scarlet.", .quirks = "min_platform_version=1" },
- { .match = "Google_Trogdor.", .quirks = "min_platform_version=1" },
+ { .match = "Google_Trogdor.", .quirks = "min_platform_version=2" },
/* Legacy white label units. */
{ .match = "Google_Enguarde.", .quirks = "allow_empty_wltag" },
diff --git a/futility/updater_utils.c b/futility/updater_utils.c
index a441e03..70ed396 100644
--- a/futility/updater_utils.c
+++ b/futility/updater_utils.c
@@ -10,7 +10,7 @@
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
-#if defined (__FreeBSD__)
+#if defined (__FreeBSD__) || defined(__OpenBSD__)
#include <sys/wait.h>
#endif
@@ -681,7 +681,7 @@
diff_image, tempfiles);
if (!tmp_diff)
return -1;
- ASPRINTF(&extra, "--noverify --diff=%s", tmp_diff);
+ ASPRINTF(&extra, "--noverify --flash-contents=%s", tmp_diff);
}
r = host_flashrom(FLASHROM_WRITE, tmp_path, programmer, verbosity,
diff --git a/futility/vb1_helper.c b/futility/vb1_helper.c
index ecb193b..39bb16a 100644
--- a/futility/vb1_helper.c
+++ b/futility/vb1_helper.c
@@ -21,7 +21,6 @@
#include "kernel_blob.h"
#include "util_misc.h"
#include "vb1_helper.h"
-#include "vb2_common.h"
/****************************************************************************/
/* Here are globals containing all the bits & pieces I'm working on.
diff --git a/host/arch/x86/lib/crossystem_arch.c b/host/arch/x86/lib/crossystem_arch.c
index 6a8f5a2..e805e2a 100644
--- a/host/arch/x86/lib/crossystem_arch.c
+++ b/host/arch/x86/lib/crossystem_arch.c
@@ -7,7 +7,7 @@
#include <dirent.h>
#include <errno.h>
#include <fcntl.h>
-#if !defined(__FreeBSD__)
+#if !defined(__FreeBSD__) && !defined(__OpenBSD__)
#include <linux/nvram.h>
#include <linux/version.h>
#endif
@@ -100,7 +100,7 @@
static void VbFixCmosChecksum(FILE* file)
{
-#if !defined(__FreeBSD__)
+#if !defined(__FreeBSD__) && !defined(__OpenBSD__)
int fd = fileno(file);
ioctl(fd, NVRAM_SETCKS);
#endif
@@ -666,7 +666,7 @@
if (uname(&host) == 0) {
if (sscanf(host.release, "%u.%u.", &maj, &min) == 2) {
-#if !defined(__FreeBSD__)
+#if !defined(__FreeBSD__) && !defined(__OpenBSD__)
if (KERNEL_VERSION(maj, min, 0) >= KERNEL_VERSION(4, 16, 0) &&
*offset > 11)
*offset += 3;
diff --git a/host/lib/crossystem.c b/host/lib/crossystem.c
index bb10c39..9d23091 100644
--- a/host/lib/crossystem.c
+++ b/host/lib/crossystem.c
@@ -25,8 +25,14 @@
#define KERNEL_CMDLINE_PATH "/proc/cmdline"
/* Filename for the mount-encrypted key */
+/* TODO(b/174807059): Remove this after we land driver-level TPM simulator on
+ * all VM boards */
#define MOUNT_ENCRYPTED_KEY_PATH "/mnt/stateful_partition/encrypted.key"
+/* Filename for the TPM simulator NV data */
+#define TPM_SIMULATOR_NVCHIP_PATH \
+ "/mnt/stateful_partition/unencrypted/tpm2-simulator/NVChip"
+
/* Fields that GetVdatString() can get */
typedef enum VdatStringField {
VDAT_STRING_DEPRECATED_TIMERS = 0, /* Timer values */
@@ -63,7 +69,7 @@
} VbBuildOption;
static const char *fw_results[] = {"unknown", "trying", "success", "failure"};
-static const char *default_boot[] = {"disk", "usb", "legacy"};
+static const char *default_boot[] = {"disk", "usb", "altfw"};
/* Masks for kern_nv usage by kernel. */
#define KERN_NV_FWUPDATE_TRIES_MASK 0x000F
@@ -374,7 +380,10 @@
} else if (!strcasecmp(name,"disable_dev_request")) {
value = vb2_get_nv_storage(VB2_NV_DISABLE_DEV_REQUEST);
} else if (!strcasecmp(name,"clear_tpm_owner_request")) {
- if (TPM2_SIMULATOR)
+ if (TPM2_SIMULATOR && VTPM_PROXY)
+ /* Check TPM simulator NVChip status */
+ value = access(TPM_SIMULATOR_NVCHIP_PATH, F_OK) != 0;
+ else if (TPM2_SIMULATOR)
/* Check mount-encrypted key status */
value = access(MOUNT_ENCRYPTED_KEY_PATH, F_OK) != 0;
else
@@ -411,8 +420,9 @@
value = vb2_get_nv_storage(VB2_NV_BACKUP_NVRAM_REQUEST);
} else if (!strcasecmp(name,"dev_boot_usb")) {
value = vb2_get_nv_storage(VB2_NV_DEV_BOOT_EXTERNAL);
- } else if (!strcasecmp(name,"dev_boot_legacy")) {
- value = vb2_get_nv_storage(VB2_NV_DEV_BOOT_LEGACY);
+ } else if (!strcasecmp(name,"dev_boot_altfw") ||
+ !strcasecmp(name,"dev_boot_legacy")) {
+ value = vb2_get_nv_storage(VB2_NV_DEV_BOOT_ALTFW);
} else if (!strcasecmp(name,"dev_boot_signed_only")) {
value = vb2_get_nv_storage(VB2_NV_DEV_BOOT_SIGNED_ONLY);
} else if (!strcasecmp(name,"dev_enable_udc")) {
@@ -556,12 +566,13 @@
* on simulator */
if (value == 0)
return -1;
- /* Check mount-encrypted key status */
- if (!access(MOUNT_ENCRYPTED_KEY_PATH, F_OK)) {
- /* Remove the mount_encrypted key, and it would
- * also clear the TPM2.0 simulator NV space on
- * it. */
- return remove(MOUNT_ENCRYPTED_KEY_PATH);
+ const char *tpm_path =
+ VTPM_PROXY ? TPM_SIMULATOR_NVCHIP_PATH
+ : MOUNT_ENCRYPTED_KEY_PATH;
+ /* Check TPM simulator data status */
+ if (!access(tpm_path, F_OK)) {
+ /* Remove the TPM2.0 simulator data */
+ return remove(tpm_path);
} else {
/* Return success when the file is already
* removed */
@@ -620,9 +631,10 @@
} else if (!strcasecmp(name,"dev_boot_usb")) {
return vb2_set_nv_storage_with_backup(
VB2_NV_DEV_BOOT_EXTERNAL, value);
- } else if (!strcasecmp(name,"dev_boot_legacy")) {
+ } else if (!strcasecmp(name,"dev_boot_altfw") ||
+ !strcasecmp(name,"dev_boot_legacy")) {
return vb2_set_nv_storage_with_backup(
- VB2_NV_DEV_BOOT_LEGACY, value);
+ VB2_NV_DEV_BOOT_ALTFW, value);
} else if (!strcasecmp(name,"dev_boot_signed_only")) {
return vb2_set_nv_storage_with_backup(
VB2_NV_DEV_BOOT_SIGNED_ONLY, value);
@@ -671,6 +683,16 @@
} else if (!strcasecmp(name, "dev_default_boot")) {
int i;
+ /* "legacy" term deprecated in favour of "altfw"
+ (see: b/179458327) */
+ if (!strcasecmp(value, "legacy")) {
+ fprintf(stderr,
+ "!!!\n"
+ "!!! PLEASE USE 'altfw' INSTEAD OF 'legacy'\n"
+ "!!!\n");
+ value = "altfw";
+ }
+
for (i = 0; i < ARRAY_SIZE(default_boot); i++) {
if (!strcasecmp(value, default_boot[i]))
return vb2_set_nv_storage(
diff --git a/host/lib/flashrom.c b/host/lib/flashrom.c
index 62ab1bc..e83dfb2 100644
--- a/host/lib/flashrom.c
+++ b/host/lib/flashrom.c
@@ -155,7 +155,7 @@
FLASHROM_EXEC_NAME,
"-p",
programmer,
- "--fast-verify",
+ "--noverify-all",
"-w",
region ? "-i" : tmpfile,
region ? region_param : NULL,
diff --git a/host/lib/host_common.c b/host/lib/host_common.c
index 63b45f2..82a5954 100644
--- a/host/lib/host_common.c
+++ b/host/lib/host_common.c
@@ -12,7 +12,6 @@
#include "2sysincludes.h"
#include "host_common.h"
#include "host_key21.h"
-#include "vb2_common.h"
struct vb2_fw_preamble *vb2_create_fw_preamble(
uint32_t firmware_version,
@@ -134,3 +133,22 @@
/* Return the header */
return h;
}
+
+void vb2_kernel_get_vmlinuz_header(const struct vb2_kernel_preamble *preamble,
+ uint64_t *vmlinuz_header_address,
+ uint32_t *vmlinuz_header_size)
+{
+ if (preamble->header_version_minor < 1) {
+ *vmlinuz_header_address = 0;
+ *vmlinuz_header_size = 0;
+ } else {
+ /*
+ * Set header and size only if the preamble header version is >
+ * 2.1 as they don't exist in version 2.0 (Note that we don't
+ * need to check header_version_major; if that's not 2 then
+ * vb2_verify_kernel_preamble() would have already failed.
+ */
+ *vmlinuz_header_address = preamble->vmlinuz_header_address;
+ *vmlinuz_header_size = preamble->vmlinuz_header_size;
+ }
+}
diff --git a/host/lib/host_key2.c b/host/lib/host_key2.c
index 913c6df..e2e3f31 100644
--- a/host/lib/host_key2.c
+++ b/host/lib/host_key2.c
@@ -19,7 +19,6 @@
#include "host_key21.h"
#include "host_key.h"
#include "host_misc.h"
-#include "vb2_common.h"
enum vb2_crypto_algorithm vb2_get_crypto_algorithm(
enum vb2_hash_algorithm hash_alg,
diff --git a/host/lib/host_keyblock.c b/host/lib/host_keyblock.c
index a7dbede..e5634ce 100644
--- a/host/lib/host_keyblock.c
+++ b/host/lib/host_keyblock.c
@@ -17,7 +17,6 @@
#include "host_key21.h"
#include "host_keyblock.h"
#include "host_key.h"
-#include "vb2_common.h"
struct vb2_keyblock *vb2_create_keyblock(
const struct vb2_packed_key *data_key,
diff --git a/host/lib/host_signature.c b/host/lib/host_signature.c
index db536c6..5b71d29 100644
--- a/host/lib/host_signature.c
+++ b/host/lib/host_signature.c
@@ -21,7 +21,6 @@
#include "2sysincludes.h"
#include "host_common.h"
#include "host_signature21.h"
-#include "vb2_common.h"
/* Invoke [external_signer] command with [pem_file] as an argument, contents of
* [inbuf] passed redirected to stdin, and the stdout of the command is put
diff --git a/host/lib/host_signature2.c b/host/lib/host_signature2.c
index f7caa71..b6cd652 100644
--- a/host/lib/host_signature2.c
+++ b/host/lib/host_signature2.c
@@ -22,7 +22,6 @@
#include "host_common.h"
#include "host_key21.h"
#include "host_signature21.h"
-#include "vb2_common.h"
struct vb2_signature *vb2_alloc_signature(uint32_t sig_size,
uint32_t data_size)
diff --git a/host/lib/include/host_common.h b/host/lib/include/host_common.h
index 55b15d3..a37a6c9 100644
--- a/host/lib/include/host_common.h
+++ b/host/lib/include/host_common.h
@@ -64,4 +64,18 @@
uint32_t desired_size,
const struct vb2_private_key *signing_key);
+/**
+ * Retrieve the 16-bit vmlinuz header address and size from the preamble.
+ *
+ * Size 0 means there is no 16-bit vmlinuz header present. Old preamble
+ * versions (<2.1) return 0 for both fields.
+ *
+ * @param preamble Preamble to check
+ * @param vmlinuz_header_address Destination for header address
+ * @param vmlinuz_header_size Destination for header size
+ */
+void vb2_kernel_get_vmlinuz_header(const struct vb2_kernel_preamble *preamble,
+ uint64_t *vmlinuz_header_address,
+ uint32_t *vmlinuz_header_size);
+
#endif /* VBOOT_REFERENCE_HOST_COMMON_H_ */
diff --git a/host/lib/util_misc.c b/host/lib/util_misc.c
index c99947f..26f7dac 100644
--- a/host/lib/util_misc.c
+++ b/host/lib/util_misc.c
@@ -20,7 +20,6 @@
#include "host_key21.h"
#include "openssl_compat.h"
#include "util_misc.h"
-#include "vb2_common.h"
const char *packed_key_sha1_string(const struct vb2_packed_key *key)
{
diff --git a/scripts/image_signing/common.sh b/scripts/image_signing/common.sh
index 9541ca0..efa00a2 100644
--- a/scripts/image_signing/common.sh
+++ b/scripts/image_signing/common.sh
@@ -10,25 +10,6 @@
. "$(dirname "$0")/common_minimal.sh"
CROS_LOG_PREFIX="${PROG}: "
-# Array of actions that are executed during the clean up process.
-declare -a cleanup_actions
-
-# Adds an action to be executed during the clean up process.
-# Actions are executed in the reverse order of when they were added.
-# ARGS: ACTION
-add_cleanup_action() {
- cleanup_actions[${#cleanup_actions[*]}]=$1
-}
-
-# Performs the latest clean up action and removes it from the list.
-perform_latest_cleanup_action() {
- local num_actions=${#cleanup_actions[*]}
- if [ "${num_actions}" -gt 0 ]; then
- eval "${cleanup_actions[$num_actions-1]} || true" > /dev/null 2>&1
- unset "cleanup_actions[$num_actions-1]"
- fi
-}
-
# Performs clean up by executing actions in the cleanup_actions array in
# reversed order.
cleanup() {
@@ -36,9 +17,8 @@
rv=$?
set +e
- while [ ${#cleanup_actions[*]} -gt 0 ]; do
- perform_latest_cleanup_action
- done
+ cleanup_temps_and_mounts
+ cleanup_loopbacks
set -e
return $rv
@@ -158,6 +138,3 @@
# This will override the trap set in common_minmal.sh
trap "cleanup" INT TERM EXIT
-
-add_cleanup_action "cleanup_temps_and_mounts"
-add_cleanup_action "cleanup_loopbacks"
diff --git a/scripts/image_signing/ensure_no_nonrelease_files.sh b/scripts/image_signing/ensure_no_nonrelease_files.sh
index 48c75af..9e549ed 100755
--- a/scripts/image_signing/ensure_no_nonrelease_files.sh
+++ b/scripts/image_signing/ensure_no_nonrelease_files.sh
@@ -37,9 +37,14 @@
# Either way, load test-expectations data from config.
. "${configfile}" || return 1
- local loopdev=$(loopback_partscan "${image}")
- local rootfs=$(make_temp_dir)
- mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+ local loopdev rootfs
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
+ else
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
+ mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ fi
# Pick the right set of test-expectation data to use.
local brdvar=$(get_boardvar_from_lsb_release "${rootfs}")
eval "release_file_blocklist=(\"\${RELEASE_FILE_BLOCKLIST_${brdvar}[@]}\")"
diff --git a/scripts/image_signing/ensure_not_ASAN.sh b/scripts/image_signing/ensure_not_ASAN.sh
index 16cc88c..f19b1dd 100755
--- a/scripts/image_signing/ensure_not_ASAN.sh
+++ b/scripts/image_signing/ensure_not_ASAN.sh
@@ -11,26 +11,31 @@
. "$(dirname "$0")/common.sh"
usage() {
- echo "Usage $PROG image"
+ echo "Usage $PROG image"
}
main() {
- if [ $# -ne 1 ]; then
- usage
- exit 1
- fi
+ if [[ $# -ne 1 ]]; then
+ usage
+ exit 1
+ fi
- local image="$1"
+ local image="$1"
- local loopdev=$(loopback_partscan "${image}")
- local rootfs=$(make_temp_dir)
+ local loopdev rootfs
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
+ else
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+ fi
- # This mirrors the check performed in the platform_ToolchainOptions
- # autotest.
- if readelf -s "$rootfs/opt/google/chrome/chrome" | \
- grep -q __asan_init; then
- exit 1
- fi
+ # This mirrors the check performed in the platform_ToolchainOptions
+ # autotest.
+ if readelf -s "$rootfs/opt/google/chrome/chrome" | \
+ grep -q __asan_init; then
+ exit 1
+ fi
}
main "$@"
diff --git a/scripts/image_signing/ensure_not_tainted_license.sh b/scripts/image_signing/ensure_not_tainted_license.sh
index cd64049..7eab1c9 100755
--- a/scripts/image_signing/ensure_not_tainted_license.sh
+++ b/scripts/image_signing/ensure_not_tainted_license.sh
@@ -42,12 +42,16 @@
license=$(find "${license_dir}" -name about_os_credits.html 2>/dev/null)
if [[ -z "${license}" ]]; then
- echo "License file about_os_credits.html not found in ${license_dir}"
- exit 1
+ echo "License file about_os_credits.html not found in ${license_dir}."
+ echo "Skipping the check of tainted license."
+ exit 0
fi
tainted_tag="<!-- tainted -->"
- tainted_status=$(grep "${tainted_tag}" "${license}")
+ # Add "|| :" to the grep command to prevent it from returning error code 1 if
+ # no match is found, which would cause the script to exit immediately with
+ # error code 1 due to set -e.
+ tainted_status=$(grep "${tainted_tag}" "${license}") || :
if [[ -n "${tainted_status}" ]]; then
echo "${license}:"
echo "License file contains packages with LICENSE=TAINTED."
@@ -60,6 +64,7 @@
/^[[:space:]]*$/d
p
}' "${license}"
+ exit 1
fi
exit 0
}
diff --git a/scripts/image_signing/ensure_secure_kernelparams.sh b/scripts/image_signing/ensure_secure_kernelparams.sh
index 12bfbe5..b971ab4 100755
--- a/scripts/image_signing/ensure_secure_kernelparams.sh
+++ b/scripts/image_signing/ensure_secure_kernelparams.sh
@@ -100,9 +100,8 @@
# which is the install kernel on the recovery image.
# crosbug.com/24274
local loop_kern="${loopdev}p4"
- local loop_rootfs="${loopdev}p3"
local rootfs=$(make_temp_dir)
- sudo mount -o ro "${loop_rootfs}" "${rootfs}"
+ mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
# Pick the right set of test-expectation data to use.
local boardvar=$(get_boardvar_from_lsb_release "${rootfs}")
diff --git a/scripts/image_signing/ensure_update_verification.sh b/scripts/image_signing/ensure_update_verification.sh
index c72b0f6..e3929c5 100755
--- a/scripts/image_signing/ensure_update_verification.sh
+++ b/scripts/image_signing/ensure_update_verification.sh
@@ -23,10 +23,16 @@
fi
local image=$1
- local loopdev=$(loopback_partscan "${image}")
- local rootfs=$(make_temp_dir)
+
+ local loopdev rootfs
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
+ else
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
+ mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+ fi
local key_location="/usr/share/update_engine/update-payload-key.pub.pem"
- mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
if [ ! -e "$rootfs/$key_location" ]; then
die "Update payload verification key not found at $key_location"
fi
diff --git a/scripts/image_signing/gbb_flags_common.sh b/scripts/image_signing/gbb_flags_common.sh
index 100f37d..63c3f12 100755
--- a/scripts/image_signing/gbb_flags_common.sh
+++ b/scripts/image_signing/gbb_flags_common.sh
@@ -26,10 +26,10 @@
VB2_GBB_FLAG_FORCE_DEV_BOOT_USB 0x00000010
VB2_GBB_FLAG_DISABLE_FW_ROLLBACK_CHECK 0x00000020
VB2_GBB_FLAG_ENTER_TRIGGERS_TONORM 0x00000040
- VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY 0x00000080
+ VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW 0x00000080
VB2_GBB_FLAG_RUNNING_FAFT 0x00000100
VB2_GBB_FLAG_DISABLE_EC_SOFTWARE_SYNC 0x00000200
- VB2_GBB_FLAG_DEFAULT_DEV_BOOT_LEGACY 0x00000400
+ VB2_GBB_FLAG_DEFAULT_DEV_BOOT_ALTFW 0x00000400
VB2_GBB_FLAG_DISABLE_AUXFW_SOFTWARE_SYNC 0x00000800
VB2_GBB_FLAG_DISABLE_LID_SHUTDOWN 0x00001000
VB2_GBB_FLAG_FORCE_MANUAL_RECOVERY 0x00004000
@@ -55,5 +55,5 @@
}
flashrom_write() {
- flashrom -p host -i GBB --fast-verify -w "$@"
+ flashrom -p host -i GBB --noverify-all -w "$@"
}
diff --git a/scripts/image_signing/insert_au_publickey.sh b/scripts/image_signing/insert_au_publickey.sh
index 9d1597d..fe0dbcc 100755
--- a/scripts/image_signing/insert_au_publickey.sh
+++ b/scripts/image_signing/insert_au_publickey.sh
@@ -21,10 +21,17 @@
EOF
exit 1
fi
- local loopdev=$(loopback_partscan "${image}")
- local rootfs=$(make_temp_dir)
+
+ local loopdev rootfs
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
+ else
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
+ mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ fi
+
local key_location="/usr/share/update_engine/"
- mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
sudo mkdir -p "$rootfs/$key_location"
sudo cp "$pub_key" "$rootfs/$key_location/update-payload-key.pub.pem"
sudo chown root:root "$rootfs/$key_location/update-payload-key.pub.pem"
diff --git a/scripts/image_signing/set_channel.sh b/scripts/image_signing/set_channel.sh
index dc21246..d4e64ad 100755
--- a/scripts/image_signing/set_channel.sh
+++ b/scripts/image_signing/set_channel.sh
@@ -26,10 +26,14 @@
local to=$2
local loopdev rootfs lsb
- loopdev=$(loopback_partscan "${image}")
- rootfs=$(make_temp_dir)
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
+ else
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
+ mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ fi
lsb="${rootfs}/etc/lsb-release"
- mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
# Get the current channel on the image.
local from=$(lsbval "${lsb}" 'CHROMEOS_RELEASE_TRACK')
from=${from%"-channel"}
diff --git a/scripts/image_signing/set_lsb_release.sh b/scripts/image_signing/set_lsb_release.sh
index e847abb..55c1653 100755
--- a/scripts/image_signing/set_lsb_release.sh
+++ b/scripts/image_signing/set_lsb_release.sh
@@ -11,15 +11,17 @@
set_lsb_release_keyval() {
local rootfs=$1
+ local lsb="${rootfs}/etc/lsb-release"
local key=$2
local value=$3
- local temp_lsb_release="$rootfs/etc/temp-lsb-release"
- echo "$key=$value" | sudo tee "$temp_lsb_release" > /dev/null
- grep -Ev "^$key=" "$rootfs/etc/lsb-release" \
- | sudo tee -a "$temp_lsb_release" > /dev/null
- sudo sort -o "$rootfs/etc/lsb-release" "$temp_lsb_release"
- sudo rm -f "$temp_lsb_release"
- restore_lsb_selinux "$rootfs/etc/lsb-release"
+ local data
+ data=$(
+ (
+ grep -Ev "^${key}=" "${lsb}"
+ echo "${key}=${value}"
+ ) | sort
+ )
+ sudo tee "${lsb}" <<<"${data}" >/dev/null
}
main() {
@@ -45,17 +47,25 @@
exit 1
fi
+ # If there are no key/value pairs to process, we don't need write access.
+ local ro=$([[ $# -eq 0 ]] && echo true || echo false)
+
local image=$1
shift
- local loopdev=$(loopback_partscan "${image}")
- local rootfs=$(make_temp_dir)
+ local loopdev rootfs
- # If there are no key/value pairs to process, we don't need write access.
- if [[ $# -eq 0 ]]; then
- mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+ if [[ -d "${image}" ]]; then
+ rootfs="${image}"
else
- mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
- touch "${image}" # Updates the image modification time.
+ rootfs=$(make_temp_dir)
+ loopdev=$(loopback_partscan "${image}")
+
+ if ${ro}; then
+ mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+ else
+ mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ touch "${image}" # Updates the image modification time.
+ fi
fi
# Process all the key/value pairs.
@@ -65,6 +75,9 @@
shift 2
set_lsb_release_keyval "${rootfs}" "${key}" "${value}"
done
+ if ! ${ro}; then
+ restore_lsb_selinux "${rootfs}/etc/lsb-release"
+ fi
# Dump the final state.
cat "${rootfs}/etc/lsb-release"
diff --git a/scripts/image_signing/sign_gsc_firmware.sh b/scripts/image_signing/sign_gsc_firmware.sh
index 30e2795..af7b7da 100755
--- a/scripts/image_signing/sign_gsc_firmware.sh
+++ b/scripts/image_signing/sign_gsc_firmware.sh
@@ -25,7 +25,7 @@
PRE_PVT_BID_FLAG=0x10
MP_BID_FLAG=0x10000
-CR50_FACTORY_VERSION="0.3.22"
+CR50_NODE_LOCKED_VERSION="0.5.12"
# Convert unsigned 32 bit value into a signed one.
to_int32() {
@@ -151,9 +151,10 @@
# that the manifest conforms to GSC version numbering and board ID flags
# conventions for various build images:
#
-# - only factory version binaries can be converted to node locked images,
-# board IDs for node locked images come from signing instructions, and the
-# config1 manifest field value must have the 0x80000000 bit set.
+# - only binaries where version is set to CR50_NODE_LOCKED_VERSION can be
+# converted to node locked images. Board IDs for node locked images come
+# from signing instructions, and the config1 manifest field value must have
+# the 0x80000000 bit set.
#
# - when signing pre-pvt binaries (major version number is even) the 0x10
# flags bit must be set.
@@ -197,8 +198,9 @@
if [[ -z ${INSN_DEVICE_ID:-} ]]; then
die "Node locked target without Device ID value"
fi
- # Case of a node locked image, it must have the fixed factory version.
- if [[ "${epoch}.${major}.${minor}" != "${CR50_FACTORY_VERSION}" ]];then
+ # Case of a node locked image, it must have the fixed version.
+ if [[ "${epoch}.${major}.${minor}" != "${CR50_NODE_LOCKED_VERSION}" ]]
+ then
die "Won't create node locked images for version $epoch.$major.$minor"
fi
@@ -492,6 +494,7 @@
local output_file="$9"
local generation="${10}"
local temp_dir
+ local chip_name
temp_dir="$(make_temp_dir)"
@@ -500,11 +503,13 @@
# H1 flash size, image size must match.
IMAGE_SIZE="$(( 512 * 1024 ))"
IMAGE_BASE="0x40000"
+ chip_name="cr50"
;;
(d)
# D2 flash size, image size must match.
IMAGE_SIZE="$(( 1024 * 1024 ))"
IMAGE_BASE="0x80000"
+ chip_name="ti50"
;;
esac
@@ -544,6 +549,9 @@
paste_bin "${output_file}" "${bin}" "${IMAGE_BASE}" "${hex_base}"
done
+ # Tell the signer how to rename the @CHIP@ portion of the output.
+ echo "${chip_name}" > "${output_file}.rename"
+
info "Image successfully signed to ${output_file}"
}
diff --git a/scripts/image_signing/tag_image.sh b/scripts/image_signing/tag_image.sh
index 8a01012..fb9492e 100755
--- a/scripts/image_signing/tag_image.sh
+++ b/scripts/image_signing/tag_image.sh
@@ -196,9 +196,13 @@
fi
# First round, mount as read-only and check if we need any modifications.
-loopdev=$(loopback_partscan "${IMAGE}")
-rootfs=$(make_temp_dir)
-mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+if [[ -d "${IMAGE}" ]]; then
+ rootfs="${IMAGE}"
+else
+ loopdev=$(loopback_partscan "${IMAGE}")
+ rootfs=$(make_temp_dir)
+ mount_loop_image_partition_ro "${loopdev}" 3 "${rootfs}"
+fi
# we don't have tags in stateful partition yet...
# stateful_dir=$(make_temp_dir)
@@ -210,8 +214,10 @@
if [ ${g_modified} = ${FLAGS_TRUE} ]; then
# Remount as RW. We can't use `mount -o rw,remount` because of the bits in
# the ext4 header we've set to block that. See enable_rw_mount for details.
- sudo umount "${rootfs}"
- mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ if [[ ! -d "${IMAGE}" ]]; then
+ sudo umount "${rootfs}"
+ mount_loop_image_partition "${loopdev}" 3 "${rootfs}"
+ fi
# second round, apply the modification to image.
process_all_tags "${rootfs}" ${FLAGS_TRUE}
diff --git a/tests/devkeys/android/networkstack.pk8 b/tests/devkeys/android/networkstack.pk8
new file mode 100644
index 0000000..890d9d3
--- /dev/null
+++ b/tests/devkeys/android/networkstack.pk8
Binary files differ
diff --git a/tests/devkeys/android/networkstack.x509.pem b/tests/devkeys/android/networkstack.x509.pem
new file mode 100644
index 0000000..042c4e3
--- /dev/null
+++ b/tests/devkeys/android/networkstack.x509.pem
@@ -0,0 +1,23 @@
+-----BEGIN CERTIFICATE-----
+MIIDxzCCAq+gAwIBAgIUcfGSt74kh+tpBdU4k71ijVm1/0cwDQYJKoZIhvcNAQEL
+BQAwdDELMAkGA1UEBhMCVVMxEzARBgNVBAgMCkNhbGlmb3JuaWExFjAUBgNVBAcM
+DU1vdW50YWluIFZpZXcxFDASBgNVBAoMC0dvb2dsZSBJbmMuMRAwDgYDVQQLDAdB
+bmRyb2lkMRAwDgYDVQQDDAdBbmRyb2lkMB4XDTIxMDQwNTIzMDk1NloXDTQ4MDgy
+MTIzMDk1NlowdDELMAkGA1UEBhMCVVMxEzARBgNVBAgMCkNhbGlmb3JuaWExFjAU
+BgNVBAcMDU1vdW50YWluIFZpZXcxFDASBgNVBAoMC0dvb2dsZSBJbmMuMRAwDgYD
+VQQLDAdBbmRyb2lkMRAwDgYDVQQDDAdBbmRyb2lkMIIBIDANBgkqhkiG9w0BAQEF
+AAOCAQ0AMIIBCAKCAQEA0KHW5P5+dCq7OkVkGRmG0eYskcbgRK3DvTY7QPXCdnOm
+Fmq08S2l23mN1C+3+XMon0/Gh3DRr+lVLX3GZPoHX3e2ZTt8tu0Ee3k8T8VopfG9
+OpPlSzfazgI8sKtLe3wJ3RDalTlNd8Ne2YNRMY8RIkIwbySzUqkTixVk57NgMXpj
+tWmP19DOZPxXsGUa5m0qSS5/demnYAIoD+mg0Wd+xG2Y1ErT9O/j2l92ekm8+JKy
+jJ0W47el/mqO392JgNAEvcI9NbrnTaNi5Zq2PKhBhK0ohXOMyHUodUSmtBTWtW8n
+U+FK70ese+OzWQbjRryrmGYWB9ybc7YZ/FhH4US+rwIBA6NTMFEwHQYDVR0OBBYE
+FMGqz0YmVUA8iWBwLCMdoTFsidIiMB8GA1UdIwQYMBaAFMGqz0YmVUA8iWBwLCMd
+oTFsidIiMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQELBQADggEBAKygSG3r
+7SHEb/nox88Pu31lxERrsjmNCtxJJMFlbf8sq1nWx59lmTLOW5sFKyWGH1Mf8f8O
+nXiZ6V+5obyAt05MJOBiSIGKBk21ds9r2ACCuFpJ+MAS3SNN7HlSfNvzRbGV3+gb
+V6FOH+2ndbqN3dkXUDctWXjNiq5QQlFFI4fIvvwiul45HZvDRrNRuexT1jzOlLVF
+Qe45E5QbJYVPMUe37kCVm1Ty3N+e/s2n1NsSHoD5BK+kvb+BPL3pK4dK62HzcdVp
+TB1EZFtrL8+aun1qhlEYNKlR/TNQdIPwZWH6ZmT7bF2GCfJcxshgWmajN/cW1rdc
+OEUdUtGkI9lgNiI=
+-----END CERTIFICATE-----
diff --git a/tests/vb20_api_kernel_tests.c b/tests/vb20_api_kernel_tests.c
index 676cb19..893cd4e 100644
--- a/tests/vb20_api_kernel_tests.c
+++ b/tests/vb20_api_kernel_tests.c
@@ -15,7 +15,6 @@
#include "2secdata.h"
#include "2sysincludes.h"
#include "test_common.h"
-#include "vb2_common.h"
#include "vboot_struct.h"
/* Common context for tests */
diff --git a/tests/vb20_kernel_tests.c b/tests/vb20_kernel_tests.c
index 3f26549..8766114 100644
--- a/tests/vb20_kernel_tests.c
+++ b/tests/vb20_kernel_tests.c
@@ -15,7 +15,6 @@
#include "2secdata.h"
#include "2sysincludes.h"
#include "test_common.h"
-#include "vb2_common.h"
/* Common context for tests */
static uint8_t workbuf[VB2_KERNEL_WORKBUF_RECOMMENDED_SIZE]
@@ -228,7 +227,7 @@
reset_common_data(FOR_KEYBLOCK);
mock_vblock.k.data_key_data[0] ^= 0xa0;
TEST_EQ(vb2_verify_keyblock_hash(kb, kb->keyblock_size, &wb),
- VB2_ERROR_KEYBLOCK_SIG_INVALID,
+ VB2_ERROR_KEYBLOCK_HASH_INVALID_IN_DEV_MODE,
"Keyblock check hash invalid");
}
diff --git a/tests/vb20_rsa_padding_tests.c b/tests/vb20_rsa_padding_tests.c
index 03a38ee..90ff42a 100644
--- a/tests/vb20_rsa_padding_tests.c
+++ b/tests/vb20_rsa_padding_tests.c
@@ -6,13 +6,13 @@
#include <stdint.h>
#include <stdio.h>
+#include "2common.h"
#include "2rsa.h"
#include "2sysincludes.h"
#include "file_keys.h"
#include "host_key.h"
#include "rsa_padding_test.h"
#include "test_common.h"
-#include "vb2_common.h"
vb2_error_t hwcrypto_modexp_return_value = VB2_SUCCESS;
vb2_error_t vb2ex_hwcrypto_modexp(const struct vb2_public_key *key,
diff --git a/tests/vb2_api_tests.c b/tests/vb2_api_tests.c
index 1fabb60..40fdf59 100644
--- a/tests/vb2_api_tests.c
+++ b/tests/vb2_api_tests.c
@@ -15,7 +15,6 @@
#include "2secdata.h"
#include "2sysincludes.h"
#include "test_common.h"
-#include "vb2_common.h"
/* Common context for tests */
diff --git a/tests/vb2_auxfw_sync_tests.c b/tests/vb2_auxfw_sync_tests.c
index f779ac0..48ce952 100644
--- a/tests/vb2_auxfw_sync_tests.c
+++ b/tests/vb2_auxfw_sync_tests.c
@@ -16,7 +16,6 @@
#include "host_common.h"
#include "load_kernel_fw.h"
#include "test_common.h"
-#include "vboot_audio.h"
#include "vboot_kernel.h"
#include "vboot_struct.h"
diff --git a/tests/vb2_common2_tests.c b/tests/vb2_common2_tests.c
index 89a560c..3f06289 100644
--- a/tests/vb2_common2_tests.c
+++ b/tests/vb2_common2_tests.c
@@ -9,36 +9,63 @@
#include <stdio.h>
#include <string.h>
+#include "2common.h"
#include "2rsa.h"
#include "2sysincludes.h"
#include "file_keys.h"
#include "host_common.h"
#include "host_key21.h"
#include "test_common.h"
-#include "vb2_common.h"
static const uint8_t test_data[] = "This is some test data to sign.";
static const uint32_t test_size = sizeof(test_data);
-static enum {
+static enum hwcrypto_state {
HWCRYPTO_OK,
HWCRYPTO_NOTSUPPORTED,
HWCRYPTO_ERROR,
-} hwcrypto_state;
+ HWCRYPTO_ABORT,
+} hwcrypto_state_rsa, hwcrypto_state_digest;
-vb2_error_t vb2ex_hwcrypto_rsa_verify_digest(const struct vb2_public_key *key,
- const uint8_t *sig, const uint8_t *digest)
+static vb2_error_t hwcrypto_mock(enum hwcrypto_state *state)
{
- switch (hwcrypto_state) {
+ switch (*state) {
case HWCRYPTO_OK:
return VB2_SUCCESS;
case HWCRYPTO_NOTSUPPORTED:
return VB2_ERROR_EX_HWCRYPTO_UNSUPPORTED;
case HWCRYPTO_ERROR:
- return VB2_ERROR_RSA_VERIFY_DIGEST;
+ return VB2_ERROR_MOCK;
+ case HWCRYPTO_ABORT:
+ vb2ex_abort();
+ /* shouldn't reach here but added for compiler */
+ return VB2_ERROR_MOCK;
}
}
+vb2_error_t vb2ex_hwcrypto_digest_init(enum vb2_hash_algorithm hash_alg,
+ uint32_t data_size)
+{
+ return hwcrypto_mock(&hwcrypto_state_digest);
+}
+
+vb2_error_t vb2ex_hwcrypto_digest_extend(const uint8_t *buf, uint32_t size)
+{
+ return hwcrypto_mock(&hwcrypto_state_digest);
+}
+
+vb2_error_t vb2ex_hwcrypto_digest_finalize(uint8_t *digest,
+ uint32_t digest_size)
+{
+ return hwcrypto_mock(&hwcrypto_state_digest);
+}
+
+vb2_error_t vb2ex_hwcrypto_rsa_verify_digest(const struct vb2_public_key *key,
+ const uint8_t *sig, const uint8_t *digest)
+{
+ return hwcrypto_mock(&hwcrypto_state_rsa);
+}
+
static void test_unpack_key(const struct vb2_packed_key *key1)
{
@@ -109,6 +136,9 @@
uint32_t sig_total_size = sig->sig_offset + sig->sig_size;
struct vb2_signature *sig2;
+ hwcrypto_state_rsa = HWCRYPTO_ABORT;
+ hwcrypto_state_digest = HWCRYPTO_ABORT;
+
vb2_workbuf_init(&wb, workbuf, sizeof(workbuf));
/* Allocate signature copy for tests */
@@ -155,18 +185,57 @@
pubk.allow_hwcrypto = 1;
- hwcrypto_state = HWCRYPTO_OK;
+ hwcrypto_state_digest = HWCRYPTO_OK;
+ hwcrypto_state_rsa = HWCRYPTO_OK;
memcpy(sig2, sig, sig_total_size);
vb2_signature_data_mutable(sig2)[0] ^= 0x5A;
TEST_EQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
0, "vb2_verify_data() hwcrypto ok");
- hwcrypto_state = HWCRYPTO_ERROR;
+ hwcrypto_state_rsa = HWCRYPTO_ERROR;
memcpy(sig2, sig, sig_total_size);
TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
0, "vb2_verify_data() hwcrypto error");
- hwcrypto_state = HWCRYPTO_NOTSUPPORTED;
+ hwcrypto_state_rsa = HWCRYPTO_NOTSUPPORTED;
+ memcpy(sig2, sig, sig_total_size);
+ TEST_EQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto fallback ok");
+
+ memcpy(sig2, sig, sig_total_size);
+ sig2->sig_size -= 16;
+ TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto fallback error");
+
+ hwcrypto_state_digest = HWCRYPTO_ERROR;
+ hwcrypto_state_rsa = HWCRYPTO_OK;
+ memcpy(sig2, sig, sig_total_size);
+ TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto error");
+
+ hwcrypto_state_rsa = HWCRYPTO_ERROR;
+ memcpy(sig2, sig, sig_total_size);
+ TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto error");
+
+ hwcrypto_state_rsa = HWCRYPTO_NOTSUPPORTED;
+ memcpy(sig2, sig, sig_total_size);
+ TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto fallback error");
+
+ hwcrypto_state_digest = HWCRYPTO_NOTSUPPORTED;
+ hwcrypto_state_rsa = HWCRYPTO_OK;
+ memcpy(sig2, sig, sig_total_size);
+ vb2_signature_data_mutable(sig2)[0] ^= 0x5A;
+ TEST_EQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto ok");
+
+ hwcrypto_state_rsa = HWCRYPTO_ERROR;
+ memcpy(sig2, sig, sig_total_size);
+ TEST_NEQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
+ 0, "vb2_verify_data() hwcrypto error");
+
+ hwcrypto_state_rsa = HWCRYPTO_NOTSUPPORTED;
memcpy(sig2, sig, sig_total_size);
TEST_EQ(vb2_verify_data(test_data, test_size, sig2, &pubk, &wb),
0, "vb2_verify_data() hwcrypto fallback ok");
diff --git a/tests/vb2_common3_tests.c b/tests/vb2_common3_tests.c
index 4219222..5805204 100644
--- a/tests/vb2_common3_tests.c
+++ b/tests/vb2_common3_tests.c
@@ -7,6 +7,7 @@
#include <stdio.h>
+#include "2common.h"
#include "2rsa.h"
#include "2sysincludes.h"
#include "file_keys.h"
@@ -15,7 +16,6 @@
#include "host_key.h"
#include "host_signature.h"
#include "test_common.h"
-#include "vb2_common.h"
static void resign_keyblock(struct vb2_keyblock *h,
const struct vb2_private_key *key)
diff --git a/tests/vb2_ec_sync_tests.c b/tests/vb2_ec_sync_tests.c
index be86fbb..8881ea7 100644
--- a/tests/vb2_ec_sync_tests.c
+++ b/tests/vb2_ec_sync_tests.c
@@ -13,7 +13,6 @@
#include "host_common.h"
#include "load_kernel_fw.h"
#include "test_common.h"
-#include "vboot_audio.h"
#include "vboot_kernel.h"
#include "vboot_struct.h"
diff --git a/tests/vb20_misc_tests.c b/tests/vb2_firmware_tests.c
similarity index 99%
rename from tests/vb20_misc_tests.c
rename to tests/vb2_firmware_tests.c
index fdab37e..681e5d6 100644
--- a/tests/vb20_misc_tests.c
+++ b/tests/vb2_firmware_tests.c
@@ -2,7 +2,7 @@
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*
- * Tests for misc library
+ * Tests for firmware verification library
*/
#include <stdio.h>
@@ -15,7 +15,6 @@
#include "2secdata.h"
#include "2sysincludes.h"
#include "test_common.h"
-#include "vb2_common.h"
/* Common context for tests */
static uint8_t workbuf[VB2_FIRMWARE_WORKBUF_RECOMMENDED_SIZE]
diff --git a/tests/vb2_host_flashrom_tests.c b/tests/vb2_host_flashrom_tests.c
index 9187e75..8552d0a 100644
--- a/tests/vb2_host_flashrom_tests.c
+++ b/tests/vb2_host_flashrom_tests.c
@@ -58,7 +58,7 @@
int captured_verify_int = FLASHROM_VERIFY_UNSPECIFIED;
struct option long_opts[] = {
{
- .name = "fast-verify",
+ .name = "noverify-all",
.has_arg = no_argument,
.flag = &captured_verify_int,
.val = FLASHROM_VERIFY_FAST,
diff --git a/tests/vb2_kernel_tests.c b/tests/vb2_kernel_tests.c
index 4b0a249..0e1cb28 100644
--- a/tests/vb2_kernel_tests.c
+++ b/tests/vb2_kernel_tests.c
@@ -14,7 +14,6 @@
#include "2secdata.h"
#include "2sysincludes.h"
#include "test_common.h"
-#include "vb2_common.h"
#include "vboot_struct.h"
/* Common context for tests */
@@ -140,7 +139,7 @@
return VB2_SUCCESS;
}
-vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t get_info_flags)
+vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t disk_flags)
{
/*
* TODO: Currently we don't have a good way of testing for an ordered
@@ -151,10 +150,10 @@
return mock_vbtlk_retval;
TEST_EQ(!!mock_vbtlk_expect_fixed,
- !!(get_info_flags & VB_DISK_FLAG_FIXED),
+ !!(disk_flags & VB_DISK_FLAG_FIXED),
" VbTryLoadKernel unexpected fixed disk call");
TEST_EQ(!!mock_vbtlk_expect_removable,
- !!(get_info_flags & VB_DISK_FLAG_REMOVABLE),
+ !!(disk_flags & VB_DISK_FLAG_REMOVABLE),
" VbTryLoadKernel unexpected removable disk call");
return mock_vbtlk_retval;
diff --git a/tests/vb2_keyblock_fuzzer.c b/tests/vb2_keyblock_fuzzer.c
index 6fabcd2..2aa83e1 100644
--- a/tests/vb2_keyblock_fuzzer.c
+++ b/tests/vb2_keyblock_fuzzer.c
@@ -7,6 +7,7 @@
#include "2misc.h"
#include "2nvstorage.h"
#include "2rsa.h"
+#include "2rsa_private.h"
#include "2secdata.h"
#include "vboot_test.h"
diff --git a/tests/vb2_misc_tests.c b/tests/vb2_misc_tests.c
index c64552c..a7cc115 100644
--- a/tests/vb2_misc_tests.c
+++ b/tests/vb2_misc_tests.c
@@ -505,14 +505,14 @@
/* Any normal mode boot clears dev boot flags */
reset_common_data();
vb2_nv_set(ctx, VB2_NV_DEV_BOOT_EXTERNAL, 1);
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 1);
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 1);
vb2_nv_set(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY, 1);
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT, 1);
TEST_SUCC(vb2_check_dev_switch(ctx), "dev mode off");
TEST_EQ(vb2_nv_get(ctx, VB2_NV_DEV_BOOT_EXTERNAL),
0, " cleared dev boot external");
- TEST_EQ(vb2_nv_get(ctx, VB2_NV_DEV_BOOT_LEGACY),
- 0, " cleared dev boot legacy");
+ TEST_EQ(vb2_nv_get(ctx, VB2_NV_DEV_BOOT_ALTFW),
+ 0, " cleared dev boot altfw");
TEST_EQ(vb2_nv_get(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY),
0, " cleared dev boot signed only");
TEST_EQ(vb2_nv_get(ctx, VB2_NV_DEV_DEFAULT_BOOT),
@@ -892,14 +892,14 @@
VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL,
"no default boot, boot disk");
- /* Set boot legacy by GBB */
+ /* Set boot altfw by GBB */
reset_common_data();
- gbb.flags |= VB2_GBB_FLAG_DEFAULT_DEV_BOOT_LEGACY;
+ gbb.flags |= VB2_GBB_FLAG_DEFAULT_DEV_BOOT_ALTFW;
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT,
VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL);
TEST_EQ(vb2api_get_dev_default_boot_target(ctx),
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY,
- "GBB set default boot legacy");
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW,
+ "GBB set default boot altfw");
/* Boot from internal disk */
reset_common_data();
@@ -926,36 +926,36 @@
VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL,
"default boot external not allowed");
reset_common_data();
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 1);
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 1);
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT,
VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL);
TEST_EQ(vb2api_get_dev_default_boot_target(ctx),
VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL,
"default boot external not allowed");
- /* Boot legacy */
+ /* Boot altfw */
reset_common_data();
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 1);
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 1);
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT,
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY);
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW);
TEST_EQ(vb2api_get_dev_default_boot_target(ctx),
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY,
- "set default boot legacy");
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW,
+ "set default boot altfw");
- /* Boot legacy not allowed */
+ /* Boot altfw not allowed */
reset_common_data();
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT,
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY);
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW);
TEST_EQ(vb2api_get_dev_default_boot_target(ctx),
VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL,
- "default boot legacy not allowed");
+ "default boot altfw not allowed");
reset_common_data();
vb2_nv_set(ctx, VB2_NV_DEV_BOOT_EXTERNAL, 1);
vb2_nv_set(ctx, VB2_NV_DEV_DEFAULT_BOOT,
- VB2_DEV_DEFAULT_BOOT_TARGET_LEGACY);
+ VB2_DEV_DEFAULT_BOOT_TARGET_ALTFW);
TEST_EQ(vb2api_get_dev_default_boot_target(ctx),
VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL,
- "default boot legacy not allowed");
+ "default boot altfw not allowed");
}
static void dev_boot_allowed_tests(void)
@@ -977,34 +977,34 @@
/* Legacy boot - not allowed by default */
reset_common_data();
- TEST_EQ(vb2_dev_boot_legacy_allowed(ctx), 0,
- "dev boot legacy - not allowed by default");
+ TEST_EQ(vb2_dev_boot_altfw_allowed(ctx), 0,
+ "dev boot altfw - not allowed by default");
/* Legacy boot - enabled by nvdata */
reset_common_data();
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 1);
- TEST_EQ(vb2_dev_boot_legacy_allowed(ctx), 1,
- "dev boot legacy - nvdata enabled");
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 1);
+ TEST_EQ(vb2_dev_boot_altfw_allowed(ctx), 1,
+ "dev boot altfw - nvdata enabled");
/* Legacy boot - enabled by FWMP */
reset_common_data();
- fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_LEGACY;
- TEST_EQ(vb2_dev_boot_legacy_allowed(ctx), 1,
- "dev boot legacy - secdata enabled");
+ fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_ALTFW;
+ TEST_EQ(vb2_dev_boot_altfw_allowed(ctx), 1,
+ "dev boot altfw - secdata enabled");
/* Legacy boot - force enabled by GBB */
reset_common_data();
- gbb.flags |= VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY;
- TEST_EQ(vb2_dev_boot_legacy_allowed(ctx), 1,
- "dev boot legacy - GBB force enabled");
+ gbb.flags |= VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW;
+ TEST_EQ(vb2_dev_boot_altfw_allowed(ctx), 1,
+ "dev boot altfw - GBB force enabled");
/* Legacy boot - set all flags */
reset_common_data();
- vb2_nv_set(ctx, VB2_NV_DEV_BOOT_LEGACY, 1);
- fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_LEGACY;
- gbb.flags |= VB2_GBB_FLAG_FORCE_DEV_BOOT_LEGACY;
- TEST_EQ(vb2_dev_boot_legacy_allowed(ctx), 1,
- "dev boot legacy - all flags set");
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_ALTFW, 1);
+ fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_ALTFW;
+ gbb.flags |= VB2_GBB_FLAG_FORCE_DEV_BOOT_ALTFW;
+ TEST_EQ(vb2_dev_boot_altfw_allowed(ctx), 1,
+ "dev boot altfw - all flags set");
/* External boot - not allowed by default */
reset_common_data();
diff --git a/tests/vb2_nvstorage_tests.c b/tests/vb2_nvstorage_tests.c
index a49f162..94bcfca 100644
--- a/tests/vb2_nvstorage_tests.c
+++ b/tests/vb2_nvstorage_tests.c
@@ -41,7 +41,7 @@
{VB2_NV_LOCALIZATION_INDEX, 0, 0x69, 0xB0, "localization index"},
{VB2_NV_KERNEL_FIELD, 0, 0x1234, 0xFEDC, "kernel field"},
{VB2_NV_DEV_BOOT_EXTERNAL, 0, 1, 0, "dev boot usb"},
- {VB2_NV_DEV_BOOT_LEGACY, 0, 1, 0, "dev boot legacy"},
+ {VB2_NV_DEV_BOOT_ALTFW, 0, 1, 0, "dev boot altfw"},
{VB2_NV_DEV_BOOT_SIGNED_ONLY, 0, 1, 0, "dev boot custom"},
{VB2_NV_DEV_DEFAULT_BOOT, 0, 1, 2, "dev default boot"},
{VB2_NV_DIAG_REQUEST, 0, 1, 0, "diagnostic rom request"},
diff --git a/tests/vb2_preamble_fuzzer.c b/tests/vb2_preamble_fuzzer.c
index b29ccc7..186ee9f 100644
--- a/tests/vb2_preamble_fuzzer.c
+++ b/tests/vb2_preamble_fuzzer.c
@@ -7,6 +7,7 @@
#include "2misc.h"
#include "2nvstorage.h"
#include "2rsa.h"
+#include "2rsa_private.h"
#include "2secdata.h"
#include "vboot_test.h"
diff --git a/tests/vb2_rsa_utility_tests.c b/tests/vb2_rsa_utility_tests.c
index cc856e8..4ad5a95 100644
--- a/tests/vb2_rsa_utility_tests.c
+++ b/tests/vb2_rsa_utility_tests.c
@@ -8,6 +8,7 @@
#include "2common.h"
#include "2rsa.h"
+#include "2rsa_private.h"
#include "2sysincludes.h"
#include "file_keys.h"
#include "rsa_padding_test.h"
diff --git a/tests/vb2_ui_action_tests.c b/tests/vb2_ui_action_tests.c
index f6f18dc..6db75bf 100644
--- a/tests/vb2_ui_action_tests.c
+++ b/tests/vb2_ui_action_tests.c
@@ -19,8 +19,9 @@
/* Mock screen index for testing screen utility functions. */
#define MOCK_NO_SCREEN 0xef00
-#define MOCK_SCREEN_BASE 0xef10
-#define MOCK_SCREEN_MENU 0xef11
+#define MOCK_SCREEN_BLANK 0xef10
+#define MOCK_SCREEN_BASE 0xef11
+#define MOCK_SCREEN_MENU 0xef12
#define MOCK_SCREEN_TARGET0 0xef20
#define MOCK_SCREEN_TARGET1 0xef21
#define MOCK_SCREEN_TARGET2 0xef22
@@ -65,11 +66,11 @@
static uint32_t mock_vbtlk_expected_flag;
static int mock_dev_boot_allowed;
-static int mock_dev_boot_legacy_allowed;
+static int mock_dev_boot_altfw_allowed;
-static int mock_vbexlegacy_called;
-static enum VbAltFwIndex_t mock_altfw_num_last;
-static uint32_t mock_bootloader_count;
+static int mock_run_altfw_called;
+static uint32_t mock_altfw_last;
+static uint32_t mock_altfw_count;
static uint32_t mock_time_ms;
static const uint32_t mock_time_start_ms = 31ULL * VB2_MSEC_PER_SEC;
@@ -80,8 +81,8 @@
static vb2_error_t mock_action_countdown(struct vb2_ui_context *ui)
{
if (++mock_action_called >= mock_action_countdown_limit)
- return VB2_SUCCESS;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_REQUEST_UI_EXIT;
+ return VB2_SUCCESS;
}
static vb2_error_t mock_action_screen_change(struct vb2_ui_context *ui)
@@ -99,35 +100,35 @@
static vb2_error_t mock_action_flag0(struct vb2_ui_context *ui)
{
if ((1 << 0) & mock_action_flags)
- return VB2_SUCCESS;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_REQUEST_UI_EXIT;
+ return VB2_SUCCESS;
}
static vb2_error_t mock_action_flag1(struct vb2_ui_context *ui)
{
if ((1 << 1) & mock_action_flags)
- return VB2_SUCCESS;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_REQUEST_UI_EXIT;
+ return VB2_SUCCESS;
}
static vb2_error_t mock_action_flag2(struct vb2_ui_context *ui)
{
if ((1 << 2) & mock_action_flags)
- return VB2_SUCCESS;
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_REQUEST_UI_EXIT;
+ return VB2_SUCCESS;
}
static uint32_t mock_action_delay_ms;
static vb2_error_t mock_action_msleep(struct vb2_ui_context *ui)
{
vb2ex_msleep(mock_action_delay_ms);
- return VB2_REQUEST_UI_CONTINUE;
+ return VB2_SUCCESS;
}
/* Mock screens */
struct vb2_screen_info mock_screen_temp;
const struct vb2_screen_info mock_screen_blank = {
- .id = VB2_SCREEN_BLANK,
+ .id = MOCK_SCREEN_BLANK,
.name = "mock_screen_blank",
};
const struct vb2_screen_info mock_screen_base = {
@@ -234,10 +235,10 @@
}
-static void set_mock_vbtlk(vb2_error_t retval, uint32_t get_info_flags)
+static void set_mock_vbtlk(vb2_error_t retval, uint32_t disk_flags)
{
mock_vbtlk_retval = retval;
- mock_vbtlk_expected_flag = get_info_flags;
+ mock_vbtlk_expected_flag = disk_flags;
}
static void displayed_eq(const char *text,
@@ -360,12 +361,12 @@
/* For dev_boot* in 2misc.h */
mock_dev_boot_allowed = 1;
- mock_dev_boot_legacy_allowed = 0;
+ mock_dev_boot_altfw_allowed = 0;
- /* For VbExLegacy */
- mock_vbexlegacy_called = 0;
- mock_altfw_num_last = -100;
- mock_bootloader_count = 2;
+ /* For vb2ex_run_altfw */
+ mock_run_altfw_called = 0;
+ mock_altfw_last = -100;
+ mock_altfw_count = 2;
/* For vb2ex_mtime and vb2ex_msleep */
mock_time_ms = mock_time_start_ms;
@@ -393,7 +394,7 @@
mock_get_screen_info_called++;
switch ((int)screen) {
- case VB2_SCREEN_BLANK:
+ case MOCK_SCREEN_BLANK:
return &mock_screen_blank;
case MOCK_SCREEN_BASE:
return &mock_screen_base;
@@ -480,10 +481,10 @@
return 0;
}
-vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t get_info_flags)
+vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t disk_flags)
{
- TEST_EQ(mock_vbtlk_expected_flag, get_info_flags,
- " unexpected get_info_flags");
+ TEST_EQ(mock_vbtlk_expected_flag, disk_flags,
+ " unexpected disk_flags");
return mock_vbtlk_retval;
}
@@ -492,25 +493,25 @@
return mock_dev_boot_allowed;
}
-int vb2_dev_boot_legacy_allowed(struct vb2_context *c)
+int vb2_dev_boot_altfw_allowed(struct vb2_context *c)
{
- return mock_dev_boot_legacy_allowed;
+ return mock_dev_boot_altfw_allowed;
}
-vb2_error_t VbExLegacy(enum VbAltFwIndex_t altfw_num)
+vb2_error_t vb2ex_run_altfw(uint32_t altfw_id)
{
- mock_vbexlegacy_called++;
- mock_altfw_num_last = altfw_num;
+ mock_run_altfw_called++;
+ mock_altfw_last = altfw_id;
- if (altfw_num <= mock_bootloader_count)
+ if (altfw_id <= mock_altfw_count)
return VB2_SUCCESS;
else
return VB2_ERROR_UNKNOWN;
}
-uint32_t vb2ex_get_bootloader_count(void)
+uint32_t vb2ex_get_altfw_count(void)
{
- return mock_bootloader_count;
+ return mock_altfw_count;
}
uint32_t vb2ex_mtime(void)
@@ -533,7 +534,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 2;
mock_ui_context.key = VB_KEY_UP;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"valid action");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 1,
MOCK_IGNORE);
@@ -544,7 +545,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->hidden_item_mask = 0x0a; /* 0b01010 */
mock_ui_context.key = VB_KEY_UP;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"valid action with hidden mask");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 0,
MOCK_IGNORE);
@@ -555,7 +556,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->disabled_item_mask = 0x0a; /* 0b01010 */
mock_ui_context.key = VB_KEY_UP;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"valid action with disabled mask");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 1,
MOCK_IGNORE);
@@ -565,7 +566,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 0;
mock_ui_context.key = VB_KEY_UP;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"invalid action (blocked)");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 0,
MOCK_IGNORE);
@@ -576,7 +577,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->hidden_item_mask = 0x0b; /* 0b01011 */
mock_ui_context.key = VB_KEY_UP;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"invalid action (blocked by mask)");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 2,
MOCK_IGNORE);
@@ -587,8 +588,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 2;
mock_ui_context.key = VB_BUTTON_VOL_UP_SHORT_PRESS;
- TEST_EQ(vb2_ui_menu_prev(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_prev(&mock_ui_context), VB2_SUCCESS,
"ignore volume-up when not DETACHABLE");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 2,
MOCK_IGNORE);
@@ -606,7 +606,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 2;
mock_ui_context.key = VB_KEY_DOWN;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"valid action");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 3,
MOCK_IGNORE);
@@ -617,7 +617,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->hidden_item_mask = 0x0a; /* 0b01010 */
mock_ui_context.key = VB_KEY_DOWN;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"valid action with hidden mask");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 4,
MOCK_IGNORE);
@@ -628,7 +628,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->disabled_item_mask = 0x0a; /* 0b01010 */
mock_ui_context.key = VB_KEY_DOWN;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"valid action with disabled mask");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 3,
MOCK_IGNORE);
@@ -638,7 +638,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 4;
mock_ui_context.key = VB_KEY_DOWN;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"invalid action (blocked)");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 4,
MOCK_IGNORE);
@@ -649,7 +649,7 @@
mock_ui_context.state->selected_item = 2;
mock_ui_context.state->hidden_item_mask = 0x1a; /* 0b11010 */
mock_ui_context.key = VB_KEY_DOWN;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"invalid action (blocked by mask)");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 2,
MOCK_IGNORE);
@@ -660,8 +660,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 2;
mock_ui_context.key = VB_BUTTON_VOL_DOWN_SHORT_PRESS;
- TEST_EQ(vb2_ui_menu_next(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_next(&mock_ui_context), VB2_SUCCESS,
"ignore volume-down when not DETACHABLE");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 2,
MOCK_IGNORE);
@@ -670,6 +669,12 @@
VB2_DEBUG("...done.\n");
}
+static vb2_error_t try_menu_select_helper(void)
+{
+ VB2_TRY(vb2_ui_menu_select(&mock_ui_context));
+ return VB2_ERROR_MOCK;
+}
+
static void menu_select_tests(void)
{
VB2_DEBUG("Testing menu_select...\n");
@@ -678,19 +683,25 @@
reset_common_data();
mock_ui_context.state->screen = &mock_screen_base;
mock_ui_context.key = VB_KEY_ENTER;
- TEST_EQ(vb2_ui_menu_select(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_select(&mock_ui_context), VB2_SUCCESS,
"vb2_ui_menu_select with no item screen");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_BASE, 0,
MOCK_IGNORE);
+ /* VB2_TRY around item selection should return right away */
+ reset_common_data();
+ mock_ui_context.state->screen = &mock_screen_menu;
+ mock_ui_context.key = VB_KEY_ENTER;
+ TEST_NEQ(try_menu_select_helper(), VB2_ERROR_MOCK,
+ "continued executing after VB2_TRY(menu_select)");
+
/* Try to select an item with a target (item 2) */
reset_common_data();
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 2;
mock_ui_context.key = VB_KEY_ENTER;
- TEST_EQ(vb2_ui_menu_select(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, "select an item with a target");
+ TEST_EQ(vb2_ui_menu_select(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
+ "select an item with a target");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_TARGET2, 0,
MOCK_IGNORE);
@@ -708,8 +719,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 4;
mock_ui_context.key = VB_KEY_ENTER;
- TEST_EQ(vb2_ui_menu_select(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_select(&mock_ui_context), VB2_SUCCESS,
"select an item with neither targets nor actions");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 4,
MOCK_IGNORE);
@@ -720,8 +730,8 @@
mock_ui_context.state->selected_item = 3;
mock_ui_context.state->disabled_item_mask = 0x08; /* 0b01000 */
mock_ui_context.key = VB_KEY_ENTER;
- TEST_EQ(vb2_ui_menu_select(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, "cannot select a disabled item");
+ TEST_EQ(vb2_ui_menu_select(&mock_ui_context), VB2_SUCCESS,
+ "cannot select a disabled item");
TEST_EQ(mock_action_called, 0, " no action called");
/* Ignore power button short press when not DETACHABLE */
@@ -730,8 +740,7 @@
mock_ui_context.state->screen = &mock_screen_menu;
mock_ui_context.state->selected_item = 1;
mock_ui_context.key = VB_BUTTON_POWER_SHORT_PRESS;
- TEST_EQ(vb2_ui_menu_select(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_menu_select(&mock_ui_context), VB2_SUCCESS,
"ignore power button short press when not DETACHABLE");
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_MENU, 1,
MOCK_IGNORE);
@@ -740,54 +749,63 @@
VB2_DEBUG("...done.\n");
}
-static void vb2_ui_developer_mode_boot_alternate_action_tests(void)
+static void vb2_ui_developer_mode_boot_altfw_action_tests(void)
{
VB2_DEBUG("Test developer mode boot alternate action...\n");
/* Not allowed: not in dev mode */
reset_common_data();
- mock_dev_boot_legacy_allowed = 1;
- TEST_EQ(vb2_ui_developer_mode_boot_alternate_action(&mock_ui_context),
+ mock_dev_boot_altfw_allowed = 1;
+ TEST_EQ(vb2_ui_developer_mode_boot_altfw_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "not allowed: not in dev mode");
- TEST_EQ(mock_vbexlegacy_called, 0, " VbExLegacy not called");
+ TEST_EQ(mock_ui_context.error_code, VB2_UI_ERROR_ALTFW_DISABLED,
+ "ui_error code is set");
+ TEST_EQ(mock_run_altfw_called, 0, " vb2ex_run_altfw not called");
/* Not allowed: dev boot not allowed */
reset_common_data();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
mock_dev_boot_allowed = 0;
- mock_dev_boot_legacy_allowed = 1;
- TEST_EQ(vb2_ui_developer_mode_boot_alternate_action(&mock_ui_context),
+ mock_dev_boot_altfw_allowed = 1;
+ TEST_EQ(vb2_ui_developer_mode_boot_altfw_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "not allowed: dev boot not allowed");
- TEST_EQ(mock_vbexlegacy_called, 0, " VbExLegacy not called");
+ TEST_EQ(mock_ui_context.error_code, VB2_UI_ERROR_ALTFW_DISABLED,
+ "ui_error code is set");
+ TEST_EQ(mock_run_altfw_called, 0, " vb2ex_run_altfw not called");
- /* Not allowed: boot legacy not allowed */
+ /* Not allowed: boot altfw not allowed */
reset_common_data();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
- TEST_EQ(vb2_ui_developer_mode_boot_alternate_action(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
- "not allowed: boot legacy not allowed");
- TEST_EQ(mock_vbexlegacy_called, 0, " VbExLegacy not called");
+ TEST_EQ(vb2_ui_developer_mode_boot_altfw_action(&mock_ui_context),
+ VB2_REQUEST_UI_CONTINUE, "not allowed: boot altfw not allowed");
+ TEST_EQ(mock_ui_context.error_code, VB2_UI_ERROR_ALTFW_DISABLED,
+ "ui_error code is set");
+ TEST_EQ(mock_run_altfw_called, 0, " vb2ex_run_altfw not called");
/* Allowed */
reset_common_data();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
mock_ui_context.state->selected_item = 2;
- TEST_EQ(vb2_ui_developer_mode_boot_alternate_action(&mock_ui_context),
+ TEST_EQ(vb2_ui_developer_mode_boot_altfw_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "allowed");
- TEST_EQ(mock_vbexlegacy_called, 1, " VbExLegacy called once");
- TEST_EQ(mock_altfw_num_last, 2, " select bootloader #2");
+ TEST_EQ(mock_ui_context.error_code, VB2_UI_ERROR_ALTFW_FAILED,
+ "ui_error code is set");
+ TEST_EQ(mock_run_altfw_called, 1, " vb2ex_run_altfw called once");
+ TEST_EQ(mock_altfw_last, 2, " select bootloader #2");
/* CTRL+L = default bootloader */
reset_common_data();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
mock_ui_context.key = VB_KEY_CTRL('L');
mock_ui_context.state->selected_item = 4; /* Ignored */
- TEST_EQ(vb2_ui_developer_mode_boot_alternate_action(&mock_ui_context),
+ TEST_EQ(vb2_ui_developer_mode_boot_altfw_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "allowed: ctrl+l");
- TEST_EQ(mock_vbexlegacy_called, 1, " VbExLegacy called once");
- TEST_EQ(mock_altfw_num_last, 0, " select bootloader #0");
+ TEST_EQ(mock_ui_context.error_code, VB2_UI_ERROR_ALTFW_FAILED,
+ "ui_error code is set");
+ TEST_EQ(mock_run_altfw_called, 1, " vb2ex_run_altfw called once");
+ TEST_EQ(mock_altfw_last, 0, " select bootloader #0");
VB2_DEBUG("...done.\n");
}
@@ -799,8 +817,8 @@
/* SUCCESS */
reset_common_data();
set_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_REMOVABLE);
- TEST_EQ(manual_recovery_action(&mock_ui_context),
- VB2_SUCCESS, "SUCCESS");
+ TEST_EQ(manual_recovery_action(&mock_ui_context), VB2_REQUEST_UI_EXIT,
+ "EXIT");
TEST_EQ(mock_get_screen_info_called, 0, " no change_screen");
/* NO_DISK_FOUND */
@@ -821,8 +839,8 @@
TEST_EQ(manual_recovery_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "INVALID_KERNEL");
set_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_REMOVABLE);
- TEST_EQ(manual_recovery_action(&mock_ui_context),
- VB2_SUCCESS, "SUCCESS");
+ TEST_EQ(manual_recovery_action(&mock_ui_context), VB2_REQUEST_UI_EXIT,
+ "EXIT");
screen_state_eq(mock_ui_context.state, VB2_SCREEN_RECOVERY_INVALID,
MOCK_IGNORE, MOCK_IGNORE);
@@ -845,8 +863,8 @@
TEST_EQ(manual_recovery_action(&mock_ui_context),
VB2_REQUEST_UI_CONTINUE, "NO_DISK_FOUND");
set_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_REMOVABLE);
- TEST_EQ(manual_recovery_action(&mock_ui_context),
- VB2_SUCCESS, "SUCCESS");
+ TEST_EQ(manual_recovery_action(&mock_ui_context), VB2_REQUEST_UI_EXIT,
+ "EXIT");
screen_state_eq(mock_ui_context.state, VB2_SCREEN_RECOVERY_SELECT,
MOCK_IGNORE, MOCK_IGNORE);
@@ -891,13 +909,13 @@
reset_common_data();
mock_calls_until_shutdown = -1;
mock_action_countdown_limit = 10;
- TEST_EQ(ui_loop(ctx, VB2_SCREEN_BLANK, mock_action_countdown),
+ TEST_EQ(ui_loop(ctx, MOCK_SCREEN_BLANK, mock_action_countdown),
VB2_SUCCESS, "global action");
TEST_EQ(mock_action_called, 10, " action called");
/* Global action can change screen */
reset_common_data();
- TEST_EQ(ui_loop(ctx, VB2_SCREEN_BLANK, mock_action_screen_change),
+ TEST_EQ(ui_loop(ctx, MOCK_SCREEN_BLANK, mock_action_screen_change),
VB2_REQUEST_SHUTDOWN, "global action can change screen");
DISPLAYED_PASS();
DISPLAYED_EQ("change to mock_screen_base", MOCK_SCREEN_BASE,
@@ -1054,7 +1072,7 @@
menu_select_tests();
/* Screen actions */
- vb2_ui_developer_mode_boot_alternate_action_tests();
+ vb2_ui_developer_mode_boot_altfw_action_tests();
/* Global actions */
manual_recovery_action_tests();
diff --git a/tests/vb2_ui_tests.c b/tests/vb2_ui_tests.c
index bc95033..9a84a93 100644
--- a/tests/vb2_ui_tests.c
+++ b/tests/vb2_ui_tests.c
@@ -74,12 +74,12 @@
static enum vb2_dev_default_boot_target mock_default_boot;
static int mock_dev_boot_allowed;
-static int mock_dev_boot_legacy_allowed;
+static int mock_dev_boot_altfw_allowed;
static int mock_dev_boot_external_allowed;
-static int mock_vbexlegacy_called;
-static enum VbAltFwIndex_t mock_altfw_num_last;
-static uint32_t mock_bootloader_count;
+static int mock_run_altfw_called;
+static uint32_t mock_altfw_last;
+static uint32_t mock_altfw_count;
static vb2_error_t mock_vbtlk_retval[32];
static uint32_t mock_vbtlk_expected_flag[32];
@@ -100,6 +100,8 @@
static int mock_prepare_log_count;
static uint32_t mock_log_page_count;
+static vb2_error_t mock_diag_storage_test_rv;
+
static void add_mock_key(uint32_t press, int trusted)
{
if (mock_key_total >= ARRAY_SIZE(mock_key) ||
@@ -118,7 +120,7 @@
add_mock_key(press, 0);
}
-static void add_mock_vbtlk(vb2_error_t retval, uint32_t get_info_flags)
+static void add_mock_vbtlk(vb2_error_t retval, uint32_t disk_flags)
{
if (mock_vbtlk_total >= ARRAY_SIZE(mock_vbtlk_retval) ||
mock_vbtlk_total >= ARRAY_SIZE(mock_vbtlk_expected_flag)) {
@@ -127,7 +129,7 @@
}
mock_vbtlk_retval[mock_vbtlk_total] = retval;
- mock_vbtlk_expected_flag[mock_vbtlk_total] = get_info_flags;
+ mock_vbtlk_expected_flag[mock_vbtlk_total] = disk_flags;
mock_vbtlk_total++;
}
@@ -317,13 +319,13 @@
/* For dev_boot* in 2misc.h */
mock_default_boot = VB2_DEV_DEFAULT_BOOT_TARGET_INTERNAL;
mock_dev_boot_allowed = 1;
- mock_dev_boot_legacy_allowed = 0;
+ mock_dev_boot_altfw_allowed = 0;
mock_dev_boot_external_allowed = 1;
- /* For VbExLegacy */
- mock_vbexlegacy_called = 0;
- mock_altfw_num_last = -100;
- mock_bootloader_count = 2;
+ /* For vb2ex_run_altfw */
+ mock_run_altfw_called = 0;
+ mock_altfw_last = -100;
+ mock_altfw_count = 2;
/* For VbTryLoadKernel */
memset(mock_vbtlk_retval, 0, sizeof(mock_vbtlk_retval));
@@ -353,6 +355,8 @@
else
add_mock_vbtlk(VB2_ERROR_MOCK, 0);
add_mock_pp_pressed(0);
+
+ mock_diag_storage_test_rv = VB2_SUCCESS;
}
/* Mock functions */
@@ -490,9 +494,9 @@
return mock_dev_boot_allowed;
}
-int vb2_dev_boot_legacy_allowed(struct vb2_context *c)
+int vb2_dev_boot_altfw_allowed(struct vb2_context *c)
{
- return mock_dev_boot_legacy_allowed;
+ return mock_dev_boot_altfw_allowed;
}
int vb2_dev_boot_external_allowed(struct vb2_context *c)
@@ -500,20 +504,20 @@
return mock_dev_boot_external_allowed;
}
-vb2_error_t VbExLegacy(enum VbAltFwIndex_t altfw_num)
+vb2_error_t vb2ex_run_altfw(uint32_t altfw_id)
{
- mock_vbexlegacy_called++;
- mock_altfw_num_last = altfw_num;
+ mock_run_altfw_called++;
+ mock_altfw_last = altfw_id;
return VB2_SUCCESS;
}
-uint32_t vb2ex_get_bootloader_count(void)
+uint32_t vb2ex_get_altfw_count(void)
{
- return mock_bootloader_count;
+ return mock_altfw_count;
}
-vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t get_info_flags)
+vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t disk_flags)
{
int i = mock_iters;
@@ -521,8 +525,8 @@
if (i >= mock_vbtlk_total)
i = mock_vbtlk_total - 1;
- TEST_EQ(mock_vbtlk_expected_flag[i], get_info_flags,
- " unexpected get_info_flags");
+ TEST_EQ(mock_vbtlk_expected_flag[i], disk_flags,
+ " unexpected disk_flags");
return mock_vbtlk_retval[i];
}
@@ -571,6 +575,11 @@
return mock_log_page_count;
}
+vb2_error_t vb2ex_diag_get_storage_test_log(const char **log)
+{
+ return mock_diag_storage_test_rv;
+}
+
/* Tests */
static void developer_tests(void)
{
@@ -598,6 +607,14 @@
TEST_EQ(mock_beep_count, 2, " beeped twice");
TEST_TRUE(mock_iters >= mock_vbtlk_total, " used up mock_vbtlk");
+ /* Don't proceed to internal disk after timeout (dev mode disallowed) */
+ reset_common_data(FOR_DEVELOPER);
+ mock_dev_boot_allowed = 0;
+ TEST_EQ(ui_loop(ctx, VB2_SCREEN_DEVELOPER_MODE, NULL),
+ VB2_REQUEST_SHUTDOWN,
+ "do not proceed to internal disk after timeout "
+ "(dev mode disallowed)");
+
/* Use short delay */
reset_common_data(FOR_DEVELOPER);
gbb.flags |= VB2_GBB_FLAG_DEV_SCREEN_SHORT_DELAY;
@@ -687,6 +704,15 @@
TEST_EQ(vb2_developer_menu(ctx), VB2_REQUEST_SHUTDOWN,
"default boot from external disk not allowed, don't boot");
+ /* Don't proceed to external disk after timeout (dev mode disallowed) */
+ reset_common_data(FOR_DEVELOPER);
+ mock_dev_boot_allowed = 0;
+ mock_default_boot = VB2_DEV_DEFAULT_BOOT_TARGET_EXTERNAL;
+ TEST_EQ(ui_loop(ctx, VB2_SCREEN_DEVELOPER_MODE, NULL),
+ VB2_REQUEST_SHUTDOWN,
+ "do not proceed to external disk after timeout "
+ "(dev mode disallowed)");
+
/* If no external disk, don't boot */
reset_common_data(FOR_DEVELOPER);
add_mock_vbtlk(VB2_ERROR_LK_NO_DISK_FOUND, VB_DISK_FLAG_REMOVABLE);
@@ -702,20 +728,21 @@
TEST_EQ(vb2_developer_menu(ctx), VB2_SUCCESS,
"select boot external in dev menu");
- /* Ctrl+L = boot legacy (allowed) */
+ /* Ctrl+L = boot altfw (allowed) */
reset_common_data(FOR_DEVELOPER);
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
add_mock_keypress(VB_KEY_CTRL('L'));
TEST_EQ(vb2_developer_menu(ctx), VB2_REQUEST_SHUTDOWN,
- "ctrl+l = boot legacy");
- TEST_EQ(mock_vbexlegacy_called, 1, " VbExLegacy called");
+ "ctrl+l = boot altfw");
+ TEST_EQ(mock_run_altfw_called, 1, " vb2ex_run_altfw called");
- /* Ctrl+L = boot legacy (disallowed) */
+ /* Ctrl+L = boot altfw (disallowed) */
reset_common_data(FOR_DEVELOPER);
add_mock_keypress(VB_KEY_CTRL('L'));
TEST_EQ(vb2_developer_menu(ctx), VB2_REQUEST_SHUTDOWN,
- "ctrl+l = boot legacy");
- TEST_EQ(mock_vbexlegacy_called, 0, " VbExLegacy not called");
+ "ctrl+l = boot altfw");
+ TEST_EQ(mock_run_altfw_called, 0,
+ " vb2ex_run_altfw not called");
/* VB_BUTTON_VOL_UP_LONG_PRESS = boot external */
if (DETACHABLE) {
@@ -726,19 +753,6 @@
"VB_BUTTON_VOL_UP_LONG_PRESS = boot external");
}
- /* If dev mode is disabled, goes to to_norm screen repeatedly */
- reset_common_data(FOR_DEVELOPER);
- add_mock_keypress(VB_KEY_ESC);
- mock_dev_boot_allowed = 0;
- TEST_EQ(vb2_developer_menu(ctx), VB2_REQUEST_SHUTDOWN,
- "if dev mode is disabled, goes to to_norm screen repeatedly");
- DISPLAYED_EQ("to_norm", VB2_SCREEN_DEVELOPER_TO_NORM, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
- DISPLAYED_PASS();
- DISPLAYED_EQ("to_norm", VB2_SCREEN_DEVELOPER_TO_NORM, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
- DISPLAYED_NO_EXTRA();
-
/* Select to_norm in dev menu and confirm */
reset_common_data(FOR_DEVELOPER);
add_mock_keypress(VB_KEY_UP);
@@ -749,6 +763,18 @@
TEST_EQ(vb2_nv_get(ctx, VB2_NV_DISABLE_DEV_REQUEST), 1,
" disable dev request");
+ /* Select to_norm in dev menu and confirm (dev mode disallowed) */
+ reset_common_data(FOR_DEVELOPER);
+ mock_dev_boot_allowed = 0;
+ add_mock_keypress(VB_KEY_UP);
+ add_mock_keypress(VB_KEY_ENTER);
+ add_mock_keypress(VB_KEY_ENTER);
+ TEST_EQ(ui_loop(ctx, VB2_SCREEN_DEVELOPER_MODE, NULL),
+ VB2_REQUEST_REBOOT,
+ "select to_norm in dev menu and confirm (dev mode disallowed)");
+ TEST_EQ(vb2_nv_get(ctx, VB2_NV_DISABLE_DEV_REQUEST), 1,
+ " disable dev request");
+
/* Select to_norm in dev menu and cancel */
reset_common_data(FOR_DEVELOPER);
add_mock_keypress(VB_KEY_UP);
@@ -1286,7 +1312,7 @@
/* Dev mode: disabled and hidden item mask */
reset_common_data(FOR_DEVELOPER);
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
add_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_FIXED);
TEST_EQ(vb2_developer_menu(ctx), VB2_SUCCESS,
"dev mode screen: no disabled or hidden item");
@@ -1294,7 +1320,7 @@
MOCK_IGNORE, MOCK_IGNORE, 0x0, 0x0, MOCK_IGNORE);
reset_common_data(FOR_DEVELOPER);
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
gbb.flags |= VB2_GBB_FLAG_FORCE_DEV_SWITCH_ON;
add_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_FIXED);
TEST_EQ(vb2_developer_menu(ctx), VB2_SUCCESS,
@@ -1305,7 +1331,7 @@
reset_common_data(FOR_DEVELOPER);
add_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_FIXED);
mock_dev_boot_external_allowed = 0;
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
TEST_EQ(vb2_developer_menu(ctx), VB2_SUCCESS,
"dev mode screen: hide boot external");
DISPLAYED_EQ("dev mode screen", VB2_SCREEN_DEVELOPER_MODE,
@@ -1364,7 +1390,7 @@
DISPLAYED_NO_EXTRA();
reset_common_data(FOR_DEVELOPER); /* Select #2 by default */
- mock_dev_boot_legacy_allowed = 1;
+ mock_dev_boot_altfw_allowed = 1;
/* #4: Alternate boot */
add_mock_keypress(VB_KEY_DOWN);
add_mock_keypress(VB_KEY_DOWN);
@@ -1372,7 +1398,7 @@
add_mock_keypress(VB_KEY_ENTER);
TEST_EQ(vb2_developer_menu(ctx), VB2_REQUEST_SHUTDOWN,
"dev mode screen");
- TEST_EQ(mock_vbexlegacy_called, 1, " VbExLegacy called");
+ TEST_EQ(mock_run_altfw_called, 1, " vb2ex_run_altfw called");
reset_common_data(FOR_DEVELOPER); /* Select #2 by default */
add_mock_vbtlk(VB2_SUCCESS, VB_DISK_FLAG_FIXED);
@@ -1777,8 +1803,8 @@
reset_common_data(FOR_DIAGNOSTICS);
TEST_EQ(vb2_diagnostic_menu(ctx), VB2_REQUEST_SHUTDOWN,
"diagnostic screen: no disabled or hidden item");
- DISPLAYED_EQ("diagnostic menu", VB2_SCREEN_DIAGNOSTICS,
- MOCK_IGNORE, MOCK_IGNORE, 0x0, 0x0, MOCK_IGNORE);
+ DISPLAYED_EQ("diagnostic menu", VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE,
+ MOCK_IGNORE, 0x0, 0x0, MOCK_IGNORE);
/* Diagnostics screen */
reset_common_data(FOR_DIAGNOSTICS);
@@ -1786,67 +1812,94 @@
/* #0: Language menu */
add_mock_keypress(VB_KEY_UP);
add_mock_keypress(VB_KEY_ENTER);
- /* #1: Storage screen */
add_mock_keypress(VB_KEY_ESC);
+ /* #1: Storage health screen */
add_mock_keypress(VB_KEY_DOWN);
add_mock_keypress(VB_KEY_ENTER);
- /* #2: Quick memory test screen */
add_mock_keypress(VB_KEY_ESC);
+ /* #2: Short storage self-test screen */
add_mock_keypress(VB_KEY_DOWN);
add_mock_keypress(VB_KEY_ENTER);
- /* #3: Full memory test screen */
add_mock_keypress(VB_KEY_ESC);
+ /* #3: Extended storage self-test screen */
add_mock_keypress(VB_KEY_DOWN);
add_mock_keypress(VB_KEY_ENTER);
- /* #4: Power off (End of menu) */
add_mock_keypress(VB_KEY_ESC);
+ /* #4: Quick memory test screen */
+ add_mock_keypress(VB_KEY_DOWN);
+ add_mock_keypress(VB_KEY_ENTER);
+ add_mock_keypress(VB_KEY_ESC);
+ /* #5: Full memory test screen */
+ add_mock_keypress(VB_KEY_DOWN);
+ add_mock_keypress(VB_KEY_ENTER);
+ add_mock_keypress(VB_KEY_ESC);
+ /* #6: Power off (End of menu) */
add_mock_keypress(VB_KEY_DOWN);
add_mock_keypress(VB_KEY_ENTER);
mock_calls_until_shutdown = -1;
TEST_EQ(vb2_diagnostic_menu(ctx), VB2_REQUEST_SHUTDOWN,
"diagnostic screen");
- DISPLAYED_EQ("default on first button of menu",
- VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 1, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("default on first button of menu", VB2_SCREEN_DIAGNOSTICS,
+ MOCK_IGNORE, 1, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
/* #0: Language menu */
- DISPLAYED_EQ("language selection",
- VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 0, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("language selection", VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE,
+ 0, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
DISPLAYED_EQ("#0: language menu", VB2_SCREEN_LANGUAGE_SELECT,
MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE,
MOCK_IGNORE);
- /* #1: Storage screen */
DISPLAYED_PASS();
- DISPLAYED_EQ("storage button",
- VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 1, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE);
- DISPLAYED_EQ("#1: storage screen", VB2_SCREEN_DIAGNOSTICS_STORAGE,
- MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE,
- MOCK_IGNORE);
- /* #2: Quick memory test screen */
- DISPLAYED_PASS();
- DISPLAYED_EQ("quick memory test button",
- VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 2, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE);
- DISPLAYED_EQ("#1: quick memory test screen",
- VB2_SCREEN_DIAGNOSTICS_MEMORY_QUICK, MOCK_IGNORE,
+ /* #1: Storage health screen */
+ DISPLAYED_EQ("storage health button", VB2_SCREEN_DIAGNOSTICS,
+ MOCK_IGNORE, 1, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("#1: storage screen",
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_HEALTH, MOCK_IGNORE,
MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
- /* #3: Full memory test screen */
DISPLAYED_PASS();
- DISPLAYED_EQ("full memory test button",
+ /* #2: Short storage self-test screen */
+ DISPLAYED_EQ("short storage self-test button", VB2_SCREEN_DIAGNOSTICS,
+ MOCK_IGNORE, 2, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("#2: short storage self-test screen",
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_SHORT, MOCK_IGNORE,
+ MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_PASS();
+ /* #3: Extended storage self-test screen */
+ DISPLAYED_EQ("extended storage self-test button",
VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 3, MOCK_IGNORE,
MOCK_IGNORE, MOCK_IGNORE);
- DISPLAYED_EQ("#3: full memory test screen",
+ DISPLAYED_EQ("#3: extended storage self-test screen",
+ VB2_SCREEN_DIAGNOSTICS_STORAGE_TEST_EXTENDED, MOCK_IGNORE,
+ MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_PASS();
+ /* #4: Quick memory test screen */
+ DISPLAYED_EQ("quick memory test button", VB2_SCREEN_DIAGNOSTICS,
+ MOCK_IGNORE, 4, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("#4: quick memory test screen",
+ VB2_SCREEN_DIAGNOSTICS_MEMORY_QUICK, MOCK_IGNORE,
+ MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_PASS();
+ /* #5: Full memory test screen */
+ DISPLAYED_EQ("full memory test button", VB2_SCREEN_DIAGNOSTICS,
+ MOCK_IGNORE, 5, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
+ DISPLAYED_EQ("#5: full memory test screen",
VB2_SCREEN_DIAGNOSTICS_MEMORY_FULL, MOCK_IGNORE,
MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
- /* #4: Power of (End of menu) */
DISPLAYED_PASS();
- DISPLAYED_EQ("power off",
- VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 4, MOCK_IGNORE,
- MOCK_IGNORE, MOCK_IGNORE);
+ /* #6: Power of (End of menu) */
+ DISPLAYED_EQ("power off", VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, 6,
+ MOCK_IGNORE, MOCK_IGNORE, MOCK_IGNORE);
DISPLAYED_NO_EXTRA();
+ /* Diagnostics screen: no nvme */
+ reset_common_data(FOR_DIAGNOSTICS);
+ /* Non-nvme storage returns UNIMPLEMENTED. */
+ mock_diag_storage_test_rv = VB2_ERROR_EX_UNIMPLEMENTED;
+ TEST_EQ(vb2_diagnostic_menu(ctx), VB2_REQUEST_SHUTDOWN,
+ "diagnostic screen: check disabled item");
+ DISPLAYED_EQ("diagnostic menu: self-test disabled",
+ VB2_SCREEN_DIAGNOSTICS, MOCK_IGNORE, MOCK_IGNORE, 0xc, 0x0,
+ MOCK_IGNORE);
+
VB2_DEBUG("...done.\n");
}
diff --git a/tests/vb2_ui_utility_tests.c b/tests/vb2_ui_utility_tests.c
index 821402a..1a7b19e 100644
--- a/tests/vb2_ui_utility_tests.c
+++ b/tests/vb2_ui_utility_tests.c
@@ -43,10 +43,6 @@
}
/* Mock screens */
-struct vb2_screen_info mock_screen_blank = {
- .id = VB2_SCREEN_BLANK,
- .name = "mock_screen_blank",
-};
struct vb2_screen_info mock_screen_base = {
.id = MOCK_SCREEN_BASE,
.name = "mock_screen_base: menuless screen",
@@ -125,8 +121,6 @@
mock_action_called = 0;
/* Reset init and action functions */
- mock_screen_blank.init = NULL;
- mock_screen_blank.action = NULL;
mock_screen_base.init = NULL;
mock_screen_base.action = NULL;
mock_screen_menu.init = NULL;
@@ -157,8 +151,6 @@
const struct vb2_screen_info *vb2_get_screen_info(enum vb2_screen screen)
{
switch ((int)screen) {
- case VB2_SCREEN_BLANK:
- return &mock_screen_blank;
case MOCK_SCREEN_BASE:
return &mock_screen_base;
case MOCK_SCREEN_MENU:
@@ -179,14 +171,13 @@
if (!DETACHABLE) {
reset_common_data();
mock_shutdown_request = 0;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
"release, press, hold, and release");
mock_shutdown_request = VB_SHUTDOWN_REQUEST_POWER_BUTTON;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, " press");
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, " hold");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ " press");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ " hold");
mock_shutdown_request = 0;
TEST_EQ(check_shutdown_request(&mock_ui_context),
VB2_REQUEST_SHUTDOWN, " release");
@@ -196,8 +187,8 @@
if (!DETACHABLE) {
reset_common_data();
mock_shutdown_request = VB_SHUTDOWN_REQUEST_POWER_BUTTON;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, "press is ignored");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ "press is ignored");
}
/* Power button short press from key */
@@ -222,13 +213,13 @@
reset_common_data();
gbb.flags |= VB2_GBB_FLAG_DISABLE_LID_SHUTDOWN;
mock_shutdown_request = VB_SHUTDOWN_REQUEST_LID_CLOSED;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, "lid ignored");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ "lid ignored");
if (!DETACHABLE) { /* Power button works for non DETACHABLE */
mock_shutdown_request = VB_SHUTDOWN_REQUEST_LID_CLOSED |
VB_SHUTDOWN_REQUEST_POWER_BUTTON;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, " lidsw + pwdsw");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ " lidsw + pwdsw");
mock_shutdown_request = 0;
TEST_EQ(check_shutdown_request(&mock_ui_context),
VB2_REQUEST_SHUTDOWN, " pwdsw release");
@@ -250,24 +241,35 @@
/* Flag pwdsw */
reset_common_data();
mock_shutdown_request = VB_SHUTDOWN_REQUEST_POWER_BUTTON;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, "DETACHABLE: ignore pwdsw");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ "DETACHABLE: ignore pwdsw");
mock_shutdown_request = 0;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE, " ignore on release");
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
+ " ignore on release");
/* Power button short press */
reset_common_data();
mock_shutdown_request = 0;
mock_ui_context.key = VB_BUTTON_POWER_SHORT_PRESS;
- TEST_EQ(check_shutdown_request(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(check_shutdown_request(&mock_ui_context), VB2_SUCCESS,
"DETACHABLE: ignore power button short press");
}
VB2_DEBUG("...done.\n");
}
+static vb2_error_t try_back_helper(void)
+{
+ VB2_TRY(vb2_ui_screen_back(&mock_ui_context));
+ return VB2_ERROR_MOCK;
+}
+
+static vb2_error_t try_screen_change_helper(enum vb2_screen screen_id)
+{
+ VB2_TRY(vb2_ui_screen_change(&mock_ui_context, screen_id));
+ return VB2_ERROR_MOCK;
+}
+
static void screen_stack_tests(void)
{
VB2_DEBUG("Testing screen stack functionality...\n");
@@ -281,8 +283,7 @@
/* Screen back with empty stack */
reset_common_data();
- TEST_EQ(vb2_ui_screen_back(&mock_ui_context),
- VB2_REQUEST_UI_CONTINUE,
+ TEST_EQ(vb2_ui_screen_back(&mock_ui_context), VB2_REQUEST_UI_CONTINUE,
"screen back with empty stack");
TEST_PTR_EQ(mock_ui_context.state, NULL, " stack is empty");
@@ -299,6 +300,16 @@
screen_state_eq(mock_ui_context.state, MOCK_SCREEN_BASE, 2, 0x10);
TEST_EQ(mock_action_called, 1, " action called once");
+ /* VB2_TRY around back should return right away */
+ reset_common_data();
+ TEST_NEQ(try_back_helper(), VB2_ERROR_MOCK,
+ "continued executing after VB2_TRY(back)");
+
+ /* VB2_TRY around screen_change should return right away */
+ reset_common_data();
+ TEST_NEQ(try_screen_change_helper(MOCK_SCREEN_ROOT), VB2_ERROR_MOCK,
+ "continued executing after VB2_TRY(screen_change)");
+
/* Change to target screen already in stack, restoring the state */
reset_common_data();
mock_screen_base.init = mock_action_base;
diff --git a/tests/vboot_api_kernel4_tests.c b/tests/vboot_api_kernel4_tests.c
index 5229ee5..32eaf02 100644
--- a/tests/vboot_api_kernel4_tests.c
+++ b/tests/vboot_api_kernel4_tests.c
@@ -17,7 +17,6 @@
#include "test_common.h"
#include "tlcl.h"
#include "tss_constants.h"
-#include "vboot_audio.h"
#include "vboot_kernel.h"
#include "vboot_struct.h"
#include "vboot_test.h"
@@ -121,7 +120,7 @@
kernel_version = value;
}
-vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t get_info_flags)
+vb2_error_t VbTryLoadKernel(struct vb2_context *c, uint32_t disk_flags)
{
sd->kernel_version = new_version;
diff --git a/tests/vboot_api_kernel_tests.c b/tests/vboot_api_kernel_tests.c
index bcb5d04..9294fd7 100644
--- a/tests/vboot_api_kernel_tests.c
+++ b/tests/vboot_api_kernel_tests.c
@@ -29,6 +29,7 @@
const char *name;
/* inputs for test case */
+ uint32_t ctx_flags;
uint32_t want_flags;
vb2_error_t diskgetinfo_return_val;
disk_desc_t disks_to_provide[MAX_TEST_DISKS];
@@ -52,7 +53,44 @@
test_case_t test[] = {
{
+ .name = "first drive (removable)",
+ .ctx_flags = 0,
+ .want_flags = VB_DISK_FLAG_REMOVABLE | VB_DISK_FLAG_FIXED,
+ .disks_to_provide = {
+ {4096, 100, VB_DISK_FLAG_REMOVABLE, pickme},
+ {4096, 100, VB_DISK_FLAG_FIXED, "holygrail"},
+ },
+ .disk_count_to_return = DEFAULT_COUNT,
+ .diskgetinfo_return_val = VB2_SUCCESS,
+ .loadkernel_return_val = {0},
+ .external_expected = {0},
+
+ .expected_recovery_request_val = VB2_RECOVERY_NOT_REQUESTED,
+ .expected_to_find_disk = pickme,
+ .expected_to_load_disk = pickme,
+ .expected_return_val = VB2_SUCCESS
+ },
+ {
+ .name = "first drive (fixed)",
+ .ctx_flags = 0,
+ .want_flags = VB_DISK_FLAG_REMOVABLE | VB_DISK_FLAG_FIXED,
+ .disks_to_provide = {
+ {4096, 100, VB_DISK_FLAG_FIXED, pickme},
+ {4096, 100, VB_DISK_FLAG_REMOVABLE, "holygrail"},
+ },
+ .disk_count_to_return = DEFAULT_COUNT,
+ .diskgetinfo_return_val = VB2_SUCCESS,
+ .loadkernel_return_val = {0},
+ .external_expected = {0},
+
+ .expected_recovery_request_val = VB2_RECOVERY_NOT_REQUESTED,
+ .expected_to_find_disk = pickme,
+ .expected_to_load_disk = pickme,
+ .expected_return_val = VB2_SUCCESS
+ },
+ {
.name = "first removable drive",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_REMOVABLE,
.disks_to_provide = {
/* too small */
@@ -83,6 +121,7 @@
},
{
.name = "first removable drive (skip external GPT)",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_REMOVABLE,
.disks_to_provide = {
/* too small */
@@ -115,6 +154,7 @@
},
{
.name = "second removable drive",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_REMOVABLE,
.disks_to_provide = {
/* wrong flags */
@@ -133,6 +173,7 @@
},
{
.name = "first fixed drive",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {
/* too small */
@@ -165,6 +206,7 @@
},
{
.name = "no drives at all",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {},
.disk_count_to_return = DEFAULT_COUNT,
@@ -177,6 +219,7 @@
},
{
.name = "VbExDiskGetInfo() error",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {
{512, 10, VB_DISK_FLAG_REMOVABLE, 0},
@@ -192,6 +235,7 @@
},
{
.name = "invalid kernel",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {
/* too small */
@@ -223,6 +267,7 @@
},
{
.name = "invalid kernel, order flipped",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {
{512, 1000, VB_DISK_FLAG_FIXED, "stateful partition"},
@@ -240,6 +285,7 @@
},
{
.name = "no Chrome OS partitions",
+ .ctx_flags = 0,
.want_flags = VB_DISK_FLAG_FIXED,
.disks_to_provide = {
{512, 100, VB_DISK_FLAG_FIXED, "stateful partition"},
@@ -257,6 +303,43 @@
},
{
.name = "invalid kernel (removable)",
+ .ctx_flags = 0,
+ .want_flags = VB_DISK_FLAG_REMOVABLE,
+ .disks_to_provide = {
+ {512, 100, VB_DISK_FLAG_REMOVABLE, "corrupted"},
+ {512, 100, VB_DISK_FLAG_REMOVABLE, "data"},
+ },
+ .disk_count_to_return = DEFAULT_COUNT,
+ .diskgetinfo_return_val = VB2_SUCCESS,
+ .loadkernel_return_val = {VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ VB2_ERROR_LK_NO_KERNEL_FOUND},
+
+ .expected_recovery_request_val = VB2_RECOVERY_RW_INVALID_OS,
+ .expected_to_find_disk = DONT_CARE,
+ .expected_to_load_disk = 0,
+ .expected_return_val = VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ },
+ {
+ .name = "invalid kernel (removable, rec mode)",
+ .ctx_flags = VB2_CONTEXT_RECOVERY_MODE,
+ .want_flags = VB_DISK_FLAG_REMOVABLE,
+ .disks_to_provide = {
+ {512, 100, VB_DISK_FLAG_REMOVABLE, "corrupted"},
+ {512, 100, VB_DISK_FLAG_REMOVABLE, "data"},
+ },
+ .disk_count_to_return = DEFAULT_COUNT,
+ .diskgetinfo_return_val = VB2_SUCCESS,
+ .loadkernel_return_val = {VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ VB2_ERROR_LK_NO_KERNEL_FOUND},
+
+ .expected_recovery_request_val = VB2_RECOVERY_NOT_REQUESTED,
+ .expected_to_find_disk = DONT_CARE,
+ .expected_to_load_disk = 0,
+ .expected_return_val = VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ },
+ {
+ .name = "invalid kernel (removable, dev mode)",
+ .ctx_flags = VB2_CONTEXT_DEVELOPER_MODE,
.want_flags = VB_DISK_FLAG_REMOVABLE,
.disks_to_provide = {
{512, 100, VB_DISK_FLAG_REMOVABLE, "corrupted"},
@@ -274,6 +357,23 @@
},
{
.name = "no kernel (removable)",
+ .ctx_flags = 0,
+ .want_flags = VB_DISK_FLAG_REMOVABLE,
+ .disks_to_provide = {
+ {512, 100, VB_DISK_FLAG_REMOVABLE, "data"},
+ },
+ .disk_count_to_return = DEFAULT_COUNT,
+ .diskgetinfo_return_val = VB2_SUCCESS,
+ .loadkernel_return_val = {VB2_ERROR_LK_NO_KERNEL_FOUND},
+
+ .expected_recovery_request_val = VB2_RECOVERY_RW_NO_KERNEL,
+ .expected_to_find_disk = DONT_CARE,
+ .expected_to_load_disk = 0,
+ .expected_return_val = VB2_ERROR_LK_NO_KERNEL_FOUND,
+ },
+ {
+ .name = "no kernel (removable, rec mode)",
+ .ctx_flags = VB2_CONTEXT_RECOVERY_MODE,
.want_flags = VB_DISK_FLAG_REMOVABLE,
.disks_to_provide = {
{512, 100, VB_DISK_FLAG_REMOVABLE, "data"},
@@ -312,7 +412,7 @@
TEST_SUCC(vb2api_init(workbuf, sizeof(workbuf), &ctx),
"vb2api_init failed");
- memset(VbApiKernelGetParams(), 0, sizeof(LoadKernelParams));
+ memset(VbApiKernelGetParams(), 0, sizeof(VbSelectAndLoadKernelParams));
memset(&mock_disks, 0, sizeof(mock_disks));
load_kernel_calls = 0;
@@ -395,14 +495,16 @@
return VB2_SUCCESS;
}
-vb2_error_t LoadKernel(struct vb2_context *c, LoadKernelParams *params)
+vb2_error_t LoadKernel(struct vb2_context *c,
+ VbSelectAndLoadKernelParams *params,
+ VbDiskInfo *disk_info)
{
got_find_disk = (const char *)params->disk_handle;
VB2_DEBUG("%s(%d): got_find_disk = %s\n", __FUNCTION__,
load_kernel_calls,
got_find_disk ? got_find_disk : "0");
if (t->external_expected[load_kernel_calls] !=
- !!(params->boot_flags & BOOT_FLAG_EXTERNAL_GPT))
+ !!(disk_info->flags & VB_DISK_FLAG_EXTERNAL_GPT))
got_external_mismatch++;
return t->loadkernel_return_val[load_kernel_calls++];
}
@@ -428,7 +530,8 @@
for (i = 0; i < num_tests; i++) {
printf("Test case: %s ...\n", test[i].name);
ResetMocks(i);
- TEST_EQ(VbTryLoadKernel(ctx, test[i].want_flags),
+ ctx->flags = t->ctx_flags;
+ TEST_EQ(VbTryLoadKernel(ctx, t->want_flags),
t->expected_return_val, " return value");
TEST_EQ(got_recovery_request_val,
t->expected_recovery_request_val, " recovery_request");
diff --git a/tests/vboot_kernel_tests.c b/tests/vboot_kernel_tests.c
index 87056ad..486602c 100644
--- a/tests/vboot_kernel_tests.c
+++ b/tests/vboot_kernel_tests.c
@@ -20,7 +20,6 @@
#include "host_common.h"
#include "load_kernel_fw.h"
#include "test_common.h"
-#include "vb2_common.h"
#include "vboot_api.h"
#include "vboot_kernel.h"
@@ -55,7 +54,8 @@
static struct vb2_gbb_header gbb;
static VbExDiskHandle_t handle;
-static LoadKernelParams lkp;
+static VbSelectAndLoadKernelParams lkp;
+static VbDiskInfo disk_info;
static struct vb2_keyblock kbh;
static struct vb2_kernel_preamble kph;
static struct vb2_secdata_fwmp *fwmp;
@@ -137,13 +137,16 @@
gbb.flags = 0;
memset(&lkp, 0, sizeof(lkp));
- lkp.bytes_per_lba = 512;
- lkp.streaming_lba_count = 1024;
- lkp.gpt_lba_count = 1024;
lkp.kernel_buffer = kernel_buffer;
lkp.kernel_buffer_size = sizeof(kernel_buffer);
lkp.disk_handle = (VbExDiskHandle_t)1;
+ memset(&disk_info, 0, sizeof(disk_info));
+ disk_info.bytes_per_lba = 512;
+ disk_info.streaming_lba_count = 1024;
+ disk_info.lba_count = 1024;
+ disk_info.handle = lkp.disk_handle;
+
memset(&kbh, 0, sizeof(kbh));
kbh.data_key.key_version = 2;
kbh.keyblock_flags = -1;
@@ -168,14 +171,19 @@
vb2_nv_init(ctx);
sd = vb2_get_sd(ctx);
- sd->kernel_version = 0x20001;
+ sd->kernel_version_secdata = 0x20001;
/* CRC will be invalid after here, but nobody's checking */
sd->status |= VB2_SD_STATUS_SECDATA_FWMP_INIT;
fwmp = (struct vb2_secdata_fwmp *)ctx->secdata_fwmp;
memcpy(&fwmp->dev_key_hash, mock_digest, sizeof(fwmp->dev_key_hash));
- // TODO: more workbuf fields - flags, secdata_firmware, secdata_kernel
+ // TODO: more workbuf fields - flags, secdata_firmware
+
+ vb2api_secdata_kernel_create(ctx);
+ vb2_secdata_kernel_init(ctx);
+ vb2_secdata_kernel_set(ctx, VB2_SECDATA_KERNEL_FLAGS,
+ VB2_SECDATA_KERNEL_FLAG_HWCRYPTO_ALLOWED);
}
/* Mocks */
@@ -588,7 +596,7 @@
static void TestLoadKernel(int expect_retval, const char *test_name)
{
- TEST_EQ(LoadKernel(ctx, &lkp), expect_retval, test_name);
+ TEST_EQ(LoadKernel(ctx, &lkp, &disk_info), expect_retval, test_name);
}
/**
@@ -603,6 +611,7 @@
/* This causes the stream open call to fail */
ResetMocks();
lkp.disk_handle = NULL;
+ disk_info.handle = NULL;
TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND, "Bad disk handle");
}
@@ -700,6 +709,24 @@
TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
"Keyblock rec!dev flag mismatch");
+ /* Check keyblock flag mismatches (dev mode + signed kernel required) */
+ ResetMocks();
+ ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY, 1);
+ kbh.keyblock_flags =
+ VB2_KEYBLOCK_FLAG_RECOVERY_1 | VB2_KEYBLOCK_FLAG_DEVELOPER_0;
+ TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ "Keyblock dev flag mismatch (signed kernel required)");
+
+ ResetMocks();
+ ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
+ fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_OFFICIAL_ONLY;
+ kbh.keyblock_flags =
+ VB2_KEYBLOCK_FLAG_RECOVERY_1 | VB2_KEYBLOCK_FLAG_DEVELOPER_0;
+ TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ "Keyblock dev flag mismatch (signed kernel required)");
+
+ /* Check kernel key version */
ResetMocks();
kbh.data_key.key_version = 1;
TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
@@ -756,6 +783,23 @@
ctx->flags |= VB2_CONTEXT_RECOVERY_MODE;
TestLoadKernel(0, "Kernel version ignored in rec mode");
+ /* Check kernel version (dev mode + signed kernel required) */
+ ResetMocks();
+ kbh.data_key.key_version = 0;
+ ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
+ vb2_nv_set(ctx, VB2_NV_DEV_BOOT_SIGNED_ONLY, 1);
+ TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ "Keyblock key version checked in dev mode "
+ "(signed kernel required)");
+
+ ResetMocks();
+ kbh.data_key.key_version = 0;
+ ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
+ fwmp->flags |= VB2_SECDATA_FWMP_DEV_ENABLE_OFFICIAL_ONLY;
+ TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
+ "Keyblock key version checked in dev mode "
+ "(signed kernel required)");
+
/* Check developer key hash - bad */
ResetMocks();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
@@ -764,6 +808,14 @@
TestLoadKernel(VB2_ERROR_LK_INVALID_KERNEL_FOUND,
"Fail keyblock dev fwmp hash");
+ /* Check developer key hash - bad (recovery mode) */
+ ResetMocks();
+ ctx->flags |= VB2_CONTEXT_RECOVERY_MODE;
+ ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
+ fwmp->flags |= VB2_SECDATA_FWMP_DEV_USE_KEY_HASH;
+ fwmp->dev_key_hash[0]++;
+ TestLoadKernel(0, "Bad keyblock dev fwmp hash ignored in rec mode");
+
/* Check developer key hash - good */
ResetMocks();
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
@@ -814,7 +866,7 @@
/* Check that EXTERNAL_GPT flag makes it down */
ResetMocks();
- lkp.boot_flags |= BOOT_FLAG_EXTERNAL_GPT;
+ disk_info.flags |= VB_DISK_FLAG_EXTERNAL_GPT;
TestLoadKernel(0, "Succeed external GPT");
TEST_EQ(gpt_flag_external, 1, "GPT was external");
diff --git a/tests/verify_kernel.c b/tests/verify_kernel.c
index 9aaad72..8fe969e 100644
--- a/tests/verify_kernel.c
+++ b/tests/verify_kernel.c
@@ -10,6 +10,7 @@
#include "2common.h"
#include "2misc.h"
#include "2nvstorage.h"
+#include "2secdata.h"
#include "host_common.h"
#include "util_misc.h"
#include "vboot_api.h"
@@ -22,16 +23,17 @@
static uint8_t *diskbuf;
-static LoadKernelParams params;
+static VbSelectAndLoadKernelParams params;
+static VbDiskInfo disk_info;
vb2_error_t VbExDiskRead(VbExDiskHandle_t handle, uint64_t lba_start,
uint64_t lba_count, void *buffer)
{
if (handle != (VbExDiskHandle_t)1)
return VB2_ERROR_UNKNOWN;
- if (lba_start >= params.streaming_lba_count)
+ if (lba_start >= disk_info.streaming_lba_count)
return VB2_ERROR_UNKNOWN;
- if (lba_start + lba_count > params.streaming_lba_count)
+ if (lba_start + lba_count > disk_info.streaming_lba_count)
return VB2_ERROR_UNKNOWN;
memcpy(buffer, diskbuf + lba_start * 512, lba_count * 512);
@@ -43,9 +45,9 @@
{
if (handle != (VbExDiskHandle_t)1)
return VB2_ERROR_UNKNOWN;
- if (lba_start >= params.streaming_lba_count)
+ if (lba_start >= disk_info.streaming_lba_count)
return VB2_ERROR_UNKNOWN;
- if (lba_start + lba_count > params.streaming_lba_count)
+ if (lba_start + lba_count > disk_info.streaming_lba_count)
return VB2_ERROR_UNKNOWN;
memcpy(diskbuf + lba_start * 512, buffer, lba_count * 512);
@@ -86,9 +88,10 @@
/* Set up params */
params.disk_handle = (VbExDiskHandle_t)1;
- params.bytes_per_lba = 512;
- params.streaming_lba_count = disk_bytes / 512;
- params.gpt_lba_count = params.streaming_lba_count;
+ disk_info.handle = (VbExDiskHandle_t)1;
+ disk_info.bytes_per_lba = 512;
+ disk_info.streaming_lba_count = disk_bytes / 512;
+ disk_info.lba_count = disk_info.streaming_lba_count;
params.kernel_buffer_size = 16 * 1024 * 1024;
params.kernel_buffer = malloc(params.kernel_buffer_size);
@@ -98,7 +101,7 @@
}
/* TODO(chromium:441893): support dev-mode flag and external gpt flag */
- params.boot_flags = 0;
+ disk_info.flags = 0;
if (vb2api_init(&workbuf, sizeof(workbuf), &ctx)) {
fprintf(stderr, "Can't initialize workbuf\n");
@@ -124,9 +127,14 @@
* dev mode. So just use defaults for nv storage.
*/
vb2_nv_init(ctx);
+ /* We need to init kernel secdata for
+ * VB2_SECDATA_KERNEL_FLAG_HWCRYPTO_ALLOWED.
+ */
+ vb2api_secdata_kernel_create(ctx);
+ vb2_secdata_kernel_init(ctx);
/* Try loading kernel */
- rv = LoadKernel(ctx, ¶ms);
+ rv = LoadKernel(ctx, ¶ms, &disk_info);
if (rv != VB2_SUCCESS) {
fprintf(stderr, "LoadKernel() failed with code %d\n", rv);
return 1;
diff --git a/utility/crossystem.c b/utility/crossystem.c
index 384c671..079bf32 100644
--- a/utility/crossystem.c
+++ b/utility/crossystem.c
@@ -37,13 +37,13 @@
{"cros_debug", 0, "OS should allow debug features"},
{"dbg_reset", CAN_WRITE, "Debug reset mode request"},
{"debug_build", 0, "OS image built for debug features"},
- {"dev_boot_legacy", CAN_WRITE, "Enable developer mode boot Legacy OSes"},
+ {"dev_boot_altfw", CAN_WRITE, "Enable developer mode alternate bootloader"},
{"dev_boot_signed_only", CAN_WRITE,
"Enable developer mode boot only from official kernels"},
{"dev_boot_usb", CAN_WRITE,
"Enable developer mode boot from external disk (USB/SD)"},
{"dev_default_boot", IS_STRING|CAN_WRITE,
- "Default boot from disk, legacy or usb"},
+ "Default boot from disk, altfw or usb"},
{"dev_enable_udc", CAN_WRITE, "Enable USB Device Controller"},
{"devsw_boot", 0, "Developer switch position at boot"},
{"devsw_cur", 0, "Developer switch current position"},
@@ -106,7 +106,7 @@
static void PrintHelp(const char *progname) {
const Param *p;
- printf("\nUsage:\n"
+ printf("Usage:\n"
" %s [--all]\n"
" Prints all parameters with descriptions and current values.\n"
" If --all is specified, prints even normally hidden fields.\n"
@@ -116,7 +116,7 @@
" Sets the parameter(s) to the specified value(s).\n"
" %s [param1?value1] [param2?value2 [...]]]\n"
" Checks if the parameter(s) all contain the specified value(s).\n"
- "Stops at the first error."
+ " Stops at the first error.\n"
"\n"
"Valid parameters:\n", progname, progname, progname, progname);
for (p = sys_param_list; p->name; p++) {
@@ -125,6 +125,10 @@
(p->flags & IS_STRING) ? "str" : "int",
p->desc);
}
+ printf("\n"
+ "For more information, please see:\n"
+ "https://chromium.googlesource.com/chromiumos/docs/+/HEAD/"
+ "os_config.md#crossystem\n");
}
@@ -135,6 +139,14 @@
const Param* p;
if (!name)
return NULL;
+ /* "legacy" term deprecated in favour of "altfw" (see: b/179458327) */
+ if (!strcasecmp(name, "dev_boot_legacy")) {
+ fprintf(stderr,
+ "!!!\n"
+ "!!! PLEASE USE 'dev_boot_altfw' INSTEAD OF 'dev_boot_legacy'\n"
+ "!!!\n");
+ name = "dev_boot_altfw";
+ }
for (p = sys_param_list; p->name; p++) {
if (!strcasecmp(p->name, name))
return p;
@@ -308,13 +320,13 @@
case PARAM_SUCCESS:
break;
case PARAM_ERROR_READ_ONLY:
- fprintf(stderr, "Parameter %s is read-only\n", name);
+ fprintf(stderr, "Parameter %s is read-only\n", p->name);
break;
case PARAM_ERROR_INVALID_INT:
fprintf(stderr, "Value %s is not a valid integer\n", value);
break;
default:
- fprintf(stderr, "Failed to set parameter %s\n", name);
+ fprintf(stderr, "Failed to set parameter %s\n", p->name);
break;
}
} else if (has_expect)
diff --git a/utility/load_kernel_test.c b/utility/load_kernel_test.c
index c5dc7cb..cad82fd 100644
--- a/utility/load_kernel_test.c
+++ b/utility/load_kernel_test.c
@@ -26,7 +26,8 @@
static struct vb2_shared_data *sd;
/* Global variables for stub functions */
-static LoadKernelParams lkp;
+static VbSelectAndLoadKernelParams lkp;
+static VbDiskInfo disk_info;
static FILE *image_file = NULL;
@@ -36,17 +37,19 @@
{
printf("Read(%" PRIu64 ", %" PRIu64 ")\n", lba_start, lba_count);
- if (lba_start >= lkp.streaming_lba_count ||
- lba_start + lba_count > lkp.streaming_lba_count) {
+ if (lba_start >= disk_info.streaming_lba_count ||
+ lba_start + lba_count > disk_info.streaming_lba_count) {
fprintf(stderr,
"Read overrun: %" PRIu64 " + %" PRIu64
" > %" PRIu64 "\n", lba_start,
- lba_count, lkp.streaming_lba_count);
+ lba_count, disk_info.streaming_lba_count);
return 1;
}
- if (0 != fseek(image_file, lba_start * lkp.bytes_per_lba, SEEK_SET) ||
- 1 != fread(buffer, lba_count * lkp.bytes_per_lba, 1, image_file)) {
+ if (0 != fseek(image_file, lba_start * disk_info.bytes_per_lba,
+ SEEK_SET) ||
+ 1 != fread(buffer, lba_count * disk_info.bytes_per_lba, 1,
+ image_file)) {
fprintf(stderr, "Read error.");
return 1;
}
@@ -59,12 +62,12 @@
{
printf("Write(%" PRIu64 ", %" PRIu64 ")\n", lba_start, lba_count);
- if (lba_start >= lkp.streaming_lba_count ||
- lba_start + lba_count > lkp.streaming_lba_count) {
+ if (lba_start >= disk_info.streaming_lba_count ||
+ lba_start + lba_count > disk_info.streaming_lba_count) {
fprintf(stderr,
"Read overrun: %" PRIu64 " + %" PRIu64
" > %" PRIu64 "\n", lba_start, lba_count,
- lkp.streaming_lba_count);
+ disk_info.streaming_lba_count);
return 1;
}
@@ -72,8 +75,9 @@
our example file */
return VB2_SUCCESS;
- fseek(image_file, lba_start * lkp.bytes_per_lba, SEEK_SET);
- if (1 != fwrite(buffer, lba_count * lkp.bytes_per_lba, 1, image_file)) {
+ fseek(image_file, lba_start * disk_info.bytes_per_lba, SEEK_SET);
+ if (1 != fwrite(buffer, lba_count * disk_info.bytes_per_lba, 1,
+ image_file)) {
fprintf(stderr, "Read error.");
return 1;
}
@@ -96,8 +100,8 @@
int errorcnt = 0;
char *e = 0;
- memset(&lkp, 0, sizeof(LoadKernelParams));
- lkp.bytes_per_lba = LBA_BYTES;
+ memset(&lkp, 0, sizeof(VbSelectAndLoadKernelParams));
+ disk_info.bytes_per_lba = LBA_BYTES;
int boot_flags = BOOT_FLAG_RECOVERY;
/* Parse options */
@@ -186,7 +190,6 @@
}
printf("bootflags = %d\n", boot_flags);
- lkp.boot_flags = boot_flags;
/* Get image size */
printf("Reading from image: %s\n", image_name);
@@ -196,10 +199,11 @@
return 1;
}
fseek(image_file, 0, SEEK_END);
- lkp.streaming_lba_count = (ftell(image_file) / LBA_BYTES);
- lkp.gpt_lba_count = lkp.streaming_lba_count;
+ disk_info.streaming_lba_count = (ftell(image_file) / LBA_BYTES);
+ disk_info.lba_count = disk_info.streaming_lba_count;
rewind(image_file);
- printf("Streaming LBA count: %" PRIu64 "\n", lkp.streaming_lba_count);
+ printf("Streaming LBA count: %" PRIu64 "\n",
+ disk_info.streaming_lba_count);
/* Allocate a buffer for the kernel */
lkp.kernel_buffer = malloc(KERNEL_BUFFER_SIZE);
@@ -241,7 +245,7 @@
ctx->flags |= VB2_CONTEXT_DEVELOPER_MODE;
/* Call LoadKernel() */
- rv = LoadKernel(ctx, &lkp);
+ rv = LoadKernel(ctx, &lkp, &disk_info);
printf("LoadKernel() returned %d\n", rv);
if (VB2_SUCCESS == rv) {
diff --git a/utility/tpmc.c b/utility/tpmc.c
index 5723edf..841551c 100644
--- a/utility/tpmc.c
+++ b/utility/tpmc.c
@@ -66,10 +66,10 @@
* success, non-zero for failure.
*/
static int HexStringToUint32(const char* string, uint32_t* value) {
- char tail[1];
+ char tail;
/* strtoul is not as good because it overflows silently */
- const char* format = strncmp(string, "0x", 2) ? "%8x%s" : "0x%8x%s";
- int n = sscanf(string, format, value, tail);
+ const char* format = strncmp(string, "0x", 2) ? "%8x%c" : "0x%8x%c";
+ int n = sscanf(string, format, value, &tail);
return n != 1;
}
diff --git a/utility/verify_data.c b/utility/verify_data.c
index 8440b3a..6d3ea15 100644
--- a/utility/verify_data.c
+++ b/utility/verify_data.c
@@ -21,7 +21,6 @@
#include "2sysincludes.h"
#include "file_keys.h"
#include "host_common.h"
-#include "vb2_common.h"
/* ANSI Color coding sequences. */
#define COL_GREEN "\e[1;32m"