Fedora kernel-2.6.17-1.2142_FC4 patched with stable patch-2.6.17.4-vs2.0.2-rc26.diff
[linux-2.6.git] / arch / ppc / kernel / relocate_kernel.S
index 837e596..9b2ad48 100644 (file)
@@ -2,7 +2,7 @@
  * relocate_kernel.S - put the kernel image in place to boot
  * Copyright (C) 2002-2003 Eric Biederman  <ebiederm@xmission.com>
  *
- * GAMECUBE/PPC32 port Copyright (C) 2004 Albert Herranz
+ * GameCube/ppc32 port Copyright (C) 2004 Albert Herranz
  *
  * This source code is licensed under the GNU General Public License,
  * Version 2.  See the file COPYING for more details.
 
 #define PAGE_SIZE      4096 /* must be same value as in <asm/page.h> */
 
-/* returns  r3 = relocated address of sym */
-/* modifies r0 */
-#define RELOC_SYM(sym) \
-       mflr    r3; \
-       bl      1f; \
-1:     mflr    r0; \
-       mtlr    r3; \
-       lis     r3, 1b@ha; \
-       ori     r3, r3, 1b@l; \
-       subf    r0, r3, r0; \
-       lis     r3, sym@ha; \
-       ori     r3, r3, sym@l; \
-       add     r3, r3, r0
-
        /*
         * Must be relocatable PIC code callable as a C function.
         */
        .globl relocate_new_kernel
 relocate_new_kernel:
-       /* r3 = indirection_page   */
+       /* r3 = page_list   */
        /* r4 = reboot_code_buffer */
        /* r5 = start_address      */
 
        li      r0, 0
 
-       /* Set Machine Status Register to a known status */
+       /*
+        * Set Machine Status Register to a known status,
+        * switch the MMU off and jump to 1: in a single step.
+        */
+
        mr      r8, r0
        ori     r8, r8, MSR_RI|MSR_ME
-       mtmsr   r8
-       isync
+       mtspr   SPRN_SRR1, r8
+       addi    r8, r4, 1f - relocate_new_kernel
+       mtspr   SPRN_SRR0, r8
+       sync
+       rfi
 
+1:
        /* from this point address translation is turned off */
        /* and interrupts are disabled */
 
@@ -57,32 +51,34 @@ relocate_new_kernel:
 
        /* Do the copies */
        li      r6, 0 /* checksum */
-       subi    r3, r3, 4
+       mr      r0, r3
+       b       1f
 
 0:     /* top, read another word for the indirection page */
        lwzu    r0, 4(r3)
 
+1:
        /* is it a destination page? (r8) */
        rlwinm. r7, r0, 0, 31, 31 /* IND_DESTINATION (1<<0) */
-       beq     1f
+       beq     2f
 
        rlwinm  r8, r0, 0, 0, 19 /* clear kexec flags, page align */
        b       0b
 
-1:     /* is it an indirection page? (r3) */
+2:     /* is it an indirection page? (r3) */
        rlwinm. r7, r0, 0, 30, 30 /* IND_INDIRECTION (1<<1) */
-       beq     1f
+       beq     2f
 
        rlwinm  r3, r0, 0, 0, 19 /* clear kexec flags, page align */
        subi    r3, r3, 4
        b       0b
 
-1:     /* are we done? */
+2:     /* are we done? */
        rlwinm. r7, r0, 0, 29, 29 /* IND_DONE (1<<2) */
-       beq     1f
-       b       2f
+       beq     2f
+       b       3f
 
-1:     /* is it a source page? (r9) */
+2:     /* is it a source page? (r9) */
        rlwinm. r7, r0, 0, 28, 28 /* IND_SOURCE (1<<3) */
        beq     0b
 
@@ -105,7 +101,7 @@ relocate_new_kernel:
        addi    r8, r8, 4
        b       0b
 
-2:
+3:
 
        /* To be certain of avoiding problems with self-modifying code
         * execute a serializing instruction here.