]> git.saurik.com Git - apple/xnu.git/blame - osfmk/ppc/start.s
xnu-201.tar.gz
[apple/xnu.git] / osfmk / ppc / start.s
CommitLineData
1c79356b
A
1/*
2 * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * The contents of this file constitute Original Code as defined in and
7 * are subject to the Apple Public Source License Version 1.1 (the
8 * "License"). You may not use this file except in compliance with the
9 * License. Please obtain a copy of the License at
10 * http://www.apple.com/publicsource and read it before using this file.
11 *
12 * This Original Code and all software distributed under the License are
13 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
14 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
15 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
17 * License for the specific language governing rights and limitations
18 * under the License.
19 *
20 * @APPLE_LICENSE_HEADER_END@
21 */
22/*
23 * @OSF_COPYRIGHT@
24 */
25#include <cpus.h>
26#include <mach_kdb.h>
27#include <mach_kdp.h>
28#include <mach_kgdb.h>
29#include <ppc/asm.h>
30#include <ppc/proc_reg.h>
31#include <mach/ppc/vm_param.h>
32#include <assym.s>
33
34#define ptFilter 0
35#define ptVersion 4
36#define ptRevision 6
37#define ptFeatures 8
38#define ptInitRout 12
39#define ptRptdProc 16
40#define ptTempMax 20
41#define ptTempThr 24
42#define ptLineSize 28
43#define ptl1iSize 32
44#define ptl1dSize 36
45#define ptSize 40
46
47#define bootCPU 10
48#define firstInit 9
49#define firstBoot 8
0b4e3aa0
A
50
51/* Defines for PVRs */
52#define PROCESSOR_VERSION_601 1
53#define PROCESSOR_VERSION_603 3
54#define PROCESSOR_VERSION_604 4
55#define PROCESSOR_VERSION_603e 6
56#define PROCESSOR_VERSION_750 8
57#define PROCESSOR_VERSION_604e 9
58#define PROCESSOR_VERSION_604ev 10 /* ? */
59#define PROCESSOR_VERSION_7400 12 /* ? */
60#define PROCESSOR_VERSION_7410 0x800C /* ? */
61#define PROCESSOR_VERSION_7450 0x8000 /* ? */
62
1c79356b
A
63/*
64 * Interrupt and bootup stack for initial processor
65 */
66
67 .file "start.s"
68
69 .data
70
71 /* Align on page boundry */
72 .align PPC_PGSHIFT
73 /* Red zone for interrupt stack, one page (will be unmapped)*/
74 .set ., .+PPC_PGBYTES
75 /* intstack itself */
76
77 .globl EXT(FixedStackStart)
78EXT(FixedStackStart):
79
80 .globl EXT(intstack)
81EXT(intstack):
82 .set ., .+INTSTACK_SIZE*NCPUS
83
84 /* Debugger stack - used by the debugger if present */
85 /* NOTE!!! Keep the debugger stack right after the interrupt stack */
86#if MACH_KDP || MACH_KDB
87 .globl EXT(debstack)
88EXT(debstack):
89 .set ., .+KERNEL_STACK_SIZE*NCPUS
90
91 .globl EXT(FixedStackEnd)
92EXT(FixedStackEnd):
93
94 .align ALIGN
95 .globl EXT(intstack_top_ss)
96EXT(intstack_top_ss):
0b4e3aa0 97 .long EXT(intstack)+INTSTACK_SIZE-FM_SIZE /* intstack_top_ss points to the top of interrupt stack */
1c79356b
A
98
99 .align ALIGN
100 .globl EXT(debstack_top_ss)
101EXT(debstack_top_ss):
102
0b4e3aa0 103 .long EXT(debstack)+KERNEL_STACK_SIZE-FM_SIZE /* debstack_top_ss points to the top of debug stack */
1c79356b
A
104
105 .globl EXT(debstackptr)
106EXT(debstackptr):
0b4e3aa0 107 .long EXT(debstack)+KERNEL_STACK_SIZE-FM_SIZE
1c79356b
A
108
109#endif /* MACH_KDP || MACH_KDB */
110
111/*
112 * All CPUs start here.
113 *
114 * This code is called from SecondaryLoader
115 *
116 * Various arguments are passed via a table:
117 * ARG0 = pointer to other startup parameters
118 */
119 .text
120
121ENTRY(_start_cpu,TAG_NO_FRAME_USED)
122 crclr bootCPU ; Set non-boot processor
123 crclr firstInit ; Set not first time init
124 mr r30,r3 ; Set current per_proc
125
126;
127; Note that we are just trying to get close. The real TB sync will take
128; place later. The value we are loading is set in two places. For the
129; main processor, it will be the TB at the last interrupt before we went
130; to sleep. For the others, it will be the time just before the main
131; processor woke us up.
132;
133
134 lwz r15,ruptStamp(r3) ; Get the timebase from the other processor
135 li r17,0 ; Clear this out
136 lwz r16,ruptStamp+4(r3) ; Get the timebase from the other processor
137 mtspr tbl,r17 ; Clear bottom so we do not tick
138 mtspr tbu,r15 ; Set top
139 mtspr tbl,r16 ; Then bottom again
140
141 b allstart
142
143ENTRY(_start,TAG_NO_FRAME_USED)
144
145 lis r30,hi16(EXT(per_proc_info)) ; Set current per_proc
146 ori r30,r30,lo16(EXT(per_proc_info)) ; Set current per_proc
147 crset bootCPU ; Set boot processor
148
149 lwz r17,pfAvailable(r30) ; Get the available bits
150 rlwinm. r0,r17,0,pfValidb,pfValidb ; Have we initialized the feature flags yet?
151 crmove firstInit,cr0_eq ; Set if we are doing first time init
152 bne allstart ; Yeah, we must be waking up from sleep...
153
154;
155; Here is where we do any one time general low-level initialization
156
157 lis r20,HIGH_ADDR(fwdisplock) ; Get address of the firmware display lock
158 li r19,0 ; Zorch a register
159 ori r20,r20,LOW_ADDR(fwdisplock) ; Get address of the firmware display lock
160 stw r19,0(r20) ; Make sure the lock is free
161
162allstart: mr r31,r3 ; Save away arguments
163 lis r23,hi16(EXT(per_proc_info)) ; Set base per_proc
164 ori r23,r23,lo16(EXT(per_proc_info)) ; Set base per_proc
165
166 mtsprg 0,r30 ; Set the per_proc
167
168 mfspr r6,hid0 ; Get the HID0
169 li r7,MSR_VM_OFF ; Get real mode MSR
170 rlwinm r6,r6,0,sleep+1,doze-1 ; Remove any vestiges of sleep
171 mtspr hid0,r6 ; Set the insominac HID0
172 mtmsr r7 ; Set the real mode SRR
173 isync
174
175; Map in the first 256Mb in both instruction and data BATs
176
177 li r7,((0x7FF<<2)|2) ; Set up for V=R 256MB in supervisor space
178 li r8,((2<<3)|2) ; Physical address = 0, coherent, R/W
179 li r9,0 ; Clear out a register
180
181 mtsprg 1,r9 ; Clear the extra SPRGs
182 mtsprg 2,r9
183 mtsprg 3,r9
184
185 sync
186 isync
187 mtdbatu 0,r7 ; Map bottom 256MB
188 mtdbatl 0,r8 ; Map bottom 256MB
189 mtdbatu 1,r9 ; Invalidate maps
190 mtdbatl 1,r9 ; Invalidate maps
191 mtdbatu 2,r9 ; Invalidate maps
192 mtdbatl 2,r9 ; Invalidate maps
193 mtdbatu 3,r9 ; Invalidate maps
194 mtdbatl 3,r9 ; Invalidate maps
195 sync
196 isync
197 mtibatu 0,r7 ; Map bottom 256MB
198 mtibatl 0,r8 ; Map bottom 256MB
199 mtibatu 1,r9 ; Invalidate maps
200 mtibatl 1,r9 ; Invalidate maps
201 mtibatu 2,r9 ; Invalidate maps
202 mtibatl 2,r9 ; Invalidate maps
203 mtibatu 3,r9 ; Invalidate maps
204 mtibatl 3,r9 ; Invalidate maps
205 sync
206 isync
207
208 lis r26,hi16(processor_types) ; Point to processor table
209 ori r26,r26,lo16(processor_types) ; Other half
210 mfpvr r10 ; Get the PVR
211
212nextPVR: lwz r28,ptFilter(r26) ; Get the filter
213 lwz r27,ptVersion(r26) ; Get the version and revision codes
214 and r28,r10,r28 ; Throw away dont care bits
215 cmplw r27,r28 ; Is this the right set?
216 beq donePVR ; We have the right one...
217 addi r26,r26,ptSize ; Point to the next type
218 b nextPVR ; Check it out...
219
220donePVR: lwz r20,ptInitRout(r26) ; Grab the special init routine
221 mtlr r20 ; Setup to call the init
222
223 bf firstInit,notFirst ; Not first boot, go...
224
225;
226; The following code just does a general initialization of the features just
227; after the initial first-time boot. This is not done after waking up or on
228; any "secondary" processor.
229;
230; We are just setting defaults. The specific initialization code will modify these
231; if necessary.
232;
233
234 lwz r17,ptFeatures(r26) ; Pick up the features
235
236 lwz r13,ptRptdProc(r26) ; Get the reported processor
237 sth r13,pfrptdProc(r30) ; Set the reported processor
238
239 lwz r13,ptTempMax(r26) ; Get maximum operating temperature
240 stw r13,thrmmaxTemp(r30) ; Set the maximum
241 lwz r13,ptTempThr(r26) ; Get temprature to throttle down when exceeded
242 stw r13,thrmthrottleTemp(r30) ; Set the temperature that we throttle
243
244 lwz r13,ptLineSize(r26) ; Get the cache line size
245 sth r13,pflineSize(r30) ; Save it
246 lwz r13,ptl1iSize(r26) ; Get icache size
247 stw r13,pfl1iSize(r30) ; Save it
248 lwz r13,ptl1dSize(r26) ; Get dcache size
249 stw r13,pfl1dSize(r30) ; Save it
250 b doOurInit ; Go do processor specific initialization...
251
252notFirst: lwz r17,pfAvailable(r30) ; Get our features
253 rlwinm. r0,r17,0,pfValidb,pfValidb ; Have we set up this CPU yet?
254 bne doOurInit ; Yeah, must be wakeup...
255
256 lis r23,hi16(EXT(per_proc_info)) ; Set base per_proc
257 ori r23,r23,lo16(EXT(per_proc_info)) ; Set base per_proc
258
259 la r7,pfAvailable(r30) ; Point to features of our processor
260 la r8,pfAvailable(r23) ; Point to features of boot processor
261 li r9,(pfSize+thrmSize)/4 ; Get size of a features area
262
263cpyFeat: subi r9,r9,1 ; Count word
264 lwz r0,0(r8) ; Get boot cpu features
265 stw r0,0(r7) ; Copy to ours
266 mr. r9,r9 ; Finished?
267 addi r7,r7,4 ; Next out
268 addi r8,r8,4 ; Next in
269 bgt cpyFeat ; Copy all boot cpu features to us...
270
271 lwz r17,pfAvailable(r30) ; Get our newly initialized features
272
273doOurInit:
274 mr. r20,r20 ; See if initialization routine
275 crand firstBoot,bootCPU,firstInit ; Indicate if we are on the initial first processor startup
276 bnelrl ; Do the initialization
277
278 ori r17,r17,lo16(pfValid) ; Set the valid bit
279 stw r17,pfAvailable(r30) ; Set the available features
280 mtsprg 2,r17 ; Remember the feature flags
281
282 rlwinm. r0,r17,0,pfFloatb,pfFloatb ; See if there is floating point
283 beq- noFloat ; Nope, this is a really stupid machine...
284
285 li r0,MSR_VM_OFF|MASK(MSR_FP) ; Enable for floating point
286 mtmsr r0 /* Set the standard MSR values */
287 isync
288
289 lis r5,HIGH_ADDR(EXT(FloatInit)) /* Get top of floating point init value */
290 ori r5,r5,LOW_ADDR(EXT(FloatInit)) /* Slam bottom */
291 lfd f0,0(r5) /* Initialize FP0 */
292 fmr f1,f0 /* Ours in not */
293 fmr f2,f0 /* to wonder why, */
294 fmr f3,f0 /* ours is but to */
295 fmr f4,f0 /* do or die! */
296 fmr f5,f0
297 fmr f6,f0
298 fmr f7,f0
299 fmr f8,f0
300 fmr f9,f0
301 fmr f10,f0
302 fmr f11,f0
303 fmr f12,f0
304 fmr f13,f0
305 fmr f14,f0
306 fmr f15,f0
307 fmr f16,f0
308 fmr f17,f0
309 fmr f18,f0
310 fmr f19,f0
311 fmr f20,f0
312 fmr f21,f0
313 fmr f22,f0
314 fmr f23,f0
315 fmr f24,f0
316 fmr f25,f0
317 fmr f26,f0
318 fmr f27,f0
319 fmr f28,f0
320 fmr f29,f0
321 fmr f30,f0
322 fmr f31,f0
323
324 li r0, MSR_VM_OFF ; Turn off floating point
325 mtmsr r0
326 isync
327
328noFloat: rlwinm. r0,r17,0,pfAltivecb,pfAltivecb ; See if there is Altivec
329 beq- noVector ; Nope...
330
331 li r0,0 ; Clear out a register
332
333 lis r7,hi16(MSR_VEC_ON) ; Get real mode MSR + Altivec
334 ori r7,r7,lo16(MSR_VM_OFF) ; Get real mode MSR + Altivec
335 mtmsr r7 ; Set the real mode SRR */
336 isync ; Make sure it has happened
337
338 lis r5,hi16(EXT(QNaNbarbarian)) ; Altivec initializer
339 ori r5,r5,lo16(EXT(QNaNbarbarian)) ; Altivec initializer
340
341 mtspr vrsave,r0 ; Set that no VRs are used yet */
342
343 vspltisw v1,0 ; Clear a register
344 lvx v0,br0,r5 ; Initialize VR0
345 mtvscr v1 ; Clear the vector status register
346 vor v2,v0,v0 ; Copy into the next register
347 vor v1,v0,v0 ; Copy into the next register
348 vor v3,v0,v0 ; Copy into the next register
349 vor v4,v0,v0 ; Copy into the next register
350 vor v5,v0,v0 ; Copy into the next register
351 vor v6,v0,v0 ; Copy into the next register
352 vor v7,v0,v0 ; Copy into the next register
353 vor v8,v0,v0 ; Copy into the next register
354 vor v9,v0,v0 ; Copy into the next register
355 vor v10,v0,v0 ; Copy into the next register
356 vor v11,v0,v0 ; Copy into the next register
357 vor v12,v0,v0 ; Copy into the next register
358 vor v13,v0,v0 ; Copy into the next register
359 vor v14,v0,v0 ; Copy into the next register
360 vor v15,v0,v0 ; Copy into the next register
361 vor v16,v0,v0 ; Copy into the next register
362 vor v17,v0,v0 ; Copy into the next register
363 vor v18,v0,v0 ; Copy into the next register
364 vor v19,v0,v0 ; Copy into the next register
365 vor v20,v0,v0 ; Copy into the next register
366 vor v21,v0,v0 ; Copy into the next register
367 vor v22,v0,v0 ; Copy into the next register
368 vor v23,v0,v0 ; Copy into the next register
369 vor v24,v0,v0 ; Copy into the next register
370 vor v25,v0,v0 ; Copy into the next register
371 vor v26,v0,v0 ; Copy into the next register
372 vor v27,v0,v0 ; Copy into the next register
373 vor v28,v0,v0 ; Copy into the next register
374 vor v29,v0,v0 ; Copy into the next register
375 vor v30,v0,v0 ; Copy into the next register
376 vor v31,v0,v0 ; Copy into the next register
377
378 li r0, MSR_VM_OFF ; Turn off vectors
379 mtmsr r0
380 isync
381
382noVector: rlwinm. r0,r17,0,pfSMPcapb,pfSMPcapb ; See if we can do SMP
383 beq- noSMP ; Nope...
384
385 lhz r13,PP_CPU_NUMBER(r30) ; Get the CPU number
386 mtspr pir,r13 ; Set the PIR
387
388noSMP: rlwinm. r0,r17,0,pfThermalb,pfThermalb ; See if there is an TAU
389 beq- noThermometer ; Nope...
390
391 li r13,0 ; Disable thermals for now
392 mtspr thrm3,r13 ; Do it
393 li r13,lo16(thrmtidm|thrmvm) ; Set for lower-than thermal event at 0 degrees
394 mtspr thrm1,r13 ; Do it
395 lis r13,hi16(thrmthrm) ; Set 127 degrees
396 ori r13,r13,lo16(thrmvm) ; Set for higher-than event
397 mtspr thrm2,r13 ; Set it
398
399noThermometer:
400
401 bl EXT(cacheInit) ; Initializes all caches (including the TLB)
402
403 li r0,MSR_SUPERVISOR_INT_OFF ; Make sure we do not have FP enabled
404 mtmsr r0 ; Set the standard MSR values
405 isync
406
407 bf bootCPU,callcpu ; Not the boot processor...
408
409 lis r29,HIGH_ADDR(EXT(intstack_top_ss)) ; move onto interrupt stack
410 ori r29,r29,LOW_ADDR(EXT(intstack_top_ss))
411 lwz r29,0(r29)
412
413 li r28,0
414 stw r28,FM_BACKPTR(r29) ; store a null frame backpointer
415
416 mr r1,r29
417 mr r3,r31 ; Restore any arguments we may have trashed
418
419 bl EXT(ppc_init) ; Jump into boot init code
420 BREAKPOINT_TRAP
421
422callcpu:
423 lwz r29,PP_INTSTACK_TOP_SS(r31) ; move onto interrupt stack
424
425 li r28,0
426 stw r28,FM_BACKPTR(r29) ; store a null frame backpointer
427
428
429 mr r1,r29 ; move onto new stack
430 mr r3,r31 ; Restore any arguments we may have trashed
431
432 bl EXT(ppc_init_cpu) ; Jump into cpu init code
433 BREAKPOINT_TRAP ; Should never return
434
435;
436; Specific processor initialization routines
437;
438
439; 750CX
440
441init750CX: bflr firstBoot ; No init for wakeup....
442 mfspr r13,hid1 ; Get HID1
443 li r14,lo16(0xFD5F) ; Get valid
444 rlwinm r13,r13,4,28,31 ; Isolate
445 slw r14,r14,r13 ; Position
446 rlwimi r17,r14,15-pfCanNapb,pfCanNapb,pfCanNapb ; Set it
447 b init750com ; Join common...
448
449; 750
450
451init750: bflr firstBoot ; No init for wakeup....
452
453init750com: mfspr r13,l2cr ; Get the L2CR
454 rlwinm. r0,r13,0,l2e,l2e ; Any L2?
455 bne+ i750hl2 ; Yes...
456 rlwinm r17,r17,0,pfL2b+1,pfL2b-1 ; No L2, turn off feature
457
458i750hl2: lis r14,hi16(256*1024) ; Base L2 size
459 addis r15,r13,0x3000 ; Hah... Figure this one out...
460 rlwinm r15,r15,4,30,31 ; Isolate
461 rlwinm. r8,r13,0,l2siz,l2sizf ; Was size valid?
462 slw r14,r14,r15 ; Set 256KB, 512KB, or 1MB
463 beq- init750none ; Not a valid setting...
464
465 stw r13,pfl2cr(r30) ; Shadow the L2CR
466 stw r14,pfl2Size(r30) ; Set the L2 size
467 blr ; Return....
468
469init750none:
470 rlwinm r17,r17,0,pfL2b+1,pfL2b-1 ; No level 2 cache
471 blr ; Return...
472
473
474init7400: bf firstBoot,i7400nb ; Do different if not initial boot...
475 mfspr r13,l2cr ; Get the L2CR
476 rlwinm. r0,r13,0,l2e,l2e ; Any L2?
477 bne+ i7400hl2 ; Yes...
478 rlwinm r17,r17,0,pfL2b+1,pfL2b-1 ; No L2, turn off feature
479
480i7400hl2: lis r14,hi16(256*1024) ; Base L2 size
481 addis r15,r13,0x3000 ; Hah... Figure this one out...
482 rlwinm r15,r15,4,30,31
483 slw r14,r14,r15 ; Set 256KB, 512KB, 1MB, or 2MB
484
485 stw r13,pfl2cr(r30) ; Shadow the L2CR
486 stw r14,pfl2Size(r30) ; Set the L2 size
487
488 mfspr r11,hid0 ; Get the current HID0
489 oris r11,r11,hi16(emcpm|eiecm) ; ?
490 mtspr hid0,r11 ; ?
491 isync
492 stw r11,pfHID0(r30) ; Save the HID0 value
493
494 mfspr r11,msscr0 ; Get the msscr0 register
495 stw r11,pfMSSCR0(r30) ; Save the MSSCR0 value
496 mfspr r11,msscr1 ; Get the msscr1 register
497 stw r11,pfMSSCR1(r30) ; Save the MSSCR1 value
498 blr ; Return...
499
500i7400nb: lwz r11,pfHID0(r30) ; Get HID0
501 sync
502 mtspr hid0,r11 ; Set the HID
503 lwz r11,pfMSSCR0(r30) ; Get MSSCR0
504 isync
505 sync
506 mtspr msscr0,r11 ; Set the MSSCR0
507 lwz r11,pfMSSCR1(r30) ; Get msscr1
508 isync
509 sync
510 mtspr msscr1,r11 ; Set the msscr1
511 isync
512 sync
513 blr
514
515; 7410
516; Note that this is the same as 7400 except we initialize the l2cr2 register
517
518init7410: li r13,0 ; Clear
519 mtspr 1016,r13 ; Turn off direct cache
520 b init7400 ; Join up with common....
521
522; 7450
523
524init7450: bf firstBoot,i7450nb ; Do different if not initial boot...
525 oris r17,r17,hi16(pfAvJava) ; Show that we do Java mode in non-open source version
526
527 mfspr r13,l2cr ; Get the L2CR
528 rlwinm. r0,r13,0,l2e,l2e ; Any L2?
529 bne+ i7450hl2 ; Yes...
530 rlwinm r17,r17,0,pfL2b+1,pfL2b-1 ; No L2, turn off feature
531
532i7450hl2: lis r14,hi16(256*1024) ; Base L2 size
533 rlwinm r15,r13,22,12,13 ; Convert to 256k, 512k, or 768k
534 add r14,r14,r15 ; Add in minimum
535
536 stw r13,pfl2cr(r30) ; Shadow the L2CR
537 stw r14,pfl2Size(r30) ; Set the L2 size
538
539; Take care of level 3 cache
540
541 mfspr r13,l3cr ; Get the L3CR
542 rlwinm. r0,r13,0,l3e,l3e ; Any L2?
543 bne+ i7450hl3 ; Yes...
544 rlwinm r17,r17,0,pfL3b+1,pfL3b-1 ; No L2, turn off feature
545
546i7450hl3: cmplwi cr0,r13,0 ; No L3 if L3CR is zero
547 beq- init7450none ; Go turn off the features...
548 lis r14,hi16(1024*1024) ; Base L3 size
549 rlwinm r15,r13,4,31,31 ; Get size multiplier
550 slw r14,r14,r15 ; Set 1 or 2MB
551
552 stw r13,pfl3cr(r30) ; Shadow the L3CR
553 stw r14,pfl3Size(r30) ; Set the L3 size
554 b init7450fin ; Return....
555
556init7450none:
0b4e3aa0
A
557 rlwinm r17,r17,0,pfL3fab+1,pfL3b-1 ; No 3rd level cache or assist
558 rlwinm r11,r17,pfWillNapb-pfCanNapb,pfCanNapb,pfCanNapb ; Set pfCanNap if pfWillNap is set
559 or r17,r17,r11
1c79356b 560
0b4e3aa0
A
561init7450fin:
562 rlwinm r17,r17,0,pfWillNapb+1,pfWillNapb-1 ; Make sure pfWillNap is not set
563
564 mfspr r11,hid0 ; Get the current HID0
1c79356b
A
565 stw r11,pfHID0(r30) ; Save the HID0 value
566 mfspr r11,hid1 ; Get the current HID1
567 stw r11,pfHID1(r30) ; Save the HID1 value
568 mfspr r11,msscr0 ; Get the msscr0 register
569 stw r11,pfMSSCR0(r30) ; Save the MSSCR0 value
570 mfspr r11,msscr1 ; Get the msscr1 register
571 stw r11,pfMSSCR1(r30) ; Save the MSSCR1 value
572 mfspr r11,ictrl ; Get the ictrl register
573 stw r11,pfICTRL(r30) ; Save the ICTRL value
574 mfspr r11,ldstcr ; Get the ldstcr register
575 stw r11,pfLDSTCR(r30) ; Save the LDSTCR value
0b4e3aa0
A
576 mfspr r11,ldstdb ; Get the ldstdb register
577 stw r11,pfLDSTDB(r30) ; Save the LDSTDB value
1c79356b
A
578 blr ; Return....
579
580
581i7450nb: lwz r11,pfHID0(r30) ; Get HID0
582 sync
583 mtspr hid0,r11 ; Set the HID
584 isync
585 lwz r11,pfHID1(r30) ; Get HID1
586 sync
587 mtspr hid1,r11 ; Set the HID
588 isync
589 lwz r11,pfMSSCR0(r30) ; Get MSSCR0
590 sync
591 mtspr msscr0,r11 ; Set the MSSCR0
592 isync
593 sync
594 lwz r11,pfICTRL(r30) ; Get ICTRL
595 sync
596 mtspr ictrl,r11 ; Set the ICTRL
597 isync
598 sync
599 lwz r11,pfLDSTCR(r30) ; Get LDSTCR
600 sync
601 mtspr ldstcr,r11 ; Set the LDSTCR
602 isync
603 sync
0b4e3aa0
A
604 lwz r11,pfLDSTDB(r30) ; Get LDSTDB
605 sync
606 mtspr ldstdb,r11 ; Set the LDSTDB
607 isync
608 sync
1c79356b
A
609 blr
610
611
612;
613; Processor to feature table
614
615; .align 2 - Always on word boundary
616; .long ptFilter - Mask of significant bits in the Version/Revision code
617; - NOTE: Always order from most restrictive to least restrictive matching
618; .short ptVersion - Version code from PVR. Always start with 0 which is default
619; .short ptRevision - Revision code from PVR. A zero value denotes the generic attributes if not specific
620; .long ptFeatures - Available features
621; .long ptInitRout - Initilization routine. Can modify any of the other attributes.
622; .long ptRptdProc - Processor type reported
623; .long ptTempMax - Maximum operating temprature
624; .long ptTempThr - Temprature threshold. We throttle if above
625; .long ptLineSize - Level 1 cache line size
626; .long ptl1iSize - Level 1 instruction cache size
627; .long ptl1dSize - Level 1 data cache size
628
629 .align 2
630processor_types:
631
632
633; 601 (generic)
634
635 .align 2
636 .long 0xFFFF0000 ; All revisions
637 .short PROCESSOR_VERSION_601
638 .short 0
639 .long pfFloat | pfSMPcap | pfL1i | pfL1d
640 .long 0
641 .long CPU_SUBTYPE_POWERPC_ALL
642 .long 0
643 .long 0
644 .long 32
645 .long 32*1024
646 .long 32*1024
647
648; 603 (generic)
649
650 .align 2
651 .long 0xFFFF0000 ; All revisions
652 .short PROCESSOR_VERSION_603
653 .short 0
654 .long pfFloat | pfL1i | pfL1d
655 .long 0
656 .long CPU_SUBTYPE_POWERPC_603
657 .long 0
658 .long 0
659 .long 32
660 .long 32*1024
661 .long 32*1024
662
663; 603e (generic)
664
665 .align 2
666 .long 0xFFFF0000 ; All revisions
667 .short PROCESSOR_VERSION_603e
668 .short 0
669 .long pfFloat | pfL1i | pfL1d
670 .long 0
671 .long CPU_SUBTYPE_POWERPC_603e
672 .long 0
673 .long 0
674 .long 32
675 .long 32*1024
676 .long 32*1024
677
678; 604 (generic)
679
680 .align 2
681 .long 0xFFFF0000 ; All revisions
682 .short PROCESSOR_VERSION_604
683 .short 0
684 .long pfFloat | pfSMPcap | pfL1i | pfL1d
685 .long 0
686 .long CPU_SUBTYPE_POWERPC_604
687 .long 0
688 .long 0
689 .long 32
690 .long 32*1024
691 .long 32*1024
692
693; 604e (generic)
694
695 .align 2
696 .long 0xFFFF0000 ; All revisions
697 .short PROCESSOR_VERSION_604e
698 .short 0
699 .long pfFloat | pfSMPcap | pfL1i | pfL1d
700 .long 0
701 .long CPU_SUBTYPE_POWERPC_604e
702 .long 0
703 .long 0
704 .long 32
705 .long 32*1024
706 .long 32*1024
707
708; 604ev (generic)
709
710 .align 2
711 .long 0xFFFF0000 ; All revisions
712 .short PROCESSOR_VERSION_604ev
713 .short 0
714 .long pfFloat | pfSMPcap | pfL1i | pfL1d
715 .long 0
716 .long CPU_SUBTYPE_POWERPC_604e
717 .long 0
718 .long 0
719 .long 32
720 .long 32*1024
721 .long 32*1024
722
723; 750 (ver 2.2)
724
725 .align 2
726 .long 0xFFFFFFFF ; Exact match
727 .short PROCESSOR_VERSION_750
728 .short 0x4202
729 .long pfFloat | pfCanSleep | pfCanNap | pfCanDoze | pfL1i | pfL1d | pfL2
730 .long init750
731 .long CPU_SUBTYPE_POWERPC_750
732 .long 105
733 .long 90
734 .long 32
735 .long 32*1024
736 .long 32*1024
737
738; 750CX (ver 2.x)
739
740 .align 2
741 .long 0xFFFF0F00 ; 2.x vers
742 .short PROCESSOR_VERSION_750
743 .short 0x0200
744 .long pfFloat | pfCanSleep | pfCanNap | pfCanDoze | pfL1i | pfL1d | pfL2
745 .long init750CX
746 .long CPU_SUBTYPE_POWERPC_750
747 .long 105
748 .long 90
749 .long 32
750 .long 32*1024
751 .long 32*1024
752
753; 750 (generic)
754
755 .align 2
756 .long 0xFFFF0000 ; All revisions
757 .short PROCESSOR_VERSION_750
758 .short 0
759 .long pfFloat | pfCanSleep | pfCanNap | pfCanDoze | pfThermal | pfL1i | pfL1d | pfL2
760 .long init750
761 .long CPU_SUBTYPE_POWERPC_750
762 .long 105
763 .long 90
764 .long 32
765 .long 32*1024
766 .long 32*1024
767
0b4e3aa0 768
1c79356b
A
769; 7400 (generic)
770
771 .align 2
772 .long 0xFFFF0000 ; All revisions
773 .short PROCESSOR_VERSION_7400
774 .short 0
775 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfCanNap | pfCanDoze | pfThermal | pfL1i | pfL1d | pfL1fa | pfL2 | pfL2fa
776 .long init7400
777 .long CPU_SUBTYPE_POWERPC_7400
778 .long 105
779 .long 90
780 .long 32
781 .long 32*1024
782 .long 32*1024
783
784; 7410 (ver 1.1)
785
786 .align 2
787 .long 0xFFFFFFFF ; Exact match
788 .short PROCESSOR_VERSION_7400
789 .short 0x1101
790 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfCanNap | pfCanDoze | pfL1i | pfL1d | pfL1fa | pfL2 | pfL2fa
791 .long init7410
792 .long CPU_SUBTYPE_POWERPC_7400
793 .long 105
794 .long 90
795 .long 32
796 .long 32*1024
797 .long 32*1024
798
799; 7410 (generic)
800
801 .align 2
802 .long 0xFFFF0000 ; All other revisions
803 .short PROCESSOR_VERSION_7410
804 .short 0
805 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfCanNap | pfCanDoze | pfL1i | pfL1d | pfL1fa | pfL2 | pfL2fa
806 .long init7410
807 .long CPU_SUBTYPE_POWERPC_7400
808 .long 105
809 .long 90
810 .long 32
811 .long 32*1024
812 .long 32*1024
813
814; 7450 (ver 1.xx)
815
816 .align 2
817 .long 0xFFFFFF00 ; Just revisions 1.xx
818 .short PROCESSOR_VERSION_7450
819 .short 0x0100
0b4e3aa0 820 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfNoMSRir | pfLClck | pfL1nnc | pfL1i | pfL1d | pfL2 | pfL2fa | pfL2i | pfL3 | pfL3fa
1c79356b
A
821 .long init7450
822 .long CPU_SUBTYPE_POWERPC_7450
823 .long 105
824 .long 90
825 .long 32
826 .long 32*1024
827 .long 32*1024
828
0b4e3aa0
A
829; 7450 (2.0)
830
831 .align 2
832 .long 0xFFFFFFFF ; Just revision 2.0
833 .short PROCESSOR_VERSION_7450
834 .short 0x0200
835 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfNoMSRir | pfLClck | pfL1i | pfL1d | pfL2 | pfL2fa | pfL2i | pfL3 | pfL3fa
836 .long init7450
837 .long CPU_SUBTYPE_POWERPC_7450
838 .long 105
839 .long 90
840 .long 32
841 .long 32*1024
842 .long 32*1024
843
844; 7450 (2.1)
1c79356b
A
845
846 .align 2
847 .long 0xFFFF0000 ; All other revisions
848 .short PROCESSOR_VERSION_7450
849 .short 0
0b4e3aa0 850 .long pfFloat | pfAltivec | pfSMPcap | pfCanSleep | pfNoMSRir | pfWillNap | pfLClck | pfL1i | pfL1d | pfL2 | pfL2fa | pfL2i | pfL3 | pfL3fa
1c79356b
A
851 .long init7450
852 .long CPU_SUBTYPE_POWERPC_7450
853 .long 105
854 .long 90
855 .long 32
856 .long 32*1024
857 .long 32*1024
858
0b4e3aa0 859
1c79356b
A
860; Default dumb loser machine
861
862 .align 2
863 .long 0x00000000 ; Matches everything
864 .short 0
865 .short 0
866 .long pfFloat | pfL1i | pfL1d
867 .long 0
868 .long CPU_SUBTYPE_POWERPC_ALL
869 .long 105
870 .long 90
871 .long 32
872 .long 32*1024
873 .long 32*1024