20090819-2-trim-down-cbfs:
CBFS uses sprintf, which requires vtxprintf, which requires (in the current design) a nested function. That works on x86, but on PPC this requires a trampoline. In the ROM stage, this is not available, so remove the single use of sprintf and replace it with a direct string handler - it's only used to fill in fixed-length hex values. 20090819-3-more-noreturns-in-romcc: Mark two more functions in romcc as noreturn. Helps clang's scan-build a bit 20090819-4-cbfsify-ppc: Make PPC use CBFS. Support big endian ELF in cbfs-mkstage. Untested and not complete yet. 20090819-5-fix-ppc-build: The CBFS build system requires ROM_IMAGE_SIZE to have a somewhat plausible value. With fixes to tohex* functions as discussed on the list, and correct function names. Signed-off-by: Patrick Georgi <patrick.georgi@coresystems.de> Acked-by: Myles Watson <mylesgw@gmail.com> Acked-by: Stefan Reinauer <stepan@coresystems.de> git-svn-id: svn://svn.coreboot.org/coreboot/trunk@4558 2b7e53f0-3cfb-0310-b3e9-8179ed1497e1
This commit is contained in:
parent
ce9d8640b1
commit
b203c2f95e
|
@ -13,7 +13,6 @@ if CONFIG_CBFS
|
||||||
if CONFIG_USE_FAILOVER_IMAGE
|
if CONFIG_USE_FAILOVER_IMAGE
|
||||||
else
|
else
|
||||||
initobject /src/lib/cbfs.o
|
initobject /src/lib/cbfs.o
|
||||||
initobject /src/console/vsprintf.o
|
|
||||||
initobject /src/lib/lzma.o
|
initobject /src/lib/lzma.o
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
uses CONFIG_CBFS
|
||||||
ldscript init/ldscript.lb
|
ldscript init/ldscript.lb
|
||||||
|
|
||||||
makerule coreboot.strip
|
makerule coreboot.strip
|
||||||
|
@ -10,6 +11,11 @@ makerule coreboot.rom
|
||||||
action "cp $< $@"
|
action "cp $< $@"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
if CONFIG_CBFS
|
||||||
|
initobject /src/lib/cbfs.o
|
||||||
|
initobject /src/lib/lzma.o
|
||||||
|
end
|
||||||
|
|
||||||
dir init
|
dir init
|
||||||
dir lib
|
dir lib
|
||||||
dir boot
|
dir boot
|
||||||
|
|
|
@ -5,12 +5,7 @@
|
||||||
|
|
||||||
#include <board.h>
|
#include <board.h>
|
||||||
#include <sdram.h>
|
#include <sdram.h>
|
||||||
|
#include <cbfs.h>
|
||||||
extern unsigned _iseg[];
|
|
||||||
extern unsigned _liseg[];
|
|
||||||
extern unsigned _eliseg[];
|
|
||||||
|
|
||||||
void (*payload)(void) = (void (*)(void))_iseg;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* At this point we're running out of flash with our
|
* At this point we're running out of flash with our
|
||||||
|
@ -25,8 +20,7 @@ extern void flush_dcache(void);
|
||||||
|
|
||||||
void ppc_main(void)
|
void ppc_main(void)
|
||||||
{
|
{
|
||||||
unsigned *from;
|
void (*payload)(void);
|
||||||
unsigned *to;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* very early board initialization
|
* very early board initialization
|
||||||
|
@ -49,15 +43,9 @@ void ppc_main(void)
|
||||||
flush_dcache();
|
flush_dcache();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Relocate payload (text & data) if necessary
|
* Relocate payload (text & data)
|
||||||
*/
|
*/
|
||||||
if (_liseg != _iseg) {
|
payload = cbfs_load_stage("fallback/coreboot_ram");
|
||||||
from = _liseg;
|
|
||||||
to = _iseg;
|
|
||||||
while (from < _eliseg)
|
|
||||||
*to++ = *from++;
|
|
||||||
}
|
|
||||||
|
|
||||||
payload();
|
payload();
|
||||||
|
|
||||||
/* NOT REACHED */
|
/* NOT REACHED */
|
||||||
|
|
|
@ -124,13 +124,27 @@ struct cbfs_stage *cbfs_find_file(const char *name, int type)
|
||||||
return (void *) CBFS_SUBHEADER(file);
|
return (void *) CBFS_SUBHEADER(file);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int tohex4(unsigned int c)
|
||||||
|
{
|
||||||
|
return (c<=9)?(c+'0'):(c-10+'a');
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tohex16(unsigned int val, char* dest)
|
||||||
|
{
|
||||||
|
dest[0]=tohex4(val>>12);
|
||||||
|
dest[1]=tohex4((val>>8) & 0xf);
|
||||||
|
dest[2]=tohex4((val>>4) & 0xf);
|
||||||
|
dest[3]=tohex4(val & 0xf);
|
||||||
|
}
|
||||||
|
|
||||||
void *cbfs_load_optionrom(u16 vendor, u16 device, void * dest)
|
void *cbfs_load_optionrom(u16 vendor, u16 device, void * dest)
|
||||||
{
|
{
|
||||||
char name[17];
|
char name[17]="pciXXXX,XXXX.rom";
|
||||||
struct cbfs_optionrom *orom;
|
struct cbfs_optionrom *orom;
|
||||||
u8 *src;
|
u8 *src;
|
||||||
|
|
||||||
sprintf(name,"pci%04x,%04x.rom", vendor, device);
|
tohex16(vendor, name+3);
|
||||||
|
tohex16(device, name+8);
|
||||||
|
|
||||||
orom = (struct cbfs_optionrom *)
|
orom = (struct cbfs_optionrom *)
|
||||||
cbfs_find_file(name, CBFS_TYPE_OPTIONROM);
|
cbfs_find_file(name, CBFS_TYPE_OPTIONROM);
|
||||||
|
|
|
@ -106,6 +106,7 @@ default CONFIG_FS_FAT=1
|
||||||
default CONFIG_AUTOBOOT_CMDLINE="hda1:/vmlinuz"
|
default CONFIG_AUTOBOOT_CMDLINE="hda1:/vmlinuz"
|
||||||
|
|
||||||
default CONFIG_ROM_SIZE=1048576
|
default CONFIG_ROM_SIZE=1048576
|
||||||
|
default CONFIG_ROM_IMAGE_SIZE=160*1024
|
||||||
|
|
||||||
## Board has fixed size RAM
|
## Board has fixed size RAM
|
||||||
default CONFIG_EMBEDDED_RAM_SIZE=64*1024*1024
|
default CONFIG_EMBEDDED_RAM_SIZE=64*1024*1024
|
||||||
|
|
|
@ -94,8 +94,8 @@ default CONFIG_FS_FAT=1
|
||||||
default CONFIG_AUTOBOOT_CMDLINE="hdc1:/vmlinuz"
|
default CONFIG_AUTOBOOT_CMDLINE="hdc1:/vmlinuz"
|
||||||
|
|
||||||
# coreboot must fit into 128KB
|
# coreboot must fit into 128KB
|
||||||
default CONFIG_ROM_IMAGE_SIZE=131072
|
default CONFIG_ROM_IMAGE_SIZE=160*1024
|
||||||
default CONFIG_ROM_SIZE={CONFIG_ROM_IMAGE_SIZE+CONFIG_PAYLOAD_SIZE}
|
default CONFIG_ROM_SIZE=384*1024
|
||||||
default CONFIG_PAYLOAD_SIZE=262144
|
default CONFIG_PAYLOAD_SIZE=262144
|
||||||
|
|
||||||
# Set stack and heap sizes (stage 2)
|
# Set stack and heap sizes (stage 2)
|
||||||
|
|
|
@ -96,6 +96,7 @@ default CONFIG_IDE_OFFSET=0
|
||||||
|
|
||||||
# ROM is 1Mb
|
# ROM is 1Mb
|
||||||
default CONFIG_ROM_SIZE=1048576
|
default CONFIG_ROM_SIZE=1048576
|
||||||
|
default CONFIG_ROM_IMAGE_SIZE=128*1024
|
||||||
|
|
||||||
# Set stack and heap sizes (stage 2)
|
# Set stack and heap sizes (stage 2)
|
||||||
default CONFIG_STACK_SIZE=0x10000
|
default CONFIG_STACK_SIZE=0x10000
|
||||||
|
|
|
@ -29,6 +29,18 @@
|
||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "../cbfs.h"
|
#include "../cbfs.h"
|
||||||
|
|
||||||
|
unsigned int idemp(unsigned int x)
|
||||||
|
{
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int swap32(unsigned int x)
|
||||||
|
{
|
||||||
|
return ((x>>24) | ((x>>8) & 0xff00) | ((x<<8) & 0xff0000) | (x<<24));
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int (*elf32_to_native)(unsigned int)=idemp;
|
||||||
|
|
||||||
int parse_elf(unsigned char *input, unsigned char **output,
|
int parse_elf(unsigned char *input, unsigned char **output,
|
||||||
int mode, void (*compress) (char *, int, char *, int *))
|
int mode, void (*compress) (char *, int, char *, int *))
|
||||||
{
|
{
|
||||||
|
@ -42,10 +54,22 @@ int parse_elf(unsigned char *input, unsigned char **output,
|
||||||
struct cbfs_stage *stage;
|
struct cbfs_stage *stage;
|
||||||
unsigned int data_start, data_end, mem_end;
|
unsigned int data_start, data_end, mem_end;
|
||||||
|
|
||||||
|
int elf_bigendian = 0;
|
||||||
|
int host_bigendian = 0;
|
||||||
|
if (ehdr->e_ident[EI_DATA]==ELFDATA2MSB) {
|
||||||
|
elf_bigendian = 1;
|
||||||
|
}
|
||||||
|
if ((unsigned int)"1234"==0x31323334) {
|
||||||
|
host_bigendian = 1;
|
||||||
|
}
|
||||||
|
if (elf_bigendian != host_bigendian) {
|
||||||
|
elf32_to_native = swap32;
|
||||||
|
}
|
||||||
|
|
||||||
headers = ehdr->e_phnum;
|
headers = ehdr->e_phnum;
|
||||||
header = (char *)ehdr;
|
header = (char *)ehdr;
|
||||||
|
|
||||||
phdr = (Elf32_Phdr *) & (header[ehdr->e_phoff]);
|
phdr = (Elf32_Phdr *) & header[elf32_to_native(ehdr->e_phoff)];
|
||||||
|
|
||||||
/* Now, regular headers - we only care about PT_LOAD headers,
|
/* Now, regular headers - we only care about PT_LOAD headers,
|
||||||
* because thats what we're actually going to load
|
* because thats what we're actually going to load
|
||||||
|
@ -58,19 +82,19 @@ int parse_elf(unsigned char *input, unsigned char **output,
|
||||||
for (i = 0; i < headers; i++) {
|
for (i = 0; i < headers; i++) {
|
||||||
unsigned int start, mend, rend;
|
unsigned int start, mend, rend;
|
||||||
|
|
||||||
if (phdr[i].p_type != PT_LOAD)
|
if (elf32_to_native(phdr[i].p_type) != PT_LOAD)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* Empty segments are never interesting */
|
/* Empty segments are never interesting */
|
||||||
if (phdr[i].p_memsz == 0)
|
if (elf32_to_native(phdr[i].p_memsz) == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/* BSS */
|
/* BSS */
|
||||||
|
|
||||||
start = phdr[i].p_paddr;
|
start = elf32_to_native(phdr[i].p_paddr);
|
||||||
|
|
||||||
mend = start + phdr[i].p_memsz;
|
mend = start + elf32_to_native(phdr[i].p_memsz);
|
||||||
rend = start + phdr[i].p_filesz;
|
rend = start + elf32_to_native(phdr[i].p_filesz);
|
||||||
|
|
||||||
if (start < data_start)
|
if (start < data_start)
|
||||||
data_start = start;
|
data_start = start;
|
||||||
|
@ -94,14 +118,14 @@ int parse_elf(unsigned char *input, unsigned char **output,
|
||||||
|
|
||||||
for (i = 0; i < headers; i++) {
|
for (i = 0; i < headers; i++) {
|
||||||
|
|
||||||
if (phdr[i].p_type != PT_LOAD)
|
if (elf32_to_native(phdr[i].p_type) != PT_LOAD)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (phdr[i].p_memsz == 0)
|
if (elf32_to_native(phdr[i].p_memsz) == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
memcpy(buffer + (phdr[i].p_paddr - data_start),
|
memcpy(buffer + (elf32_to_native(phdr[i].p_paddr) - data_start),
|
||||||
&header[phdr[i].p_offset], phdr[i].p_filesz);
|
&header[elf32_to_native(phdr[i].p_offset)], elf32_to_native(phdr[i].p_filesz));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Now make the output buffer */
|
/* Now make the output buffer */
|
||||||
|
|
|
@ -1768,7 +1768,7 @@ static void loc(FILE *fp, struct compile_state *state, struct triple *triple)
|
||||||
state->file->report_name, state->file->report_line, col);
|
state->file->report_name, state->file->report_line, col);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void internal_error(struct compile_state *state, struct triple *ptr,
|
static void __attribute__ ((noreturn)) internal_error(struct compile_state *state, struct triple *ptr,
|
||||||
const char *fmt, ...)
|
const char *fmt, ...)
|
||||||
{
|
{
|
||||||
FILE *fp = state->errout;
|
FILE *fp = state->errout;
|
||||||
|
@ -1806,7 +1806,7 @@ static void internal_warning(struct compile_state *state, struct triple *ptr,
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void error(struct compile_state *state, struct triple *ptr,
|
static void __attribute__ ((noreturn)) error(struct compile_state *state, struct triple *ptr,
|
||||||
const char *fmt, ...)
|
const char *fmt, ...)
|
||||||
{
|
{
|
||||||
FILE *fp = state->errout;
|
FILE *fp = state->errout;
|
||||||
|
|
Loading…
Reference in New Issue