xref: /OK3568_Linux_fs/kernel/arch/sh/boot/compressed/head_64.S (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun/*
2*4882a593Smuzhiyun * This file is subject to the terms and conditions of the GNU General Public
3*4882a593Smuzhiyun * License.  See the file "COPYING" in the main directory of this archive
4*4882a593Smuzhiyun * for more details.
5*4882a593Smuzhiyun *
6*4882a593Smuzhiyun * arch/shmedia/boot/compressed/head.S
7*4882a593Smuzhiyun *
8*4882a593Smuzhiyun * Copied from
9*4882a593Smuzhiyun *   arch/shmedia/kernel/head.S
10*4882a593Smuzhiyun * which carried the copyright:
11*4882a593Smuzhiyun *   Copyright (C) 2000, 2001  Paolo Alberelli
12*4882a593Smuzhiyun *
13*4882a593Smuzhiyun * Modification for compressed loader:
14*4882a593Smuzhiyun *   Copyright (C) 2002 Stuart Menefy (stuart.menefy@st.com)
15*4882a593Smuzhiyun */
16*4882a593Smuzhiyun#include <asm/cache.h>
17*4882a593Smuzhiyun#include <asm/tlb.h>
18*4882a593Smuzhiyun#include <cpu/mmu_context.h>
19*4882a593Smuzhiyun#include <cpu/registers.h>
20*4882a593Smuzhiyun
21*4882a593Smuzhiyun/*
22*4882a593Smuzhiyun * Fixed TLB entries to identity map the beginning of RAM
23*4882a593Smuzhiyun */
24*4882a593Smuzhiyun#define MMUIR_TEXT_H	0x0000000000000003 | CONFIG_MEMORY_START
25*4882a593Smuzhiyun			/* Enabled, Shared, ASID 0, Eff. Add. 0xA0000000 */
26*4882a593Smuzhiyun#define MMUIR_TEXT_L	0x000000000000009a | CONFIG_MEMORY_START
27*4882a593Smuzhiyun			/* 512 Mb, Cacheable (Write-back), execute, Not User, Ph. Add. */
28*4882a593Smuzhiyun
29*4882a593Smuzhiyun#define MMUDR_CACHED_H	0x0000000000000003 | CONFIG_MEMORY_START
30*4882a593Smuzhiyun			/* Enabled, Shared, ASID 0, Eff. Add. 0xA0000000 */
31*4882a593Smuzhiyun#define MMUDR_CACHED_L	0x000000000000015a | CONFIG_MEMORY_START
32*4882a593Smuzhiyun			/* 512 Mb, Cacheable (Write-back), read/write, Not User, Ph. Add. */
33*4882a593Smuzhiyun
34*4882a593Smuzhiyun#define	ICCR0_INIT_VAL	ICCR0_ON | ICCR0_ICI		/* ICE + ICI */
35*4882a593Smuzhiyun#define	ICCR1_INIT_VAL	ICCR1_NOLOCK			/* No locking */
36*4882a593Smuzhiyun
37*4882a593Smuzhiyun#define	OCCR0_INIT_VAL	OCCR0_ON | OCCR0_OCI | OCCR0_WB	/* OCE + OCI + WB */
38*4882a593Smuzhiyun#define	OCCR1_INIT_VAL	OCCR1_NOLOCK			/* No locking */
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun	.text
41*4882a593Smuzhiyun
42*4882a593Smuzhiyun	.global	startup
43*4882a593Smuzhiyunstartup:
44*4882a593Smuzhiyun	/*
45*4882a593Smuzhiyun	 * Prevent speculative fetch on device memory due to
46*4882a593Smuzhiyun	 * uninitialized target registers.
47*4882a593Smuzhiyun	 * This must be executed before the first branch.
48*4882a593Smuzhiyun	 */
49*4882a593Smuzhiyun	ptabs/u	r63, tr0
50*4882a593Smuzhiyun	ptabs/u	r63, tr1
51*4882a593Smuzhiyun	ptabs/u	r63, tr2
52*4882a593Smuzhiyun	ptabs/u	r63, tr3
53*4882a593Smuzhiyun	ptabs/u	r63, tr4
54*4882a593Smuzhiyun	ptabs/u	r63, tr5
55*4882a593Smuzhiyun	ptabs/u	r63, tr6
56*4882a593Smuzhiyun	ptabs/u	r63, tr7
57*4882a593Smuzhiyun	synci
58*4882a593Smuzhiyun
59*4882a593Smuzhiyun	/*
60*4882a593Smuzhiyun	 * Set initial TLB entries for cached and uncached regions.
61*4882a593Smuzhiyun	 * Note: PTA/BLINK is PIC code, PTABS/BLINK isn't !
62*4882a593Smuzhiyun	 */
63*4882a593Smuzhiyun	/* Clear ITLBs */
64*4882a593Smuzhiyun	pta	1f, tr1
65*4882a593Smuzhiyun	movi	ITLB_FIXED, r21
66*4882a593Smuzhiyun	movi	ITLB_LAST_VAR_UNRESTRICTED+TLB_STEP, r22
67*4882a593Smuzhiyun1:	putcfg	r21, 0, r63		/* Clear MMUIR[n].PTEH.V */
68*4882a593Smuzhiyun	addi	r21, TLB_STEP, r21
69*4882a593Smuzhiyun        bne	r21, r22, tr1
70*4882a593Smuzhiyun
71*4882a593Smuzhiyun	/* Clear DTLBs */
72*4882a593Smuzhiyun	pta	1f, tr1
73*4882a593Smuzhiyun	movi	DTLB_FIXED, r21
74*4882a593Smuzhiyun	movi	DTLB_LAST_VAR_UNRESTRICTED+TLB_STEP, r22
75*4882a593Smuzhiyun1:	putcfg	r21, 0, r63		/* Clear MMUDR[n].PTEH.V */
76*4882a593Smuzhiyun	addi	r21, TLB_STEP, r21
77*4882a593Smuzhiyun        bne	r21, r22, tr1
78*4882a593Smuzhiyun
79*4882a593Smuzhiyun	/* Map one big (512Mb) page for ITLB */
80*4882a593Smuzhiyun	movi	ITLB_FIXED, r21
81*4882a593Smuzhiyun	movi	MMUIR_TEXT_L, r22	/* PTEL first */
82*4882a593Smuzhiyun	putcfg	r21, 1, r22		/* Set MMUIR[0].PTEL */
83*4882a593Smuzhiyun	movi	MMUIR_TEXT_H, r22	/* PTEH last */
84*4882a593Smuzhiyun	putcfg	r21, 0, r22		/* Set MMUIR[0].PTEH */
85*4882a593Smuzhiyun
86*4882a593Smuzhiyun	/* Map one big CACHED (512Mb) page for DTLB */
87*4882a593Smuzhiyun	movi	DTLB_FIXED, r21
88*4882a593Smuzhiyun	movi	MMUDR_CACHED_L, r22	/* PTEL first */
89*4882a593Smuzhiyun	putcfg	r21, 1, r22		/* Set MMUDR[0].PTEL */
90*4882a593Smuzhiyun	movi	MMUDR_CACHED_H, r22	/* PTEH last */
91*4882a593Smuzhiyun	putcfg	r21, 0, r22		/* Set MMUDR[0].PTEH */
92*4882a593Smuzhiyun
93*4882a593Smuzhiyun	/* ICache */
94*4882a593Smuzhiyun	movi	ICCR_BASE, r21
95*4882a593Smuzhiyun	movi	ICCR0_INIT_VAL, r22
96*4882a593Smuzhiyun	movi	ICCR1_INIT_VAL, r23
97*4882a593Smuzhiyun	putcfg	r21, ICCR_REG0, r22
98*4882a593Smuzhiyun	putcfg	r21, ICCR_REG1, r23
99*4882a593Smuzhiyun	synci
100*4882a593Smuzhiyun
101*4882a593Smuzhiyun	/* OCache */
102*4882a593Smuzhiyun	movi	OCCR_BASE, r21
103*4882a593Smuzhiyun	movi	OCCR0_INIT_VAL, r22
104*4882a593Smuzhiyun	movi	OCCR1_INIT_VAL, r23
105*4882a593Smuzhiyun	putcfg	r21, OCCR_REG0, r22
106*4882a593Smuzhiyun	putcfg	r21, OCCR_REG1, r23
107*4882a593Smuzhiyun	synco
108*4882a593Smuzhiyun
109*4882a593Smuzhiyun	/*
110*4882a593Smuzhiyun	 * Enable the MMU.
111*4882a593Smuzhiyun	 * From here-on code can be non-PIC.
112*4882a593Smuzhiyun	 */
113*4882a593Smuzhiyun	movi	SR_HARMLESS | SR_ENABLE_MMU, r22
114*4882a593Smuzhiyun	putcon	r22, SSR
115*4882a593Smuzhiyun	movi	1f, r22
116*4882a593Smuzhiyun	putcon	r22, SPC
117*4882a593Smuzhiyun	synco
118*4882a593Smuzhiyun	rte				/* And now go into the hyperspace ... */
119*4882a593Smuzhiyun1:					/* ... that's the next instruction ! */
120*4882a593Smuzhiyun
121*4882a593Smuzhiyun	/* Set initial stack pointer */
122*4882a593Smuzhiyun	movi	datalabel stack_start, r0
123*4882a593Smuzhiyun	ld.l	r0, 0, r15
124*4882a593Smuzhiyun
125*4882a593Smuzhiyun	/*
126*4882a593Smuzhiyun	 * Clear bss
127*4882a593Smuzhiyun	 */
128*4882a593Smuzhiyun	pt	1f, tr1
129*4882a593Smuzhiyun	movi	datalabel __bss_start, r22
130*4882a593Smuzhiyun	movi	datalabel _end, r23
131*4882a593Smuzhiyun1:	st.l	r22, 0, r63
132*4882a593Smuzhiyun	addi	r22, 4, r22
133*4882a593Smuzhiyun	bne	r22, r23, tr1
134*4882a593Smuzhiyun
135*4882a593Smuzhiyun	/*
136*4882a593Smuzhiyun	 * Decompress the kernel.
137*4882a593Smuzhiyun	 */
138*4882a593Smuzhiyun	pt	decompress_kernel, tr0
139*4882a593Smuzhiyun	blink	tr0, r18
140*4882a593Smuzhiyun
141*4882a593Smuzhiyun	/*
142*4882a593Smuzhiyun	 * Disable the MMU.
143*4882a593Smuzhiyun	 */
144*4882a593Smuzhiyun	movi	SR_HARMLESS, r22
145*4882a593Smuzhiyun	putcon	r22, SSR
146*4882a593Smuzhiyun	movi	1f, r22
147*4882a593Smuzhiyun	putcon	r22, SPC
148*4882a593Smuzhiyun	synco
149*4882a593Smuzhiyun	rte				/* And now go into the hyperspace ... */
150*4882a593Smuzhiyun1:					/* ... that's the next instruction ! */
151*4882a593Smuzhiyun
152*4882a593Smuzhiyun	/* Jump into the decompressed kernel */
153*4882a593Smuzhiyun	movi	datalabel (CONFIG_MEMORY_START + 0x2000)+1, r19
154*4882a593Smuzhiyun	ptabs	r19, tr0
155*4882a593Smuzhiyun	blink	tr0, r18
156*4882a593Smuzhiyun
157*4882a593Smuzhiyun	/* Shouldn't return here, but just in case, loop forever */
158*4882a593Smuzhiyun	pt	1f, tr0
159*4882a593Smuzhiyun1:	blink	tr0, r63
160