diff options
author | Daisuke Nojiri <dnojiri@chromium.org> | 2014-06-30 08:51:39 -0700 |
---|---|---|
committer | Aaron Durbin <adurbin@google.com> | 2015-03-23 19:53:09 +0100 |
commit | 79cac09cd19342bbc9cad97e862aa58c67b995da (patch) | |
tree | 37baaead011bc4350ea52fa39934e4f6c95dd7db /src | |
parent | 302ed00cb6876e7701d3779648e3f2870355ef78 (diff) |
vboot2: translate shared data to hand off to depthcharge
TEST=Built Blaze with USE=+/-vboot2. Ran faft: CorruptBothFwAB,
CorruptBothFWSigAB, CorruptFwBodyA/B, CoccurptFwSigA/B, DevBootUSB, DevMode,
TryFwB, UserRequestRecovery, SelfSignedBoot, RollbackFirmware.
BUG=None
BRANCH=none
Signed-off-by: Daisuke Nojiri <dnojiri@chromium.org>
Original-Change-Id: I45a1efd4d55fde37cc67fc02642fed0bc9366469
Original-Reviewed-on: https://chromium-review.googlesource.com/205236
Original-Reviewed-by: Randall Spangler <rspangler@chromium.org>
Original-Reviewed-by: Daisuke Nojiri <dnojiri@chromium.org>
Original-Commit-Queue: Daisuke Nojiri <dnojiri@chromium.org>
Original-Tested-by: Daisuke Nojiri <dnojiri@chromium.org>
(cherry picked from commit 0a9e7f099251c33ce286fa8d704a3e021eac4d3e)
Change-Id: I5f61c03c66ca83a5837c14378905ba178aba5300
Signed-off-by: Aaron Durbin <adurbin@chromium.org>
Reviewed-on: http://review.coreboot.org/8655
Tested-by: build bot (Jenkins)
Reviewed-by: Furquan Shaikh <furquan@google.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/lib/coreboot_table.c | 2 | ||||
-rw-r--r-- | src/mainboard/google/nyan_blaze/romstage.c | 2 | ||||
-rw-r--r-- | src/vendorcode/google/chromeos/Makefile.inc | 1 | ||||
-rw-r--r-- | src/vendorcode/google/chromeos/chromeos.h | 1 | ||||
-rw-r--r-- | src/vendorcode/google/chromeos/vboot_handoff.c | 142 | ||||
-rw-r--r-- | src/vendorcode/google/chromeos/vboot_handoff.h | 1 |
6 files changed, 147 insertions, 2 deletions
diff --git a/src/lib/coreboot_table.c b/src/lib/coreboot_table.c index 2b484d4b64..4126e82811 100644 --- a/src/lib/coreboot_table.c +++ b/src/lib/coreboot_table.c @@ -192,7 +192,7 @@ static void lb_vbnv(struct lb_header *header) #endif } -#if CONFIG_VBOOT_VERIFY_FIRMWARE +#if CONFIG_VBOOT_VERIFY_FIRMWARE || CONFIG_VBOOT2_VERIFY_FIRMWARE static void lb_vboot_handoff(struct lb_header *header) { void *addr; diff --git a/src/mainboard/google/nyan_blaze/romstage.c b/src/mainboard/google/nyan_blaze/romstage.c index 1d7d77d42f..a0dde9e615 100644 --- a/src/mainboard/google/nyan_blaze/romstage.c +++ b/src/mainboard/google/nyan_blaze/romstage.c @@ -200,7 +200,7 @@ static void __attribute__((noinline)) romstage(void) configure_tpm_i2c_bus(); #if CONFIG_VBOOT2_VERIFY_FIRMWARE - // vboot_create_handoff((void *)CONFIG_VBOOT_WORK_BUFFER_ADDRESS); + vboot_create_handoff((void *)CONFIG_VBOOT_WORK_BUFFER_ADDRESS); #else vboot_verify_firmware(romstage_handoff_find_or_add()); #endif diff --git a/src/vendorcode/google/chromeos/Makefile.inc b/src/vendorcode/google/chromeos/Makefile.inc index c8781dd645..1fcb42e68b 100644 --- a/src/vendorcode/google/chromeos/Makefile.inc +++ b/src/vendorcode/google/chromeos/Makefile.inc @@ -102,6 +102,7 @@ INCLUDES += -I$(VB_SOURCE)/firmware/2lib/include INCLUDES += -I$(VB_SOURCE)/firmware/include verstage-y += vboot_main.c fmap.c chromeos.c verstage-y += antirollback.c vbnv_ec.c +romstage-y += vboot_handoff.c VB_FIRMWARE_ARCH := $(ARCHDIR-$(ARCH-VERSTAGE-y)) VB2_LIB = $(obj)/external/vboot_reference/vboot_fw2.a diff --git a/src/vendorcode/google/chromeos/chromeos.h b/src/vendorcode/google/chromeos/chromeos.h index a799528d53..724ff57893 100644 --- a/src/vendorcode/google/chromeos/chromeos.h +++ b/src/vendorcode/google/chromeos/chromeos.h @@ -88,6 +88,7 @@ static inline void chromeos_reserve_ram_oops(struct device *dev, int idx) {} #if CONFIG_VBOOT2_VERIFY_FIRMWARE void select_firmware(void); +void vboot_create_handoff(void * vboot_workbuf); #endif #endif diff --git a/src/vendorcode/google/chromeos/vboot_handoff.c b/src/vendorcode/google/chromeos/vboot_handoff.c new file mode 100644 index 0000000000..3b276aac95 --- /dev/null +++ b/src/vendorcode/google/chromeos/vboot_handoff.c @@ -0,0 +1,142 @@ +/* + * This file is part of the coreboot project. + * + * Copyright (C) 2013 Google, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include <2recovery_reasons.h> +#include <2struct.h> +#include <stdint.h> +#include <stddef.h> +#include <string.h> +#include <cbfs.h> +#include <cbmem.h> +#include <console/console.h> +#include <console/vtxprintf.h> +#include <stdlib.h> +#include <timestamp.h> +#include "chromeos.h" +#include "fmap.h" +#include "vboot_handoff.h" +#include <vboot_struct.h> + +/** + * Sets vboot_handoff based on the information in vb2_shared_data + * + * TODO: Read wp switch to set VBSD_BOOT_FIRMWARE_WP_ENABLED + */ +static void fill_vboot_handoff(struct vboot_handoff *vboot_handoff, + struct vb2_shared_data *vb2_sd) +{ + VbSharedDataHeader *vb_sd = + (VbSharedDataHeader *)vboot_handoff->shared_data; + uint32_t *oflags = &vboot_handoff->init_params.out_flags; + + vb_sd->flags |= VBSD_BOOT_FIRMWARE_VBOOT2; + + vboot_handoff->selected_firmware = vb2_sd->fw_slot; + + /* TODO: fw_slot is never 0xff while firmware_index can. */ + vb_sd->firmware_index = vb2_sd->fw_slot; + + vb_sd->magic = VB_SHARED_DATA_MAGIC; + vb_sd->struct_version = VB_SHARED_DATA_VERSION; + vb_sd->struct_size = sizeof(VbSharedDataHeader); + vb_sd->data_size = VB_SHARED_DATA_MIN_SIZE; + vb_sd->data_used = sizeof(VbSharedDataHeader); + + if (vb2_sd->recovery_reason) { + vb_sd->firmware_index = 0xFF; + if (vb2_sd->recovery_reason == VB2_RECOVERY_RO_MANUAL) + vb_sd->flags |= VBSD_BOOT_REC_SWITCH_ON; + *oflags |= VB_INIT_OUT_ENABLE_RECOVERY; + *oflags |= VB_INIT_OUT_CLEAR_RAM; + *oflags |= VB_INIT_OUT_ENABLE_DISPLAY; + *oflags |= VB_INIT_OUT_ENABLE_USB_STORAGE; + } + if (vb2_sd->flags & VB2_SD_DEV_MODE_ENABLED) { + *oflags |= VB_INIT_OUT_ENABLE_DEVELOPER; + *oflags |= VB_INIT_OUT_CLEAR_RAM; + *oflags |= VB_INIT_OUT_ENABLE_DISPLAY; + *oflags |= VB_INIT_OUT_ENABLE_USB_STORAGE; + vb_sd->flags |= VBSD_BOOT_DEV_SWITCH_ON; + vb_sd->flags |= VBSD_LF_DEV_SWITCH_ON; + } + if (CONFIG_VIRTUAL_DEV_SWITCH) + vb_sd->flags |= VBSD_HONOR_VIRT_DEV_SWITCH; + if (CONFIG_EC_SOFTWARE_SYNC) { + vb_sd->flags |= VBSD_EC_SOFTWARE_SYNC; + vb_sd->flags |= VBSD_BOOT_REC_SWITCH_VIRTUAL; + } + /* In vboot1, VBSD_FWB_TRIED is + * set only if B is booted as explicitly requested. Therefore, if B is + * booted because A was found bad, the flag should not be set. It's + * better not to touch it if we can only ambiguously control it. */ + /* if (vb2_sd->fw_slot) + vb_sd->flags |= VBSD_FWB_TRIED; */ + + /* copy kernel subkey if it's found */ + if (vb2_sd->workbuf_preamble_size) { + struct vb2_fw_preamble *fp; + uintptr_t dst, src; + printk(BIOS_ERR, "Copying FW preamble\n"); + fp = (struct vb2_fw_preamble *)( (uintptr_t)vb2_sd + + vb2_sd->workbuf_preamble_offset); + src = (uintptr_t)&fp->kernel_subkey + fp->kernel_subkey.key_offset; + dst = (uintptr_t)vb_sd + sizeof(VbSharedDataHeader); + memcpy((void *)dst, (void *)src, fp->kernel_subkey.key_size); + vb_sd->data_used += fp->kernel_subkey.key_size; + vb_sd->kernel_subkey.key_offset = + dst - (uintptr_t)&vb_sd->kernel_subkey; + vb_sd->kernel_subkey.key_size = fp->kernel_subkey.key_size; + vb_sd->kernel_subkey.algorithm = fp->kernel_subkey.algorithm; + vb_sd->kernel_subkey.key_version = fp->kernel_subkey.key_version; + } + + vb_sd->recovery_reason = vb2_sd->recovery_reason; +} + +/** + * Create vboot handoff struct + * + * struct vboot_handoff { + * VbInitParams init_params; + * uint32_t selected_firmware; + * struct firmware_component components[MAX_PARSED_FW_COMPONENTS]; + * char shared_data[VB_SHARED_DATA_MIN_SIZE]; + * } __attribute__((packed)); + */ +void vboot_create_handoff(void *vboot_workbuf) +{ + struct vboot_handoff *vh; + struct vb2_shared_data *sd; + + sd = (struct vb2_shared_data *)vboot_workbuf; + sd->workbuf_hash_offset = 0; + sd->workbuf_hash_size = 0; + + printk(BIOS_INFO, "Creating vboot_handoff structure\n"); + vh = cbmem_add(CBMEM_ID_VBOOT_HANDOFF, sizeof(*vh)); + + if (vh == NULL) { + printk(BIOS_ERR, "Could not add vboot_handoff structure\n"); + return; + } + + memset(vh, 0, sizeof(*vh)); + + fill_vboot_handoff(vh, sd); +} diff --git a/src/vendorcode/google/chromeos/vboot_handoff.h b/src/vendorcode/google/chromeos/vboot_handoff.h index 09c7897f54..e1e519f081 100644 --- a/src/vendorcode/google/chromeos/vboot_handoff.h +++ b/src/vendorcode/google/chromeos/vboot_handoff.h @@ -20,6 +20,7 @@ #define VBOOT_HANDOFF_H #include <vboot_api.h> +#include <vboot_struct.h> /* * The vboot handoff structure keeps track of a maximum number of firmware |