1 /* SPDX-License-Identifier: GPL-2.0-only */ 2 /* 3 * linux/arch/arm/mm/cache-fa.S 4 * 5 * Copyright (C) 2005 Faraday Corp. 6 * Copyright (C) 2008-2009 Paulius Zaleckas <p 7 * 8 * Based on cache-v4wb.S: 9 * Copyright (C) 1997-2002 Russell king 10 * 11 * Processors: FA520 FA526 FA626 12 */ 13 #include <linux/linkage.h> 14 #include <linux/init.h> 15 #include <linux/cfi_types.h> 16 #include <asm/assembler.h> 17 #include <asm/page.h> 18 19 #include "proc-macros.S" 20 21 /* 22 * The size of one data cache line. 23 */ 24 #define CACHE_DLINESIZE 16 25 26 /* 27 * The total size of the data cache. 28 */ 29 #ifdef CONFIG_ARCH_GEMINI 30 #define CACHE_DSIZE 8192 31 #else 32 #define CACHE_DSIZE 16384 33 #endif 34 35 /* FIXME: put optimal value here. Current one 36 #define CACHE_DLIMIT (CACHE_DSIZE * 2) 37 38 /* 39 * flush_icache_all() 40 * 41 * Unconditionally clean and invalidate t 42 */ 43 SYM_TYPED_FUNC_START(fa_flush_icache_all) 44 mov r0, #0 45 mcr p15, 0, r0, c7, c5, 0 46 ret lr 47 SYM_FUNC_END(fa_flush_icache_all) 48 49 /* 50 * flush_user_cache_all() 51 * 52 * Clean and invalidate all cache entries 53 * space. 54 */ 55 SYM_FUNC_ALIAS(fa_flush_user_cache_all, fa_flu 56 57 /* 58 * flush_kern_cache_all() 59 * 60 * Clean and invalidate the entire cache. 61 */ 62 SYM_TYPED_FUNC_START(fa_flush_kern_cache_all) 63 mov ip, #0 64 mov r2, #VM_EXEC 65 __flush_whole_cache: 66 mcr p15, 0, ip, c7, c14, 0 67 tst r2, #VM_EXEC 68 mcrne p15, 0, ip, c7, c5, 0 69 mcrne p15, 0, ip, c7, c5, 6 70 mcrne p15, 0, ip, c7, c10, 4 71 mcrne p15, 0, ip, c7, c5, 4 72 ret lr 73 SYM_FUNC_END(fa_flush_kern_cache_all) 74 75 /* 76 * flush_user_cache_range(start, end, fla 77 * 78 * Invalidate a range of cache entries in 79 * address space. 80 * 81 * - start - start address (inclusive, pa 82 * - end - end address (exclusive, page 83 * - flags - vma_area_struct flags descri 84 */ 85 SYM_TYPED_FUNC_START(fa_flush_user_cache_range 86 mov ip, #0 87 sub r3, r1, r0 88 cmp r3, #CACHE_DLIMIT 89 bhs __flush_whole_cache 90 91 1: tst r2, #VM_EXEC 92 mcrne p15, 0, r0, c7, c5, 1 93 mcr p15, 0, r0, c7, c14, 1 94 add r0, r0, #CACHE_DLINESIZE 95 cmp r0, r1 96 blo 1b 97 tst r2, #VM_EXEC 98 mcrne p15, 0, ip, c7, c5, 6 99 mcrne p15, 0, ip, c7, c10, 4 100 mcrne p15, 0, ip, c7, c5, 4 101 ret lr 102 SYM_FUNC_END(fa_flush_user_cache_range) 103 104 /* 105 * coherent_kern_range(start, end) 106 * 107 * Ensure coherency between the Icache an 108 * region described by start. If you hav 109 * Harvard caches, you need to implement 110 * 111 * - start - virtual start address 112 * - end - virtual end address 113 */ 114 SYM_TYPED_FUNC_START(fa_coherent_kern_range) 115 #ifdef CONFIG_CFI_CLANG /* Fallthrough if !CFI 116 b fa_coherent_user_range 117 #endif 118 SYM_FUNC_END(fa_coherent_kern_range) 119 120 /* 121 * coherent_user_range(start, end) 122 * 123 * Ensure coherency between the Icache an 124 * region described by start. If you hav 125 * Harvard caches, you need to implement 126 * 127 * - start - virtual start address 128 * - end - virtual end address 129 */ 130 SYM_TYPED_FUNC_START(fa_coherent_user_range) 131 bic r0, r0, #CACHE_DLINESIZE - 1 132 1: mcr p15, 0, r0, c7, c14, 1 133 mcr p15, 0, r0, c7, c5, 1 134 add r0, r0, #CACHE_DLINESIZE 135 cmp r0, r1 136 blo 1b 137 mov r0, #0 138 mcr p15, 0, r0, c7, c5, 6 139 mcr p15, 0, r0, c7, c10, 4 140 mcr p15, 0, r0, c7, c5, 4 141 ret lr 142 SYM_FUNC_END(fa_coherent_user_range) 143 144 /* 145 * flush_kern_dcache_area(void *addr, siz 146 * 147 * Ensure that the data held in the page 148 * to the page in question. 149 * 150 * - addr - kernel address 151 * - size - size of region 152 */ 153 SYM_TYPED_FUNC_START(fa_flush_kern_dcache_area 154 add r1, r0, r1 155 1: mcr p15, 0, r0, c7, c14, 1 156 add r0, r0, #CACHE_DLINESIZE 157 cmp r0, r1 158 blo 1b 159 mov r0, #0 160 mcr p15, 0, r0, c7, c5, 0 161 mcr p15, 0, r0, c7, c10, 4 162 ret lr 163 SYM_FUNC_END(fa_flush_kern_dcache_area) 164 165 /* 166 * dma_inv_range(start, end) 167 * 168 * Invalidate (discard) the specified vir 169 * May not write back any entries. If 's 170 * are not cache line aligned, those line 171 * back. 172 * 173 * - start - virtual start address 174 * - end - virtual end address 175 */ 176 fa_dma_inv_range: 177 tst r0, #CACHE_DLINESIZE - 1 178 bic r0, r0, #CACHE_DLINESIZE - 1 179 mcrne p15, 0, r0, c7, c14, 1 180 tst r1, #CACHE_DLINESIZE - 1 181 bic r1, r1, #CACHE_DLINESIZE - 1 182 mcrne p15, 0, r1, c7, c14, 1 183 1: mcr p15, 0, r0, c7, c6, 1 184 add r0, r0, #CACHE_DLINESIZE 185 cmp r0, r1 186 blo 1b 187 mov r0, #0 188 mcr p15, 0, r0, c7, c10, 4 189 ret lr 190 191 /* 192 * dma_clean_range(start, end) 193 * 194 * Clean (write back) the specified virtu 195 * 196 * - start - virtual start address 197 * - end - virtual end address 198 */ 199 fa_dma_clean_range: 200 bic r0, r0, #CACHE_DLINESIZE - 1 201 1: mcr p15, 0, r0, c7, c10, 1 202 add r0, r0, #CACHE_DLINESIZE 203 cmp r0, r1 204 blo 1b 205 mov r0, #0 206 mcr p15, 0, r0, c7, c10, 4 207 ret lr 208 209 /* 210 * dma_flush_range(start,end) 211 * - start - virtual start address of r 212 * - end - virtual end address of reg 213 */ 214 SYM_TYPED_FUNC_START(fa_dma_flush_range) 215 bic r0, r0, #CACHE_DLINESIZE - 1 216 1: mcr p15, 0, r0, c7, c14, 1 217 add r0, r0, #CACHE_DLINESIZE 218 cmp r0, r1 219 blo 1b 220 mov r0, #0 221 mcr p15, 0, r0, c7, c10, 4 222 ret lr 223 SYM_FUNC_END(fa_dma_flush_range) 224 225 /* 226 * dma_map_area(start, size, dir) 227 * - start - kernel virtual start address 228 * - size - size of region 229 * - dir - DMA direction 230 */ 231 SYM_TYPED_FUNC_START(fa_dma_map_area) 232 add r1, r1, r0 233 cmp r2, #DMA_TO_DEVICE 234 beq fa_dma_clean_range 235 bcs fa_dma_inv_range 236 b fa_dma_flush_range 237 SYM_FUNC_END(fa_dma_map_area) 238 239 /* 240 * dma_unmap_area(start, size, dir) 241 * - start - kernel virtual start address 242 * - size - size of region 243 * - dir - DMA direction 244 */ 245 SYM_TYPED_FUNC_START(fa_dma_unmap_area) 246 ret lr 247 SYM_FUNC_END(fa_dma_unmap_area)
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.