summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/arch/x86/lib/cbfs_and_run.c21
-rw-r--r--src/cpu/intel/haswell/romstage.c2
-rw-r--r--src/include/cbfs.h22
-rw-r--r--src/include/cbmem.h5
-rw-r--r--src/include/ramstage_loader.h34
-rw-r--r--src/include/romstage_handoff.h10
-rw-r--r--src/lib/Makefile.inc1
-rw-r--r--src/lib/cbfs.c53
-rw-r--r--src/lib/loaders/Makefile.inc21
-rw-r--r--src/lib/loaders/cbfs_ramstage_loader.c67
-rw-r--r--src/lib/loaders/load_and_run_ramstage.c100
-rw-r--r--src/soc/intel/baytrail/romstage/romstage.c4
-rw-r--r--src/vendorcode/google/chromeos/chromeos.h4
-rw-r--r--src/vendorcode/google/chromeos/vboot_loader.c87
14 files changed, 297 insertions, 134 deletions
diff --git a/src/arch/x86/lib/cbfs_and_run.c b/src/arch/x86/lib/cbfs_and_run.c
index 3d56e19318..ca8d61be54 100644
--- a/src/arch/x86/lib/cbfs_and_run.c
+++ b/src/arch/x86/lib/cbfs_and_run.c
@@ -17,27 +17,10 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
-#include <console/console.h>
-#include <cbfs.h>
#include <arch/stages.h>
-#include <timestamp.h>
-
-static void cbfs_and_run_core(const char *filename)
-{
- u8 *dst;
-
- timestamp_add_now(TS_START_COPYRAM);
- print_debug("Loading image.\n");
- dst = cbfs_load_stage(CBFS_DEFAULT_MEDIA, filename);
- if ((void *)dst == (void *) -1)
- die("FATAL: Essential component is missing.\n");
-
- timestamp_add_now(TS_END_COPYRAM);
- print_debug("Jumping to image.\n");
- stage_exit(dst);
-}
+#include <ramstage_loader.h>
void asmlinkage copy_and_run(void)
{
- cbfs_and_run_core(CONFIG_CBFS_PREFIX "/coreboot_ram");
+ run_ramstage();
}
diff --git a/src/cpu/intel/haswell/romstage.c b/src/cpu/intel/haswell/romstage.c
index 60a1c3a155..9e2766808d 100644
--- a/src/cpu/intel/haswell/romstage.c
+++ b/src/cpu/intel/haswell/romstage.c
@@ -309,8 +309,6 @@ void romstage_after_car(void)
prepare_for_resume(handoff);
- vboot_verify_firmware(handoff);
-
/* Load the ramstage. */
copy_and_run();
}
diff --git a/src/include/cbfs.h b/src/include/cbfs.h
index c05566d0b0..9ce862bbe5 100644
--- a/src/include/cbfs.h
+++ b/src/include/cbfs.h
@@ -83,6 +83,10 @@ void selfboot(void *entry);
/* Defined in individual arch / board implementation. */
int init_default_cbfs_media(struct cbfs_media *media);
+#if defined(__PRE_RAM__)
+struct romstage_handoff;
+struct cbmem_entry;
+
#if CONFIG_RELOCATABLE_RAMSTAGE && defined(__PRE_RAM__)
/* The cache_loaded_ramstage() and load_cached_ramstage() functions are defined
* to be weak so that board and chipset code may override them. Their job is to
@@ -90,9 +94,6 @@ int init_default_cbfs_media(struct cbfs_media *media);
* relocated ramstage is saved using the cbmem infrastructure. These
* functions are only valid during romstage. */
-struct romstage_handoff;
-struct cbmem_entry;
-
/* The implementer of cache_loaded_ramstage() may use the romstage_handoff
* structure to store information, but note that the handoff variable can be
* NULL. The ramstage cbmem_entry represents the region occupied by the loaded
@@ -105,7 +106,22 @@ cache_loaded_ramstage(struct romstage_handoff *handoff,
void * __attribute__((weak))
load_cached_ramstage(struct romstage_handoff *handoff,
const struct cbmem_entry *ramstage);
+#else /* CONFIG_RELOCATABLE_RAMSTAGE */
+
+static inline void cache_loaded_ramstage(struct romstage_handoff *handoff,
+ const struct cbmem_entry *ramstage, void *entry_point)
+{
+}
+
+static inline void *
+load_cached_ramstage(struct romstage_handoff *handoff,
+ const struct cbmem_entry *ramstage)
+{
+ return NULL;
+}
+
#endif /* CONFIG_RELOCATABLE_RAMSTAGE */
+#endif /* defined(__PRE_RAM__) */
#endif
diff --git a/src/include/cbmem.h b/src/include/cbmem.h
index 9e68ba92f4..b47a847718 100644
--- a/src/include/cbmem.h
+++ b/src/include/cbmem.h
@@ -66,6 +66,7 @@
#define CBMEM_ID_HOB_POINTER 0x484f4221
#ifndef __ASSEMBLER__
+#include <stddef.h>
#include <stdint.h>
struct cbmem_entry;
@@ -150,6 +151,10 @@ void cbmem_late_set_table(uint64_t base, uint64_t size);
void get_cbmem_table(uint64_t *base, uint64_t *size);
struct cbmem_entry *get_cbmem_toc(void);
+static inline const struct cbmem_entry *cbmem_entry_find(uint32_t id)
+{
+ return NULL;
+}
#endif /* CONFIG_DYNAMIC_CBMEM */
/* Common API between cbmem and dynamic cbmem. */
diff --git a/src/include/ramstage_loader.h b/src/include/ramstage_loader.h
new file mode 100644
index 0000000000..ad085c0ba5
--- /dev/null
+++ b/src/include/ramstage_loader.h
@@ -0,0 +1,34 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2014 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
+ */
+#ifndef RAMSTAGE_LOADER_H
+#define RAMSTAGE_LOADER_H
+
+#include <stdint.h>
+struct cbmem_entry;
+
+/* Run ramstage from romstage. */
+void run_ramstage(void);
+
+struct ramstage_loader_ops {
+ const char *name;
+ void *(*load)(uint32_t cbmem_id, const char *name,
+ const struct cbmem_entry **cbmem_entry);
+};
+
+#endif /* RAMSTAGE_LOADER_H */
diff --git a/src/include/romstage_handoff.h b/src/include/romstage_handoff.h
index 699838a260..307babd329 100644
--- a/src/include/romstage_handoff.h
+++ b/src/include/romstage_handoff.h
@@ -41,6 +41,7 @@ struct romstage_handoff {
};
#if defined(__PRE_RAM__)
+#if CONFIG_EARLY_CBMEM_INIT
/* The romstage_handoff_find_or_add() function provides the necessary logic
* for initializing the romstage_handoff structure in cbmem. Different components
* of the romstage may be responsible for setting up different fields. Therefore
@@ -63,7 +64,14 @@ static inline struct romstage_handoff *romstage_handoff_find_or_add(void)
return handoff;
}
-#endif
+#else /* CONFIG_EARLY_CBMEM_INIT */
+static inline struct romstage_handoff *romstage_handoff_find_or_add(void)
+{
+ return NULL;
+}
+#endif /* CONFIG_EARLY_CBMEM_INIT */
+
+#endif /* defined(__PRE_RAM__) */
#endif /* ROMSTAGE_HANDOFF_H */
diff --git a/src/lib/Makefile.inc b/src/lib/Makefile.inc
index 79ceebf44b..5c37329b5c 100644
--- a/src/lib/Makefile.inc
+++ b/src/lib/Makefile.inc
@@ -16,6 +16,7 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#
+subdirs-y += loaders
bootblock-y += cbfs.c
ifneq ($(CONFIG_HAVE_ARCH_MEMSET),y)
diff --git a/src/lib/cbfs.c b/src/lib/cbfs.c
index 9fe1757a65..f2a2587669 100644
--- a/src/lib/cbfs.c
+++ b/src/lib/cbfs.c
@@ -123,58 +123,6 @@ void *cbfs_load_optionrom(struct cbfs_media *media, uint16_t vendor,
return dest;
}
-#if CONFIG_RELOCATABLE_RAMSTAGE && defined(__PRE_RAM__)
-
-#include <rmodule.h>
-#include <romstage_handoff.h>
-static void *load_stage_from_cbfs(struct cbfs_media *media, const char *name,
- struct romstage_handoff *handoff)
-{
- struct rmod_stage_load rmod_ram = {
- .cbmem_id = CBMEM_ID_RAMSTAGE,
- .name = name,
- };
-
- if (rmodule_stage_load_from_cbfs(&rmod_ram)) {
- printk(BIOS_DEBUG, "Could not load ramstage.\n");
- return (void *) -1;
- }
-
- cache_loaded_ramstage(handoff, rmod_ram.cbmem_entry, rmod_ram.entry);
-
- return rmod_ram.entry;
-}
-
-void * cbfs_load_stage(struct cbfs_media *media, const char *name)
-{
- struct romstage_handoff *handoff;
- const struct cbmem_entry *ramstage;
- void *entry;
-
- handoff = romstage_handoff_find_or_add();
-
- if (handoff == NULL) {
- LOG("Couldn't find or allocate romstage handoff.\n");
- return load_stage_from_cbfs(media, name, handoff);
- } else if (!handoff->s3_resume)
- return load_stage_from_cbfs(media, name, handoff);
-
- ramstage = cbmem_entry_find(CBMEM_ID_RAMSTAGE);
-
- if (ramstage == NULL)
- return load_stage_from_cbfs(media, name, handoff);
-
- /* S3 resume path. Load a cached copy of the loaded ramstage. If
- * return value is NULL load from cbfs. */
- entry = load_cached_ramstage(handoff, ramstage);
- if (entry == NULL)
- return load_stage_from_cbfs(media, name, handoff);
-
- return entry;
-}
-
-#else
-
void * cbfs_load_stage(struct cbfs_media *media, const char *name)
{
struct cbfs_stage *stage = (struct cbfs_stage *)
@@ -211,7 +159,6 @@ void * cbfs_load_stage(struct cbfs_media *media, const char *name)
return (void *) entry;
}
-#endif /* CONFIG_RELOCATABLE_RAMSTAGE */
#if !CONFIG_ALT_CBFS_LOAD_PAYLOAD
void *cbfs_load_payload(struct cbfs_media *media, const char *name)
diff --git a/src/lib/loaders/Makefile.inc b/src/lib/loaders/Makefile.inc
new file mode 100644
index 0000000000..eceaa00c44
--- /dev/null
+++ b/src/lib/loaders/Makefile.inc
@@ -0,0 +1,21 @@
+#
+# This file is part of the coreboot project.
+#
+# Copyright (C) 2014 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
+#
+
+romstage-y += cbfs_ramstage_loader.c
+romstage-y += load_and_run_ramstage.c
diff --git a/src/lib/loaders/cbfs_ramstage_loader.c b/src/lib/loaders/cbfs_ramstage_loader.c
new file mode 100644
index 0000000000..5d5cc0b0ec
--- /dev/null
+++ b/src/lib/loaders/cbfs_ramstage_loader.c
@@ -0,0 +1,67 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2008-2009 coresystems GmbH
+ * Copyright (C) 2014 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 <console/console.h>
+#include <cbfs.h>
+#include <arch/stages.h>
+#include <ramstage_loader.h>
+#include <timestamp.h>
+
+#if CONFIG_RELOCATABLE_RAMSTAGE
+#include <rmodule.h>
+
+static void *cbfs_load_ramstage(uint32_t cbmem_id, const char *name,
+ const struct cbmem_entry **cbmem_entry)
+{
+ struct rmod_stage_load rmod_ram = {
+ .cbmem_id = cbmem_id,
+ .name = name,
+ };
+
+ if (rmodule_stage_load_from_cbfs(&rmod_ram)) {
+ printk(BIOS_DEBUG, "Could not load ramstage.\n");
+ return NULL;
+ }
+
+ *cbmem_entry = rmod_ram.cbmem_entry;
+
+ return rmod_ram.entry;
+}
+
+#else /* CONFIG_RELOCATABLE_RAMSTAGE */
+
+static void *cbfs_load_ramstage(uint32_t cbmem_id, const char *name,
+ const struct cbmem_entry **cbmem_entry)
+{
+ void *entry;
+
+ entry = cbfs_load_stage(CBFS_DEFAULT_MEDIA, name);
+
+ if ((void *)entry == (void *) -1)
+ entry = NULL;
+
+ return entry;
+}
+
+#endif /* CONFIG_RELOCATABLE_RAMSTAGE */
+
+const struct ramstage_loader_ops cbfs_ramstage_loader = {
+ .name = "CBFS",
+ .load = cbfs_load_ramstage,
+};
diff --git a/src/lib/loaders/load_and_run_ramstage.c b/src/lib/loaders/load_and_run_ramstage.c
new file mode 100644
index 0000000000..be2be8219c
--- /dev/null
+++ b/src/lib/loaders/load_and_run_ramstage.c
@@ -0,0 +1,100 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2014 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 <stdlib.h>
+#include <console/console.h>
+#include <arch/stages.h>
+#include <cbfs.h>
+#include <cbmem.h>
+#include <ramstage_loader.h>
+#include <romstage_handoff.h>
+#include <timestamp.h>
+
+extern const struct ramstage_loader_ops cbfs_ramstage_loader;
+extern const struct ramstage_loader_ops vboot_ramstage_loader;
+
+static const struct ramstage_loader_ops *loaders[] = {
+#if CONFIG_VBOOT_VERIFY_FIRMWARE
+ &vboot_ramstage_loader,
+#endif
+ &cbfs_ramstage_loader,
+};
+
+static const char *ramstage_name = CONFIG_CBFS_PREFIX "/coreboot_ram";
+static const uint32_t ramstage_id = CBMEM_ID_RAMSTAGE;
+
+static void
+load_ramstage(const struct ramstage_loader_ops *ops, struct romstage_handoff *handoff)
+{
+ const struct cbmem_entry *cbmem_entry;
+ void *entry_point;
+
+ timestamp_add_now(TS_START_COPYRAM);
+ entry_point = ops->load(ramstage_id, ramstage_name, &cbmem_entry);
+
+ if (entry_point == NULL)
+ return;
+
+ cache_loaded_ramstage(handoff, cbmem_entry, entry_point);
+
+ timestamp_add_now(TS_END_COPYRAM);
+
+ stage_exit(entry_point);
+}
+
+static void run_ramstage_from_resume(struct romstage_handoff *handoff)
+{
+ void *entry;
+ const struct cbmem_entry *cbmem_entry;
+
+ if (handoff != NULL && handoff->s3_resume) {
+ cbmem_entry = cbmem_entry_find(ramstage_id);
+
+ /* No place to load ramstage. */
+ if (cbmem_entry == NULL)
+ return;
+
+ /* Load the cached ramstage to runtime location. */
+ entry = load_cached_ramstage(handoff, cbmem_entry);
+
+ if (entry != NULL) {
+ print_debug("Jumping to image.\n");
+ stage_exit(entry);
+ }
+ }
+}
+
+void run_ramstage(void)
+{
+ struct romstage_handoff *handoff;
+ const struct ramstage_loader_ops *ops;
+ int i;
+
+ handoff = romstage_handoff_find_or_add();
+
+ run_ramstage_from_resume(handoff);
+
+ for (i = 0; i < ARRAY_SIZE(loaders); i++) {
+ ops = loaders[i];
+ printk(BIOS_DEBUG, "Trying %s ramstage loader.\n", ops->name);
+ load_ramstage(ops, handoff);
+ }
+
+ die("Ramstage was not loaded!\n");
+}
diff --git a/src/soc/intel/baytrail/romstage/romstage.c b/src/soc/intel/baytrail/romstage/romstage.c
index 4d74b53e3e..3ab726df91 100644
--- a/src/soc/intel/baytrail/romstage/romstage.c
+++ b/src/soc/intel/baytrail/romstage/romstage.c
@@ -28,7 +28,6 @@
#include <ramstage_cache.h>
#include <romstage_handoff.h>
#include <timestamp.h>
-#include <vendorcode/google/chromeos/chromeos.h>
#include <baytrail/gpio.h>
#include <baytrail/iomap.h>
#include <baytrail/lpc.h>
@@ -172,9 +171,6 @@ void asmlinkage romstage_after_car(void)
timestamp_add_now(TS_END_ROMSTAGE);
- /* Run vboot verification if configured. */
- vboot_verify_firmware(romstage_handoff_find_or_add());
-
/* Load the ramstage. */
copy_and_run();
while (1);
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,
+};