3 * \brief Device manager for Barrelfish.
5 * Interacts with the SKB / PCI to start cores, drivers etc.
7 * x86 specific startup code
12 * Copyright (c) 2007-2010, 2016 ETH Zurich.
13 * Copyright (c) 2015, Hewlett Packard Enterprise Development LP.
14 * All rights reserved.
16 * This file is distributed under the terms in the attached LICENSE file.
17 * If you do not find this file, copies can be found by writing to:
18 * ETH Zurich D-INFK, Universitaetstr. 6, CH-8092 Zurich. Attn: Systems Group.
21 #include <barrelfish/barrelfish.h>
26 #define SERIAL_BINARY "serial_pc16550d"
28 #define LPC_TIMER_IRQ 0
29 #define LPC_TIMER_BINARY "lpc_timer"
31 static errval_t start_serial(void){
33 struct module_info * mi = find_module(SERIAL_BINARY);
35 // Get internal int number. COM1 uses ISA nr. 4
36 struct driver_argument arg;
37 err = skb_execute_query("isa_irq_to_int(%d,N), writeln(N).", SERIAL_IRQ);
39 DEBUG_SKB_ERR(err, "skb_execute_query");
43 err = skb_read_output("%d", &int_nr);
45 DEBUG_ERR(err, "skb_read_output");
48 KALUGA_DEBUG("Found internal int number (%d) for serial.\n", int_nr);
49 arg.int_arg.int_range_start = int_nr;
50 arg.int_arg.int_range_end = int_nr;
51 arg.int_arg.model = INT_MODEL_LEGACY;
53 struct cnoderef argnode_ref;
54 err = cnode_create_l2(&arg.arg_caps, &argnode_ref);
56 DEBUG_ERR(err, "cnode_create_l2");
62 cap.cnode = argnode_ref;
64 err = sys_debug_create_irq_src_cap(cap, int_nr, int_nr);
67 DEBUG_ERR(err, "Could not create int_src cap");
70 err = mi->start_function(0, mi, "hw.legacy.uart.1 {}", &arg);
72 USER_PANIC_ERR(err, "serial->start_function");
75 printf("Kaluga: Not starting \"%s\", binary not found\n", SERIAL_BINARY);
76 return KALUGA_ERR_MODULE_NOT_FOUND;
81 static errval_t start_lpc_timer(void){
83 struct module_info * mi = find_module(LPC_TIMER_BINARY);
85 // Get internal int number.
86 struct driver_argument arg;
87 err = skb_execute_query("isa_irq_to_int(%d,N), writeln(N).", LPC_TIMER_IRQ);
89 DEBUG_SKB_ERR(err, "skb_execute");
93 err = skb_read_output("%d", &int_nr);
95 DEBUG_ERR(err, "skb_read_output");
98 KALUGA_DEBUG("Found internal int number (%d) for lpc_timer.\n", int_nr);
99 arg.int_arg.int_range_start = int_nr;
100 arg.int_arg.int_range_end = int_nr;
101 arg.int_arg.model = INT_MODEL_LEGACY;
103 struct cnoderef argnode_ref;
104 err = cnode_create_l2(&arg.arg_caps, &argnode_ref);
105 if(err_is_fail(err)){
106 DEBUG_ERR(err, "cnode_create_l2");
112 cap.cnode = argnode_ref;
114 err = sys_debug_create_irq_src_cap(cap, int_nr, int_nr);
116 if(err_is_fail(err)){
117 DEBUG_ERR(err, "Could not create int_src cap");
120 err = mi->start_function(0, mi, "hw.legacy.timer.1 {}", &arg);
121 if(err_is_fail(err)){
122 USER_PANIC_ERR(err, "serial->start_function");
125 printf("Kaluga: Not starting \"%s\", binary not found\n", LPC_TIMER_BINARY);
126 return KALUGA_ERR_MODULE_NOT_FOUND;
131 errval_t arch_startup(char * add_device_db_file)
133 errval_t err = SYS_ERR_OK;
134 // We need to run on core 0
135 // (we are responsible for booting all the other cores)
136 assert(my_core_id == BSP_CORE_ID);
137 KALUGA_DEBUG("Kaluga running on x86.\n");
139 err = skb_client_connect();
140 if (err_is_fail(err)) {
141 USER_PANIC_ERR(err, "Connect to SKB.");
144 // Make sure the driver db is loaded
145 err = skb_execute("[device_db].");
146 if (err_is_fail(err)) {
147 USER_PANIC_SKB_ERR(err, "Device DB not loaded.");
149 if(add_device_db_file != NULL){
150 err = skb_execute_query("[%s].", add_device_db_file);
151 if(err_is_fail(err)){
152 USER_PANIC_SKB_ERR(err,"Additional device db file %s not loaded.", add_device_db_file);
156 // The current boot protocol needs us to have
157 // knowledge about how many CPUs are available at boot
158 // time in order to start-up properly.
160 err = oct_barrier_enter("barrier.acpi", &record, 2);
162 KALUGA_DEBUG("Kaluga: watch_for_cores\n");
164 err = watch_for_cores();
165 if (err_is_fail(err)) {
166 USER_PANIC_ERR(err, "Watching cores.");
169 KALUGA_DEBUG("Kaluga: pci_root_bridge\n");
171 err = watch_for_pci_root_bridge();
172 if (err_is_fail(err)) {
173 USER_PANIC_ERR(err, "Watching PCI root bridges.");
176 KALUGA_DEBUG("Kaluga: pci_devices\n");
178 err = watch_for_pci_devices();
179 if (err_is_fail(err)) {
180 USER_PANIC_ERR(err, "Watching PCI devices.");
183 KALUGA_DEBUG("Kaluga: int_controller_devices\n");
185 err = watch_for_int_controller();
186 if (err_is_fail(err)) {
187 USER_PANIC_ERR(err, "Watching interrupt controllers.");
190 KALUGA_DEBUG("Kaluga: wait_for_all_spawnds\n");
192 err = wait_for_all_spawnds();
193 if (err_is_fail(err)) {
194 USER_PANIC_ERR(err, "Unable to wait for spawnds failed.");
197 KALUGA_DEBUG("Kaluga: Starting serial...\n");
198 err = start_serial();
199 if (err_is_fail(err) && err != KALUGA_ERR_MODULE_NOT_FOUND) {
200 USER_PANIC_ERR(err, "start_serial");
203 KALUGA_DEBUG("Kaluga: Starting lpc timer...\n");
204 err = start_lpc_timer();
205 if (err_is_fail(err) && err != KALUGA_ERR_MODULE_NOT_FOUND) {
206 USER_PANIC_ERR(err, "start_lpc_timer");