summaryrefslogtreecommitdiff
path: root/firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c
diff options
context:
space:
mode:
Diffstat (limited to 'firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c')
-rw-r--r--firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c84
1 files changed, 84 insertions, 0 deletions
diff --git a/firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c b/firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c
new file mode 100644
index 0000000000..05b206c8ea
--- /dev/null
+++ b/firmware/target/arm/gigabeat/meg-fx/mmu-meg-fx.c
@@ -0,0 +1,84 @@
1#include <string.h>
2#include "s3c2440.h"
3
4void map_memory(void);
5static void enable_mmu(void);
6static void set_ttb(void);
7static void set_page_tables(void);
8static void map_section(unsigned int pa, unsigned int va, int mb, int cache_flags);
9
10#define SECTION_ADDRESS_MASK (-1 << 20)
11#define CACHE_ALL (1 << 3 | 1 << 2 )
12#define CACHE_NONE 0
13#define BUFFERED (1 << 2)
14#define MB (1 << 20)
15
16void map_memory(void) {
17 set_ttb();
18 set_page_tables();
19 enable_mmu();
20}
21
22unsigned int* ttb_base;
23const int ttb_size = 4096;
24
25void set_ttb() {
26 int i;
27 int* ttbPtr;
28 int domain_access;
29
30 /* must be 16Kb (0x4000) aligned */
31 ttb_base = (int*)0x31F00000;
32 for (i=0; i<ttb_size; i++,ttbPtr++)
33 ttbPtr = 0;
34 asm volatile("mcr p15, 0, %0, c2, c0, 0" : : "r" (ttb_base));
35
36 /* set domain D0 to "client" permission access */
37
38 domain_access = 3;
39 asm volatile("mcr p15, 0, %0, c3, c0, 0" : : "r" (domain_access));
40
41}
42
43void set_page_tables() {
44
45 map_section(0, 0, 0x1000, CACHE_NONE);
46
47 map_section(0x30000000, 0, 32, CACHE_NONE); /* map RAM to 0 */
48
49 map_section(0x30000000, 0, 30, CACHE_ALL); /* cache the first 30 MB or RAM */
50 map_section(0x31E00000, 0x31E00000, 1, BUFFERED); /* enable buffered writing for the framebuffer */
51}
52
53void map_section(unsigned int pa, unsigned int va, int mb, int cache_flags) {
54 unsigned int* ttbPtr;
55 int i;
56 int section_no;
57
58 section_no = va >> 20; /* sections are 1Mb size */
59 ttbPtr = ttb_base + section_no;
60 pa &= SECTION_ADDRESS_MASK; /* align to 1Mb */
61 for(i=0; i<mb; i++, pa += MB) {
62 *(ttbPtr + i) =
63 pa |
64 1 << 10 | /* superuser - r/w, user - no access */
65 0 << 5 | /* domain 0th */
66 1 << 4 | /* should be "1" */
67 cache_flags |
68 1 << 1; /* Section signature */
69 }
70}
71
72static void enable_mmu(void) {
73 asm volatile("mov r0, #0\n"
74 "mcr p15, 0, r0, c8, c7, 0\n" /* invalidate TLB */
75
76 "mcr p15, 0, r0, c7, c7,0\n" /* invalidate both icache and dcache */
77
78 "mrc p15, 0, r0, c1, c0, 0\n"
79 "orr r0, r0, #1<<0\n" /* enable mmu bit, icache and dcache */
80 "orr r0, r0, #1<<2\n" /* enable dcache */
81 "orr r0, r0, #1<<12\n" /* enable icache */
82 "mcr p15, 0, r0, c1, c0, 0" : : : "r0");
83 asm volatile("nop \n nop \n nop \n nop");
84}