summaryrefslogtreecommitdiff
path: root/boot/bootloader.h
blob: e5c013d7f0e0c670188b4e5da403c983113f87e5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
#include "../src/bootinfo.h"

/* to be provider by the bootloader including this header */
_Noreturn void bootloader(struct systemid *boot);

__asm__(
".text \n"
".extern __bss_start \n"
".extern __bss_end \n"
".global __start \n"
".type __start, @function \n"
"__start: \n"

/* zero any bss section */
"	mov #0, r0 \n"
"	mov.l 1f, r1 \n"
"	mov.l 2f, r2 \n"
"0:	cmp/hi r1, r2 \n"
"	bf 0f \n"
"	bra 0b \n"
"	 mov.l r0, @-r2 \n"

/* cannibalize code before this for stack space, and pass control to C */
"0:	mov.l 3f, r15 \n"
"	mov.l 4f, r4 \n"
"	bra bootloader \n"
"	 nop \n"

".align 2 \n"
"1:	.long __bss_start \n"
"2:	.long __bss_end \n"
"3:	.long __start \n"
"4:	.long 0x06002000 \n"
);

/* helper to jump to the specified code with the specified stack */
static inline _Noreturn void jump(const void *code, long *stack)
{
	__asm__ __volatile__(
		"	jmp @%0\n"
		"	 mov %1, r15\n"
		: : "r"(code), "r"(stack)
	);
	__builtin_unreachable();
}

/* helper to abort by repeatedly executing an illegal instruction */
static inline _Noreturn void fail(void)
{
	__asm__ __volatile__(
		"0:	bra 0b\n"
		"	.word 0xfffd\n"
	);
	__builtin_unreachable();
}