summaryrefslogtreecommitdiff
path: root/src/vendorcode
diff options
context:
space:
mode:
authorAaron Durbin <adurbin@chromium.org>2014-01-30 17:19:46 -0600
committerAaron Durbin <adurbin@google.com>2014-02-15 18:39:29 +0100
commit0f333071ef9151b89de3fcf6dc5c14dba596941a (patch)
tree7a250a88218d16dd9baf7d5b1d9a35baa08c3390 /src/vendorcode
parente9aaa71fb1e05c4432d768d87071ef842c536cb4 (diff)
coreboot: infrastructure for different ramstage loaders
There are 2 methods currently available in coreboot to load ramstage from romstage: cbfs and vboot. The vboot path had to be explicitly enabled and code needed to be added to each chipset to support both. Additionally, many of the paths were duplicated between the two. An additional complication is the presence of having a relocatable ramstage which creates another path with duplication. To rectify this situation provide a common API through the use of a callback to load the ramstage. The rest of the existing logic to handle all the various cases is put in a common place. Change-Id: I5268ce70686cc0d121161a775c3a86ea38a4d8ae Signed-off-by: Aaron Durbin <adurbin@chromium.org> Reviewed-on: http://review.coreboot.org/5087 Tested-by: build bot (Jenkins) Reviewed-by: Paul Menzel <paulepanter@users.sourceforge.net> Reviewed-by: Patrick Georgi <patrick@georgi-clan.de>
Diffstat (limited to 'src/vendorcode')
-rw-r--r--src/vendorcode/google/chromeos/chromeos.h4
-rw-r--r--src/vendorcode/google/chromeos/vboot_loader.c87
2 files changed, 39 insertions, 52 deletions
diff --git a/src/vendorcode/google/chromeos/chromeos.h b/src/vendorcode/google/chromeos/chromeos.h
index 5493801a09..0359c91409 100644
--- a/src/vendorcode/google/chromeos/chromeos.h
+++ b/src/vendorcode/google/chromeos/chromeos.h
@@ -46,14 +46,10 @@ int recovery_mode_enabled(void);
/* functions implemented in vboot.c */
void init_chromeos(int bootmode);
-struct romstage_handoff;
#if CONFIG_VBOOT_VERIFY_FIRMWARE
-void vboot_verify_firmware(struct romstage_handoff *handoff);
void *vboot_get_payload(size_t *len);
/* Returns 0 on success < 0 on error. */
int vboot_get_handoff_info(void **addr, uint32_t *size);
-#else
-static inline void vboot_verify_firmware(struct romstage_handoff *h) {}
#endif
#endif
diff --git a/src/vendorcode/google/chromeos/vboot_loader.c b/src/vendorcode/google/chromeos/vboot_loader.c
index cc7c25d873..0c5220a82b 100644
--- a/src/vendorcode/google/chromeos/vboot_loader.c
+++ b/src/vendorcode/google/chromeos/vboot_loader.c
@@ -26,6 +26,7 @@
#include <console/vtxprintf.h>
#include <pc80/tpm.h>
#include <reset.h>
+#include <ramstage_loader.h>
#include <romstage_handoff.h>
#include <rmodule.h>
#include <string.h>
@@ -141,27 +142,52 @@ static void vboot_invoke_wrapper(struct vboot_handoff *vboot_handoff)
vboot_run_stub(&context);
}
-static void vboot_load_ramstage(struct vboot_handoff *vboot_handoff,
- struct romstage_handoff *handoff)
+static void *vboot_load_ramstage(uint32_t cbmem_id, const char *name,
+ const struct cbmem_entry **cbmem_entry)
{
+ struct vboot_handoff *vboot_handoff;
struct cbfs_stage *stage;
const struct firmware_component *fwc;
struct rmod_stage_load rmod_load = {
- .cbmem_id = CBMEM_ID_RAMSTAGE,
- .name = CONFIG_CBFS_PREFIX "/coreboot_ram",
+ .cbmem_id = cbmem_id,
+ .name = name,
};
+ timestamp_add_now(TS_START_VBOOT);
+
+ vboot_handoff = cbmem_add(CBMEM_ID_VBOOT_HANDOFF,
+ sizeof(*vboot_handoff));
+
+ if (vboot_handoff == NULL) {
+ printk(BIOS_DEBUG, "Could not add vboot_handoff structure.\n");
+ return NULL;
+ }
+
+ memset(vboot_handoff, 0, sizeof(*vboot_handoff));
+
+ vboot_invoke_wrapper(vboot_handoff);
+
+ timestamp_add_now(TS_END_VBOOT);
+
+ /* Take RO firmware path since no RW area was selected. */
+ if (vboot_handoff->selected_firmware != VB_SELECT_FIRMWARE_A &&
+ vboot_handoff->selected_firmware != VB_SELECT_FIRMWARE_B) {
+ printk(BIOS_DEBUG, "No RW firmware selected: 0x%08x\n",
+ vboot_handoff->selected_firmware);
+ return NULL;
+ }
+
if (CONFIG_VBOOT_RAMSTAGE_INDEX >= MAX_PARSED_FW_COMPONENTS) {
printk(BIOS_ERR, "Invalid ramstage index: %d\n",
CONFIG_VBOOT_RAMSTAGE_INDEX);
- return;
+ return NULL;
}
/* Check for invalid address. */
fwc = &vboot_handoff->components[CONFIG_VBOOT_RAMSTAGE_INDEX];
if (fwc->address == 0) {
printk(BIOS_DEBUG, "RW ramstage image address invalid.\n");
- return;
+ return NULL;
}
printk(BIOS_DEBUG, "RW ramstage image at 0x%08x, 0x%08x bytes.\n",
@@ -169,53 +195,18 @@ static void vboot_load_ramstage(struct vboot_handoff *vboot_handoff,
stage = (void *)fwc->address;
- timestamp_add_now(TS_START_COPYRAM);
-
if (rmodule_stage_load(&rmod_load, stage)) {
vboot_handoff->selected_firmware = VB_SELECT_FIRMWARE_READONLY;
printk(BIOS_DEBUG, "Could not load ramstage region.\n");
- return;
+ return NULL;
}
- cache_loaded_ramstage(handoff, rmod_load.cbmem_entry, rmod_load.entry);
-
- timestamp_add_now(TS_END_COPYRAM);
+ *cbmem_entry = rmod_load.cbmem_entry;
- stage_exit(rmod_load.entry);
+ return rmod_load.entry;
}
-void vboot_verify_firmware(struct romstage_handoff *handoff)
-{
- struct vboot_handoff *vboot_handoff;
-
- /* Don't go down verified boot path on S3 resume. */
- if (handoff != NULL && handoff->s3_resume)
- return;
-
- timestamp_add_now(TS_START_VBOOT);
-
- vboot_handoff = cbmem_add(CBMEM_ID_VBOOT_HANDOFF,
- sizeof(*vboot_handoff));
-
- if (vboot_handoff == NULL) {
- printk(BIOS_DEBUG, "Could not add vboot_handoff structure.\n");
- return;
- }
-
- memset(vboot_handoff, 0, sizeof(*vboot_handoff));
-
- vboot_invoke_wrapper(vboot_handoff);
-
- timestamp_add_now(TS_END_VBOOT);
-
- /* Take RO firmware path since no RW area was selected. */
- if (vboot_handoff->selected_firmware != VB_SELECT_FIRMWARE_A &&
- vboot_handoff->selected_firmware != VB_SELECT_FIRMWARE_B) {
- printk(BIOS_DEBUG, "No RW firmware selected: 0x%08x\n",
- vboot_handoff->selected_firmware);
- return;
- }
-
- /* Load ramstage from the vboot_handoff structure. */
- vboot_load_ramstage(vboot_handoff, handoff);
-}
+const struct ramstage_loader_ops vboot_ramstage_loader = {
+ .name = "VBOOT",
+ .load = vboot_load_ramstage,
+};