[ARM] 4224/2: allow XIP kernel to boot again
authorNicolas Pitre <nico@cam.org>
Thu, 22 Feb 2007 15:18:09 +0000 (16:18 +0100)
committerRussell King <rmk+kernel@arm.linux.org.uk>
Sun, 25 Feb 2007 16:41:38 +0000 (16:41 +0000)
Since commit 2552fc27ff79b10b9678d92bcaef21df38bb7bb6 XIP kernels failed
to boot because (_end - PAGE_OFFSET - 1) is much smaller than the size
of the kernel text and data in the XIP case, causing the kernel not to
be entirely mapped.

Even in the non-XIP case, the use of (_end - PAGE_OFFSET - 1) is wrong
because it produces a too large value if TEXT_OFFSET is larger than 1MB.

Finally the original code was performing one loop too many.

Let's break the loop when the section pointer has passed the last byte
of the kernel instead.

Signed-off-by: Nicolas Pitre <nico@cam.org>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
arch/arm/kernel/head.S
arch/arm/kernel/vmlinux.lds.S

index cf495a3084b31f8a7ead7089508ff16096864ae9..c5f0c52660b254d7e1ef699a3dab99259af62e0d 100644 (file)
        .endm
 
 #ifdef CONFIG_XIP_KERNEL
-#define TEXTADDR  XIP_VIRT_ADDR(CONFIG_XIP_PHYS_ADDR)
+#define KERNEL_START   XIP_VIRT_ADDR(CONFIG_XIP_PHYS_ADDR)
+#define KERNEL_END     _edata_loc
 #else
-#define TEXTADDR  KERNEL_RAM_VADDR
+#define KERNEL_START   KERNEL_RAM_VADDR
+#define KERNEL_END     _end
 #endif
 
 /*
@@ -240,16 +242,15 @@ __create_page_tables:
         * Now setup the pagetables for our kernel direct
         * mapped region.
         */
-       add     r0, r4,  #(TEXTADDR & 0xff000000) >> 18 @ start of kernel
-       str     r3, [r0, #(TEXTADDR & 0x00f00000) >> 18]!
-
-       ldr     r6, =(_end - PAGE_OFFSET - 1)   @ r6 = number of sections
-       mov     r6, r6, lsr #20                 @ needed for kernel minus 1
-
-1:     add     r3, r3, #1 << 20
-       str     r3, [r0, #4]!
-       subs    r6, r6, #1
-       bgt     1b
+       add     r0, r4,  #(KERNEL_START & 0xff000000) >> 18
+       str     r3, [r0, #(KERNEL_START & 0x00f00000) >> 18]!
+       ldr     r6, =(KERNEL_END - 1)
+       add     r0, r0, #4
+       add     r6, r4, r6, lsr #18
+1:     cmp     r0, r6
+       add     r3, r3, #1 << 20
+       strls   r3, [r0], #4
+       bls     1b
 
        /*
         * Then map first 1MB of ram in case it contains our boot params.
index b929a60f7547cdde716dca1c18b06aafd92f8a22..ddbdad48f5b2636285c36d4836bb863f5b2e25f7 100644 (file)
@@ -156,6 +156,7 @@ SECTIONS
 
                _edata = .;
        }
+       _edata_loc = __data_loc + SIZEOF(.data);
 
        .bss : {
                __bss_start = .;        /* BSS                          */