armv7/snow: get to romstage
This patch does a few things to get us into romstage: - Add romstage as a stage (a later patch adds it as a binary, which is probably wrong). The Makefile magic is complex enough that we let it build the XIP file for now, but we no longer use it. - Replace findstage with loadstage. Loadstage will find a stage, load the code to memory, and zero the remaining part of memory. Now we can link the romstage to go anywhere! - Eliminate magic offsets from code/ldscripts and centralize Kconfig variables in src/cpu/samsung/exynos5250/Kconfig. - Tidy up code and serial output Change-Id: Iae4d2f9e7f429cb1df15d49daf9a08b88d75d79d Signed-off-by: David Hendricks <dhendrix@chromium.org> Signed-off-by: Ronald G. Minnich <rminnich@gmail.com> Reviewed-on: http://review.coreboot.org/2174 Tested-by: build bot (Jenkins)
This commit is contained in:
committed by
Ronald G. Minnich
parent
f572e1e5fc
commit
211a5d56db
@@ -215,9 +215,8 @@ $(obj)/coreboot.pre: $(objcbfs)/romstage_xip.elf $(obj)/coreboot.pre1 $(CBFSTOOL
|
||||
@printf " CBFS $(subst $(obj)/,,$(@))\n"
|
||||
cp $(obj)/coreboot.pre1 $@.tmp
|
||||
$(CBFSTOOL) $@.tmp add-stage \
|
||||
-f $(objcbfs)/romstage_xip.elf \
|
||||
-n $(CONFIG_CBFS_PREFIX)/romstage -c none \
|
||||
-b $(shell cat $(objcbfs)/base_xip.txt)
|
||||
-f $(objcbfs)/romstage_null.debug \
|
||||
-n $(CONFIG_CBFS_PREFIX)/romstage -c none
|
||||
mv $@.tmp $@
|
||||
|
||||
################################################################################
|
||||
|
@@ -92,4 +92,4 @@ wait_for_interrupt:
|
||||
*/
|
||||
.align 2
|
||||
.Stack:
|
||||
.word CONFIG_SYS_INIT_SP_ADDR
|
||||
.word CONFIG_IRAM_STACK
|
||||
|
@@ -39,12 +39,13 @@ void main(unsigned long bist)
|
||||
unsigned long entry;
|
||||
|
||||
if (boot_cpu()) {
|
||||
bootblock_mainboard_init();
|
||||
bootblock_cpu_init();
|
||||
bootblock_mainboard_init();
|
||||
}
|
||||
|
||||
entry = findstage(target1);
|
||||
printk(BIOS_INFO, "bootblock main(): loading romstage\n");
|
||||
entry = loadstage(target1);
|
||||
printk(BIOS_INFO, "bootblock main(): jumping to romstage\n");
|
||||
if (entry) call(entry);
|
||||
|
||||
hlt();
|
||||
}
|
||||
|
@@ -26,42 +26,93 @@
|
||||
#include <arch/byteorder.h>
|
||||
#include <arch/cbfs.h>
|
||||
|
||||
|
||||
static int cbfs_check_magic(struct cbfs_file *file)
|
||||
{
|
||||
return !strcmp(file->magic, CBFS_FILE_MAGIC) ? 1 : 0;
|
||||
return strcmp(file->magic, CBFS_FILE_MAGIC) ? 0 : 1;
|
||||
}
|
||||
|
||||
static unsigned long findstage(const char* target)
|
||||
static unsigned long loadstage(const char* target)
|
||||
{
|
||||
unsigned long offset, align;
|
||||
struct cbfs_header *header = (struct cbfs_header *)(CONFIG_BOOTBLOCK_BASE + 0x40);
|
||||
/* FIXME: magic offsets */
|
||||
struct cbfs_header *header = (struct cbfs_header *)(0x02023400 + 0x40);
|
||||
// if (ntohl(header->magic) != CBFS_HEADER_MAGIC)
|
||||
// printk(BIOS_ERR, "ERROR: No valid CBFS header found!\n");
|
||||
|
||||
offset = ntohl(header->offset);
|
||||
align = ntohl(header->align);
|
||||
printk(BIOS_INFO, "cbfs header (0x%p)\n", header);
|
||||
printk(BIOS_INFO, "\tmagic: 0x%08x\n", ntohl(header->magic));
|
||||
printk(BIOS_INFO, "\tversion: 0x%08x\n", ntohl(header->version));
|
||||
printk(BIOS_INFO, "\tromsize: 0x%08x\n", ntohl(header->romsize));
|
||||
printk(BIOS_INFO, "\tbootblocksize: 0x%08x\n", ntohl(header->bootblocksize));
|
||||
printk(BIOS_INFO, "\talign: 0x%08x\n", ntohl(header->align));
|
||||
printk(BIOS_INFO, "\toffset: 0x%08x\n", ntohl(header->offset));
|
||||
while(1) {
|
||||
struct cbfs_file *file;
|
||||
file = (struct cbfs_file *)(offset + CONFIG_ROMSTAGE_BASE);
|
||||
if (!cbfs_check_magic(file))
|
||||
struct cbfs_stage *stage;
|
||||
/* FIXME: SPI image hack */
|
||||
file = (struct cbfs_file *)(offset + CONFIG_SPI_IMAGE_HACK);
|
||||
if (!cbfs_check_magic(file)) {
|
||||
printk(BIOS_INFO, "magic is wrong, file: %p\n", file);
|
||||
return 0;
|
||||
if (!strcmp(CBFS_NAME(file), target))
|
||||
return (unsigned long)CBFS_SUBHEADER(file);
|
||||
}
|
||||
if (!strcmp(CBFS_NAME(file), target)) {
|
||||
uint32_t load, entry;
|
||||
printk(BIOS_INFO, "CBFS name matched, offset: %p\n", file);
|
||||
printk(BIOS_INFO, "\tmagic: %02x%02x%02x%02x%02x%02x%02x%02x\n",
|
||||
file->magic[0], file->magic[1], file->magic[2], file->magic[3],
|
||||
file->magic[4], file->magic[5], file->magic[6], file->magic[7]);
|
||||
printk(BIOS_INFO, "\tlen: 0x%08x\n", ntohl(file->len));
|
||||
printk(BIOS_INFO, "\ttype: 0x%08x\n", ntohl(file->type));
|
||||
printk(BIOS_INFO, "\tchecksum: 0x%08x\n", ntohl(file->checksum));
|
||||
printk(BIOS_INFO, "\toffset: 0x%08x\n", ntohl(file->offset));
|
||||
/* exploit the fact that this is all word-aligned. */
|
||||
stage = CBFS_SUBHEADER(file);
|
||||
load = stage->load;
|
||||
entry = stage->entry;
|
||||
int i;
|
||||
u32 *to = (void *)load;
|
||||
u32 *from = (void *)((u8 *)stage+sizeof(*stage));
|
||||
/* we could do memmove/memset here. But the math gets messy.
|
||||
* far easier just to do what we want.
|
||||
*/
|
||||
printk(BIOS_INFO, "entry: 0x%08x, load: 0x%08x, "
|
||||
"len: 0x%08x, memlen: 0x%08x\n", entry,
|
||||
load, stage->len, stage->memlen);
|
||||
for(i = 0; i < stage->len; i += 4)
|
||||
*to++ = *from++;
|
||||
for(; i < stage->memlen; i += 4)
|
||||
*to++ = 0;
|
||||
return entry;
|
||||
}
|
||||
int flen = ntohl(file->len);
|
||||
int foffset = ntohl(file->offset);
|
||||
unsigned long oldoffset = offset;
|
||||
offset = ALIGN(offset + foffset + flen, align);
|
||||
printk(BIOS_INFO, "offset: 0x%08lx\n", offset);
|
||||
if (offset <= oldoffset)
|
||||
return 0;
|
||||
if (offset < CONFIG_ROMSTAGE_BASE + ntohl(header->romsize));
|
||||
if (offset > CONFIG_ROMSTAGE_SIZE)
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
static inline void call(unsigned long addr)
|
||||
{
|
||||
void (*doit)(void) = (void *)addr;
|
||||
__attribute__((noreturn)) void (*doit)(void) = (void *)addr;
|
||||
printk(BIOS_INFO, "addr: %08lx, doit: %p\n", addr, doit);
|
||||
/* FIXME: dumping SRAM content for sanity checking */
|
||||
int i;
|
||||
for (i = 0; i < 128; i++) {
|
||||
if (i % 16 == 0)
|
||||
printk(BIOS_INFO, "\n0x%08lx: ", addr + i);
|
||||
else
|
||||
printk(BIOS_INFO, " ");
|
||||
printk(BIOS_INFO, "%02x", *(uint8_t *)(addr + i));
|
||||
}
|
||||
/* FIXME: do we need to change to/from arm/thumb? */
|
||||
doit();
|
||||
}
|
||||
#endif
|
||||
|
@@ -4,7 +4,6 @@
|
||||
static inline __attribute__((always_inline)) void hlt(void)
|
||||
{
|
||||
for (;;) ;
|
||||
//asm("hlt");
|
||||
}
|
||||
|
||||
#endif /* ARCH_HLT_H */
|
||||
|
@@ -1,6 +1,5 @@
|
||||
SECTIONS {
|
||||
/* FIXME: determine a sensible location... */
|
||||
. = (0x2026400);
|
||||
. = CONFIG_ID_SECTION_BASE;
|
||||
.id (.): {
|
||||
*(.id)
|
||||
}
|
||||
|
@@ -24,22 +24,16 @@
|
||||
INCLUDE ldoptions
|
||||
*/
|
||||
|
||||
/*
|
||||
* FIXME: what exactly should these be? maybe defined on a per-CPU basis?
|
||||
* FIXME 2: Somehow linker didn't like CONFIG_SPL_MAX_SIZE and CONFIG_SPL_TEXT_BASE...
|
||||
*/
|
||||
/* MEMORY { .sram : ORIGIN = 0x02023400, LENGTH = 0x3800 } */
|
||||
/*MEMORY { .sram : ORIGIN = 0x02023400, LENGTH = 0x10000 }*/
|
||||
|
||||
/* We use ELF as output format. So that we can debug the code in some form. */
|
||||
OUTPUT_FORMAT("elf32-littlearm", "elf32-littlearm", "elf32-littlearm")
|
||||
OUTPUT_ARCH(arm)
|
||||
|
||||
/* ENTRY(_start) */
|
||||
ENTRY(_start)
|
||||
|
||||
SECTIONS
|
||||
{
|
||||
. = 0x02023400 + 0x4000;
|
||||
/* TODO make this a configurable option (per chipset). */
|
||||
. = CONFIG_ROMSTAGE_BASE;
|
||||
|
||||
.romtext . : {
|
||||
_rom = .;
|
||||
|
Reference in New Issue
Block a user