0001
0002
0003
0004
0005
0006
0007 #include <linux/linkage.h>
0008 #include <linux/init.h>
0009 #include <linux/pgtable.h>
0010 #include <asm/assembler.h>
0011 #include <asm/hwcap.h>
0012 #include <asm/pgtable-hwdef.h>
0013 #include <asm/ptrace.h>
0014 #include "proc-macros.S"
0015
0016
0017 #define CACHE_DLINESIZE 16
0018 #define CACHE_DSEGMENTS 4
0019 #define CACHE_DENTRIES 64
0020
0021 .text
0022
0023
0024
0025
0026
0027
0028 ENTRY(cpu_arm940_proc_init)
0029 ENTRY(cpu_arm940_switch_mm)
0030 ret lr
0031
0032
0033
0034
0035 ENTRY(cpu_arm940_proc_fin)
0036 mrc p15, 0, r0, c1, c0, 0 @ ctrl register
0037 bic r0, r0, #0x00001000 @ i-cache
0038 bic r0, r0, #0x00000004 @ d-cache
0039 mcr p15, 0, r0, c1, c0, 0 @ disable caches
0040 ret lr
0041
0042
0043
0044
0045
0046
0047 .pushsection .idmap.text, "ax"
0048 ENTRY(cpu_arm940_reset)
0049 mov ip, #0
0050 mcr p15, 0, ip, c7, c5, 0 @ flush I cache
0051 mcr p15, 0, ip, c7, c6, 0 @ flush D cache
0052 mcr p15, 0, ip, c7, c10, 4 @ drain WB
0053 mrc p15, 0, ip, c1, c0, 0 @ ctrl register
0054 bic ip, ip, #0x00000005 @ .............c.p
0055 bic ip, ip, #0x00001000 @ i-cache
0056 mcr p15, 0, ip, c1, c0, 0 @ ctrl register
0057 ret r0
0058 ENDPROC(cpu_arm940_reset)
0059 .popsection
0060
0061
0062
0063
0064 .align 5
0065 ENTRY(cpu_arm940_do_idle)
0066 mcr p15, 0, r0, c7, c0, 4 @ Wait for interrupt
0067 ret lr
0068
0069
0070
0071
0072
0073
0074 ENTRY(arm940_flush_icache_all)
0075 mov r0, #0
0076 mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
0077 ret lr
0078 ENDPROC(arm940_flush_icache_all)
0079
0080
0081
0082
0083 ENTRY(arm940_flush_user_cache_all)
0084
0085
0086
0087
0088
0089
0090
0091 ENTRY(arm940_flush_kern_cache_all)
0092 mov r2, #VM_EXEC
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105 ENTRY(arm940_flush_user_cache_range)
0106 mov ip, #0
0107 #ifdef CONFIG_CPU_DCACHE_WRITETHROUGH
0108 mcr p15, 0, ip, c7, c6, 0 @ flush D cache
0109 #else
0110 mov r1, #(CACHE_DSEGMENTS - 1) << 4 @ 4 segments
0111 1: orr r3, r1, #(CACHE_DENTRIES - 1) << 26 @ 64 entries
0112 2: mcr p15, 0, r3, c7, c14, 2 @ clean/flush D index
0113 subs r3, r3, #1 << 26
0114 bcs 2b @ entries 63 to 0
0115 subs r1, r1, #1 << 4
0116 bcs 1b @ segments 3 to 0
0117 #endif
0118 tst r2, #VM_EXEC
0119 mcrne p15, 0, ip, c7, c5, 0 @ invalidate I cache
0120 mcrne p15, 0, ip, c7, c10, 4 @ drain WB
0121 ret lr
0122
0123
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133 ENTRY(arm940_coherent_kern_range)
0134
0135
0136
0137
0138
0139
0140
0141
0142
0143
0144
0145
0146 ENTRY(arm940_coherent_user_range)
0147
0148
0149
0150
0151
0152
0153
0154
0155
0156
0157
0158 ENTRY(arm940_flush_kern_dcache_area)
0159 mov r0, #0
0160 mov r1, #(CACHE_DSEGMENTS - 1) << 4 @ 4 segments
0161 1: orr r3, r1, #(CACHE_DENTRIES - 1) << 26 @ 64 entries
0162 2: mcr p15, 0, r3, c7, c14, 2 @ clean/flush D index
0163 subs r3, r3, #1 << 26
0164 bcs 2b @ entries 63 to 0
0165 subs r1, r1, #1 << 4
0166 bcs 1b @ segments 7 to 0
0167 mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
0168 mcr p15, 0, r0, c7, c10, 4 @ drain WB
0169 ret lr
0170
0171
0172
0173
0174
0175
0176
0177
0178
0179
0180 arm940_dma_inv_range:
0181 mov ip, #0
0182 mov r1, #(CACHE_DSEGMENTS - 1) << 4 @ 4 segments
0183 1: orr r3, r1, #(CACHE_DENTRIES - 1) << 26 @ 64 entries
0184 2: mcr p15, 0, r3, c7, c6, 2 @ flush D entry
0185 subs r3, r3, #1 << 26
0186 bcs 2b @ entries 63 to 0
0187 subs r1, r1, #1 << 4
0188 bcs 1b @ segments 7 to 0
0189 mcr p15, 0, ip, c7, c10, 4 @ drain WB
0190 ret lr
0191
0192
0193
0194
0195
0196
0197
0198
0199
0200
0201 arm940_dma_clean_range:
0202 ENTRY(cpu_arm940_dcache_clean_area)
0203 mov ip, #0
0204 #ifndef CONFIG_CPU_DCACHE_WRITETHROUGH
0205 mov r1, #(CACHE_DSEGMENTS - 1) << 4 @ 4 segments
0206 1: orr r3, r1, #(CACHE_DENTRIES - 1) << 26 @ 64 entries
0207 2: mcr p15, 0, r3, c7, c10, 2 @ clean D entry
0208 subs r3, r3, #1 << 26
0209 bcs 2b @ entries 63 to 0
0210 subs r1, r1, #1 << 4
0211 bcs 1b @ segments 7 to 0
0212 #endif
0213 mcr p15, 0, ip, c7, c10, 4 @ drain WB
0214 ret lr
0215
0216
0217
0218
0219
0220
0221
0222
0223
0224
0225 ENTRY(arm940_dma_flush_range)
0226 mov ip, #0
0227 mov r1, #(CACHE_DSEGMENTS - 1) << 4 @ 4 segments
0228 1: orr r3, r1, #(CACHE_DENTRIES - 1) << 26 @ 64 entries
0229 2:
0230 #ifndef CONFIG_CPU_DCACHE_WRITETHROUGH
0231 mcr p15, 0, r3, c7, c14, 2 @ clean/flush D entry
0232 #else
0233 mcr p15, 0, r3, c7, c6, 2 @ invalidate D entry
0234 #endif
0235 subs r3, r3, #1 << 26
0236 bcs 2b @ entries 63 to 0
0237 subs r1, r1, #1 << 4
0238 bcs 1b @ segments 7 to 0
0239 mcr p15, 0, ip, c7, c10, 4 @ drain WB
0240 ret lr
0241
0242
0243
0244
0245
0246
0247
0248 ENTRY(arm940_dma_map_area)
0249 add r1, r1, r0
0250 cmp r2, #DMA_TO_DEVICE
0251 beq arm940_dma_clean_range
0252 bcs arm940_dma_inv_range
0253 b arm940_dma_flush_range
0254 ENDPROC(arm940_dma_map_area)
0255
0256
0257
0258
0259
0260
0261
0262 ENTRY(arm940_dma_unmap_area)
0263 ret lr
0264 ENDPROC(arm940_dma_unmap_area)
0265
0266 .globl arm940_flush_kern_cache_louis
0267 .equ arm940_flush_kern_cache_louis, arm940_flush_kern_cache_all
0268
0269 @ define struct cpu_cache_fns (see <asm/cacheflush.h> and proc-macros.S)
0270 define_cache_functions arm940
0271
0272 .type __arm940_setup, #function
0273 __arm940_setup:
0274 mov r0, #0
0275 mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
0276 mcr p15, 0, r0, c7, c6, 0 @ invalidate D cache
0277 mcr p15, 0, r0, c7, c10, 4 @ drain WB
0278
0279 mcr p15, 0, r0, c6, c3, 0 @ disable data area 3~7
0280 mcr p15, 0, r0, c6, c4, 0
0281 mcr p15, 0, r0, c6, c5, 0
0282 mcr p15, 0, r0, c6, c6, 0
0283 mcr p15, 0, r0, c6, c7, 0
0284
0285 mcr p15, 0, r0, c6, c3, 1 @ disable instruction area 3~7
0286 mcr p15, 0, r0, c6, c4, 1
0287 mcr p15, 0, r0, c6, c5, 1
0288 mcr p15, 0, r0, c6, c6, 1
0289 mcr p15, 0, r0, c6, c7, 1
0290
0291 mov r0, #0x0000003F @ base = 0, size = 4GB
0292 mcr p15, 0, r0, c6, c0, 0 @ set area 0, default
0293 mcr p15, 0, r0, c6, c0, 1
0294
0295 ldr r0, =(CONFIG_DRAM_BASE & 0xFFFFF000) @ base[31:12] of RAM
0296 ldr r7, =CONFIG_DRAM_SIZE >> 12 @ size of RAM (must be >= 4KB)
0297 pr_val r3, r0, r7, #1
0298 mcr p15, 0, r3, c6, c1, 0 @ set area 1, RAM
0299 mcr p15, 0, r3, c6, c1, 1
0300
0301 ldr r0, =(CONFIG_FLASH_MEM_BASE & 0xFFFFF000) @ base[31:12] of FLASH
0302 ldr r7, =CONFIG_FLASH_SIZE @ size of FLASH (must be >= 4KB)
0303 pr_val r3, r0, r6, #1
0304 mcr p15, 0, r3, c6, c2, 0 @ set area 2, ROM/FLASH
0305 mcr p15, 0, r3, c6, c2, 1
0306
0307 mov r0, #0x06
0308 mcr p15, 0, r0, c2, c0, 0 @ Region 1&2 cacheable
0309 mcr p15, 0, r0, c2, c0, 1
0310 #ifdef CONFIG_CPU_DCACHE_WRITETHROUGH
0311 mov r0, #0x00 @ disable whole write buffer
0312 #else
0313 mov r0, #0x02 @ Region 1 write bufferred
0314 #endif
0315 mcr p15, 0, r0, c3, c0, 0
0316
0317 mov r0, #0x10000
0318 sub r0, r0, #1 @ r0 = 0xffff
0319 mcr p15, 0, r0, c5, c0, 0 @ all read/write access
0320 mcr p15, 0, r0, c5, c0, 1
0321
0322 mrc p15, 0, r0, c1, c0 @ get control register
0323 orr r0, r0, #0x00001000 @ I-cache
0324 orr r0, r0, #0x00000005 @ MPU/D-cache
0325
0326 ret lr
0327
0328 .size __arm940_setup, . - __arm940_setup
0329
0330 __INITDATA
0331
0332 @ define struct processor (see <asm/proc-fns.h> and proc-macros.S)
0333 define_processor_functions arm940, dabort=nommu_early_abort, pabort=legacy_pabort, nommu=1
0334
0335 .section ".rodata"
0336
0337 string cpu_arch_name, "armv4t"
0338 string cpu_elf_name, "v4"
0339 string cpu_arm940_name, "ARM940T"
0340
0341 .align
0342
0343 .section ".proc.info.init", "a"
0344
0345 .type __arm940_proc_info,#object
0346 __arm940_proc_info:
0347 .long 0x41009400
0348 .long 0xff00fff0
0349 .long 0
0350 initfn __arm940_setup, __arm940_proc_info
0351 .long cpu_arch_name
0352 .long cpu_elf_name
0353 .long HWCAP_SWP | HWCAP_HALF | HWCAP_THUMB
0354 .long cpu_arm940_name
0355 .long arm940_processor_functions
0356 .long 0
0357 .long 0
0358 .long arm940_cache_fns
0359 .size __arm940_proc_info, . - __arm940_proc_info
0360