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
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
|
/*
* BCM947XX Boot code for standalone apps.
*
* Code should be position-independent until it copies itself to SDRAM.
*
* Copyright 2007, Broadcom Corporation
* All Rights Reserved.
*
* THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
* KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
* SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
*
* $Id: boot.S,v 1.1.1.1 2008/07/21 09:20:53 james26_jang Exp $
*/
#include "mipsinc.h"
#include "sbconfig.h"
#include "sbchipc.h"
#include "bcmdevs.h"
.text
LEAF(startup)
.set noreorder
li a2,KSEG1ADDR(SB_ENUM_BASE)
# XXX: the following code snipet sets clk frequency to 200M
# correct pll clk freq to real speed in the 5350 case.
# unless its vsim which we detect as pkg option 1 (should be 0xe)
# It is Ugly...but
li a3,BCM5350_CHIP_ID # 5350 ChipID
lw t1,CC_CHIPID(a2) # ChipID register
li t2,CID_ID_MASK # chip id is bit 0-15
and t2,t1,t2
bne t2,a3,2f # if not 5350 then skip
nop
li t2,CID_PKG_MASK # if it is a vsim 5350, also skip
and t2,t1,t2
li a3,(HDLSIM5350_PKG_ID << CID_PKG_SHIFT)
beq t2,a3,ramcheck # if pkg opt 1 then skip
nop
li a3,CLKC_5350_N
lw t3,CC_CLKC_N(a2)
beq a3,t3,ramcheck # move ahead if clk freq set correctly
nop
sw a3,CC_CLKC_N(a2) # set control N1 to select 6
li t3,1
sw t3,CC_WATCHDOG(a2) # set WatchDog Reset
1: b 1b
nop
2: li a3,BCM5354_CHIP_ID # 5354 ChipID
bne t2,a3,ramcheck # if not 5354 then skip
nop
li t2,CID_REV_MASK # Get chip rev
and t2,t1,t2
li t3,(3 << CID_REV_SHIFT) # Is it an a3?
blt t2,t3,a0a1a2
nop
/* Fix up for a3 (and up?) */
li a0,0x01330000 # Value for regcontrol 2
li t2,2
sw t2,PMU_REG_CONTROL_ADDR(a2)
sw a0,PMU_REG_CONTROL_DATA(a2)
a0a1a2:
li a0,0x00002000 # Value for regcontrol 0
li a1,0x06800000 # Value for regcontrol 1
li a3,0x02000000 # Value for regcontrol 3
fixregctl:
li t2,0x1 # Need define
sw t2,PMU_REG_CONTROL_ADDR(a2)
sw a1,PMU_REG_CONTROL_DATA(a2)
/*
* Trim the output voltage of the 1.2V BB switcher and 2.5V
* regulator to the correct value.
*/
li t2,0x0
sw t2,PMU_REG_CONTROL_ADDR(a2)
sw a0,PMU_REG_CONTROL_DATA(a2) # BB switcher to get 1.2V
li t2,0x3
sw t2,PMU_REG_CONTROL_ADDR(a2)
sw a3,PMU_REG_CONTROL_DATA(a2) # of VDDP LDO to get 2.5V
lw t2,PMU_CTL(a2) # Check if PLL has been programmed
andi t2,t2,PCTL_XTALFREQ_MASK
bnez t2,3f # Yup, leave it alone
nop
li t2,0x7ffff # Should only turn off the PLL bit
sw t2,PMU_MIN_RES_MASK(a2) # Disable base band PLL
sw t2,PMU_MAX_RES_MASK(a2)
li t2,0x1
sw t2,PMU_PLL_CONTROL_ADDR(a2)
li t2,0x66666602 # Set the PLL Mode properly
sw t2,PMU_PLL_CONTROL_DATA(a2)
li t2,0xfffff # Enable base band PLL
sw t2,PMU_MIN_RES_MASK(a2)
sw t2,PMU_MAX_RES_MASK(a2)
nop
/* Init code for ff4 space without TLB, enabling RAC */
3: li t0,0x1fa0000c # Set up CBR to 0x1fax_xxxx
.set mips32
mtc0 t0,$22,6
li t1,0x1fa00000
lw t2,0x14(t1)
or t3,t2,0xc0000000 # enable ffxx_xxxx space # without programming TLB
sw t3,0x14(t1)
li t0,0xff40000c # change CBR to ff4x_xxxx
mtc0 t0,$22,6
.set mips0
ramcheck:
/* Check if we booted from SDRAM */
bal 1f
nop
1: li t0,PHYSADDR_MASK
and t0,t0,ra
li t1,SB_FLASH1
bge t0,t1,inflash
nop
/* Call draminit to size memory */
jal board_draminit
nop
b setsp
nop
inflash:
/* Is this chipc rev 11 or 12 and a serial flash? */
li t0,KSEG1ADDR(SB_ENUM_BASE)
lw t1,(SBCONFIGOFF + SBIDHIGH)(t0)
and t2,t1,SBIDH_CC_MASK
srl t2,t2,SBIDH_CC_SHIFT
bne t2,SB_CC,checkcon /* Not chipc */
nop
and t2,t1,SBIDH_RC_MASK
and t3,t1,SBIDH_RCE_MASK
srl t3,t3,SBIDH_RCE_SHIFT
or t2,t3
ble t2,10,checkcon /* ccrev <= 10 */
nop
bge t2,13,checkcon /* ccrev >= 13 */
nop
lw t0,CC_CAPABILITIES(t0)
and t0,t0,CC_CAP_FLASH_MASK
beq t0,SFLASH_AT,switchkseg0 /* Atmel sflash */
nop
beq t0,SFLASH_ST,switchkseg0 /* ST sflash */
nop
checkcon:
/* Check if the caches are already on */
mfc0 t0,C0_CONFIG
and t0,CONF_CM_CMASK
beq t0,CONF_CM_UNCACHED,initcaches
nop
b switchkseg0
nop
initcaches:
/* Turn on the caches in the CP0 register */
mfc0 t0,C0_DIAGNOSTIC
or t0,(BRCM_IC_ENABLE | BRCM_DC_ENABLE) /* Enable both I$ and D$ */
mtc0 t0,C0_DIAGNOSTIC
1: /* Get cache sizes */
.set mips32
mfc0 s0,C0_CONFIG,1
.set mips0
li s1,CONF1_DL_MASK
and s1,s0
beq s1,zero,nodc
nop
srl s1,CONF1_DL_SHIFT
li t0,CONF1_DL_BASE
sll s1,t0,s1 /* s1 has D$ cache line size */
li s2,CONF1_DA_MASK
and s2,s0
srl s2,CONF1_DA_SHIFT
addiu s2,CONF1_DA_BASE /* s2 now has D$ associativity */
li t0,CONF1_DS_MASK
and t0,s0
srl t0,CONF1_DS_SHIFT
li s3,CONF1_DS_BASE
sll s3,s3,t0 /* s3 has D$ sets per way */
multu s2,s3 /* sets/way * associativity */
mflo t0 /* total cache lines */
multu s1,t0 /* D$ linesize * lines */
mflo s2 /* s2 is now D$ size in bytes */
/* Initilize the D$: */
mtc0 zero,C0_TAGLO
mtc0 zero,C0_TAGHI
li t0,KSEG0 /* Just an address for the first $ line */
addu t1,t0,s2 /* + size of cache == end */
.set mips3
1: cache Index_Store_Tag_D,0(t0)
.set mips0
bne t0,t1,1b
addu t0,s1
nodc:
/* Now we get to do it all again for the I$ */
li t0,CONF1_IL_MASK
and t0,s0
beq t0,zero,noic
nop
srl t0,CONF1_IL_SHIFT
li s3,CONF1_IL_BASE
sll s3,t0 /* s3 has I$ cache line size */
li t0,CONF1_IA_MASK
and t0,s0
srl t0,CONF1_IA_SHIFT
addiu s4,t0,CONF1_IA_BASE /* s4 now has I$ associativity */
li t0,CONF1_IS_MASK
and t0,s0
srl t0,CONF1_IS_SHIFT
li s5,CONF1_IS_BASE
sll s5,t0 /* s5 has I$ sets per way */
multu s4,s5 /* sets/way * associativity */
mflo t0 /* s4 is not total cache lines */
multu s3,t0 /* I$ linesize * lines */
mflo s4 /* s4 is cache size in bytes */
/* Initilize the I$: */
mtc0 zero,C0_TAGLO
mtc0 zero,C0_TAGHI
li t0,KSEG0 /* Just an address for the first $ line */
addu t1,t0,s4 /* + size of cache == end */
.set mips3
1: cache Index_Store_Tag_I,0(t0)
.set mips0
bne t0,t1,1b
addu t0,s1
noic:
/* Caches initialized, change cacheability */
mfc0 t0,C0_CONFIG
and t0,~CONF_CM_CMASK
or t0,CONF_CM_CACHABLE_NONCOHERENT
mtc0 t0,C0_CONFIG
nop
switchkseg0:
/* And now jump to KSEG0 */
li t0,KSEG1ADDR(SB_FLASH1)
la t1,text_start
la t2,initdram
sub t0,t0,t1
add t2,t2,t0
and t2,PHYSADDR_MASK
or t2,KSEG0
jr t2
nop
/* Black hole for traps with BEV on */
.org 0x380
bevtrap: nop
nop
.set mips32
wait
.set mips0
nop
nop
b bevtrap
nop
/* Record the size of the binary */
.org BISZ_OFFSET
.word BISZ_MAGIC
.word text_start
.word text_end
.word data_start
.word data_end
.word bss_start
.word bss_end
.word _end
/* Embedded NVRAM */
.balign 0x400
.globl embedded_nvram
embedded_nvram:
.fill 0x100,4,~(0x48534c46)
initdram:
/* Initialize SDRAM */
li t0,KSEG0ADDR(SB_FLASH1)
la t1,text_start
la t2,board_draminit
sub t0,t0,t1
add t2,t2,t0
jalr t2
nop
/* v0 now contains memory size in bytes */
/* Copy self to SDRAM */
#ifdef CONFIG_XIP
la a0,text_end
la a1,data_start
la a2,input_data
#else
li a0,KSEG0ADDR(SB_FLASH1)
la a1,text_start
and a1,PHYSADDR_MASK /* Uncached writes to avoid a flush */
or a1,KSEG1
la a2,_end
and a2,PHYSADDR_MASK
or a2,KSEG1
#endif
1: lw t0,0(a0)
sw t0,0(a1)
add a0,4
add a1,4
blt a1,a2,1b
nop
setsp:
/* Record the memory size */
la t0,_memsize
sw v0,0(t0)
/* Set up stack pointer */
or v0,KSEG0
sub sp,v0,4
/* Clear BSS */
la a0,bss_start
la a1,bss_end
1: sw zero,0(a0)
addi a0,a0,4
blt a0,a1,1b
nop
/* Setup trap handlers */
#ifdef CONFIG_XIP
li t0,KSEG0ADDR(SB_FLASH1)
la t1,text_start
la t2,trap_init
sub t0,t0,t1
add t2,t2,t0
jalr t2
nop
#else
la t0,trap_init
jalr t0
nop
#endif
/* Jump to C */
la t0,c_main
jal t0
move a0,ra
/* In case c_main returns */
theend: nop
nop
.set mips32
wait
.set mips0
nop
nop
b theend
nop
.set reorder
END(startup)
.data
.globl _memsize
_memsize:
.word 0
|