version 1.1.1.1, 2008/06/03 10:38:41 |
version 1.1.1.1.2.1, 2008/08/13 17:12:20 |
|
|
#include <boot.h> |
#include <boot.h> |
#include <ar.h> |
#include <ar.h> |
|
|
u_long load_base; /* current load address */ |
#ifdef DEBUG |
u_long load_start; /* start address for loading */ |
#define DPRINTF(a) printf a |
|
#else |
|
#define DPRINTF(a) |
|
#endif |
|
|
|
paddr_t load_base; /* current load address */ |
|
paddr_t load_start; /* start address for loading */ |
int nr_img; /* number of module images */ |
int nr_img; /* number of module images */ |
|
|
struct boot_info *boot_info; /* pointer to boot information. */ |
struct boot_info *boot_info; /* pointer to boot information. */ |
|
|
* Define memory block as reserved area. |
* Define memory block as reserved area. |
*/ |
*/ |
void |
void |
reserve_memory(u_long start, size_t size) |
reserve_memory(paddr_t start, size_t size) |
{ |
{ |
int i; |
int i; |
u_long mem_end; |
paddr_t mem_end; |
|
|
printk("reserve_memory: start=%x size=%x\n", start, size); |
DPRINTF(("reserved memory: start=%x size=%x\n", start, size)); |
|
|
if (boot_info->main_mem.size == 0) |
if (boot_info->main_mem.size == 0) |
panic("bad mem size"); |
panic("bad mem size"); |
|
|
if (start > mem_end) |
if (start > mem_end) |
return; |
return; |
if (start + size > mem_end) |
if (start + size > mem_end) |
size = mem_end - start; |
size = (size_t)(mem_end - start); |
|
|
for (i = 0; i < NRESMEM; i++) { |
for (i = 0; i < NRESMEM; i++) { |
if (boot_info->reserved[i].size == 0) { |
if (boot_info->reserved[i].size == 0) { |
|
|
while (*c != '/' && *c != ' ') |
while (*c != '/' && *c != ' ') |
c++; |
c++; |
*c = '\0'; |
*c = '\0'; |
printk("load_image hdr=%x module=%x name=%s\n", |
|
(int)hdr, (int)m, (char *)&m->name); |
DPRINTF(("loading: hdr=%x module=%x name=%s\n", |
|
(int)hdr, (int)m, (char *)&m->name)); |
|
|
if (elf_load((char *)hdr + sizeof(struct ar_hdr), m)) |
if (elf_load((char *)hdr + sizeof(struct ar_hdr), m)) |
panic("Load error"); |
panic("Load error"); |
return 0; |
return 0; |
|
|
return; |
return; |
|
|
ram_disk = (struct mem_map *)&boot_info->ram_disk; |
ram_disk = (struct mem_map *)&boot_info->ram_disk; |
ram_disk->start = (u_long)hdr + sizeof(struct ar_hdr); |
ram_disk->start = (paddr_t)hdr + sizeof(struct ar_hdr); |
ram_disk->size = size; |
ram_disk->size = size; |
|
|
reserve_memory(ram_disk->start, ram_disk->size); |
reserve_memory(ram_disk->start, ram_disk->size); |
|
|
printk("RAM disk base=%x size=%x\n", ram_disk->start, ram_disk->size); |
DPRINTF(("RAM disk base=%x size=%x\n", ram_disk->start, |
|
ram_disk->size)); |
} |
} |
#endif /* CONFIG_RAMDISK */ |
#endif /* CONFIG_RAMDISK */ |
|
|
|
|
* It reads each module file image and copy it to the appropriate |
* It reads each module file image and copy it to the appropriate |
* memory area. The image is built as generic archive (.a) file. |
* memory area. The image is built as generic archive (.a) file. |
* |
* |
* The image information is strored into the boot information area. |
* The image information is stored into the boot information area. |
*/ |
*/ |
static void |
static void |
setup_image(void) |
setup_image(void) |
|
|
/* |
/* |
* Load kernel image |
* Load kernel image |
*/ |
*/ |
hdr = (char *)((u_long)magic + 8); |
hdr = (char *)((paddr_t)magic + 8); |
if (load_image((struct ar_hdr *)hdr, &boot_info->kernel)) |
if (load_image((struct ar_hdr *)hdr, &boot_info->kernel)) |
panic("Can not load kernel"); |
panic("Can not load kernel"); |
|
|
|
|
len = atol((char *)&((struct ar_hdr *)hdr)->ar_size); |
len = atol((char *)&((struct ar_hdr *)hdr)->ar_size); |
if (len == 0) |
if (len == 0) |
panic("Invalid OS image"); |
panic("Invalid OS image"); |
hdr = (char *)((u_long)hdr + sizeof(struct ar_hdr) + len); |
hdr = (char *)((paddr_t)hdr + sizeof(struct ar_hdr) + len); |
if (load_image((struct ar_hdr *)hdr, &boot_info->driver)) |
if (load_image((struct ar_hdr *)hdr, &boot_info->driver)) |
panic("Can not load driver"); |
panic("Can not load driver"); |
|
|
|
|
len = atol((char *)&((struct ar_hdr *)hdr)->ar_size); |
len = atol((char *)&((struct ar_hdr *)hdr)->ar_size); |
if (len == 0) |
if (len == 0) |
break; |
break; |
hdr = (char *)((u_long)hdr + sizeof(struct ar_hdr) + len); |
hdr = (char *)((paddr_t)hdr + sizeof(struct ar_hdr) + len); |
|
|
/* Pad to even boundary */ |
/* Pad to even boundary */ |
hdr += ((u_long)hdr % 2); |
hdr += ((paddr_t)hdr % 2); |
|
|
/* Check archive header */ |
/* Check archive header */ |
if (strncmp((char *)&((struct ar_hdr *)hdr)->ar_fmag, |
if (strncmp((char *)&((struct ar_hdr *)hdr)->ar_fmag, |
|
|
boot_info->modules.size = (size_t)(load_base - load_start); |
boot_info->modules.size = (size_t)(load_base - load_start); |
} |
} |
|
|
#ifdef DEBUG_BOOT |
#ifdef DEBUG_BOOTINFO |
static void |
static void |
dump_image(struct module *m) |
dump_image(struct module *m) |
{ |
{ |
printk |
printf("%s: entry=%x phys=%x size=%x text=%x data=%x textsz=%x datasz=%x bss=%x\n", |
("%s: entry=%x phys=%x size=%x text=%x data=%x textsz=%x datasz=%x bss=%x\n", |
m->name, (int)m->entry, (int)m->phys, (int)m->size, |
m->name, (int)m->entry, (int)m->phys, (int)m->size, |
(int)m->text, (int)m->data, (int)m->textsz, |
(int)m->text, (int)m->data, (int)m->textsz, |
(int)m->datasz, (int)m->bsssz); |
(int)m->datasz, (int)m->bsssz); |
|
} |
} |
|
|
static void |
static void |
|
|
struct module *m; |
struct module *m; |
int i; |
int i; |
|
|
printk("main memory start=%x size=%x\n", |
printf("main memory start=%x size=%x\n", |
(int)boot_info->main_mem.start, |
(int)boot_info->main_mem.start, |
(int)boot_info->main_mem.size); |
(int)boot_info->main_mem.size); |
|
|
for (i = 0; i < NRESMEM; i++) { |
for (i = 0; i < NRESMEM; i++) { |
if (boot_info->reserved[i].size != 0) { |
if (boot_info->reserved[i].size != 0) { |
printk("reserved mem start=%x size=%x\n", |
printf("reserved mem start=%x size=%x\n", |
(int)boot_info->reserved[i].start, |
(int)boot_info->reserved[i].start, |
(int)boot_info->reserved[i].size); |
(int)boot_info->reserved[i].size); |
} |
} |
} |
} |
printk("ramdisk start=%x size=%x\n", |
printf("ramdisk start=%x size=%x\n", |
(int)boot_info->ram_disk.start, |
(int)boot_info->ram_disk.start, |
(int)boot_info->ram_disk.size); |
(int)boot_info->ram_disk.size); |
|
|
|
|
void |
void |
loader_main(void) |
loader_main(void) |
{ |
{ |
u_int kernel_entry; |
paddr_t kernel_entry; |
|
|
printk("Prex Boot Loader V1.00\n"); |
DPRINTF(("Prex Boot Loader V1.00\n")); |
|
|
load_base = 0; |
load_base = 0; |
load_start = 0; |
load_start = 0; |
nr_img = 0; |
nr_img = 0; |
|
|
|
/* |
|
* Get machine-dependent information. |
|
*/ |
setup_bootinfo(&boot_info); |
setup_bootinfo(&boot_info); |
|
|
|
/* |
|
* Load program image. |
|
*/ |
setup_image(); |
setup_image(); |
#ifdef DEBUG_BOOT |
|
|
#ifdef DEBUG_BOOTINFO |
dump_bootinfo(); |
dump_bootinfo(); |
#endif |
#endif |
kernel_entry = (unsigned int)phys_to_virt(boot_info->kernel.entry); |
|
printk("kernel_entry=%x\n", kernel_entry); |
/* |
printk("Entering kernel...\n\n"); |
* Jump to the kernel entry point |
start_kernel(kernel_entry, (unsigned int)boot_info); |
* via machine-dependent code. |
|
*/ |
|
kernel_entry = (paddr_t)phys_to_virt(boot_info->kernel.entry); |
|
DPRINTF(("kernel_entry=%x\n", kernel_entry)); |
|
DPRINTF(("Entering kernel...\n\n")); |
|
start_kernel(kernel_entry, (paddr_t)boot_info); |
|
|
|
/* NOTREACHED */ |
} |
} |