Implement a basic C loader function in load.c that tries to load each supported executable file format. Now that the ihandle

hierarchy is correct, we can simply pass an ihandle into the loader and it will work correctly regardless of whether it is being 
invoked on an entire disk, partition or individual file.

In order to test the new code, start by switching the Fcode loader over to the new infrastructure for testing on SPARC64. Note 
this patch also contains a correction to load-base on SPARC which was being set to a value other than 0x4000 which is the 
documented default.

Signed-off-by: Mark Cave-Ayland <mark.cave-ayland@siriusit.co.uk>


git-svn-id: svn://coreboot.org/openbios/trunk/openbios-devel@798 f158a5a8-5612-0410-a976-696ce0be7e32
This commit is contained in:
Mark Cave-Ayland
2010-06-25 20:42:00 +00:00
committed by Mark Cave-Ayland
parent add30adb7d
commit 3d7832bba9
13 changed files with 98 additions and 19 deletions

View File

@@ -30,12 +30,16 @@ static int try_path(const char *path, char *param)
{
void *boot_notes = NULL;
ucell valid;
ihandle_t dev;
push_str(path);
fword("pathres-resolve-aliases");
bootpath = pop_fstr_copy();
printk("Trying %s (%s)\n", path, bootpath);
/* Open device used by this path */
dev = open_dev(path);
#ifdef CONFIG_LOADER_ELF
/* ELF Boot loader */
elf_load(&sys_info, path, param, &boot_notes);
@@ -59,7 +63,7 @@ static int try_path(const char *path, char *param)
#ifdef CONFIG_LOADER_FCODE
/* Fcode loader */
fcode_load(path);
fcode_load(dev);
feval("state-valid @");
valid = POP();
if (valid)
@@ -75,6 +79,8 @@ static int try_path(const char *path, char *param)
goto start_image;
#endif
close_dev(dev);
return 0;

View File

@@ -27,6 +27,10 @@ extern int sparc64_of_client_interface( int *params );
static int try_path(const char *path, char *param)
{
ucell valid;
ihandle_t dev;
/* Open device used by this path */
dev = open_dev(path);
#ifdef CONFIG_LOADER_ELF
/* ELF Boot loader */
@@ -51,7 +55,7 @@ static int try_path(const char *path, char *param)
#ifdef CONFIG_LOADER_FCODE
/* Fcode loader */
fcode_load(path);
fcode_load(dev);
feval("state-valid @");
valid = POP();
if (valid)
@@ -67,6 +71,8 @@ static int try_path(const char *path, char *param)
goto start_image;
#endif
close_dev(dev);
return 0;

View File

@@ -24,6 +24,10 @@ void *boot_notes = NULL;
static int try_path(const char *path, char *param)
{
ucell valid;
ihandle_t dev;
/* Open device used by this path */
dev = open_dev(path);
#ifdef CONFIG_LOADER_ELF
/* ELF Boot loader */
@@ -48,7 +52,7 @@ static int try_path(const char *path, char *param)
#ifdef CONFIG_LOADER_FCODE
/* Fcode loader */
fcode_load(path);
fcode_load(dev);
feval("state-valid @");
valid = POP();
if (valid)
@@ -64,6 +68,8 @@ static int try_path(const char *path, char *param)
goto start_image;
#endif
close_dev(dev);
return 0;

View File

@@ -358,7 +358,7 @@ s" false" s" ttyb-rts-dtr-off" bool-config
[IFDEF] CONFIG_SPARC64
\ ---- SPARC64 ----
s" 4000000" s" load-base" int-config
s" 4000" s" load-base" int-config
s" false" s" little-endian?" bool-config
[THEN]

View File

@@ -18,7 +18,7 @@
#define _H_FCODELOAD
extern int is_fcode(unsigned char *fcode);
extern int fcode_load(const char *filename);
extern int fcode_load(ihandle_t dev);
extern void fcode_init_program(void);
#endif /* _H_FCODELOAD */

View File

@@ -0,0 +1,22 @@
/*
* Creation Date: <2010/06/25 20:00:00 mcayland>
* Time-stamp: <2010/06/25 20:00:00 mcayland>
*
* <load.h>
*
* C implementation of load
*
* Copyright (C) 2010 Mark Cave-Ayland (mark.cave-ayland@siriusit.co.uk)
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2
*
*/
#ifndef _H_LOAD
#define _H_LOAD
extern void load(ihandle_t dev);
#endif /* _H_LOAD */

View File

@@ -15,6 +15,7 @@
<object source="init.c"/>
<object source="initprogram.c"/>
<object source="ipchecksum.c"/>
<object source="load.c"/>
<object source="linuxbios_info.c" condition="LINUXBIOS"/>
<object source="ofmem_common.c" condition="OFMEM"/>
<object source="xcoff_load.c" condition="LOADER_XCOFF"/>

View File

@@ -24,7 +24,7 @@ is_fcode(unsigned char *fcode)
}
int
fcode_load(const char *filename)
fcode_load(ihandle_t dev)
{
int retval = -1;
uint8_t fcode_header[8];
@@ -34,7 +34,7 @@ fcode_load(const char *filename)
/* Mark the saved-program-state as invalid */
feval("0 state-valid !");
fd = open_io(filename);
fd = open_ih(dev);
if (!fd)
goto out;
@@ -42,7 +42,7 @@ fcode_load(const char *filename)
seek_io(fd, offset);
if (read_io(fd, &fcode_header, sizeof(fcode_header))
!= sizeof(fcode_header)) {
debug("Can't read FCode header from file %s\n", filename);
debug("Can't read FCode header from ihandle " FMT_ucellx "\n", dev);
retval = LOADER_NOT_SUPPORT;
goto out;
}
@@ -59,11 +59,12 @@ fcode_load(const char *filename)
size = (fcode_header[4] << 24) | (fcode_header[5] << 16) |
(fcode_header[6] << 8) | fcode_header[7];
start = 0x4000;
fword("load-base");
start = POP();
printf("Loading FCode image...\n");
printf("\nLoading FCode image...\n");
seek_io(fd, offset + sizeof(fcode_header));
seek_io(fd, offset);
if ((size_t)read_io(fd, (void *)start, size) != size) {
printf("Can't read file (size 0x%lx)\n", size);
@@ -92,6 +93,7 @@ fcode_init_program(void)
{
/* If the payload is Fcode then we execute it immediately */
ucell address;
uint8_t fcode_header[8];
fword("load-base");
address = POP();
@@ -101,7 +103,7 @@ fcode_init_program(void)
return;
}
PUSH(address);
PUSH(address + sizeof(fcode_header));
PUSH(1);
fword("byte-load");
}

33
libopenbios/load.c Normal file
View File

@@ -0,0 +1,33 @@
/*
* Creation Date: <2010/06/25 20:00:00 mcayland>
* Time-stamp: <2010/06/25 20:00:00 mcayland>
*
* <load.c>
*
* C implementation of load
*
* Copyright (C) 2010 Mark Cave-Ayland (mark.cave-ayland@siriusit.co.uk)
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2
*
*/
#include "config.h"
#include "kernel/kernel.h"
#include "libopenbios/bindings.h"
#include "libopenbios/load.h"
#include "libopenbios/fcode_load.h"
void load(ihandle_t dev)
{
/* Invoke the loaders on the specified device */
#ifdef CONFIG_LOADER_FCODE
fcode_load(dev);
#endif
}

View File

@@ -177,7 +177,7 @@ dlabel_load( __attribute__((unused)) dlabel_info_t *di )
xt = find_ih_method("load", di->part_ih);
if (!xt) {
forth_printf("load currently not implemented for /packages/disk-label\n");
forth_printf("load currently not implemented for ihandle " FMT_ucellx "\n", di->part_ih);
PUSH(0);
return;
}

View File

@@ -16,6 +16,7 @@
#include "config.h"
#include "libopenbios/bindings.h"
#include "libopenbios/load.h"
#include "mac-parts.h"
#include "libc/byteorder.h"
#include "libc/vsprintf.h"
@@ -328,8 +329,8 @@ macparts_read(macparts_info_t *di )
static void
macparts_load( __attribute__((unused))macparts_info_t *di )
{
forth_printf("load currently not implemented for /packages/mac-parts\n");
PUSH(0);
/* Invoke the loader */
load(my_self());
}
NODE_METHODS( macparts ) = {

View File

@@ -14,6 +14,7 @@
#include "config.h"
#include "libopenbios/bindings.h"
#include "libopenbios/load.h"
#include "libc/byteorder.h"
#include "libc/vsprintf.h"
#include "packages.h"
@@ -352,8 +353,8 @@ pcparts_read(pcparts_info_t *di )
static void
pcparts_load( __attribute__((unused))pcparts_info_t *di )
{
forth_printf("load currently not implemented for /packages/pc-parts\n");
PUSH(0);
/* Invoke the loader */
load(my_self());
}

View File

@@ -14,6 +14,7 @@
#include "config.h"
#include "libopenbios/bindings.h"
#include "libopenbios/load.h"
#include "libc/byteorder.h"
#include "libc/vsprintf.h"
#include "packages.h"
@@ -284,8 +285,8 @@ sunparts_read(sunparts_info_t *di )
static void
sunparts_load( __attribute__((unused))sunparts_info_t *di )
{
forth_printf("load currently not implemented for /packages/sun-parts\n");
PUSH(0);
/* Invoke the loader */
load(my_self());
}