]> rtime.felk.cvut.cz Git - l4.git/blob - kernel/fiasco/src/kern/arm/main.cpp
update
[l4.git] / kernel / fiasco / src / kern / arm / main.cpp
1 INTERFACE [arm]:
2 #include <cstddef>
3
4 //---------------------------------------------------------------------------
5 IMPLEMENTATION [arm]:
6
7 #include <cstdlib>
8 #include <cstdio>
9 #include <cstring>
10
11 #include "config.h"
12 #include "globals.h"
13 #include "initcalls.h"
14 #include "kmem_alloc.h"
15 #include "kip_init.h"
16 #include "pagetable.h"
17 #include "kdb_ke.h"
18 #include "kernel_thread.h"
19 #include "kernel_task.h"
20 #include "kernel_console.h"
21 #include "reset.h"
22 #include "space.h"
23 #include "terminate.h"
24
25 #include "processor.h"
26
27 static int exit_question_active = 0;
28
29 extern "C" void __attribute__ ((noreturn))
30 _exit(int)
31 {
32   if (exit_question_active)
33     platform_reset();
34
35   while (1)
36     {
37       Proc::halt();
38       Proc::pause();
39     }
40 }
41
42
43 static void exit_question()
44 {
45   exit_question_active = 1;
46
47   while (1)
48     {
49       puts("\nReturn reboots, \"k\" enters L4 kernel debugger...");
50
51       char c = Kconsole::console()->getchar();
52
53       if (c == 'k' || c == 'K')
54         {
55           kdb_ke("_exit");
56         }
57       else
58         {
59           // it may be better to not call all the destruction stuff
60           // because of unresolved static destructor dependency
61           // problems.
62           // SO just do the reset at this point.
63           puts("\033[1mRebooting...\033[0m");
64           platform_reset();
65           break;
66         }
67     }
68 }
69
70 void
71 kernel_main()
72 {
73   // caution: no stack variables in this function because we're going
74   // to change the stack pointer!
75
76   // make some basic initializations, then create and run the kernel
77   // thread
78   set_exit_question(&exit_question);
79
80   printf("%s\n", Kip::k()->version_string());
81
82   // disallow all interrupts before we selectively enable them
83   //  pic_disable_all();
84
85   // create kernel thread
86   static Kernel_thread *kernel = new (Ram_quota::root) Kernel_thread;
87   nil_thread = kernel;
88   Task *const ktask = Kernel_task::kernel_task();
89   check(kernel->bind(ktask, User<Utcb>::Ptr(0)));
90
91   Mem_unit::tlb_flush();
92
93   // switch to stack of kernel thread and bootstrap the kernel
94   asm volatile
95     ("  str sp,%0               \n"     // save stack pointer in safe register
96      "  mov sp,%1               \n"     // switch stack
97      "  mov r0,%2               \n"     // push "this" pointer
98      "  bl call_bootstrap     \n"
99      :  "=m" (boot_stack)
100      :  "r" (kernel->init_stack()), "r" (kernel));
101 }
102
103 //------------------------------------------------------------------------
104 IMPLEMENTATION[arm && mp]:
105
106 #include <cstdio>
107 #include "config.h"
108 #include "cpu.h"
109 #include "globals.h"
110 #include "app_cpu_thread.h"
111 #include "per_cpu_data_alloc.h"
112 #include "perf_cnt.h"
113 #include "pic.h"
114 #include "spin_lock.h"
115 #include "utcb_init.h"
116
117
118 int boot_ap_cpu(unsigned cpu) __asm__("BOOT_AP_CPU");
119
120 int boot_ap_cpu(unsigned _cpu)
121 {
122   if (!Per_cpu_data_alloc::alloc(_cpu))
123     {
124       extern Spin_lock<Mword> _tramp_mp_spinlock;
125       printf("CPU allocation failed for CPU%u, disabling CPU.\n", _cpu);
126       _tramp_mp_spinlock.clear();
127       while (1)
128         Proc::halt();
129     }
130   Per_cpu_data::run_ctors(_cpu);
131   Cpu &cpu = Cpu::cpus.cpu(_cpu);
132   cpu.init();
133
134   Utcb_init::init_ap(cpu);
135   Pic::init_ap();
136   Ipi::cpu(_cpu).init();
137   Timer::init();
138   Perf_cnt::init_ap();
139
140   // create kernel thread
141   App_cpu_thread *kernel = new (Ram_quota::root) App_cpu_thread();
142   set_cpu_of(kernel, _cpu);
143   check(kernel->bind(Kernel_task::kernel_task(), User<Utcb>::Ptr(0)));
144
145   // switch to stack of kernel thread and bootstrap the kernel
146   asm volatile
147     ("  mov sp,%0               \n"     // switch stack
148      "  mov r0,%1               \n"     // push "this" pointer
149      "  bl call_ap_bootstrap    \n"
150      :
151      :  "r" (kernel->init_stack()), "r" (kernel));
152   return 0;
153 }
154