/trunk/kernel/generic/include/main/main.h |
---|
35,8 → 35,13 |
#ifndef KERN_MAIN_H_ |
#define KERN_MAIN_H_ |
#include <arch/types.h> |
extern uintptr_t stack_safe; |
extern void main_bsp(void); |
extern void main_ap(void); |
#endif |
/** @} |
/trunk/kernel/generic/src/main/main.c |
---|
81,8 → 81,8 |
#include <adt/btree.h> |
#include <smp/smp.h> |
#include <ddi/ddi.h> |
#include <main/main.h> |
/** Global configuration structure. */ |
config_t config; |
114,9 → 114,6 |
/** Lowest safe stack virtual address. */ |
uintptr_t stack_safe = 0; |
void main_bsp(void); |
void main_ap(void); |
/* |
* These two functions prevent stack from underflowing during the |
* kernel boot phase when SP is set to the very top of the reserved |
/trunk/kernel/arch/ia32/include/boot/cboot.h |
---|
0,0 → 1,91 |
/* |
* Copyright (c) 2005 Martin Decky |
* All rights reserved. |
* |
* Redistribution and use in source and binary forms, with or without |
* modification, are permitted provided that the following conditions |
* are met: |
* |
* - Redistributions of source code must retain the above copyright |
* notice, this list of conditions and the following disclaimer. |
* - Redistributions in binary form must reproduce the above copyright |
* notice, this list of conditions and the following disclaimer in the |
* documentation and/or other materials provided with the distribution. |
* - The name of the author may not be used to endorse or promote products |
* derived from this software without specific prior written permission. |
* |
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR |
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES |
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. |
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, |
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT |
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
*/ |
/** @addtogroup ia32 |
* @{ |
*/ |
/** @file |
*/ |
#ifndef KERN_ia32_CBOOT_H__ |
#define KERN_ia32_CBOOT_H_ |
#include <arch/types.h> |
#include <arch/boot/memmap.h> |
/** Multiboot mod structure */ |
typedef struct { |
uintptr_t start; |
uintptr_t end; |
char *string; |
uint32_t reserved; |
} __attribute__ ((packed)) mb_mod_t; |
/** Multiboot mmap structure */ |
typedef struct { |
uint32_t size; |
e820memmap_t mm_info; |
} __attribute__ ((packed)) mb_mmap_t; |
/** Multiboot information structure */ |
typedef struct { |
uint32_t flags; |
uintptr_t mem_lower; |
uintptr_t mem_upper; |
uint32_t boot_device; |
char *cmdline; |
uint32_t mods_count; |
mb_mod_t *mods_addr; |
uint32_t syms[4]; |
uint32_t mmap_length; |
mb_mmap_t *mmap_addr; |
/* ... */ |
} __attribute__ ((packed)) mb_info_t; |
enum mb_info_flags { |
MBINFO_FLAGS_MEM = 0x01, |
MBINFO_FLAGS_BOOT = 0x02, |
MBINFO_FLAGS_CMDLINE = 0x04, |
MBINFO_FLAGS_MODS = 0x08, |
MBINFO_FLAGS_SYMS1 = 0x10, |
MBINFO_FLAGS_SYMS2 = 0x20, |
MBINFO_FLAGS_MMAP = 0x40 |
/* ... */ |
}; |
extern void ia32_cboot(uint32_t signature, const mb_info_t *mi); |
#endif |
/** @} |
*/ |
/trunk/kernel/arch/ia32/Makefile.inc |
---|
99,6 → 99,7 |
arch/$(KARCH)/src/drivers/i8259.c \ |
arch/$(KARCH)/src/drivers/vesa.c \ |
arch/$(KARCH)/src/boot/boot.S \ |
arch/$(KARCH)/src/boot/cboot.c \ |
arch/$(KARCH)/src/boot/memmap.c \ |
arch/$(KARCH)/src/fpu_context.c \ |
arch/$(KARCH)/src/debugger.c \ |
/trunk/kernel/arch/ia32/src/boot/boot.S |
---|
101,117 → 101,33 |
shr $16, %ebx |
mov %bx, KA2PA(vesa_bpp) |
#endif |
call map_kernel # map kernel and turn paging on |
movl grub_eax, %eax |
movl grub_ebx, %ebx |
cmpl $MULTIBOOT_LOADER_MAGIC, %eax # compare GRUB signature |
je valid_boot |
xorl %ecx, %ecx # no memory map available |
movl %ecx, e820counter |
jmp invalid_boot |
valid_boot: |
movl (%ebx), %eax # ebx = physical address of struct multiboot_info |
bt $3, %eax # mbi->flags[3] (mods_count, mods_addr valid) |
jc mods_valid |
xorl %ecx, %ecx |
movl %ecx, init |
jmp mods_end |
mods_valid: |
movl 20(%ebx), %ecx # mbi->mods_count |
movl %ecx, init |
cmpl $0, %ecx |
je mods_end |
movl 24(%ebx), %esi # mbi->mods_addr |
movl $init, %edi |
mods_loop: |
movl 0(%esi), %edx # mods->mod_start |
addl $0x80000000, %edx |
movl %edx, 4(%edi) |
movl 4(%esi), %edx |
subl 0(%esi), %edx # mods->mod_end - mods->mod_start |
movl %edx, 8(%edi) |
addl $16, %esi |
addl $8 , %edi |
loop mods_loop |
mods_end: |
bt $6, %eax # mbi->flags[6] (mmap_length, mmap_addr valid) |
jc mmap_valid |
xorl %edx, %edx |
jmp mmap_invalid |
mmap_valid: |
movl 44(%ebx), %ecx # mbi->mmap_length |
movl 48(%ebx), %esi # mbi->mmap_addr |
movl $e820table, %edi |
xorl %edx, %edx |
mmap_loop: |
cmpl $0, %ecx |
jle mmap_end |
movl 4(%esi), %eax # mmap->base_addr_low |
movl %eax, (%edi) |
movl 8(%esi), %eax # mmap->base_addr_high |
movl %eax, 4(%edi) |
movl 12(%esi), %eax # mmap->length_low |
movl %eax, 8(%edi) |
movl 16(%esi), %eax # mmap->length_high |
movl %eax, 12(%edi) |
movl 20(%esi), %eax # mmap->type |
movl %eax, 16(%edi) |
movl (%esi), %eax # mmap->size |
addl $0x4, %eax |
addl %eax, %esi |
subl %eax, %ecx |
addl $MEMMAP_E820_RECORD_SIZE, %edi |
incl %edx |
jmp mmap_loop |
mmap_end: |
mmap_invalid: |
movl %edx, e820counter |
movl grub_eax, %eax |
movl grub_ebx, %ebx |
# ia32_boot(grub_eax, grub_ebx) |
pushl %ebx |
pushl %eax |
call ia32_cboot # Does not return. |
# Not reached. |
invalid_boot: |
#ifdef CONFIG_SMP |
# copy AP bootstrap routines below 1 MB |
movl $BOOT_OFFSET, %esi |
movl $AP_BOOT_OFFSET, %edi |
movl $_hardcoded_unmapped_size, %ecx |
rep movsb |
#endif |
call main_bsp # never returns |
cli |
hlt |
/trunk/kernel/arch/ia32/src/boot/cboot.c |
---|
0,0 → 1,107 |
/* |
* Copyright (c) 2009 Jiri Svoboda |
* All rights reserved. |
* |
* Redistribution and use in source and binary forms, with or without |
* modification, are permitted provided that the following conditions |
* are met: |
* |
* - Redistributions of source code must retain the above copyright |
* notice, this list of conditions and the following disclaimer. |
* - Redistributions in binary form must reproduce the above copyright |
* notice, this list of conditions and the following disclaimer in the |
* documentation and/or other materials provided with the distribution. |
* - The name of the author may not be used to endorse or promote products |
* derived from this software without specific prior written permission. |
* |
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR |
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES |
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. |
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, |
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT |
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
*/ |
/** @addtogroup ia32 |
* @{ |
*/ |
/** @file |
*/ |
#include <main/main.h> |
#include <arch/boot/boot.h> |
#include <arch/boot/cboot.h> |
#include <arch/boot/memmap.h> |
#include <config.h> |
#include <memstr.h> |
/* This is a symbol so the type is only dummy. Obtain the value using &. */ |
extern int _hardcoded_unmapped_size; |
/** C part of ia32 boot sequence. |
* @param signature Should contain the multiboot signature. |
* @param mi Pointer to the multiboot information structure. |
*/ |
void ia32_cboot(uint32_t signature, const mb_info_t *mi) |
{ |
uint32_t flags; |
mb_mod_t *mods; |
uint32_t i; |
flags = mi->flags; |
/* Copy module information. */ |
if ((flags & MBINFO_FLAGS_MODS) != 0) { |
init.cnt = mi->mods_count; |
mods = mi->mods_addr; |
for (i = 0; i < init.cnt; i++) { |
init.tasks[i].addr = mods[i].start + 0x80000000; |
init.tasks[i].size = mods[i].end - mods[i].start; |
} |
} else { |
init.cnt = 0; |
} |
/* Copy memory map. */ |
int32_t mmap_length; |
mb_mmap_t *mme; |
uint32_t size; |
if ((flags & MBINFO_FLAGS_MMAP) != 0) { |
mmap_length = mi->mmap_length; |
mme = mi->mmap_addr; |
e820counter = 0; |
i = 0; |
while (mmap_length > 0) { |
e820table[i++] = mme->mm_info; |
/* Compute address of next structure. */ |
size = sizeof(mme->size) + mme->size; |
mme = ((void *) mme) + size; |
mmap_length -= size; |
} |
e820counter = i; |
} else { |
e820counter = 0; |
} |
#ifdef CONFIG_SMP |
/* Copy AP bootstrap routines below 1 MB. */ |
memcpy((void *) AP_BOOT_OFFSET, (void *) BOOT_OFFSET, |
(size_t) &_hardcoded_unmapped_size); |
#endif |
main_bsp(); |
} |
/** @} |
*/ |