summaryrefslogtreecommitdiffstats
path: root/local_src/geckoboot-2013.01.0/geckoboot.S
blob: cb2c66f9155bf53c352856284f66dc1b9869fa82 (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
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
#define UARTBASE	0x4000e400
#define UARTLOCATION	2
#define DTB_SRC		0x80000
#define DTB_DST		0x10000000
#define LINUX_ENTRY	0x8c000000

#define BC_REGISTER	0x80000000

	.syntax unified
	.thumb
	.int 0x10001000			@ Initial SP value
	.int reset + 1

reset:
	/* init external RAM, serial port, EBI and stuff */
	adr	r0, reginit
1:
	ldr	r1, [r0]
	ldr	r2, [r0, #4]
	str	r2, [r1]
	add	r0, r0, #8
	cmp	r0, #(reginit_end)
	blo	1b

	/* init some BC registers */
	adr	r0, bcinit
1:
	ldrh	r1, [r0]
	ldrh	r2, [r0, #2]
	add	r1, r1, #BC_REGISTER
	strh	r2, [r1]
	add	r0, r0, 4
	cmp	r0, #(bcinit_end)
	blo	1b

	/* give mux some time to enable the level shifter */
	ldr	r0, =0x4000
1:	subs	r0, r0, #1
	bne	1b

	/* First sign of life */
	ldr	r0, =(UARTBASE + 0x34)
	mov	r1, #'G'
	str	r1, [r0]

	/* only boot into Linux when PB2 is pressed */
	ldr	r0, =(BC_REGISTER)
1:	ldr	r1, [r0, #8]		@ BC_REGISTER->UIF_PB
	tst	r1, #2
	bne	1b

boot_linux:
	/* Copy oftree to RAM */
	ldr	r0, =(DTB_DST)
	ldr	r1, =(DTB_SRC)
	ldr	r2, [r1, #4]
	rev	r2, r2

	bl	memcpy

	/* boot Linux */
	mov	r0, #0
	ldr	r1, =#0xf11
	ldr	r2, =(DTB_DST)
	mov	r3, #0
	mov	r4, #0
	mov	r5, #0
	mov	r6, #0

	ldr	r7, =(LINUX_ENTRY + 1)
	bx	r7

memcpy:
	@ copies r2 bytes from r1 to r0 with r2 > 0
	ldrb	r3, [r1], #1
	strb	r3, [r0], #1
	subs	r2, r2, #1
	bhi	memcpy
	bx	lr

	.ltorg

	.align 3
	.type reginit, %object
reginit:
	.int	0x400c8020, 0x00000004		@ CMU_OSCENCMD = HFXOEN

	.int	0x400c8008, 0x00000100		@ CMU_HFPERCLKDIV, reset default
	.int	0x43900814, 0x00000001		@ CMU_HFCORECLKEN0 |= EBI via bitband
	.int	0x439008b4, 0x00000001		@ CMU_HFPERCLKEN0 |= GPIO via bitband
	.int	0x43900890, 0x00000001		@ CMU_HFPERCLKEN0 |= UART1 via bitband

	/* XXX: these should be enabled in Linux */
	.int	0x43900884, 0x00000001		@ CMU_HFPERCLKEN0 |= USART1 via bitband
	.int	0x439008c0, 0x00000001		@ CMU_HFPERCLKEN0 |= ADC via bitband

	/* pinmuxing */
	.int	0x40006000, 0x00000000		@ GPIO_PA_CTRL, reset default
	.int	0x40006014, 0x0000807f		@ GPIO_PA_DOUTCLR; EBI AD8..15 set dataout to 0
	.int	0x40006004, 0x04444444		@ GPIO_PA_MODEL; EBI AD9..15 set mode=pushpull
	.int	0x40006008, 0x40000000		@ GPIO_PA_MODEH; EBI AD8 set mode=pushpull

	.int	0x40006024, 0x00000000		@ GPIO_PB_CTRL, reset default
/* XXX join following two */
	.int	0x40006038, 0x00008000		@ GPIO_PB_DOUTCLR; EBI mode on PB15 MCU_EBI_CONNECT (0)
	.int	0x40006038, 0x0000007f		@ GPIO_PB_DOUTCLR; EBI A16-22
	.int	0x40006028, 0x04444444		@ GPIO_PB_MODEL; EBI A16-22
	.int	0x40006034, 0x00000200		@ GPIO_PB_DOUTSET; set UART_TX to avoid false start
	.int	0x4000602c, 0x40000140		@ GPIO_PB_MODEH; MCU_EBI_CONNECT -> output, UART_TX, UART_RX

	.int	0x40006048, 0x00000000		@ GPIO_PC_CTRL, reset default
	.int	0x4000605c, 0x00000001		@ GPIO_PC_DOUTCLR; PC11 (EBI_ALE)
	.int	0x40006050, 0x00004000		@ GPIO_PC_MODEH; PC11: Push-pull output

	.int	0x4000606c, 0x00000000		@ GPIO_PD_CTRL, reset default
	.int	0x4000607c, 0x00003e08		@ GPIO_PD_DOUTSET, EBI CS0-3, spiconnect set dataout to 1; ETH_SPI_#CS (D3)
	.int	0x40006080, 0x00000007		@ GPIO_PD_DOUTCLR, ETH_SPI_{TX, RX, CLK}
	.int	0x40006070, 0x00004414		@ GPIO_PD_MODEL; ETH_SPI_
	.int	0x40006074, 0x00444440		@ GPIO_PD_MODEH; EBI CS0-3, spiconnect set mode=pushpull

	.int	0x40006090, 0x00000000		@ GPIO_PE_CTRL, reset default
	.int	0x400060a4, 0x0000ff00		@ GPIO_PE_DOUTCLR; EBI AD0..7 set dataout to 0
	.int	0x40006098, 0x44444444		@ GPIO_PE_MODEH; EBI AD0..7 set mode=pushpull

	.int	0x400060b4, 0x00000000		@ GPIO_PF_CTRL, reset default
	.int	0x400060c8, 0x000003c0		@ GPIO_PF_DOUTCLR; EBI Wen+Ren set dataout to 0
	.int	0x400060b8, 0x44000000		@ GPIO_PF_MODEL; EBI Byte Lane 0 support BL0/BL1
	.int	0x400060bc, 0x00000044		@ GPIO_PF_MODEH; EBI WEN, REN

	.int	0x40006100, 0x00000004		@ GPIO_EXTIPSELL: select port E for irq 0
	.int	0x4000610c, 0x00000001		@ GPIO_EXTIFALL: trigger for falling FPGA irq line
	.int	0x4000611c, 0x0000ffff		@ GPIO_IFC: clear all irqs
	.int	0x40006110, 0x00000001		@ GPIO_IEN: enable irq 0

	/* EBI */
	.int	0x40008000, 0x4f00d051		@ EBI_CTRL, enable ITS, mode0=mode2=mode3=D16A16ALE, bl0-3, noidle[023]
	/* EBI PSRAM */
	.int	0x40008028, 0x10000000		@ EBI_ADDRTIMING2; HALFALE
	.int	0x4000802c, 0x20000400		@ EBI_RDTIMING2; Prefetch, StrobeCycles = 4, HoldCycles = SetupCycles = 0
	.int	0x40008030, 0x00000200		@ EBI_WRTIMING2; StrobeCycles = 2, HoldCycles = SetupCycles = 0
	.int	0x40008034, 0x00000008		@ EBI_POLARITY2, ARDY_, ALE, WE_, RE_, CS_, BL_

	/* Board Control FPGA */
	.int	0x40008004, 0x10000303		@ EBI_ADDRTIMING; HALFALE, HoldCycles = SetupCycles = 3
	.int	0x40008008, 0x00030703		@ EBI_RDTIMING; StrobeCycles = 7, HoldCycles = SetupCycles = 3
	.int	0x4000800c, 0x00030703		@ EBI_WRTIMING; StrobeCycles = 7, HoldCycles = SetupCycles = 3
	.int	0x40008010, 0x00000008		@ EBI_POLARITY, ARDY_, ALE, WE_, RE_, CS_, BL_

	/* external NOR flash */
	.int	0x40008038, 0x10000000		@ EBI_ADDRTIMING3; HALFALE, HoldCycles = SetupCycles = 0
#define PRE
#ifdef PRE
	.int	0x4000803c, 0x00000700		@ EBI_RDTIMING3; StrobeCycles = 7, HoldCycles = SetupCycles = 0
	.int	0x40008040, 0x00000200		@ EBI_WRTIMING3; StrobeCycles = 2, HoldCycles = SetupCycles =0
#else
	/* reference: kits/common/bsp/bsp_dk_3201.c: 5 strobe cycles, hold=setup=0 */
	.int	0x4000803c, 0x00000700		@ EBI_RDTIMING3; StrobeCycles = 7, HoldCycles = SetupCycles = 0
	.int	0x40008040, 0x00000700		@ EBI_WRTIMING3; StrobeCycles = 7, HoldCycles = SetupCycles =0
#endif
	.int	0x40008044, 0x00000008		@ EBI_POLARITY3, ARDY_, ALE, WE_, RE_, CS_, BL_

	.int	0x40008014, 0x105e00bb		@ EBI_ROUTE
	.int	0x40008000, 0x4f00dd51		@ EBI_CTRL, enable ITS, mode0=mode2=mode3=D16A16ALE, bl0-3, noidle[023], bank[023]en

	.int	UARTBASE + 0x00, 0x00000000		@ UART1_CTRL
	.int	UARTBASE + 0x04, 0x00001005		@ UART1_FRAME
	.int	UARTBASE + 0x14, 0x00001900		@ UART1_CLKDIV
	.int	UARTBASE + 0x0c, 0x00000c04		@ UART1_CMD
	.int	UARTBASE + 0x54, 0x00000003 + (UARTLOCATION << 8)		@ UART1_ROUTE
	.int	0x400c8024, 0x00000002		@ CMU_CMD = HFCLKSEL_HFXO

reginit_end:
	.size reginit, . - reginit

	.align	3
	.type	bcinit, %object
bcinit:
	.short	0x0018, 0x1300			@ enable UART mux and ETH
	.short	0x0014, 0x0001			@ /
	.short	0x001a, 0x0001			@ ETH

bcinit_end:
	.size	bcinit, . - bcinit