blob: 8c83b458688323c6730e65668fe0bb046aaca9ac [file] [log] [blame]
Thomas Gleixnerd2912cb2019-06-04 10:11:33 +02001/* SPDX-License-Identifier: GPL-2.0-only */
Catalin Marinasbbe88882007-05-08 22:27:46 +01002/*
3 * linux/arch/arm/mm/cache-v7.S
4 *
5 * Copyright (C) 2001 Deep Blue Solutions Ltd.
6 * Copyright (C) 2005 ARM Ltd.
7 *
Catalin Marinasbbe88882007-05-08 22:27:46 +01008 * This is the "shell" of the ARMv7 processor support.
9 */
10#include <linux/linkage.h>
11#include <linux/init.h>
12#include <asm/assembler.h>
Will Deaconc5102f52012-04-27 13:08:53 +010013#include <asm/errno.h>
Catalin Marinas32cfb1b2009-10-06 17:57:09 +010014#include <asm/unwind.h>
Florian Fainelli1238c4f2017-12-01 01:10:10 +010015#include <asm/hardware/cache-b15-rac.h>
Catalin Marinasbbe88882007-05-08 22:27:46 +010016
17#include "proc-macros.S"
18
19/*
Dinh Nguyenc08e20d2013-02-11 17:30:32 -060020 * The secondary kernel init calls v7_flush_dcache_all before it enables
21 * the L1; however, the L1 comes out of reset in an undefined state, so
22 * the clean + invalidate performed by v7_flush_dcache_all causes a bunch
23 * of cache lines with uninitialized data and uninitialized tags to get
24 * written out to memory, which does really unpleasant things to the main
25 * processor. We fix this by performing an invalidate, rather than a
26 * clean + invalidate, before jumping into the kernel.
27 *
28 * This function is cloned from arch/arm/mach-tegra/headsmp.S, and needs
29 * to be called for both secondary cores startup and primary core resume
30 * procedures.
31 */
32ENTRY(v7_invalidate_l1)
33 mov r0, #0
34 mcr p15, 2, r0, c0, c0, 0
35 mrc p15, 1, r0, c0, c0, 0
36
Russell King5aca37082015-04-03 11:10:46 +010037 movw r1, #0x7fff
Dinh Nguyenc08e20d2013-02-11 17:30:32 -060038 and r2, r1, r0, lsr #13
39
Russell King5aca37082015-04-03 11:10:46 +010040 movw r1, #0x3ff
Dinh Nguyenc08e20d2013-02-11 17:30:32 -060041
42 and r3, r1, r0, lsr #3 @ NumWays - 1
43 add r2, r2, #1 @ NumSets
44
45 and r0, r0, #0x7
46 add r0, r0, #4 @ SetShift
47
48 clz r1, r3 @ WayShift
49 add r4, r3, #1 @ NumWays
501: sub r2, r2, #1 @ NumSets--
51 mov r3, r4 @ Temp = NumWays
522: subs r3, r3, #1 @ Temp--
53 mov r5, r3, lsl r1
54 mov r6, r2, lsl r0
55 orr r5, r5, r6 @ Reg = (Temp<<WayShift)|(NumSets<<SetShift)
56 mcr p15, 0, r5, c7, c6, 2
57 bgt 2b
58 cmp r2, #0
59 bgt 1b
Will Deacon95819602014-05-09 18:36:27 +010060 dsb st
Dinh Nguyenc08e20d2013-02-11 17:30:32 -060061 isb
Russell King6ebbf2c2014-06-30 16:29:12 +010062 ret lr
Dinh Nguyenc08e20d2013-02-11 17:30:32 -060063ENDPROC(v7_invalidate_l1)
64
65/*
Tony Lindgren81d11952010-09-21 17:16:40 +010066 * v7_flush_icache_all()
67 *
68 * Flush the whole I-cache.
69 *
70 * Registers:
71 * r0 - set to 0
72 */
73ENTRY(v7_flush_icache_all)
74 mov r0, #0
75 ALT_SMP(mcr p15, 0, r0, c7, c1, 0) @ invalidate I-cache inner shareable
76 ALT_UP(mcr p15, 0, r0, c7, c5, 0) @ I+BTB cache invalidate
Russell King6ebbf2c2014-06-30 16:29:12 +010077 ret lr
Tony Lindgren81d11952010-09-21 17:16:40 +010078ENDPROC(v7_flush_icache_all)
79
Lorenzo Pieralisi031bd872012-09-06 18:35:13 +053080 /*
81 * v7_flush_dcache_louis()
82 *
83 * Flush the D-cache up to the Level of Unification Inner Shareable
84 *
85 * Corrupted registers: r0-r7, r9-r11 (r6 only in Thumb mode)
86 */
87
88ENTRY(v7_flush_dcache_louis)
89 dmb @ ensure ordering with previous memory accesses
90 mrc p15, 1, r0, c0, c0, 1 @ read clidr, r0 = clidr
Russell King47b84842015-04-03 11:15:53 +010091ALT_SMP(mov r3, r0, lsr #20) @ move LoUIS into position
92ALT_UP( mov r3, r0, lsr #26) @ move LoUU into position
93 ands r3, r3, #7 << 1 @ extract LoU*2 field from clidr
Russell Kingd3cd4512015-04-03 11:25:39 +010094 bne start_flush_levels @ LoU != 0, start flushing
Jon Medhurst69155792013-06-07 10:35:35 +010095#ifdef CONFIG_ARM_ERRATA_643719
Russell Kingd3cd4512015-04-03 11:25:39 +010096ALT_SMP(mrc p15, 0, r2, c0, c0, 0) @ read main ID register
97ALT_UP( ret lr) @ LoUU is zero, so nothing to do
Russell Kingaaf4b5d2015-04-03 11:32:34 +010098 movw r1, #:lower16:(0x410fc090 >> 4) @ ID of ARM Cortex A9 r0p?
99 movt r1, #:upper16:(0x410fc090 >> 4)
100 teq r1, r2, lsr #4 @ test for errata affected core and if so...
Russell Kingd3cd4512015-04-03 11:25:39 +0100101 moveq r3, #1 << 1 @ fix LoUIS value
102 beq start_flush_levels @ start flushing cache levels
Jon Medhurst69155792013-06-07 10:35:35 +0100103#endif
Russell Kingd3cd4512015-04-03 11:25:39 +0100104 ret lr
Lorenzo Pieralisi031bd872012-09-06 18:35:13 +0530105ENDPROC(v7_flush_dcache_louis)
106
Tony Lindgren81d11952010-09-21 17:16:40 +0100107/*
Catalin Marinasbbe88882007-05-08 22:27:46 +0100108 * v7_flush_dcache_all()
109 *
110 * Flush the whole D-cache.
111 *
Catalin Marinas347c8b72009-07-24 12:32:56 +0100112 * Corrupted registers: r0-r7, r9-r11 (r6 only in Thumb mode)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100113 *
114 * - mm - mm_struct describing address space
115 */
116ENTRY(v7_flush_dcache_all)
Catalin Marinasc30c2f92008-11-06 13:23:07 +0000117 dmb @ ensure ordering with previous memory accesses
Catalin Marinasbbe88882007-05-08 22:27:46 +0100118 mrc p15, 1, r0, c0, c0, 1 @ read clidr
Russell King47b84842015-04-03 11:15:53 +0100119 mov r3, r0, lsr #23 @ move LoC into position
120 ands r3, r3, #7 << 1 @ extract LoC*2 from clidr
Catalin Marinasbbe88882007-05-08 22:27:46 +0100121 beq finished @ if loc is 0, then no need to clean
Russell Kingcd8b24d2015-04-03 11:21:42 +0100122start_flush_levels:
Catalin Marinasbbe88882007-05-08 22:27:46 +0100123 mov r10, #0 @ start clean at cache level 0
Lorenzo Pieralisi3287be82012-09-18 16:29:44 +0100124flush_levels:
Catalin Marinasbbe88882007-05-08 22:27:46 +0100125 add r2, r10, r10, lsr #1 @ work out 3x current cache level
126 mov r1, r0, lsr r2 @ extract cache type bits from clidr
127 and r1, r1, #7 @ mask of the bits for current cache only
128 cmp r1, #2 @ see what cache we have at this level
129 blt skip @ skip if no cache, or just i-cache
Stephen Boydb46c0f72012-02-07 19:42:07 +0100130#ifdef CONFIG_PREEMPT
Rabin Vincent8e43a902012-02-15 16:01:42 +0100131 save_and_disable_irqs_notrace r9 @ make cssr&csidr read atomic
Stephen Boydb46c0f72012-02-07 19:42:07 +0100132#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +0100133 mcr p15, 2, r10, c0, c0, 0 @ select current cache level in cssr
134 isb @ isb to sych the new cssr&csidr
135 mrc p15, 1, r1, c0, c0, 0 @ read the new csidr
Stephen Boydb46c0f72012-02-07 19:42:07 +0100136#ifdef CONFIG_PREEMPT
137 restore_irqs_notrace r9
138#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +0100139 and r2, r1, #7 @ extract the length of the cache lines
140 add r2, r2, #4 @ add 4 (line length offset)
Russell King5aca37082015-04-03 11:10:46 +0100141 movw r4, #0x3ff
Catalin Marinasbbe88882007-05-08 22:27:46 +0100142 ands r4, r4, r1, lsr #3 @ find maximum number on the way size
143 clz r5, r4 @ find bit position of way size increment
Russell King5aca37082015-04-03 11:10:46 +0100144 movw r7, #0x7fff
Catalin Marinasbbe88882007-05-08 22:27:46 +0100145 ands r7, r7, r1, lsr #13 @ extract max number of the index size
Lorenzo Pieralisi3287be82012-09-18 16:29:44 +0100146loop1:
Lorenzo Pieralisi70f665f2013-12-09 18:06:53 +0100147 mov r9, r7 @ create working copy of max index
Lorenzo Pieralisi3287be82012-09-18 16:29:44 +0100148loop2:
Lorenzo Pieralisi70f665f2013-12-09 18:06:53 +0100149 ARM( orr r11, r10, r4, lsl r5 ) @ factor way and cache number into r11
150 THUMB( lsl r6, r4, r5 )
Catalin Marinas347c8b72009-07-24 12:32:56 +0100151 THUMB( orr r11, r10, r6 ) @ factor way and cache number into r11
Lorenzo Pieralisi70f665f2013-12-09 18:06:53 +0100152 ARM( orr r11, r11, r9, lsl r2 ) @ factor index number into r11
153 THUMB( lsl r6, r9, r2 )
Catalin Marinas347c8b72009-07-24 12:32:56 +0100154 THUMB( orr r11, r11, r6 ) @ factor index number into r11
Catalin Marinasbbe88882007-05-08 22:27:46 +0100155 mcr p15, 0, r11, c7, c14, 2 @ clean & invalidate by set/way
Lorenzo Pieralisi70f665f2013-12-09 18:06:53 +0100156 subs r9, r9, #1 @ decrement the index
Catalin Marinasbbe88882007-05-08 22:27:46 +0100157 bge loop2
Lorenzo Pieralisi70f665f2013-12-09 18:06:53 +0100158 subs r4, r4, #1 @ decrement the way
Lorenzo Pieralisi3287be82012-09-18 16:29:44 +0100159 bge loop1
Catalin Marinasbbe88882007-05-08 22:27:46 +0100160skip:
161 add r10, r10, #2 @ increment cache number
162 cmp r3, r10
Lorenzo Pieralisi3287be82012-09-18 16:29:44 +0100163 bgt flush_levels
Catalin Marinasbbe88882007-05-08 22:27:46 +0100164finished:
Masahiro Yamada08a7e622017-02-27 14:28:41 -0800165 mov r10, #0 @ switch back to cache level 0
Catalin Marinasbbe88882007-05-08 22:27:46 +0100166 mcr p15, 2, r10, c0, c0, 0 @ select current cache level in cssr
Will Deacon95819602014-05-09 18:36:27 +0100167 dsb st
Catalin Marinasbbe88882007-05-08 22:27:46 +0100168 isb
Russell King6ebbf2c2014-06-30 16:29:12 +0100169 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100170ENDPROC(v7_flush_dcache_all)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100171
172/*
173 * v7_flush_cache_all()
174 *
175 * Flush the entire cache system.
176 * The data cache flush is now achieved using atomic clean / invalidates
177 * working outwards from L1 cache. This is done using Set/Way based cache
Lucas De Marchi25985ed2011-03-30 22:57:33 -0300178 * maintenance instructions.
Catalin Marinasbbe88882007-05-08 22:27:46 +0100179 * The instruction cache can still be invalidated back to the point of
180 * unification in a single instruction.
181 *
182 */
183ENTRY(v7_flush_kern_cache_all)
Catalin Marinas347c8b72009-07-24 12:32:56 +0100184 ARM( stmfd sp!, {r4-r5, r7, r9-r11, lr} )
185 THUMB( stmfd sp!, {r4-r7, r9-r11, lr} )
Catalin Marinasbbe88882007-05-08 22:27:46 +0100186 bl v7_flush_dcache_all
187 mov r0, #0
Russell Kingf00ec482010-09-04 10:47:48 +0100188 ALT_SMP(mcr p15, 0, r0, c7, c1, 0) @ invalidate I-cache inner shareable
189 ALT_UP(mcr p15, 0, r0, c7, c5, 0) @ I+BTB cache invalidate
Catalin Marinas347c8b72009-07-24 12:32:56 +0100190 ARM( ldmfd sp!, {r4-r5, r7, r9-r11, lr} )
191 THUMB( ldmfd sp!, {r4-r7, r9-r11, lr} )
Russell King6ebbf2c2014-06-30 16:29:12 +0100192 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100193ENDPROC(v7_flush_kern_cache_all)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100194
Lorenzo Pieralisi031bd872012-09-06 18:35:13 +0530195 /*
196 * v7_flush_kern_cache_louis(void)
197 *
198 * Flush the data cache up to Level of Unification Inner Shareable.
199 * Invalidate the I-cache to the point of unification.
200 */
201ENTRY(v7_flush_kern_cache_louis)
202 ARM( stmfd sp!, {r4-r5, r7, r9-r11, lr} )
203 THUMB( stmfd sp!, {r4-r7, r9-r11, lr} )
204 bl v7_flush_dcache_louis
205 mov r0, #0
206 ALT_SMP(mcr p15, 0, r0, c7, c1, 0) @ invalidate I-cache inner shareable
207 ALT_UP(mcr p15, 0, r0, c7, c5, 0) @ I+BTB cache invalidate
208 ARM( ldmfd sp!, {r4-r5, r7, r9-r11, lr} )
209 THUMB( ldmfd sp!, {r4-r7, r9-r11, lr} )
Russell King6ebbf2c2014-06-30 16:29:12 +0100210 ret lr
Lorenzo Pieralisi031bd872012-09-06 18:35:13 +0530211ENDPROC(v7_flush_kern_cache_louis)
212
Catalin Marinasbbe88882007-05-08 22:27:46 +0100213/*
214 * v7_flush_cache_all()
215 *
216 * Flush all TLB entries in a particular address space
217 *
218 * - mm - mm_struct describing address space
219 */
220ENTRY(v7_flush_user_cache_all)
221 /*FALLTHROUGH*/
222
223/*
224 * v7_flush_cache_range(start, end, flags)
225 *
226 * Flush a range of TLB entries in the specified address space.
227 *
228 * - start - start address (may not be aligned)
229 * - end - end address (exclusive, may not be aligned)
230 * - flags - vm_area_struct flags describing address space
231 *
232 * It is assumed that:
233 * - we have a VIPT cache.
234 */
235ENTRY(v7_flush_user_cache_range)
Russell King6ebbf2c2014-06-30 16:29:12 +0100236 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100237ENDPROC(v7_flush_user_cache_all)
238ENDPROC(v7_flush_user_cache_range)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100239
240/*
241 * v7_coherent_kern_range(start,end)
242 *
243 * Ensure that the I and D caches are coherent within specified
244 * region. This is typically used when code has been written to
245 * a memory region, and will be executed.
246 *
247 * - start - virtual start address of region
248 * - end - virtual end address of region
249 *
250 * It is assumed that:
251 * - the Icache does not read data from the write buffer
252 */
253ENTRY(v7_coherent_kern_range)
254 /* FALLTHROUGH */
255
256/*
257 * v7_coherent_user_range(start,end)
258 *
259 * Ensure that the I and D caches are coherent within specified
260 * region. This is typically used when code has been written to
261 * a memory region, and will be executed.
262 *
263 * - start - virtual start address of region
264 * - end - virtual end address of region
265 *
266 * It is assumed that:
267 * - the Icache does not read data from the write buffer
268 */
269ENTRY(v7_coherent_user_range)
Catalin Marinas32cfb1b2009-10-06 17:57:09 +0100270 UNWIND(.fnstart )
Catalin Marinasbbe88882007-05-08 22:27:46 +0100271 dcache_line_size r2, r3
272 sub r3, r2, #1
Catalin Marinasda30e0a2010-12-07 16:56:29 +0100273 bic r12, r0, r3
Will Deaconf630c1b2011-09-15 11:45:15 +0100274#ifdef CONFIG_ARM_ERRATA_764369
275 ALT_SMP(W(dsb))
276 ALT_UP(W(nop))
277#endif
Catalin Marinas32cfb1b2009-10-06 17:57:09 +01002781:
Catalin Marinasda30e0a2010-12-07 16:56:29 +0100279 USER( mcr p15, 0, r12, c7, c11, 1 ) @ clean D line to the point of unification
280 add r12, r12, r2
281 cmp r12, r1
Catalin Marinasbbe88882007-05-08 22:27:46 +0100282 blo 1b
Will Deacon6abdd492013-05-13 12:01:12 +0100283 dsb ishst
Catalin Marinasda30e0a2010-12-07 16:56:29 +0100284 icache_line_size r2, r3
285 sub r3, r2, #1
286 bic r12, r0, r3
2872:
288 USER( mcr p15, 0, r12, c7, c5, 1 ) @ invalidate I line
289 add r12, r12, r2
290 cmp r12, r1
291 blo 2b
Catalin Marinasbbe88882007-05-08 22:27:46 +0100292 mov r0, #0
Russell Kingf00ec482010-09-04 10:47:48 +0100293 ALT_SMP(mcr p15, 0, r0, c7, c1, 6) @ invalidate BTB Inner Shareable
294 ALT_UP(mcr p15, 0, r0, c7, c5, 6) @ invalidate BTB
Will Deacon6abdd492013-05-13 12:01:12 +0100295 dsb ishst
Catalin Marinasbbe88882007-05-08 22:27:46 +0100296 isb
Russell King6ebbf2c2014-06-30 16:29:12 +0100297 ret lr
Catalin Marinas32cfb1b2009-10-06 17:57:09 +0100298
299/*
300 * Fault handling for the cache operation above. If the virtual address in r0
Will Deaconc5102f52012-04-27 13:08:53 +0100301 * isn't mapped, fail with -EFAULT.
Catalin Marinas32cfb1b2009-10-06 17:57:09 +0100302 */
3039001:
Simon Horman7253b852012-09-28 02:12:45 +0100304#ifdef CONFIG_ARM_ERRATA_775420
305 dsb
306#endif
Will Deaconc5102f52012-04-27 13:08:53 +0100307 mov r0, #-EFAULT
Russell King6ebbf2c2014-06-30 16:29:12 +0100308 ret lr
Catalin Marinas32cfb1b2009-10-06 17:57:09 +0100309 UNWIND(.fnend )
Catalin Marinas93ed3972008-08-28 11:22:32 +0100310ENDPROC(v7_coherent_kern_range)
311ENDPROC(v7_coherent_user_range)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100312
313/*
Russell King2c9b9c82009-11-26 12:56:21 +0000314 * v7_flush_kern_dcache_area(void *addr, size_t size)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100315 *
316 * Ensure that the data held in the page kaddr is written back
317 * to the page in question.
318 *
Russell King2c9b9c82009-11-26 12:56:21 +0000319 * - addr - kernel address
320 * - size - region size
Catalin Marinasbbe88882007-05-08 22:27:46 +0100321 */
Russell King2c9b9c82009-11-26 12:56:21 +0000322ENTRY(v7_flush_kern_dcache_area)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100323 dcache_line_size r2, r3
Russell King2c9b9c82009-11-26 12:56:21 +0000324 add r1, r0, r1
Will Deacona248b132011-05-26 11:20:19 +0100325 sub r3, r2, #1
326 bic r0, r0, r3
Will Deaconf630c1b2011-09-15 11:45:15 +0100327#ifdef CONFIG_ARM_ERRATA_764369
328 ALT_SMP(W(dsb))
329 ALT_UP(W(nop))
330#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +01003311:
332 mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D line / unified line
333 add r0, r0, r2
334 cmp r0, r1
335 blo 1b
Will Deacon95819602014-05-09 18:36:27 +0100336 dsb st
Russell King6ebbf2c2014-06-30 16:29:12 +0100337 ret lr
Russell King2c9b9c82009-11-26 12:56:21 +0000338ENDPROC(v7_flush_kern_dcache_area)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100339
340/*
341 * v7_dma_inv_range(start,end)
342 *
343 * Invalidate the data cache within the specified region; we will
344 * be performing a DMA operation in this region and we want to
345 * purge old data in the cache.
346 *
347 * - start - virtual start address of region
348 * - end - virtual end address of region
349 */
Russell King702b94b2009-11-26 16:24:19 +0000350v7_dma_inv_range:
Catalin Marinasbbe88882007-05-08 22:27:46 +0100351 dcache_line_size r2, r3
352 sub r3, r2, #1
353 tst r0, r3
354 bic r0, r0, r3
Will Deaconf630c1b2011-09-15 11:45:15 +0100355#ifdef CONFIG_ARM_ERRATA_764369
356 ALT_SMP(W(dsb))
357 ALT_UP(W(nop))
358#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +0100359 mcrne p15, 0, r0, c7, c14, 1 @ clean & invalidate D / U line
Chris Colea1208f62018-11-23 12:20:45 +0100360 addne r0, r0, r2
Catalin Marinasbbe88882007-05-08 22:27:46 +0100361
362 tst r1, r3
363 bic r1, r1, r3
364 mcrne p15, 0, r1, c7, c14, 1 @ clean & invalidate D / U line
Catalin Marinasbbe88882007-05-08 22:27:46 +0100365 cmp r0, r1
Chris Colea1208f62018-11-23 12:20:45 +01003661:
367 mcrlo p15, 0, r0, c7, c6, 1 @ invalidate D / U line
368 addlo r0, r0, r2
369 cmplo r0, r1
Catalin Marinasbbe88882007-05-08 22:27:46 +0100370 blo 1b
Will Deacon95819602014-05-09 18:36:27 +0100371 dsb st
Russell King6ebbf2c2014-06-30 16:29:12 +0100372 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100373ENDPROC(v7_dma_inv_range)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100374
375/*
376 * v7_dma_clean_range(start,end)
377 * - start - virtual start address of region
378 * - end - virtual end address of region
379 */
Russell King702b94b2009-11-26 16:24:19 +0000380v7_dma_clean_range:
Catalin Marinasbbe88882007-05-08 22:27:46 +0100381 dcache_line_size r2, r3
382 sub r3, r2, #1
383 bic r0, r0, r3
Will Deaconf630c1b2011-09-15 11:45:15 +0100384#ifdef CONFIG_ARM_ERRATA_764369
385 ALT_SMP(W(dsb))
386 ALT_UP(W(nop))
387#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +01003881:
389 mcr p15, 0, r0, c7, c10, 1 @ clean D / U line
390 add r0, r0, r2
391 cmp r0, r1
392 blo 1b
Will Deacon95819602014-05-09 18:36:27 +0100393 dsb st
Russell King6ebbf2c2014-06-30 16:29:12 +0100394 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100395ENDPROC(v7_dma_clean_range)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100396
397/*
398 * v7_dma_flush_range(start,end)
399 * - start - virtual start address of region
400 * - end - virtual end address of region
401 */
402ENTRY(v7_dma_flush_range)
403 dcache_line_size r2, r3
404 sub r3, r2, #1
405 bic r0, r0, r3
Will Deaconf630c1b2011-09-15 11:45:15 +0100406#ifdef CONFIG_ARM_ERRATA_764369
407 ALT_SMP(W(dsb))
408 ALT_UP(W(nop))
409#endif
Catalin Marinasbbe88882007-05-08 22:27:46 +01004101:
411 mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D / U line
412 add r0, r0, r2
413 cmp r0, r1
414 blo 1b
Will Deacon95819602014-05-09 18:36:27 +0100415 dsb st
Russell King6ebbf2c2014-06-30 16:29:12 +0100416 ret lr
Catalin Marinas93ed3972008-08-28 11:22:32 +0100417ENDPROC(v7_dma_flush_range)
Catalin Marinasbbe88882007-05-08 22:27:46 +0100418
Russell Kinga9c91472009-11-26 16:19:58 +0000419/*
420 * dma_map_area(start, size, dir)
421 * - start - kernel virtual start address
422 * - size - size of region
423 * - dir - DMA direction
424 */
425ENTRY(v7_dma_map_area)
426 add r1, r1, r0
Russell King2ffe2da2009-10-31 16:52:16 +0000427 teq r2, #DMA_FROM_DEVICE
428 beq v7_dma_inv_range
429 b v7_dma_clean_range
Russell Kinga9c91472009-11-26 16:19:58 +0000430ENDPROC(v7_dma_map_area)
431
432/*
433 * dma_unmap_area(start, size, dir)
434 * - start - kernel virtual start address
435 * - size - size of region
436 * - dir - DMA direction
437 */
438ENTRY(v7_dma_unmap_area)
Russell King2ffe2da2009-10-31 16:52:16 +0000439 add r1, r1, r0
440 teq r2, #DMA_TO_DEVICE
441 bne v7_dma_inv_range
Russell King6ebbf2c2014-06-30 16:29:12 +0100442 ret lr
Russell Kinga9c91472009-11-26 16:19:58 +0000443ENDPROC(v7_dma_unmap_area)
444
Catalin Marinasbbe88882007-05-08 22:27:46 +0100445 __INITDATA
446
Dave Martin455a01e2011-06-23 17:16:25 +0100447 @ define struct cpu_cache_fns (see <asm/cacheflush.h> and proc-macros.S)
448 define_cache_functions v7
Florian Fainelli1238c4f2017-12-01 01:10:10 +0100449
450 /* The Broadcom Brahma-B15 read-ahead cache requires some modifications
451 * to the v7_cache_fns, we only override the ones we need
452 */
453#ifndef CONFIG_CACHE_B15_RAC
454 globl_equ b15_flush_kern_cache_all, v7_flush_kern_cache_all
455#endif
456 globl_equ b15_flush_icache_all, v7_flush_icache_all
457 globl_equ b15_flush_kern_cache_louis, v7_flush_kern_cache_louis
458 globl_equ b15_flush_user_cache_all, v7_flush_user_cache_all
459 globl_equ b15_flush_user_cache_range, v7_flush_user_cache_range
460 globl_equ b15_coherent_kern_range, v7_coherent_kern_range
461 globl_equ b15_coherent_user_range, v7_coherent_user_range
462 globl_equ b15_flush_kern_dcache_area, v7_flush_kern_dcache_area
463
464 globl_equ b15_dma_map_area, v7_dma_map_area
465 globl_equ b15_dma_unmap_area, v7_dma_unmap_area
466 globl_equ b15_dma_flush_range, v7_dma_flush_range
467
468 define_cache_functions b15