X-Git-Url: http://git.onelab.eu/?a=blobdiff_plain;f=arch%2Fm32r%2Fboot%2Fcompressed%2Fhead.S;h=10b928ed0f5079566708b1a4423c6951c8efe4ce;hb=6a77f38946aaee1cd85eeec6cf4229b204c15071;hp=28de481bdd099bfa518a0796661d6c2b32c070ed;hpb=87fc8d1bb10cd459024a742c6a10961fefcef18f;p=linux-2.6.git diff --git a/arch/m32r/boot/compressed/head.S b/arch/m32r/boot/compressed/head.S index 28de481bd..10b928ed0 100644 --- a/arch/m32r/boot/compressed/head.S +++ b/arch/m32r/boot/compressed/head.S @@ -13,20 +13,62 @@ #include #include + /* + * This code can be loaded anywhere, as long as output will not + * overlap it. + * + * NOTE: This head.S should *NOT* be compiled with -fpic. + * + */ + .global startup + .global __bss_start, _ebss, end, zimage_data, zimage_len __ALIGN startup: ldi r0, #0x0000 /* SPI, disable EI */ mvtc r0, psw + ldi r12, #-8 + bl 1f + .fillinsn +1: + seth r1, #high(CONFIG_MEMORY_START + 0x00400000) /* Start address */ + add r12, r14 /* Real address */ + sub r12, r1 /* difference */ + + .global got_len + seth r3, #high(_GLOBAL_OFFSET_TABLE_+8) + or3 r3, r3, #low(_GLOBAL_OFFSET_TABLE_+12) + add r3, r14 + + /* Update the contents of global offset table */ + ldi r1, #low(got_len) + srli r1, #2 + beqz r1, 2f + .fillinsn +1: + ld r2, @r3 + add r2, r12 + st r2, @r3 + addi r3, #4 + addi r1, #-1 + bnez r1, 1b + .fillinsn +2: + /* XXX: resolve plt */ + /* * Clear BSS first so that there are no surprises... */ #ifdef CONFIG_ISA_DUAL_ISSUE + seth r2, #high(__bss_start) + or3 r2, r2, #low(__bss_start) + add r2, r12 + seth r3, #high(_ebss) + or3 r3, r3, #low(_ebss) + add r3, r12 + sub r3, r2 - LDIMM (r2, __bss_start) - LDIMM (r3, _end) - sub r3, r2 ; BSS size in bytes ; R4 = BSS size in longwords (rounded down) mv r4, r3 || ldi r1, #0 srli r4, #4 || addi r2, #-4 @@ -52,10 +94,13 @@ startup: .Lendloop2: #else /* not CONFIG_ISA_DUAL_ISSUE */ - - LDIMM (r2, __bss_start) - LDIMM (r3, _end) - sub r3, r2 ; BSS size in bytes + seth r2, #high(__bss_start) + or3 r2, r2, #low(__bss_start) + add r2, r12 + seth r3, #high(_ebss) + or3 r3, r3, #low(_ebss) + add r3, r12 + sub r3, r2 mv r4, r3 srli r4, #2 ; R4 = BSS size in longwords (rounded down) ldi r1, #0 ; clear R1 for longwords store @@ -66,27 +111,29 @@ startup: addi r4, #-1 ; decrement count bnez r4, .Lloop1 ; go do some more .Lendloop1: - and3 r4, r3, #3 ; get no. of remaining BSS bytes to clear - addi r2, #4 ; account for pre-inc store - beqz r4, .Lendloop2 ; any more to go? -.Lloop2: - stb r1, @r2 ; yep, zero out another byte - addi r2, #1 ; bump address - addi r4, #-1 ; decrement count - bnez r4, .Lloop2 ; go do some more -.Lendloop2: #endif /* not CONFIG_ISA_DUAL_ISSUE */ - seth r0, #shigh(stack_start) - ld sp, @(r0, low(stack_start)) /* set stack point */ + seth r1, #high(end) + or3 r1, r1, #low(end) + add r1, r12 + mv sp, r1 /* * decompress the kernel */ + mv r0, sp + srli r0, 31 /* MMU is ON or OFF */ + seth r1, #high(zimage_data) + or3 r1, r1, #low(zimage_data) + add r1, r12 + seth r2, #high(zimage_len) + or3 r2, r2, #low(zimage_len) + mv r3, sp + bl decompress_kernel -#if defined(CONFIG_CHIP_M32700) +#if defined(CONFIG_CHIP_M32700) || defined(CONFIG_CHIP_OPSP) || defined(CONFIG_CHIP_VDEC2) /* Cache flush */ ldi r0, -1 ldi r1, 0xd0 ; invalidate i-cache, copy back d-cache @@ -94,9 +141,14 @@ startup: #else #error "put your cache flush function, please" #endif - seth r0, #high(CONFIG_MEMORY_START) - or3 r0, r0, #0x2000 - jmp r0 + + mv r0, sp + srli r0, 31 /* MMU is ON or OFF */ + slli r0, 31 + or3 r0, r0, #0x2000 + seth r1, #high(CONFIG_MEMORY_START) + or r0, r1 + jmp r0 .balign 512 fake_headers_as_bzImage: