xref: /openbmc/linux/arch/sh/kernel/relocate_kernel.S (revision 9d44190e)
19d44190eSkogiidena/*
29d44190eSkogiidena * relocate_kernel.S - put the kernel image in place to boot
39d44190eSkogiidena * 2005.9.17 kogiidena@eggplant.ddo.jp
49d44190eSkogiidena *
59d44190eSkogiidena * LANDISK/sh4 is supported. Maybe, SH archtecture works well.
69d44190eSkogiidena *
79d44190eSkogiidena * This source code is licensed under the GNU General Public License,
89d44190eSkogiidena * Version 2.  See the file COPYING for more details.
99d44190eSkogiidena */
109d44190eSkogiidena
119d44190eSkogiidena#include <linux/config.h>
129d44190eSkogiidena#include <linux/linkage.h>
139d44190eSkogiidena
149d44190eSkogiidena#define PAGE_SIZE      4096 /* must be same value as in <asm/page.h> */
159d44190eSkogiidena
169d44190eSkogiidena
179d44190eSkogiidena		.globl relocate_new_kernel
189d44190eSkogiidenarelocate_new_kernel:
199d44190eSkogiidena	/* r4 = indirection_page   */
209d44190eSkogiidena	/* r5 = reboot_code_buffer */
219d44190eSkogiidena	/* r6 = start_address      */
229d44190eSkogiidena	/* r7 = vbr_reg            */
239d44190eSkogiidena
249d44190eSkogiidena	mov.l	10f,r8	  /* 4096 */
259d44190eSkogiidena	mov.l	11f,r9    /* 0xa0000000 */
269d44190eSkogiidena
279d44190eSkogiidena	/*  stack setting */
289d44190eSkogiidena	add	r8,r5
299d44190eSkogiidena	mov	r5,r15
309d44190eSkogiidena
319d44190eSkogiidena	bra	1f
329d44190eSkogiidena	mov	r4,r0	  /* cmd = indirection_page */
339d44190eSkogiidena0:
349d44190eSkogiidena	mov.l	@r4+,r0	  /* cmd = *ind++ */
359d44190eSkogiidena
369d44190eSkogiidena1:	/* addr = (cmd | 0xa0000000) & 0xfffffff0 */
379d44190eSkogiidena	mov	r0,r2
389d44190eSkogiidena	or	r9,r2
399d44190eSkogiidena	mov	#-16,r1
409d44190eSkogiidena	and	r1,r2
419d44190eSkogiidena
429d44190eSkogiidena	/* if(cmd & IND_DESTINATION) dst = addr  */
439d44190eSkogiidena	tst	#1,r0
449d44190eSkogiidena	bt	2f
459d44190eSkogiidena	bra	0b
469d44190eSkogiidena	mov	r2,r5
479d44190eSkogiidena
489d44190eSkogiidena2:	/* else if(cmd & IND_INDIRECTION) ind = addr  */
499d44190eSkogiidena	tst	#2,r0
509d44190eSkogiidena	bt	3f
519d44190eSkogiidena	bra	0b
529d44190eSkogiidena	mov	r2,r4
539d44190eSkogiidena
549d44190eSkogiidena3:	/* else if(cmd & IND_DONE) goto 6  */
559d44190eSkogiidena	tst	#4,r0
569d44190eSkogiidena	bt	4f
579d44190eSkogiidena	bra	6f
589d44190eSkogiidena	nop
599d44190eSkogiidena
609d44190eSkogiidena4:	/* else if(cmd & IND_SOURCE) memcpy(dst,addr,PAGE_SIZE) */
619d44190eSkogiidena	tst	#8,r0
629d44190eSkogiidena	bt	0b
639d44190eSkogiidena
649d44190eSkogiidena	mov	r8,r3
659d44190eSkogiidena	shlr2	r3
669d44190eSkogiidena	shlr2	r3
679d44190eSkogiidena5:
689d44190eSkogiidena	dt	r3
699d44190eSkogiidena	mov.l	@r2+,r1   /*  16n+0 */
709d44190eSkogiidena	mov.l	r1,@r5
719d44190eSkogiidena	add	#4,r5
729d44190eSkogiidena	mov.l	@r2+,r1	  /*  16n+4 */
739d44190eSkogiidena	mov.l	r1,@r5
749d44190eSkogiidena	add	#4,r5
759d44190eSkogiidena	mov.l	@r2+,r1   /*  16n+8 */
769d44190eSkogiidena	mov.l	r1,@r5
779d44190eSkogiidena	add	#4,r5
789d44190eSkogiidena	mov.l	@r2+,r1   /*  16n+12 */
799d44190eSkogiidena	mov.l	r1,@r5
809d44190eSkogiidena	add	#4,r5
819d44190eSkogiidena	bf	5b
829d44190eSkogiidena
839d44190eSkogiidena	bra	0b
849d44190eSkogiidena	nop
859d44190eSkogiidena6:
869d44190eSkogiidena#ifdef CONFIG_SH_STANDARD_BIOS
879d44190eSkogiidena	ldc   r7, vbr
889d44190eSkogiidena#endif
899d44190eSkogiidena	jmp @r6
909d44190eSkogiidena	nop
919d44190eSkogiidena
929d44190eSkogiidena	.align 2
939d44190eSkogiidena10:
949d44190eSkogiidena	.long	PAGE_SIZE
959d44190eSkogiidena11:
969d44190eSkogiidena	.long	0xa0000000
979d44190eSkogiidena
989d44190eSkogiidenarelocate_new_kernel_end:
999d44190eSkogiidena
1009d44190eSkogiidena	.globl relocate_new_kernel_size
1019d44190eSkogiidenarelocate_new_kernel_size:
1029d44190eSkogiidena	.long relocate_new_kernel_end - relocate_new_kernel
103