]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - arch/mips/cpu/mips32/cache.S
am33xx/ddr_defs.h: rename DDR2/DDR3 defines to their actual part numbers
[karo-tx-uboot.git] / arch / mips / cpu / mips32 / cache.S
1 /*
2  *  Cache-handling routined for MIPS CPUs
3  *
4  *  Copyright (c) 2003  Wolfgang Denk <wd@denx.de>
5  *
6  * See file CREDITS for list of people who contributed to this
7  * project.
8  *
9  * This program is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License as
11  * published by the Free Software Foundation; either version 2 of
12  * the License, or (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
22  * MA 02111-1307 USA
23  */
24
25 #include <asm-offsets.h>
26 #include <config.h>
27 #include <asm/asm.h>
28 #include <asm/regdef.h>
29 #include <asm/mipsregs.h>
30 #include <asm/addrspace.h>
31 #include <asm/cacheops.h>
32
33 #ifndef CONFIG_SYS_MIPS_CACHE_MODE
34 #define CONFIG_SYS_MIPS_CACHE_MODE CONF_CM_CACHABLE_NONCOHERENT
35 #endif
36
37 #define RA              t8
38
39 /*
40  * 16kB is the maximum size of instruction and data caches on MIPS 4K,
41  * 64kB is on 4KE, 24K, 5K, etc. Set bigger size for convenience.
42  *
43  * Note that the above size is the maximum size of primary cache. U-Boot
44  * doesn't have L2 cache support for now.
45  */
46 #define MIPS_MAX_CACHE_SIZE     0x10000
47
48 #define INDEX_BASE      CKSEG0
49
50         .macro  cache_op op addr
51         .set    push
52         .set    noreorder
53         .set    mips3
54         cache   \op, 0(\addr)
55         .set    pop
56         .endm
57
58         .macro  f_fill64 dst, offset, val
59         LONG_S  \val, (\offset +  0 * LONGSIZE)(\dst)
60         LONG_S  \val, (\offset +  1 * LONGSIZE)(\dst)
61         LONG_S  \val, (\offset +  2 * LONGSIZE)(\dst)
62         LONG_S  \val, (\offset +  3 * LONGSIZE)(\dst)
63         LONG_S  \val, (\offset +  4 * LONGSIZE)(\dst)
64         LONG_S  \val, (\offset +  5 * LONGSIZE)(\dst)
65         LONG_S  \val, (\offset +  6 * LONGSIZE)(\dst)
66         LONG_S  \val, (\offset +  7 * LONGSIZE)(\dst)
67 #if LONGSIZE == 4
68         LONG_S  \val, (\offset +  8 * LONGSIZE)(\dst)
69         LONG_S  \val, (\offset +  9 * LONGSIZE)(\dst)
70         LONG_S  \val, (\offset + 10 * LONGSIZE)(\dst)
71         LONG_S  \val, (\offset + 11 * LONGSIZE)(\dst)
72         LONG_S  \val, (\offset + 12 * LONGSIZE)(\dst)
73         LONG_S  \val, (\offset + 13 * LONGSIZE)(\dst)
74         LONG_S  \val, (\offset + 14 * LONGSIZE)(\dst)
75         LONG_S  \val, (\offset + 15 * LONGSIZE)(\dst)
76 #endif
77         .endm
78
79 /*
80  * mips_init_icache(uint PRId, ulong icache_size, unchar icache_linesz)
81  */
82 LEAF(mips_init_icache)
83         blez            a1, 9f
84         mtc0            zero, CP0_TAGLO
85         /* clear tag to invalidate */
86         PTR_LI          t0, INDEX_BASE
87         PTR_ADDU        t1, t0, a1
88 1:      cache_op        Index_Store_Tag_I t0
89         PTR_ADDU        t0, a2
90         bne             t0, t1, 1b
91         /* fill once, so data field parity is correct */
92         PTR_LI          t0, INDEX_BASE
93 2:      cache_op        Fill t0
94         PTR_ADDU        t0, a2
95         bne             t0, t1, 2b
96         /* invalidate again - prudent but not strictly neccessary */
97         PTR_LI          t0, INDEX_BASE
98 1:      cache_op        Index_Store_Tag_I t0
99         PTR_ADDU        t0, a2
100         bne             t0, t1, 1b
101 9:      jr              ra
102         END(mips_init_icache)
103
104 /*
105  * mips_init_dcache(uint PRId, ulong dcache_size, unchar dcache_linesz)
106  */
107 LEAF(mips_init_dcache)
108         blez            a1, 9f
109         mtc0            zero, CP0_TAGLO
110         /* clear all tags */
111         PTR_LI          t0, INDEX_BASE
112         PTR_ADDU        t1, t0, a1
113 1:      cache_op        Index_Store_Tag_D t0
114         PTR_ADDU        t0, a2
115         bne             t0, t1, 1b
116         /* load from each line (in cached space) */
117         PTR_LI          t0, INDEX_BASE
118 2:      LONG_L          zero, 0(t0)
119         PTR_ADDU        t0, a2
120         bne             t0, t1, 2b
121         /* clear all tags */
122         PTR_LI          t0, INDEX_BASE
123 1:      cache_op        Index_Store_Tag_D t0
124         PTR_ADDU        t0, a2
125         bne             t0, t1, 1b
126 9:      jr              ra
127         END(mips_init_dcache)
128
129 /*
130  * mips_cache_reset - low level initialisation of the primary caches
131  *
132  * This routine initialises the primary caches to ensure that they have good
133  * parity.  It must be called by the ROM before any cached locations are used
134  * to prevent the possibility of data with bad parity being written to memory.
135  *
136  * To initialise the instruction cache it is essential that a source of data
137  * with good parity is available. This routine will initialise an area of
138  * memory starting at location zero to be used as a source of parity.
139  *
140  * RETURNS: N/A
141  *
142  */
143 NESTED(mips_cache_reset, 0, ra)
144         move    RA, ra
145         li      t2, CONFIG_SYS_ICACHE_SIZE
146         li      t3, CONFIG_SYS_DCACHE_SIZE
147         li      t4, CONFIG_SYS_CACHELINE_SIZE
148         move    t5, t4
149
150         li      v0, MIPS_MAX_CACHE_SIZE
151
152         /*
153          * Now clear that much memory starting from zero.
154          */
155         PTR_LI          a0, CKSEG1
156         PTR_ADDU        a1, a0, v0
157 2:      PTR_ADDIU       a0, 64
158         f_fill64        a0, -64, zero
159         bne             a0, a1, 2b
160
161         /*
162          * The caches are probably in an indeterminate state,
163          * so we force good parity into them by doing an
164          * invalidate, load/fill, invalidate for each line.
165          */
166
167         /*
168          * Assume bottom of RAM will generate good parity for the cache.
169          */
170
171         /*
172          * Initialize the I-cache first,
173          */
174         move    a1, t2
175         move    a2, t4
176         PTR_LA  t7, mips_init_icache
177         jalr    t7
178
179         /*
180          * then initialize D-cache.
181          */
182         move    a1, t3
183         move    a2, t5
184         PTR_LA  t7, mips_init_dcache
185         jalr    t7
186
187         jr      RA
188         END(mips_cache_reset)
189
190 /*
191  * dcache_status - get cache status
192  *
193  * RETURNS: 0 - cache disabled; 1 - cache enabled
194  *
195  */
196 LEAF(dcache_status)
197         mfc0    t0, CP0_CONFIG
198         li      t1, CONF_CM_UNCACHED
199         andi    t0, t0, CONF_CM_CMASK
200         move    v0, zero
201         beq     t0, t1, 2f
202         li      v0, 1
203 2:      jr      ra
204         END(dcache_status)
205
206 /*
207  * dcache_disable - disable cache
208  *
209  * RETURNS: N/A
210  *
211  */
212 LEAF(dcache_disable)
213         mfc0    t0, CP0_CONFIG
214         li      t1, -8
215         and     t0, t0, t1
216         ori     t0, t0, CONF_CM_UNCACHED
217         mtc0    t0, CP0_CONFIG
218         jr      ra
219         END(dcache_disable)
220
221 /*
222  * dcache_enable - enable cache
223  *
224  * RETURNS: N/A
225  *
226  */
227 LEAF(dcache_enable)
228         mfc0    t0, CP0_CONFIG
229         ori     t0, CONF_CM_CMASK
230         xori    t0, CONF_CM_CMASK
231         ori     t0, CONFIG_SYS_MIPS_CACHE_MODE
232         mtc0    t0, CP0_CONFIG
233         jr      ra
234         END(dcache_enable)