aboutsummaryrefslogtreecommitdiffstats
path: root/arch/powerpc/kernel
diff options
context:
space:
mode:
authorJoakim Tjernlund <joakim.tjernlund@transmode.se>2010-03-02 00:37:12 -0500
committerBenjamin Herrenschmidt <benh@kernel.crashing.org>2010-04-07 04:00:34 -0400
commit469d62be9263b92f2c3329540cbb1c076111f4f3 (patch)
tree02916b88e15132cc8bf9f74647c4b3d5400b986a /arch/powerpc/kernel
parentd069cb4373fe0d451357c4d3769623a7564dfa9f (diff)
powerpc/8xx: Use SPRG2 and DAR registers to stash r11 and cr.
This avoids storing these registers in memory. CPU6 errata will still use the old way. Remove some G2 leftover accesses from 2.4 Signed-off-by: Joakim Tjernlund <Joakim.Tjernlund@transmode.se> Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Diffstat (limited to 'arch/powerpc/kernel')
-rw-r--r--arch/powerpc/kernel/head_8xx.S49
1 files changed, 36 insertions, 13 deletions
diff --git a/arch/powerpc/kernel/head_8xx.S b/arch/powerpc/kernel/head_8xx.S
index 6478a963255..1f1a04b5c2a 100644
--- a/arch/powerpc/kernel/head_8xx.S
+++ b/arch/powerpc/kernel/head_8xx.S
@@ -71,9 +71,6 @@ _ENTRY(_start);
71 * in the first level table, but that would require many changes to the 71 * in the first level table, but that would require many changes to the
72 * Linux page directory/table functions that I don't want to do right now. 72 * Linux page directory/table functions that I don't want to do right now.
73 * 73 *
74 * I used to use SPRG2 for a temporary register in the TLB handler, but it
75 * has since been put to other uses. I now use a hack to save a register
76 * and the CCR at memory location 0.....Someday I'll fix this.....
77 * -- Dan 74 * -- Dan
78 */ 75 */
79 .globl __start 76 .globl __start
@@ -302,8 +299,13 @@ InstructionTLBMiss:
302 DO_8xx_CPU6(0x3f80, r3) 299 DO_8xx_CPU6(0x3f80, r3)
303 mtspr SPRN_M_TW, r10 /* Save a couple of working registers */ 300 mtspr SPRN_M_TW, r10 /* Save a couple of working registers */
304 mfcr r10 301 mfcr r10
302#ifdef CONFIG_8xx_CPU6
305 stw r10, 0(r0) 303 stw r10, 0(r0)
306 stw r11, 4(r0) 304 stw r11, 4(r0)
305#else
306 mtspr SPRN_DAR, r10
307 mtspr SPRN_SPRG2, r11
308#endif
307 mfspr r10, SPRN_SRR0 /* Get effective address of fault */ 309 mfspr r10, SPRN_SRR0 /* Get effective address of fault */
308#ifdef CONFIG_8xx_CPU15 310#ifdef CONFIG_8xx_CPU15
309 addi r11, r10, 0x1000 311 addi r11, r10, 0x1000
@@ -359,13 +361,19 @@ InstructionTLBMiss:
359 DO_8xx_CPU6(0x2d80, r3) 361 DO_8xx_CPU6(0x2d80, r3)
360 mtspr SPRN_MI_RPN, r10 /* Update TLB entry */ 362 mtspr SPRN_MI_RPN, r10 /* Update TLB entry */
361 363
362 mfspr r10, SPRN_M_TW /* Restore registers */ 364 /* Restore registers */
365#ifndef CONFIG_8xx_CPU6
366 mfspr r10, SPRN_DAR
367 mtcr r10
368 mtspr SPRN_DAR, r11 /* Tag DAR */
369 mfspr r11, SPRN_SPRG2
370#else
363 lwz r11, 0(r0) 371 lwz r11, 0(r0)
364 mtcr r11 372 mtcr r11
365 lwz r11, 4(r0) 373 lwz r11, 4(r0)
366#ifdef CONFIG_8xx_CPU6
367 lwz r3, 8(r0) 374 lwz r3, 8(r0)
368#endif 375#endif
376 mfspr r10, SPRN_M_TW
369 rfi 377 rfi
3702: 3782:
371 mfspr r11, SPRN_SRR1 379 mfspr r11, SPRN_SRR1
@@ -375,13 +383,20 @@ InstructionTLBMiss:
375 rlwinm r11, r11, 0, 0xffff 383 rlwinm r11, r11, 0, 0xffff
376 mtspr SPRN_SRR1, r11 384 mtspr SPRN_SRR1, r11
377 385
378 mfspr r10, SPRN_M_TW /* Restore registers */ 386 /* Restore registers */
387#ifndef CONFIG_8xx_CPU6
388 mfspr r10, SPRN_DAR
389 mtcr r10
390 li r11, 0x00f0
391 mtspr SPRN_DAR, r11 /* Tag DAR */
392 mfspr r11, SPRN_SPRG2
393#else
379 lwz r11, 0(r0) 394 lwz r11, 0(r0)
380 mtcr r11 395 mtcr r11
381 lwz r11, 4(r0) 396 lwz r11, 4(r0)
382#ifdef CONFIG_8xx_CPU6
383 lwz r3, 8(r0) 397 lwz r3, 8(r0)
384#endif 398#endif
399 mfspr r10, SPRN_M_TW
385 b InstructionAccess 400 b InstructionAccess
386 401
387 . = 0x1200 402 . = 0x1200
@@ -392,8 +407,13 @@ DataStoreTLBMiss:
392 DO_8xx_CPU6(0x3f80, r3) 407 DO_8xx_CPU6(0x3f80, r3)
393 mtspr SPRN_M_TW, r10 /* Save a couple of working registers */ 408 mtspr SPRN_M_TW, r10 /* Save a couple of working registers */
394 mfcr r10 409 mfcr r10
410#ifdef CONFIG_8xx_CPU6
395 stw r10, 0(r0) 411 stw r10, 0(r0)
396 stw r11, 4(r0) 412 stw r11, 4(r0)
413#else
414 mtspr SPRN_DAR, r10
415 mtspr SPRN_SPRG2, r11
416#endif
397 mfspr r10, SPRN_M_TWB /* Get level 1 table entry address */ 417 mfspr r10, SPRN_M_TWB /* Get level 1 table entry address */
398 418
399 /* If we are faulting a kernel address, we have to use the 419 /* If we are faulting a kernel address, we have to use the
@@ -461,18 +481,24 @@ DataStoreTLBMiss:
461 * of the MMU. 481 * of the MMU.
462 */ 482 */
4632: li r11, 0x00f0 4832: li r11, 0x00f0
464 mtspr SPRN_DAR,r11 /* Tag DAR */
465 rlwimi r10, r11, 0, 24, 28 /* Set 24-27, clear 28 */ 484 rlwimi r10, r11, 0, 24, 28 /* Set 24-27, clear 28 */
466 DO_8xx_CPU6(0x3d80, r3) 485 DO_8xx_CPU6(0x3d80, r3)
467 mtspr SPRN_MD_RPN, r10 /* Update TLB entry */ 486 mtspr SPRN_MD_RPN, r10 /* Update TLB entry */
468 487
469 mfspr r10, SPRN_M_TW /* Restore registers */ 488 /* Restore registers */
489#ifndef CONFIG_8xx_CPU6
490 mfspr r10, SPRN_DAR
491 mtcr r10
492 mtspr SPRN_DAR, r11 /* Tag DAR */
493 mfspr r11, SPRN_SPRG2
494#else
495 mtspr SPRN_DAR, r11 /* Tag DAR */
470 lwz r11, 0(r0) 496 lwz r11, 0(r0)
471 mtcr r11 497 mtcr r11
472 lwz r11, 4(r0) 498 lwz r11, 4(r0)
473#ifdef CONFIG_8xx_CPU6
474 lwz r3, 8(r0) 499 lwz r3, 8(r0)
475#endif 500#endif
501 mfspr r10, SPRN_M_TW
476 rfi 502 rfi
477 503
478/* This is an instruction TLB error on the MPC8xx. This could be due 504/* This is an instruction TLB error on the MPC8xx. This could be due
@@ -684,9 +710,6 @@ start_here:
684 tophys(r4,r2) 710 tophys(r4,r2)
685 addi r4,r4,THREAD /* init task's THREAD */ 711 addi r4,r4,THREAD /* init task's THREAD */
686 mtspr SPRN_SPRG_THREAD,r4 712 mtspr SPRN_SPRG_THREAD,r4
687 li r3,0
688 /* XXX What is that for ? SPRG2 appears otherwise unused on 8xx */
689 mtspr SPRN_SPRG2,r3 /* 0 => r1 has kernel sp */
690 713
691 /* stack */ 714 /* stack */
692 lis r1,init_thread_union@ha 715 lis r1,init_thread_union@ha