1 /*
2 * Copyright 2003-2010, Axel Dörfler, axeld@pinc-software.de.
3 * Copyright 2008, François Revol, revol@free.fr. All rights reserved.
4 * Distributed under the terms of the MIT License.
5 */
6
7
8 #include <KernelExport.h>
9 #include <boot/platform.h>
10 #include <boot/heap.h>
11 #include <boot/stage2.h>
12 #include <arch/cpu.h>
13
14 #include <string.h>
15
16 #include "console.h"
17 #include "cpu.h"
18 #include "mmu.h"
19 #include "keyboard.h"
20 #include "rom_calls.h"
21
22
23 // GCC defined globals
24 extern void (*__ctor_list)(void);
25 extern void (*__ctor_end)(void);
26 extern uint8 __bss_start;
27 extern uint8 _end;
28
29 extern "C" int main(stage2_args *args);
30 extern "C" void _start(void);
31
32
33 static uint32 sBootOptions;
34
35
36 static void
clear_bss(void)37 clear_bss(void)
38 {
39 memset(&__bss_start, 0, &_end - &__bss_start);
40 }
41
42
43 static void
call_ctors(void)44 call_ctors(void)
45 {
46 void (**f)(void);
47
48 for (f = &__ctor_list; f < &__ctor_end; f++) {
49 (**f)();
50 }
51 }
52
53
54 extern "C" uint32
platform_boot_options(void)55 platform_boot_options(void)
56 {
57 #if 0
58 if (!gKernelArgs.fb.enabled)
59 sBootOptions |= check_for_boot_keys();
60 #endif
61 return sBootOptions;
62 }
63
64
65 extern "C" void
platform_start_kernel(void)66 platform_start_kernel(void)
67 {
68 static struct kernel_args *args = &gKernelArgs;
69 // something goes wrong when we pass &gKernelArgs directly
70 // to the assembler inline below - might be a bug in GCC
71 // or I don't see something important...
72 addr_t stackTop
73 = gKernelArgs.cpu_kstack[0].start + gKernelArgs.cpu_kstack[0].size;
74
75 preloaded_elf32_image *image = static_cast<preloaded_elf32_image *>(
76 gKernelArgs.kernel_image.Pointer());
77
78 //smp_init_other_cpus();
79 //serial_cleanup();
80 mmu_init_for_kernel();
81 //smp_boot_other_cpus();
82
83 #warning M68K: stop ints
84
85 dprintf("kernel entry at %lx\n", image->elf_header.e_entry);
86
87 asm volatile (
88 "move.l %0,%%sp; " // move stack out of way
89 : : "m" (stackTop));
90
91 asm volatile (
92 "or #0x0700,%%sr; " : : ); // disable interrupts
93
94 asm volatile (
95 "move.l #0x0,-(%%sp); " // we're the BSP cpu (0)
96 "move.l %0,-(%%sp); " // kernel args
97 "move.l #0x0,-(%%sp);" // dummy retval for call to main
98 "move.l %1,-(%%sp); " // this is the start address
99 "rts; " // jump.
100 : : "g" (args), "g" (image->elf_header.e_entry));
101
102 // Huston, we have a problem!
103
104 asm volatile (
105 "and #0xf8ff,%%sr; " : : ); // reenable interrupts
106
107 panic("kernel returned!\n");
108
109 }
110
111
112 extern "C" void
platform_exit(void)113 platform_exit(void)
114 {
115 ColdReboot();
116 // Terminate
117 //TODO
118 while (true) {}
119 }
120
121 extern "C" void
_start(void)122 _start(void)
123 {
124 stage2_args args;
125
126 //asm("cld"); // Ain't nothing but a GCC thang.
127 //asm("fninit"); // initialize floating point unit
128
129 clear_bss();
130 call_ctors();
131 // call C++ constructors before doing anything else
132
133 args.heap_size = 0;
134 args.arguments = NULL;
135
136 //serial_init();
137 console_init();
138 dprintf("ramtop = %p\n", NULL);
139 cpu_init();
140 mmu_init();
141
142 // wait a bit to give the user the opportunity to press a key
143 spin(750000);
144
145 // reading the keyboard doesn't seem to work in graphics mode (maybe a bochs problem)
146 sBootOptions = check_for_boot_keys();
147 //if (sBootOptions & BOOT_OPTION_DEBUG_OUTPUT)
148 //serial_enable();
149
150 //apm_init();
151 //smp_init();
152 main(&args);
153 }
154