summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/arch/arm/tables.c11
-rw-r--r--src/arch/arm64/tables.c7
-rw-r--r--src/include/bootmem.h22
-rw-r--r--src/lib/bootmem.c38
-rw-r--r--src/lib/selfboot.c2
5 files changed, 74 insertions, 6 deletions
diff --git a/src/arch/arm/tables.c b/src/arch/arm/tables.c
index eef6bf2ffd..682c2bc39e 100644
--- a/src/arch/arm/tables.c
+++ b/src/arch/arm/tables.c
@@ -18,6 +18,7 @@
#include <bootmem.h>
#include <boot/tables.h>
#include <boot/coreboot_tables.h>
+#include <symbols.h>
void arch_write_tables(uintptr_t coreboot_table)
{
@@ -25,6 +26,16 @@ void arch_write_tables(uintptr_t coreboot_table)
void bootmem_arch_add_ranges(void)
{
+ DECLARE_OPTIONAL_REGION(ttb_subtables);
+
+ bootmem_add_range((uintptr_t)_ttb, _ttb_size, BM_MEM_RAMSTAGE);
+ bootmem_add_range((uintptr_t)_ttb_subtables, _ttb_subtables_size,
+ BM_MEM_RAMSTAGE);
+
+ if (!IS_ENABLED(CONFIG_COMMON_CBFS_SPI_WRAPPER))
+ return;
+ bootmem_add_range((uintptr_t)_postram_cbfs_cache,
+ _postram_cbfs_cache_size, BM_MEM_RAMSTAGE);
}
void lb_arch_add_records(struct lb_header *header)
diff --git a/src/arch/arm64/tables.c b/src/arch/arm64/tables.c
index eef6bf2ffd..f36679e67f 100644
--- a/src/arch/arm64/tables.c
+++ b/src/arch/arm64/tables.c
@@ -18,6 +18,7 @@
#include <bootmem.h>
#include <boot/tables.h>
#include <boot/coreboot_tables.h>
+#include <symbols.h>
void arch_write_tables(uintptr_t coreboot_table)
{
@@ -25,6 +26,12 @@ void arch_write_tables(uintptr_t coreboot_table)
void bootmem_arch_add_ranges(void)
{
+ bootmem_add_range((uintptr_t)_ttb, _ttb_size, BM_MEM_RAMSTAGE);
+
+ if (!IS_ENABLED(CONFIG_COMMON_CBFS_SPI_WRAPPER))
+ return;
+ bootmem_add_range((uintptr_t)_postram_cbfs_cache,
+ _postram_cbfs_cache_size, BM_MEM_RAMSTAGE);
}
void lb_arch_add_records(struct lb_header *header)
diff --git a/src/include/bootmem.h b/src/include/bootmem.h
index df2233f202..4964c18f38 100644
--- a/src/include/bootmem.h
+++ b/src/include/bootmem.h
@@ -21,7 +21,12 @@
#include <boot/coreboot_tables.h>
/**
- * Bootmem types match to LB_MEM tags.
+ * Bootmem types match to LB_MEM tags, except for the following:
+ * BM_MEM_RAMSTAGE : Memory where any kind of boot firmware resides and that
+ * should not be touched by bootmem (by example: stack,
+ * TTB, program, ...).
+ * BM_MEM_PAYLOAD : Memory where any kind of payload resides and that should
+ * not be touched by bootmem.
* Start at 0x10000 to make sure that the caller doesn't provide LB_MEM tags.
*/
enum bootmem_type {
@@ -33,18 +38,29 @@ enum bootmem_type {
BM_MEM_UNUSABLE, /* Unusable address space */
BM_MEM_VENDOR_RSVD, /* Vendor Reserved */
BM_MEM_TABLE, /* Ram configuration tables are kept in */
+ BM_MEM_RAMSTAGE,
+ BM_MEM_PAYLOAD,
BM_MEM_LAST, /* Last entry in this list */
};
-/* Write memory coreboot table. Current resource map is serialized into
+/**
+ * Write memory coreboot table. Current resource map is serialized into
* memtable (LB_MEM_* types). bootmem library is unusable until this function
- * is called first in the write tables path before payload is loaded. */
+ * is called first in the write tables path before payload is loaded.
+ *
+ * Bootmem types match to LB_MEM tags, except for the following:
+ * BM_MEM_RAMSTAGE : Translates to LB_MEM_RAM.
+ * BM_MEM_PAYLOAD : Translates to LB_MEM_RAM.
+ */
void bootmem_write_memory_table(struct lb_memory *mem);
/* Architecture hook to add bootmem areas the architecture controls when
* bootmem_write_memory_table() is called. */
void bootmem_arch_add_ranges(void);
+/* Platform hook to add bootmem areas the platform / board controls. */
+void bootmem_platform_add_ranges(void);
+
/* Add a range of a given type to the bootmem address space. */
void bootmem_add_range(uint64_t start, uint64_t size,
const enum bootmem_type tag);
diff --git a/src/lib/bootmem.c b/src/lib/bootmem.c
index 5e9f7bd1af..4fbc4b3a3f 100644
--- a/src/lib/bootmem.c
+++ b/src/lib/bootmem.c
@@ -20,9 +20,11 @@
#include <cbmem.h>
#include <device/resource.h>
#include <stdlib.h>
+#include <symbols.h>
#include <assert.h>
static int initialized;
+static int table_written;
static struct memranges bootmem;
static int bootmem_is_initialized(void)
@@ -30,6 +32,16 @@ static int bootmem_is_initialized(void)
return initialized;
}
+static int bootmem_memory_table_written(void)
+{
+ return table_written;
+}
+
+/* Platform hook to add bootmem areas the platform / board controls. */
+void __attribute__((weak)) bootmem_platform_add_ranges(void)
+{
+}
+
/* Convert bootmem tag to LB_MEM tag */
static uint32_t bootmem_to_lb_tag(const enum bootmem_type tag)
{
@@ -73,7 +85,12 @@ static void bootmem_init(void)
/* Add memory used by CBMEM. */
cbmem_add_bootmem();
+ /* Add memory used by coreboot. */
+ bootmem_add_range((uintptr_t)_stack, _stack_size, BM_MEM_RAMSTAGE);
+ bootmem_add_range((uintptr_t)_program, _program_size, BM_MEM_RAMSTAGE);
+
bootmem_arch_add_ranges();
+ bootmem_platform_add_ranges();
}
void bootmem_add_range(uint64_t start, uint64_t size,
@@ -81,6 +98,8 @@ void bootmem_add_range(uint64_t start, uint64_t size,
{
assert(tag > BM_MEM_FIRST && tag < BM_MEM_LAST);
assert(bootmem_is_initialized());
+ assert(!bootmem_memory_table_written() || tag == BM_MEM_RAMSTAGE ||
+ tag == BM_MEM_PAYLOAD);
memranges_insert(&bootmem, start, size, tag);
}
@@ -89,13 +108,22 @@ void bootmem_write_memory_table(struct lb_memory *mem)
{
const struct range_entry *r;
struct lb_memory_range *lb_r;
+ struct memranges bm;
lb_r = &mem->map[0];
bootmem_init();
bootmem_dump_ranges();
- memranges_each_entry(r, &bootmem) {
+ /**
+ * Convert BM_MEM_RAMSTAGE and BM_MEM_PAYLOAD to BM_MEM_RAM and
+ * merge ranges. The payload doesn't care about memory used by firmware.
+ */
+ memranges_clone(&bm, &bootmem);
+ memranges_update_tag(&bm, BM_MEM_RAMSTAGE, BM_MEM_RAM);
+ memranges_update_tag(&bm, BM_MEM_PAYLOAD, BM_MEM_RAM);
+
+ memranges_each_entry(r, &bm) {
lb_r->start = pack_lb64(range_entry_base(r));
lb_r->size = pack_lb64(range_entry_size(r));
lb_r->type = bootmem_to_lb_tag(range_entry_tag(r));
@@ -103,6 +131,10 @@ void bootmem_write_memory_table(struct lb_memory *mem)
lb_r++;
mem->size += sizeof(struct lb_memory_range);
}
+
+ memranges_teardown(&bm);
+
+ table_written = 1;
}
struct range_strings {
@@ -118,6 +150,8 @@ static const struct range_strings type_strings[] = {
{ BM_MEM_UNUSABLE, "UNUSABLE" },
{ BM_MEM_VENDOR_RSVD, "VENDOR RESERVED" },
{ BM_MEM_TABLE, "CONFIGURATION TABLES" },
+ { BM_MEM_RAMSTAGE, "RAM, RAMSTAGE" },
+ { BM_MEM_PAYLOAD, "RAM, PAYLOAD" },
};
static const char *bootmem_range_string(const enum bootmem_type tag)
@@ -212,7 +246,7 @@ void *bootmem_allocate_buffer(size_t size)
begin = end - size;
/* Mark buffer as unusuable for future buffer use. */
- bootmem_add_range(begin, size, BM_MEM_UNUSABLE);
+ bootmem_add_range(begin, size, BM_MEM_PAYLOAD);
return (void *)(uintptr_t)begin;
}
diff --git a/src/lib/selfboot.c b/src/lib/selfboot.c
index 20886b43b8..1cf32e5bd7 100644
--- a/src/lib/selfboot.c
+++ b/src/lib/selfboot.c
@@ -381,7 +381,7 @@ static int load_self_segments(struct segment *head, struct prog *payload,
*/
if (check_regions) {
bootmem_add_range(ptr->s_dstaddr, ptr->s_memsz,
- BM_MEM_UNUSABLE);
+ BM_MEM_PAYLOAD);
}
if (!overlaps_coreboot(ptr))