xref: /haiku/src/system/boot/platform/riscv/start.cpp (revision cbe0a0c436162d78cc3f92a305b64918c839d079)
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 "fdt.h"
20 #include "Htif.h"
21 #include "virtio.h"
22 #include "graphics.h"
23 
24 
25 #define HEAP_SIZE (1024*1024)
26 
27 // GCC defined globals
28 extern void (*__ctor_list)(void);
29 extern void (*__ctor_end)(void);
30 extern uint8 __bss_start;
31 extern uint8 _end;
32 
33 extern "C" int main(stage2_args* args);
34 extern "C" void _start(int hartId, void* fdt);
35 extern "C" status_t arch_enter_kernel(struct kernel_args* kernelArgs,
36 	addr_t kernelEntry, addr_t kernelStackTop);;
37 
38 
39 static uint32 sBootOptions;
40 static bool sBootOptionsValid = false;
41 
42 
43 static void
44 clear_bss(void)
45 {
46 	memset(&__bss_start, 0, &_end - &__bss_start);
47 }
48 
49 
50 static void
51 call_ctors(void)
52 {
53 	void (**f)(void);
54 
55 	for (f = &__ctor_list; f < &__ctor_end; f++)
56 		(**f)();
57 }
58 
59 
60 static uint32
61 check_for_boot_keys()
62 {
63 	uint32 options = 0;
64 	bigtime_t t0 = system_time();
65 	while (system_time() - t0 < 100000) {
66 		int key = virtio_input_get_key();
67 		switch(key) {
68 			case 94 /* space */:
69 				options |= BOOT_OPTION_MENU;
70 				break;
71 		}
72 	}
73 	return options;
74 }
75 
76 
77 extern "C" uint32
78 platform_boot_options(void)
79 {
80 	if (!sBootOptionsValid) {
81 		sBootOptions = check_for_boot_keys();
82 		sBootOptionsValid = true;
83 /*
84 		if (sBootOptions & BOOT_OPTION_DEBUG_OUTPUT)
85 			serial_enable();
86 */
87 	}
88 
89 	return sBootOptions;
90 }
91 
92 
93 extern "C" void
94 platform_start_kernel(void)
95 {
96 	static struct kernel_args* args = &gKernelArgs;
97 	preloaded_elf64_image* image = static_cast<preloaded_elf64_image*>(
98 		gKernelArgs.kernel_image.Pointer());
99 
100 	//smp_init_other_cpus();
101 	//serial_cleanup();
102 	//mmu_init_for_kernel();
103 	//smp_boot_other_cpus();
104 
105 	// Avoid interrupts from virtio devices before kernel driver takes control.
106 	virtio_fini();
107 
108 	fdt_set_kernel_args();
109 	mmu_init_for_kernel();
110 
111 	dprintf("kernel entry at %lx\n", image->elf_header.e_entry);
112 
113 	addr_t stackTop
114 		= gKernelArgs.cpu_kstack[0].start + gKernelArgs.cpu_kstack[0].size;
115 	arch_enter_kernel(args, image->elf_header.e_entry, stackTop);
116 
117 	panic("kernel returned!\n");
118 
119 }
120 
121 
122 extern "C" void
123 platform_exit(void)
124 {
125 	HtifShutdown();
126 }
127 
128 
129 extern "C" void
130 _start(int hartId, void* fdt)
131 {
132 	HtifOutString("haiku_loader entry point\n");
133 
134 	clear_bss();
135 	fdt_init(fdt);
136 	call_ctors();
137 
138 	stage2_args args;
139 	args.heap_size = HEAP_SIZE;
140 	args.arguments = NULL;
141 
142 	// console_init();
143 	// virtio_init();
144 	cpu_init();
145 	mmu_init();
146 	//apm_init();
147 	//smp_init();
148 
149 	main(&args);
150 }
151