aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mm
diff options
context:
space:
mode:
authorRussell King <rmk@dyn-67.arm.linux.org.uk>2009-03-26 19:10:11 -0400
committerRussell King <rmk+kernel@arm.linux.org.uk>2009-03-26 19:10:11 -0400
commit542f869f1826f092606efd0c4c771f070d1314f5 (patch)
tree9c9d265ab0c87ea7862ccb70933f33d3d7011334 /arch/arm/mm
parente8b374bb6c888a70530d800c9e2fcd153e2c325d (diff)
parent839e642f3dda44a35c6a91780bff41d84c288022 (diff)
Merge branch 'for-rmk' of git://gitorious.org/linux-gemini/mainline into devel
Conflicts: arch/arm/mm/Kconfig Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'arch/arm/mm')
-rw-r--r--arch/arm/mm/Kconfig35
-rw-r--r--arch/arm/mm/Makefile4
-rw-r--r--arch/arm/mm/cache-fa.S220
-rw-r--r--arch/arm/mm/copypage-fa.c86
-rw-r--r--arch/arm/mm/proc-fa526.S248
-rw-r--r--arch/arm/mm/tlb-fa.S75
6 files changed, 666 insertions, 2 deletions
diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig
index a6230f7a24c..20979564e7e 100644
--- a/arch/arm/mm/Kconfig
+++ b/arch/arm/mm/Kconfig
@@ -186,6 +186,24 @@ config CPU_ARM926T
186 Say Y if you want support for the ARM926T processor. 186 Say Y if you want support for the ARM926T processor.
187 Otherwise, say N. 187 Otherwise, say N.
188 188
189# FA526
190config CPU_FA526
191 bool
192 select CPU_32v4
193 select CPU_ABRT_EV4
194 select CPU_PABRT_NOIFAR
195 select CPU_CACHE_VIVT
196 select CPU_CP15_MMU
197 select CPU_CACHE_FA
198 select CPU_COPY_FA if MMU
199 select CPU_TLB_FA if MMU
200 help
201 The FA526 is a version of the ARMv4 compatible processor with
202 Branch Target Buffer, Unified TLB and cache line size 16.
203
204 Say Y if you want support for the FA526 processor.
205 Otherwise, say N.
206
189# ARM940T 207# ARM940T
190config CPU_ARM940T 208config CPU_ARM940T
191 bool "Support ARM940T processor" if ARCH_INTEGRATOR 209 bool "Support ARM940T processor" if ARCH_INTEGRATOR
@@ -495,6 +513,9 @@ config CPU_CACHE_VIVT
495config CPU_CACHE_VIPT 513config CPU_CACHE_VIPT
496 bool 514 bool
497 515
516config CPU_CACHE_FA
517 bool
518
498if MMU 519if MMU
499# The copy-page model 520# The copy-page model
500config CPU_COPY_V3 521config CPU_COPY_V3
@@ -509,6 +530,9 @@ config CPU_COPY_V4WB
509config CPU_COPY_FEROCEON 530config CPU_COPY_FEROCEON
510 bool 531 bool
511 532
533config CPU_COPY_FA
534 bool
535
512config CPU_COPY_V6 536config CPU_COPY_V6
513 bool 537 bool
514 538
@@ -539,6 +563,13 @@ config CPU_TLB_FEROCEON
539 help 563 help
540 Feroceon TLB (v4wbi with non-outer-cachable page table walks). 564 Feroceon TLB (v4wbi with non-outer-cachable page table walks).
541 565
566config CPU_TLB_FA
567 bool
568 help
569 Faraday ARM FA526 architecture, unified TLB with writeback cache
570 and invalidate instruction cache entry. Branch target buffer is
571 also supported.
572
542config CPU_TLB_V6 573config CPU_TLB_V6
543 bool 574 bool
544 575
@@ -649,7 +680,7 @@ config CPU_DCACHE_SIZE
649 680
650config CPU_DCACHE_WRITETHROUGH 681config CPU_DCACHE_WRITETHROUGH
651 bool "Force write through D-cache" 682 bool "Force write through D-cache"
652 depends on (CPU_ARM740T || CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM940T || CPU_ARM946E || CPU_ARM1020) && !CPU_DCACHE_DISABLE 683 depends on (CPU_ARM740T || CPU_ARM920T || CPU_ARM922T || CPU_ARM925T || CPU_ARM926T || CPU_ARM940T || CPU_ARM946E || CPU_ARM1020 || CPU_FA526) && !CPU_DCACHE_DISABLE
653 default y if CPU_ARM925T 684 default y if CPU_ARM925T
654 help 685 help
655 Say Y here to use the data cache in writethrough mode. Unless you 686 Say Y here to use the data cache in writethrough mode. Unless you
@@ -664,7 +695,7 @@ config CPU_CACHE_ROUND_ROBIN
664 695
665config CPU_BPREDICT_DISABLE 696config CPU_BPREDICT_DISABLE
666 bool "Disable branch prediction" 697 bool "Disable branch prediction"
667 depends on CPU_ARM1020 || CPU_V6 || CPU_MOHAWK || CPU_XSC3 || CPU_V7 698 depends on CPU_ARM1020 || CPU_V6 || CPU_MOHAWK || CPU_XSC3 || CPU_V7 || CPU_FA526
668 help 699 help
669 Say Y here to disable branch prediction. If unsure, say N. 700 Say Y here to disable branch prediction. If unsure, say N.
670 701
diff --git a/arch/arm/mm/Makefile b/arch/arm/mm/Makefile
index c264683538b..63e3f6dd0e2 100644
--- a/arch/arm/mm/Makefile
+++ b/arch/arm/mm/Makefile
@@ -33,6 +33,7 @@ obj-$(CONFIG_CPU_CACHE_V4WT) += cache-v4wt.o
33obj-$(CONFIG_CPU_CACHE_V4WB) += cache-v4wb.o 33obj-$(CONFIG_CPU_CACHE_V4WB) += cache-v4wb.o
34obj-$(CONFIG_CPU_CACHE_V6) += cache-v6.o 34obj-$(CONFIG_CPU_CACHE_V6) += cache-v6.o
35obj-$(CONFIG_CPU_CACHE_V7) += cache-v7.o 35obj-$(CONFIG_CPU_CACHE_V7) += cache-v7.o
36obj-$(CONFIG_CPU_CACHE_FA) += cache-fa.o
36 37
37obj-$(CONFIG_CPU_COPY_V3) += copypage-v3.o 38obj-$(CONFIG_CPU_COPY_V3) += copypage-v3.o
38obj-$(CONFIG_CPU_COPY_V4WT) += copypage-v4wt.o 39obj-$(CONFIG_CPU_COPY_V4WT) += copypage-v4wt.o
@@ -42,6 +43,7 @@ obj-$(CONFIG_CPU_COPY_V6) += copypage-v6.o context.o
42obj-$(CONFIG_CPU_SA1100) += copypage-v4mc.o 43obj-$(CONFIG_CPU_SA1100) += copypage-v4mc.o
43obj-$(CONFIG_CPU_XSCALE) += copypage-xscale.o 44obj-$(CONFIG_CPU_XSCALE) += copypage-xscale.o
44obj-$(CONFIG_CPU_XSC3) += copypage-xsc3.o 45obj-$(CONFIG_CPU_XSC3) += copypage-xsc3.o
46obj-$(CONFIG_CPU_COPY_FA) += copypage-fa.o
45 47
46obj-$(CONFIG_CPU_TLB_V3) += tlb-v3.o 48obj-$(CONFIG_CPU_TLB_V3) += tlb-v3.o
47obj-$(CONFIG_CPU_TLB_V4WT) += tlb-v4.o 49obj-$(CONFIG_CPU_TLB_V4WT) += tlb-v4.o
@@ -50,6 +52,7 @@ obj-$(CONFIG_CPU_TLB_V4WBI) += tlb-v4wbi.o
50obj-$(CONFIG_CPU_TLB_FEROCEON) += tlb-v4wbi.o # reuse v4wbi TLB functions 52obj-$(CONFIG_CPU_TLB_FEROCEON) += tlb-v4wbi.o # reuse v4wbi TLB functions
51obj-$(CONFIG_CPU_TLB_V6) += tlb-v6.o 53obj-$(CONFIG_CPU_TLB_V6) += tlb-v6.o
52obj-$(CONFIG_CPU_TLB_V7) += tlb-v7.o 54obj-$(CONFIG_CPU_TLB_V7) += tlb-v7.o
55obj-$(CONFIG_CPU_TLB_FA) += tlb-fa.o
53 56
54obj-$(CONFIG_CPU_ARM610) += proc-arm6_7.o 57obj-$(CONFIG_CPU_ARM610) += proc-arm6_7.o
55obj-$(CONFIG_CPU_ARM710) += proc-arm6_7.o 58obj-$(CONFIG_CPU_ARM710) += proc-arm6_7.o
@@ -63,6 +66,7 @@ obj-$(CONFIG_CPU_ARM925T) += proc-arm925.o
63obj-$(CONFIG_CPU_ARM926T) += proc-arm926.o 66obj-$(CONFIG_CPU_ARM926T) += proc-arm926.o
64obj-$(CONFIG_CPU_ARM940T) += proc-arm940.o 67obj-$(CONFIG_CPU_ARM940T) += proc-arm940.o
65obj-$(CONFIG_CPU_ARM946E) += proc-arm946.o 68obj-$(CONFIG_CPU_ARM946E) += proc-arm946.o
69obj-$(CONFIG_CPU_FA526) += proc-fa526.o
66obj-$(CONFIG_CPU_ARM1020) += proc-arm1020.o 70obj-$(CONFIG_CPU_ARM1020) += proc-arm1020.o
67obj-$(CONFIG_CPU_ARM1020E) += proc-arm1020e.o 71obj-$(CONFIG_CPU_ARM1020E) += proc-arm1020e.o
68obj-$(CONFIG_CPU_ARM1022) += proc-arm1022.o 72obj-$(CONFIG_CPU_ARM1022) += proc-arm1022.o
diff --git a/arch/arm/mm/cache-fa.S b/arch/arm/mm/cache-fa.S
new file mode 100644
index 00000000000..b63a8f7b95c
--- /dev/null
+++ b/arch/arm/mm/cache-fa.S
@@ -0,0 +1,220 @@
1/*
2 * linux/arch/arm/mm/cache-fa.S
3 *
4 * Copyright (C) 2005 Faraday Corp.
5 * Copyright (C) 2008-2009 Paulius Zaleckas <paulius.zaleckas@teltonika.lt>
6 *
7 * Based on cache-v4wb.S:
8 * Copyright (C) 1997-2002 Russell king
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2 as
12 * published by the Free Software Foundation.
13 *
14 * Processors: FA520 FA526 FA626
15 */
16#include <linux/linkage.h>
17#include <linux/init.h>
18#include <asm/memory.h>
19#include <asm/page.h>
20
21#include "proc-macros.S"
22
23/*
24 * The size of one data cache line.
25 */
26#define CACHE_DLINESIZE 16
27
28/*
29 * The total size of the data cache.
30 */
31#ifdef CONFIG_ARCH_GEMINI
32#define CACHE_DSIZE 8192
33#else
34#define CACHE_DSIZE 16384
35#endif
36
37/* FIXME: put optimal value here. Current one is just estimation */
38#define CACHE_DLIMIT (CACHE_DSIZE * 2)
39
40/*
41 * flush_user_cache_all()
42 *
43 * Clean and invalidate all cache entries in a particular address
44 * space.
45 */
46ENTRY(fa_flush_user_cache_all)
47 /* FALLTHROUGH */
48/*
49 * flush_kern_cache_all()
50 *
51 * Clean and invalidate the entire cache.
52 */
53ENTRY(fa_flush_kern_cache_all)
54 mov ip, #0
55 mov r2, #VM_EXEC
56__flush_whole_cache:
57 mcr p15, 0, ip, c7, c14, 0 @ clean/invalidate D cache
58 tst r2, #VM_EXEC
59 mcrne p15, 0, ip, c7, c5, 0 @ invalidate I cache
60 mcrne p15, 0, ip, c7, c5, 6 @ invalidate BTB
61 mcrne p15, 0, ip, c7, c10, 4 @ drain write buffer
62 mcrne p15, 0, ip, c7, c5, 4 @ prefetch flush
63 mov pc, lr
64
65/*
66 * flush_user_cache_range(start, end, flags)
67 *
68 * Invalidate a range of cache entries in the specified
69 * address space.
70 *
71 * - start - start address (inclusive, page aligned)
72 * - end - end address (exclusive, page aligned)
73 * - flags - vma_area_struct flags describing address space
74 */
75ENTRY(fa_flush_user_cache_range)
76 mov ip, #0
77 sub r3, r1, r0 @ calculate total size
78 cmp r3, #CACHE_DLIMIT @ total size >= limit?
79 bhs __flush_whole_cache @ flush whole D cache
80
811: tst r2, #VM_EXEC
82 mcrne p15, 0, r0, c7, c5, 1 @ invalidate I line
83 mcr p15, 0, r0, c7, c14, 1 @ clean and invalidate D entry
84 add r0, r0, #CACHE_DLINESIZE
85 cmp r0, r1
86 blo 1b
87 tst r2, #VM_EXEC
88 mcrne p15, 0, ip, c7, c5, 6 @ invalidate BTB
89 mcrne p15, 0, ip, c7, c10, 4 @ data write barrier
90 mcrne p15, 0, ip, c7, c5, 4 @ prefetch flush
91 mov pc, lr
92
93/*
94 * coherent_kern_range(start, end)
95 *
96 * Ensure coherency between the Icache and the Dcache in the
97 * region described by start. If you have non-snooping
98 * Harvard caches, you need to implement this function.
99 *
100 * - start - virtual start address
101 * - end - virtual end address
102 */
103ENTRY(fa_coherent_kern_range)
104 /* fall through */
105
106/*
107 * coherent_user_range(start, end)
108 *
109 * Ensure coherency between the Icache and the Dcache in the
110 * region described by start. If you have non-snooping
111 * Harvard caches, you need to implement this function.
112 *
113 * - start - virtual start address
114 * - end - virtual end address
115 */
116ENTRY(fa_coherent_user_range)
117 bic r0, r0, #CACHE_DLINESIZE - 1
1181: mcr p15, 0, r0, c7, c14, 1 @ clean and invalidate D entry
119 mcr p15, 0, r0, c7, c5, 1 @ invalidate I entry
120 add r0, r0, #CACHE_DLINESIZE
121 cmp r0, r1
122 blo 1b
123 mov r0, #0
124 mcr p15, 0, r0, c7, c5, 6 @ invalidate BTB
125 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
126 mcr p15, 0, r0, c7, c5, 4 @ prefetch flush
127 mov pc, lr
128
129/*
130 * flush_kern_dcache_page(kaddr)
131 *
132 * Ensure that the data held in the page kaddr is written back
133 * to the page in question.
134 *
135 * - kaddr - kernel address (guaranteed to be page aligned)
136 */
137ENTRY(fa_flush_kern_dcache_page)
138 add r1, r0, #PAGE_SZ
1391: mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D line
140 add r0, r0, #CACHE_DLINESIZE
141 cmp r0, r1
142 blo 1b
143 mov r0, #0
144 mcr p15, 0, r0, c7, c5, 0 @ invalidate I cache
145 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
146 mov pc, lr
147
148/*
149 * dma_inv_range(start, end)
150 *
151 * Invalidate (discard) the specified virtual address range.
152 * May not write back any entries. If 'start' or 'end'
153 * are not cache line aligned, those lines must be written
154 * back.
155 *
156 * - start - virtual start address
157 * - end - virtual end address
158 */
159ENTRY(fa_dma_inv_range)
160 tst r0, #CACHE_DLINESIZE - 1
161 bic r0, r0, #CACHE_DLINESIZE - 1
162 mcrne p15, 0, r0, c7, c14, 1 @ clean & invalidate D entry
163 tst r1, #CACHE_DLINESIZE - 1
164 bic r1, r1, #CACHE_DLINESIZE - 1
165 mcrne p15, 0, r1, c7, c14, 1 @ clean & invalidate D entry
1661: mcr p15, 0, r0, c7, c6, 1 @ invalidate D entry
167 add r0, r0, #CACHE_DLINESIZE
168 cmp r0, r1
169 blo 1b
170 mov r0, #0
171 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
172 mov pc, lr
173
174/*
175 * dma_clean_range(start, end)
176 *
177 * Clean (write back) the specified virtual address range.
178 *
179 * - start - virtual start address
180 * - end - virtual end address
181 */
182ENTRY(fa_dma_clean_range)
183 bic r0, r0, #CACHE_DLINESIZE - 1
1841: mcr p15, 0, r0, c7, c10, 1 @ clean D entry
185 add r0, r0, #CACHE_DLINESIZE
186 cmp r0, r1
187 blo 1b
188 mov r0, #0
189 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
190 mov pc, lr
191
192/*
193 * dma_flush_range(start,end)
194 * - start - virtual start address of region
195 * - end - virtual end address of region
196 */
197ENTRY(fa_dma_flush_range)
198 bic r0, r0, #CACHE_DLINESIZE - 1
1991: mcr p15, 0, r0, c7, c14, 1 @ clean & invalidate D entry
200 add r0, r0, #CACHE_DLINESIZE
201 cmp r0, r1
202 blo 1b
203 mov r0, #0
204 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
205 mov pc, lr
206
207 __INITDATA
208
209 .type fa_cache_fns, #object
210ENTRY(fa_cache_fns)
211 .long fa_flush_kern_cache_all
212 .long fa_flush_user_cache_all
213 .long fa_flush_user_cache_range
214 .long fa_coherent_kern_range
215 .long fa_coherent_user_range
216 .long fa_flush_kern_dcache_page
217 .long fa_dma_inv_range
218 .long fa_dma_clean_range
219 .long fa_dma_flush_range
220 .size fa_cache_fns, . - fa_cache_fns
diff --git a/arch/arm/mm/copypage-fa.c b/arch/arm/mm/copypage-fa.c
new file mode 100644
index 00000000000..b2a6008b011
--- /dev/null
+++ b/arch/arm/mm/copypage-fa.c
@@ -0,0 +1,86 @@
1/*
2 * linux/arch/arm/lib/copypage-fa.S
3 *
4 * Copyright (C) 2005 Faraday Corp.
5 * Copyright (C) 2008-2009 Paulius Zaleckas <paulius.zaleckas@teltonika.lt>
6 *
7 * Based on copypage-v4wb.S:
8 * Copyright (C) 1995-1999 Russell King
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2 as
12 * published by the Free Software Foundation.
13 */
14#include <linux/init.h>
15#include <linux/highmem.h>
16
17/*
18 * Faraday optimised copy_user_page
19 */
20static void __naked
21fa_copy_user_page(void *kto, const void *kfrom)
22{
23 asm("\
24 stmfd sp!, {r4, lr} @ 2\n\
25 mov r2, %0 @ 1\n\
261: ldmia r1!, {r3, r4, ip, lr} @ 4\n\
27 stmia r0, {r3, r4, ip, lr} @ 4\n\
28 mcr p15, 0, r0, c7, c14, 1 @ 1 clean and invalidate D line\n\
29 add r0, r0, #16 @ 1\n\
30 ldmia r1!, {r3, r4, ip, lr} @ 4\n\
31 stmia r0, {r3, r4, ip, lr} @ 4\n\
32 mcr p15, 0, r0, c7, c14, 1 @ 1 clean and invalidate D line\n\
33 add r0, r0, #16 @ 1\n\
34 subs r2, r2, #1 @ 1\n\
35 bne 1b @ 1\n\
36 mcr p15, 0, r2, c7, c10, 4 @ 1 drain WB\n\
37 ldmfd sp!, {r4, pc} @ 3"
38 :
39 : "I" (PAGE_SIZE / 32));
40}
41
42void fa_copy_user_highpage(struct page *to, struct page *from,
43 unsigned long vaddr)
44{
45 void *kto, *kfrom;
46
47 kto = kmap_atomic(to, KM_USER0);
48 kfrom = kmap_atomic(from, KM_USER1);
49 fa_copy_user_page(kto, kfrom);
50 kunmap_atomic(kfrom, KM_USER1);
51 kunmap_atomic(kto, KM_USER0);
52}
53
54/*
55 * Faraday optimised clear_user_page
56 *
57 * Same story as above.
58 */
59void fa_clear_user_highpage(struct page *page, unsigned long vaddr)
60{
61 void *ptr, *kaddr = kmap_atomic(page, KM_USER0);
62 asm volatile("\
63 mov r1, %2 @ 1\n\
64 mov r2, #0 @ 1\n\
65 mov r3, #0 @ 1\n\
66 mov ip, #0 @ 1\n\
67 mov lr, #0 @ 1\n\
681: stmia %0, {r2, r3, ip, lr} @ 4\n\
69 mcr p15, 0, %0, c7, c14, 1 @ 1 clean and invalidate D line\n\
70 add %0, %0, #16 @ 1\n\
71 stmia %0, {r2, r3, ip, lr} @ 4\n\
72 mcr p15, 0, %0, c7, c14, 1 @ 1 clean and invalidate D line\n\
73 add %0, %0, #16 @ 1\n\
74 subs r1, r1, #1 @ 1\n\
75 bne 1b @ 1\n\
76 mcr p15, 0, r1, c7, c10, 4 @ 1 drain WB"
77 : "=r" (ptr)
78 : "0" (kaddr), "I" (PAGE_SIZE / 32)
79 : "r1", "r2", "r3", "ip", "lr");
80 kunmap_atomic(kaddr, KM_USER0);
81}
82
83struct cpu_user_fns fa_user_fns __initdata = {
84 .cpu_clear_user_highpage = fa_clear_user_highpage,
85 .cpu_copy_user_highpage = fa_copy_user_highpage,
86};
diff --git a/arch/arm/mm/proc-fa526.S b/arch/arm/mm/proc-fa526.S
new file mode 100644
index 00000000000..08b8a955d5d
--- /dev/null
+++ b/arch/arm/mm/proc-fa526.S
@@ -0,0 +1,248 @@
1/*
2 * linux/arch/arm/mm/proc-fa526.S: MMU functions for FA526
3 *
4 * Written by : Luke Lee
5 * Copyright (C) 2005 Faraday Corp.
6 * Copyright (C) 2008-2009 Paulius Zaleckas <paulius.zaleckas@teltonika.lt>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 *
14 * These are the low level assembler for performing cache and TLB
15 * functions on the fa526.
16 */
17#include <linux/linkage.h>
18#include <linux/init.h>
19#include <asm/assembler.h>
20#include <asm/hwcap.h>
21#include <asm/pgtable-hwdef.h>
22#include <asm/pgtable.h>
23#include <asm/page.h>
24#include <asm/ptrace.h>
25#include <asm/system.h>
26
27#include "proc-macros.S"
28
29#define CACHE_DLINESIZE 16
30
31 .text
32/*
33 * cpu_fa526_proc_init()
34 */
35ENTRY(cpu_fa526_proc_init)
36 mov pc, lr
37
38/*
39 * cpu_fa526_proc_fin()
40 */
41ENTRY(cpu_fa526_proc_fin)
42 stmfd sp!, {lr}
43 mov ip, #PSR_F_BIT | PSR_I_BIT | SVC_MODE
44 msr cpsr_c, ip
45 bl fa_flush_kern_cache_all
46 mrc p15, 0, r0, c1, c0, 0 @ ctrl register
47 bic r0, r0, #0x1000 @ ...i............
48 bic r0, r0, #0x000e @ ............wca.
49 mcr p15, 0, r0, c1, c0, 0 @ disable caches
50 nop
51 nop
52 ldmfd sp!, {pc}
53
54/*
55 * cpu_fa526_reset(loc)
56 *
57 * Perform a soft reset of the system. Put the CPU into the
58 * same state as it would be if it had been reset, and branch
59 * to what would be the reset vector.
60 *
61 * loc: location to jump to for soft reset
62 */
63 .align 4
64ENTRY(cpu_fa526_reset)
65/* TODO: Use CP8 if possible... */
66 mov ip, #0
67 mcr p15, 0, ip, c7, c7, 0 @ invalidate I,D caches
68 mcr p15, 0, ip, c7, c10, 4 @ drain WB
69#ifdef CONFIG_MMU
70 mcr p15, 0, ip, c8, c7, 0 @ invalidate I & D TLBs
71#endif
72 mrc p15, 0, ip, c1, c0, 0 @ ctrl register
73 bic ip, ip, #0x000f @ ............wcam
74 bic ip, ip, #0x1100 @ ...i...s........
75 bic ip, ip, #0x0800 @ BTB off
76 mcr p15, 0, ip, c1, c0, 0 @ ctrl register
77 nop
78 nop
79 mov pc, r0
80
81/*
82 * cpu_fa526_do_idle()
83 */
84 .align 4
85ENTRY(cpu_fa526_do_idle)
86 mcr p15, 0, r0, c7, c0, 4 @ Wait for interrupt
87 mov pc, lr
88
89
90ENTRY(cpu_fa526_dcache_clean_area)
911: mcr p15, 0, r0, c7, c10, 1 @ clean D entry
92 add r0, r0, #CACHE_DLINESIZE
93 subs r1, r1, #CACHE_DLINESIZE
94 bhi 1b
95 mcr p15, 0, r0, c7, c10, 4 @ drain WB
96 mov pc, lr
97
98/* =============================== PageTable ============================== */
99
100/*
101 * cpu_fa526_switch_mm(pgd)
102 *
103 * Set the translation base pointer to be as described by pgd.
104 *
105 * pgd: new page tables
106 */
107 .align 4
108ENTRY(cpu_fa526_switch_mm)
109#ifdef CONFIG_MMU
110 mov ip, #0
111#ifdef CONFIG_CPU_DCACHE_WRITETHROUGH
112 mcr p15, 0, ip, c7, c6, 0 @ invalidate D cache
113#else
114 mcr p15, 0, ip, c7, c14, 0 @ clean and invalidate whole D cache
115#endif
116 mcr p15, 0, ip, c7, c5, 0 @ invalidate I cache
117 mcr p15, 0, ip, c7, c5, 6 @ invalidate BTB since mm changed
118 mcr p15, 0, ip, c7, c10, 4 @ data write barrier
119 mcr p15, 0, ip, c7, c5, 4 @ prefetch flush
120 mcr p15, 0, r0, c2, c0, 0 @ load page table pointer
121 mcr p15, 0, ip, c8, c7, 0 @ invalidate UTLB
122#endif
123 mov pc, lr
124
125/*
126 * cpu_fa526_set_pte_ext(ptep, pte, ext)
127 *
128 * Set a PTE and flush it out
129 */
130 .align 4
131ENTRY(cpu_fa526_set_pte_ext)
132#ifdef CONFIG_MMU
133 armv3_set_pte_ext
134 mov r0, r0
135 mcr p15, 0, r0, c7, c10, 1 @ clean D entry
136 mov r0, #0
137 mcr p15, 0, r0, c7, c10, 4 @ drain WB
138#endif
139 mov pc, lr
140
141 __INIT
142
143 .type __fa526_setup, #function
144__fa526_setup:
145 /* On return of this routine, r0 must carry correct flags for CFG register */
146 mov r0, #0
147 mcr p15, 0, r0, c7, c7 @ invalidate I,D caches on v4
148 mcr p15, 0, r0, c7, c10, 4 @ drain write buffer on v4
149#ifdef CONFIG_MMU
150 mcr p15, 0, r0, c8, c7 @ invalidate I,D TLBs on v4
151#endif
152 mcr p15, 0, r0, c7, c5, 5 @ invalidate IScratchpad RAM
153
154 mov r0, #1
155 mcr p15, 0, r0, c1, c1, 0 @ turn-on ECR
156
157 mov r0, #0
158 mcr p15, 0, r0, c7, c5, 6 @ invalidate BTB All
159 mcr p15, 0, r0, c7, c10, 4 @ data write barrier
160 mcr p15, 0, r0, c7, c5, 4 @ prefetch flush
161
162 mov r0, #0x1f @ Domains 0, 1 = manager, 2 = client
163 mcr p15, 0, r0, c3, c0 @ load domain access register
164
165 mrc p15, 0, r0, c1, c0 @ get control register v4
166 ldr r5, fa526_cr1_clear
167 bic r0, r0, r5
168 ldr r5, fa526_cr1_set
169 orr r0, r0, r5
170 mov pc, lr
171 .size __fa526_setup, . - __fa526_setup
172
173 /*
174 * .RVI ZFRS BLDP WCAM
175 * ..11 1001 .111 1101
176 *
177 */
178 .type fa526_cr1_clear, #object
179 .type fa526_cr1_set, #object
180fa526_cr1_clear:
181 .word 0x3f3f
182fa526_cr1_set:
183 .word 0x397D
184
185 __INITDATA
186
187/*
188 * Purpose : Function pointers used to access above functions - all calls
189 * come through these
190 */
191 .type fa526_processor_functions, #object
192fa526_processor_functions:
193 .word v4_early_abort
194 .word pabort_noifar
195 .word cpu_fa526_proc_init
196 .word cpu_fa526_proc_fin
197 .word cpu_fa526_reset
198 .word cpu_fa526_do_idle
199 .word cpu_fa526_dcache_clean_area
200 .word cpu_fa526_switch_mm
201 .word cpu_fa526_set_pte_ext
202 .size fa526_processor_functions, . - fa526_processor_functions
203
204 .section ".rodata"
205
206 .type cpu_arch_name, #object
207cpu_arch_name:
208 .asciz "armv4"
209 .size cpu_arch_name, . - cpu_arch_name
210
211 .type cpu_elf_name, #object
212cpu_elf_name:
213 .asciz "v4"
214 .size cpu_elf_name, . - cpu_elf_name
215
216 .type cpu_fa526_name, #object
217cpu_fa526_name:
218 .asciz "FA526"
219 .size cpu_fa526_name, . - cpu_fa526_name
220
221 .align
222
223 .section ".proc.info.init", #alloc, #execinstr
224
225 .type __fa526_proc_info,#object
226__fa526_proc_info:
227 .long 0x66015261
228 .long 0xff01fff1
229 .long PMD_TYPE_SECT | \
230 PMD_SECT_BUFFERABLE | \
231 PMD_SECT_CACHEABLE | \
232 PMD_BIT4 | \
233 PMD_SECT_AP_WRITE | \
234 PMD_SECT_AP_READ
235 .long PMD_TYPE_SECT | \
236 PMD_BIT4 | \
237 PMD_SECT_AP_WRITE | \
238 PMD_SECT_AP_READ
239 b __fa526_setup
240 .long cpu_arch_name
241 .long cpu_elf_name
242 .long HWCAP_SWP | HWCAP_HALF
243 .long cpu_fa526_name
244 .long fa526_processor_functions
245 .long fa_tlb_fns
246 .long fa_user_fns
247 .long fa_cache_fns
248 .size __fa526_proc_info, . - __fa526_proc_info
diff --git a/arch/arm/mm/tlb-fa.S b/arch/arm/mm/tlb-fa.S
new file mode 100644
index 00000000000..9694f1f6f48
--- /dev/null
+++ b/arch/arm/mm/tlb-fa.S
@@ -0,0 +1,75 @@
1/*
2 * linux/arch/arm/mm/tlb-fa.S
3 *
4 * Copyright (C) 2005 Faraday Corp.
5 * Copyright (C) 2008-2009 Paulius Zaleckas <paulius.zaleckas@teltonika.lt>
6 *
7 * Based on tlb-v4wbi.S:
8 * Copyright (C) 1997-2002 Russell King
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2 as
12 * published by the Free Software Foundation.
13 *
14 * ARM architecture version 4, Faraday variation.
15 * This assume an unified TLBs, with a write buffer, and branch target buffer (BTB)
16 *
17 * Processors: FA520 FA526 FA626
18 */
19#include <linux/linkage.h>
20#include <linux/init.h>
21#include <asm/asm-offsets.h>
22#include <asm/tlbflush.h>
23#include "proc-macros.S"
24
25
26/*
27 * flush_user_tlb_range(start, end, mm)
28 *
29 * Invalidate a range of TLB entries in the specified address space.
30 *
31 * - start - range start address
32 * - end - range end address
33 * - mm - mm_struct describing address space
34 */
35 .align 4
36ENTRY(fa_flush_user_tlb_range)
37 vma_vm_mm ip, r2
38 act_mm r3 @ get current->active_mm
39 eors r3, ip, r3 @ == mm ?
40 movne pc, lr @ no, we dont do anything
41 mov r3, #0
42 mcr p15, 0, r3, c7, c10, 4 @ drain WB
43 bic r0, r0, #0x0ff
44 bic r0, r0, #0xf00
451: mcr p15, 0, r0, c8, c7, 1 @ invalidate UTLB entry
46 add r0, r0, #PAGE_SZ
47 cmp r0, r1
48 blo 1b
49 mcr p15, 0, r3, c7, c5, 6 @ invalidate BTB
50 mcr p15, 0, r3, c7, c10, 4 @ data write barrier
51 mov pc, lr
52
53
54ENTRY(fa_flush_kern_tlb_range)
55 mov r3, #0
56 mcr p15, 0, r3, c7, c10, 4 @ drain WB
57 bic r0, r0, #0x0ff
58 bic r0, r0, #0xf00
591: mcr p15, 0, r0, c8, c7, 1 @ invalidate UTLB entry
60 add r0, r0, #PAGE_SZ
61 cmp r0, r1
62 blo 1b
63 mcr p15, 0, r3, c7, c5, 6 @ invalidate BTB
64 mcr p15, 0, r3, c7, c10, 4 @ data write barrier
65 mcr p15, 0, r3, c7, c5, 4 @ prefetch flush
66 mov pc, lr
67
68 __INITDATA
69
70 .type fa_tlb_fns, #object
71ENTRY(fa_tlb_fns)
72 .long fa_flush_user_tlb_range
73 .long fa_flush_kern_tlb_range
74 .long fa_tlb_flags
75 .size fa_tlb_fns, . - fa_tlb_fns