summaryrefslogtreecommitdiffstats
path: root/arch/arm/mm
diff options
context:
space:
mode:
authorRalf Baechle <ralf@linux-mips.org>2000-02-16 01:07:24 +0000
committerRalf Baechle <ralf@linux-mips.org>2000-02-16 01:07:24 +0000
commit95db6b748fc86297827fbd9c9ef174d491c9ad89 (patch)
tree27a92a942821cde1edda9a1b088718d436b3efe4 /arch/arm/mm
parent45b27b0a0652331d104c953a5b192d843fff88f8 (diff)
Merge with Linux 2.3.40.
Diffstat (limited to 'arch/arm/mm')
-rw-r--r--arch/arm/mm/fault-armv.c184
-rw-r--r--arch/arm/mm/fault-common.c15
-rw-r--r--arch/arm/mm/init.c31
-rw-r--r--arch/arm/mm/mm-armo.c14
-rw-r--r--arch/arm/mm/mm-armv.c139
-rw-r--r--arch/arm/mm/mm-sa1100.c53
-rw-r--r--arch/arm/mm/proc-arm6,7.S14
-rw-r--r--arch/arm/mm/proc-sa110.S17
8 files changed, 239 insertions, 228 deletions
diff --git a/arch/arm/mm/fault-armv.c b/arch/arm/mm/fault-armv.c
index 8715ea271..5151591b8 100644
--- a/arch/arm/mm/fault-armv.c
+++ b/arch/arm/mm/fault-armv.c
@@ -29,6 +29,8 @@
#define DO_COW(m) (!((m) & FAULT_CODE_READ))
#define READ_FAULT(m) ((m) & FAULT_CODE_READ)
+extern void die_if_kernel(const char *str, struct pt_regs *regs, int err);
+
#include "fault-common.c"
#ifdef DEBUG
@@ -118,17 +120,18 @@ static int proc_alignment_read(char *page, char **start, off_t off,
* This needs to be done after sysctl_init, otherwise sys/
* will be overwritten.
*/
-void __init alignment_init(void)
+static int __init alignment_init(void)
{
create_proc_read_entry("sys/debug/alignment", 0, NULL,
- proc_alignment_read);
+ proc_alignment_read, NULL);
+ return 0;
}
__initcall(alignment_init);
#endif /* CONFIG_SYSCTL */
static int
-do_alignment_exception(struct pt_regs *regs)
+do_alignment(unsigned long addr, int error_code, struct pt_regs *regs)
{
unsigned int instr, rd, rn, correction, nr_regs, regbits;
unsigned long eaddr;
@@ -308,116 +311,99 @@ do_alignment_exception(struct pt_regs *regs)
return 0;
}
+#else
+
+#define do_alignment NULL
+
#endif
-#define BUG_PROC_MSG \
- "Buggy processor (%08X), trying to continue.\n" \
- "Please read http://www.arm.linux.org.uk/state.html for more information"
+#ifdef CONFIG_DEBUG_USER
-asmlinkage void
-do_DataAbort(unsigned long addr, int fsr, int error_code, struct pt_regs *regs)
+static int
+do_sect_fault(unsigned long addr, int error_code, struct pt_regs *regs)
{
if (user_mode(regs)) {
- if (addr == regs->ARM_pc) {
- static int first = 1;
- if (first) {
- /*
- * I want statistical information on this problem!
- */
- printk(KERN_ERR BUG_PROC_MSG, fsr);
- first = 0;
+ printk("%s: permission fault on section, "
+ "address=0x%08lx, code %d\n",
+ current->comm, addr, error_code);
+#ifdef DEBUG
+ {
+ unsigned int i, j;
+ unsigned long *sp;
+
+ sp = (unsigned long *) (regs->ARM_sp - 128);
+ for (j = 0; j < 20 && sp_valid(sp); j++) {
+ printk("%p: ", sp);
+ for (i = 0; i < 8 && sp_valid(sp); i += 1, sp++)
+ printk("%08lx ", *sp);
+ printk("\n");
}
- return;
+ show_regs(regs);
+ c_backtrace(regs->ARM_fp, regs->ARM_cpsr);
}
+#endif
}
+ return 1; /* not fixed up */
+}
+#else
-#define DIE(signr,nam)\
- force_sig(signr, current);\
- die(nam, regs, fsr);\
- do_exit(signr);\
- break
-
- switch (fsr & 15) {
- /*
- * 0 - vector exception
- */
- case 0:
- force_sig(SIGSEGV, current);
- if (!user_mode(regs)) {
- die("vector exception", regs, fsr);
- do_exit(SIGSEGV);
- }
- break;
-
- /*
- * 15 - permission fault on page
- * 5 - page-table entry descriptor fault
- * 7 - first-level descriptor fault
- */
- case 15: case 5: case 7:
- do_page_fault(addr, error_code, regs);
- break;
+#define do_sect_fault NULL
- /*
- * 13 - permission fault on section
- */
- case 13:
- force_sig(SIGSEGV, current);
- if (!user_mode(regs)) {
- die("section permission fault", regs, fsr);
- do_exit(SIGSEGV);
- } else {
-#ifdef CONFIG_DEBUG_USER
- printk("%s: permission fault on section, "
- "address=0x%08lx, code %d\n",
- current->comm, addr, error_code);
-#ifdef DEBUG
- {
- unsigned int i, j;
- unsigned long *sp;
-
- sp = (unsigned long *) (regs->ARM_sp - 128);
- for (j = 0; j < 20 && sp_valid(sp); j++) {
- printk("%p: ", sp);
- for (i = 0; i < 8 && sp_valid(sp); i += 1, sp++)
- printk("%08lx ", *sp);
- printk("\n");
- }
- show_regs(regs);
- c_backtrace(regs->ARM_fp, regs->ARM_cpsr);
- }
-#endif
#endif
+
+static struct fsr_info {
+ int (*fn)(unsigned long addr, int error_code, struct pt_regs *regs);
+ int sig;
+ char *name;
+} fsr_info[] = {
+ { NULL, SIGSEGV, "vector exception" },
+ { do_alignment, SIGBUS, "alignment exception" },
+ { NULL, SIGKILL, "terminal exception" },
+ { do_alignment, SIGBUS, "alignment exception" },
+ { NULL, SIGBUS, "external abort on linefetch" },
+ { do_page_fault, SIGSEGV, "page fault" },
+ { NULL, SIGBUS, "external abort on linefetch" },
+ { do_page_fault, SIGSEGV, "page fault" },
+ { NULL, SIGBUS, "external abort on non-linefetch" },
+ { NULL, SIGSEGV, "domain fault" },
+ { NULL, SIGBUS, "external abort on non-linefetch" },
+ { NULL, SIGSEGV, "domain fault" },
+ { NULL, SIGBUS, "external abort on translation" },
+ { do_sect_fault, SIGSEGV, "section permission fault" },
+ { NULL, SIGBUS, "external abort on translation" },
+ { do_page_fault, SIGSEGV, "page permission fault" }
+};
+
+/*
+ * Currently dropped down to debug level
+ */
+#define BUG_PROC_MSG \
+ KERN_DEBUG "Weird data abort (%08X).\n" \
+ KERN_DEBUG "Please see http://www.arm.linux.org.uk/state.html for more information"
+
+asmlinkage void
+do_DataAbort(unsigned long addr, int fsr, int error_code, struct pt_regs *regs)
+{
+ struct fsr_info *inf;
+
+ if (user_mode(regs) && addr == regs->ARM_pc) {
+ static int first = 1;
+ if (first) {
+ /*
+ * I want statistical information on this problem,
+ * but we don't want to hastle the users too much.
+ */
+ printk(BUG_PROC_MSG, fsr);
+ first = 0;
}
- break;
+ return;
+ }
- case 1:
- case 3:
-#ifdef CONFIG_ALIGNMENT_TRAP
- if (!do_alignment_exception(regs))
- break;
-#endif
- /*
- * this should never happen
- */
- DIE(SIGBUS, "Alignment exception");
- break;
+ inf = fsr_info + (fsr & 15);
- case 2:
- DIE(SIGKILL, "Terminal exception");
- case 12:
- case 14:
- DIE(SIGBUS, "External abort on translation");
- case 9:
- case 11:
- DIE(SIGSEGV, "Domain fault");
-
- case 4:
- case 6:
- DIE(SIGBUS, "External abort on linefetch");
- case 8:
- case 10:
- DIE(SIGBUS, "External abort on non-linefetch");
+ if (!inf->fn || inf->fn(addr, error_code, regs)) {
+ force_sig(inf->sig, current);
+ die_if_kernel(inf->name, regs, fsr);
}
}
diff --git a/arch/arm/mm/fault-common.c b/arch/arm/mm/fault-common.c
index e516261ed..d04808ffa 100644
--- a/arch/arm/mm/fault-common.c
+++ b/arch/arm/mm/fault-common.c
@@ -6,7 +6,7 @@
*/
#include <linux/config.h>
-extern void die(char *msg, struct pt_regs *regs, unsigned int err);
+extern void die(const char *msg, struct pt_regs *regs, unsigned int err);
/*
* This is useful to dump out the page tables associated with
@@ -79,7 +79,7 @@ kernel_page_fault(unsigned long addr, int write_access, struct pt_regs *regs,
do_exit(SIGKILL);
}
-static void do_page_fault(unsigned long addr, int mode, struct pt_regs *regs)
+static int do_page_fault(unsigned long addr, int mode, struct pt_regs *regs)
{
struct task_struct *tsk;
struct mm_struct *mm;
@@ -127,7 +127,7 @@ good_area:
goto do_sigbus;
up(&mm->mmap_sem);
- return;
+ return 0;
/*
* Something tried to access memory that isn't in our memory map..
@@ -138,6 +138,7 @@ bad_area:
/* User mode accesses just cause a SIGSEGV */
if (user_mode(regs)) {
+ tsk->thread.address = addr;
tsk->thread.error_code = mode;
tsk->thread.trap_no = 14;
#ifdef CONFIG_DEBUG_USER
@@ -145,7 +146,7 @@ bad_area:
tsk->comm, regs->ARM_pc, regs->ARM_lr, addr, mode);
#endif
force_sig(SIGSEGV, tsk);
- return;
+ return 0;
}
no_context:
@@ -156,11 +157,11 @@ no_context:
tsk->comm, regs->ARM_pc, addr, fixup);
#endif
regs->ARM_pc = fixup;
- return;
+ return 0;
}
kernel_page_fault(addr, mode, regs, tsk, mm);
- return;
+ return 0;
do_sigbus:
/*
@@ -173,6 +174,7 @@ do_sigbus:
* Send a sigbus, regardless of whether we were in kernel
* or user mode.
*/
+ tsk->thread.address = addr;
tsk->thread.error_code = mode;
tsk->thread.trap_no = 14;
force_sig(SIGBUS, tsk);
@@ -180,6 +182,7 @@ do_sigbus:
/* Kernel mode? Handle exceptions or die */
if (!user_mode(regs))
goto no_context;
+ return 0;
}
diff --git a/arch/arm/mm/init.c b/arch/arm/mm/init.c
index 17972e427..bc4cf1ed1 100644
--- a/arch/arm/mm/init.c
+++ b/arch/arm/mm/init.c
@@ -168,7 +168,8 @@ void show_mem(void)
void __init paging_init(void)
{
void *zero_page, *bad_page, *bad_table;
- unsigned int zone_size[3];
+ unsigned int zone_size[MAX_NR_ZONES];
+ int i;
#ifdef CONFIG_CPU_32
#define TABLE_OFFSET (PTRS_PER_PTE)
@@ -193,7 +194,24 @@ void __init paging_init(void)
/*
* Initialise the zones and mem_map
*/
- zonesize_init(zone_size);
+ for (i = 0; i < MAX_NR_ZONES; i++)
+ zone_size[i] = 0;
+
+ /*
+ * Calculate the size of the zones. On ARM, we don't have
+ * any problems with DMA or highmem, so all memory is
+ * allocated to the DMA zone.
+ */
+ for (i = 0; i < meminfo.nr_banks; i++) {
+ if (meminfo.bank[i].size) {
+ unsigned int end;
+
+ end = (meminfo.bank[i].start - PHYS_OFFSET +
+ meminfo.bank[i].size) >> PAGE_SHIFT;
+ if (zone_size[0] < end)
+ zone_size[0] = end;
+ }
+ }
free_area_init(zone_size);
/*
@@ -339,10 +357,11 @@ void free_initmem(void)
#ifdef CONFIG_BLK_DEV_INITRD
void free_initrd_mem(unsigned long start, unsigned long end)
{
- for (; start < end; start += PAGE_SIZE) {
- ClearPageReserved(mem_map + MAP_NR(start));
- set_page_count(mem_map+MAP_NR(start), 1);
- free_page(start);
+ unsigned long addr;
+ for (addr = start; addr < end; addr += PAGE_SIZE) {
+ ClearPageReserved(mem_map + MAP_NR(addr));
+ set_page_count(mem_map+MAP_NR(addr), 1);
+ free_page(addr);
totalram_pages++;
}
printk ("Freeing initrd memory: %ldk freed\n", (end - start) >> 10);
diff --git a/arch/arm/mm/mm-armo.c b/arch/arm/mm/mm-armo.c
index 680a52948..a5d4cdfe8 100644
--- a/arch/arm/mm/mm-armo.c
+++ b/arch/arm/mm/mm-armo.c
@@ -135,20 +135,6 @@ pte_t *get_pte_slow(pmd_t *pmd, unsigned long offset)
}
/*
- * Calculate the size of the DMA, normal and highmem zones.
- * On 26-bit ARMs, we don't have any real DMA or highmem,
- * so we allocate the whole memory as being DMA-capable.
- */
-void __init zonesize_init(unsigned int *zone_size)
-{
- int i;
-
- zone_size[0] = max_low_pfn;
- zone_size[1] = 0;
- zone_size[2] = 0;
-}
-
-/*
* This contains the code to setup the memory map on an ARM2/ARM250/ARM3
* machine. This is both processor & architecture specific, and requires
* some more work to get it to fit into our separate processor and
diff --git a/arch/arm/mm/mm-armv.c b/arch/arm/mm/mm-armv.c
index ee4750c62..76d101507 100644
--- a/arch/arm/mm/mm-armv.c
+++ b/arch/arm/mm/mm-armv.c
@@ -46,6 +46,15 @@ static int __init nowrite_setup(char *__unused)
return 1;
}
+static int __init noalign_setup(char *__unused)
+{
+ cr_alignment &= ~2;
+ cr_no_alignment &= ~2;
+ set_cr(cr_alignment);
+ return 1;
+}
+
+__setup("noalign", noalign_setup);
__setup("nocache", nocache_setup);
__setup("nowb", nowrite_setup);
@@ -218,7 +227,7 @@ alloc_init_page(unsigned long virt, unsigned long phys, int domain, int prot)
* the clearance is done by the middle-level functions (pmd)
* rather than the top-level (pgd) functions.
*/
-static inline void free_init_section(unsigned long virt)
+static inline void clear_mapping(unsigned long virt)
{
pmd_clear(pmd_offset(pgd_offset_k(virt), virt));
}
@@ -273,73 +282,76 @@ static void __init create_mapping(struct map_desc *md)
}
}
-/*
- * Initial boot-time mapping. This covers just the zero page, kernel and
- * the flush area. NB: it must be sorted by virtual address, and no
- * virtual address overlaps.
- * init_map[2..4] are for architectures with banked memory.
- */
-static struct map_desc init_map[] __initdata = {
- { 0, 0, PAGE_SIZE, DOMAIN_USER, 0, 0, 1, 0 }, /* zero page */
- { 0, 0, 0, DOMAIN_KERNEL, 0, 1, 1, 1 }, /* kernel memory */
- { 0, 0, 0, DOMAIN_KERNEL, 0, 1, 1, 1 }, /* (4 banks) */
- { 0, 0, 0, DOMAIN_KERNEL, 0, 1, 1, 1 },
- { 0, 0, 0, DOMAIN_KERNEL, 0, 1, 1, 1 },
- { 0, 0, PGDIR_SIZE, DOMAIN_KERNEL, 1, 0, 1, 1 }, /* cache flush 1 */
- { 0, 0, 0, DOMAIN_KERNEL, 1, 0, 1, 0 } /* cache flush 2 */
-};
-
-#define NR_INIT_MAPS (sizeof(init_map) / sizeof(init_map[0]))
-
-/*
- * Calculate the size of the DMA, normal and highmem zones.
- * On ARM, we don't have any problems with DMA, so all memory
- * is allocated to the DMA zone. We also don't have any
- * highmem either.
- */
-void __init zonesize_init(unsigned int *zone_size)
+void __init pagetable_init(void)
{
+ struct map_desc *init_maps, *p;
+ unsigned long address = 0;
int i;
- zone_size[0] = 0;
- zone_size[1] = 0;
- zone_size[2] = 0;
+ /*
+ * Setup initial mappings. We use the page we allocated
+ * for zero page to hold the mappings, which will get
+ * overwritten by the vectors in traps_init(). The
+ * mappings must be in virtual address order.
+ */
+ init_maps = p = alloc_bootmem_low_pages(PAGE_SIZE);
+
+ p->physical = virt_to_phys(init_maps);
+ p->virtual = 0;
+ p->length = PAGE_SIZE;
+ p->domain = DOMAIN_USER;
+ p->prot_read = 0;
+ p->prot_write = 0;
+ p->cacheable = 1;
+ p->bufferable = 0;
+
+ p ++;
for (i = 0; i < meminfo.nr_banks; i++) {
- if (meminfo.bank[i].size) {
- unsigned int end;
+ if (meminfo.bank[i].size == 0)
+ continue;
- end = (meminfo.bank[i].start - PHYS_OFFSET +
- meminfo.bank[i].size) >> PAGE_SHIFT;
- if (end > zone_size[0])
- zone_size[0] = end;
- }
+ p->physical = meminfo.bank[i].start;
+ p->virtual = __phys_to_virt(p->physical);
+ p->length = meminfo.bank[i].size;
+ p->domain = DOMAIN_KERNEL;
+ p->prot_read = 0;
+ p->prot_write = 1;
+ p->cacheable = 1;
+ p->bufferable = 1;
+
+ p ++;
}
-}
-void __init pagetable_init(void)
-{
- unsigned long address = 0;
- int i;
+ p->physical = FLUSH_BASE_PHYS;
+ p->virtual = FLUSH_BASE;
+ p->length = PGDIR_SIZE;
+ p->domain = DOMAIN_KERNEL;
+ p->prot_read = 1;
+ p->prot_write = 0;
+ p->cacheable = 1;
+ p->bufferable = 1;
+
+ p ++;
- /*
- * Setup the above mappings
- */
- init_map[0].physical = virt_to_phys(alloc_bootmem_low_pages(PAGE_SIZE));
- init_map[5].physical = FLUSH_BASE_PHYS;
- init_map[5].virtual = FLUSH_BASE;
#ifdef FLUSH_BASE_MINICACHE
- init_map[6].physical = FLUSH_BASE_PHYS + PGDIR_SIZE;
- init_map[6].virtual = FLUSH_BASE_MINICACHE;
- init_map[6].length = PGDIR_SIZE;
+ p->physical = FLUSH_BASE_PHYS + PGDIR_SIZE;
+ p->virtual = FLUSH_BASE_MINICACHE;
+ p->length = PGDIR_SIZE;
+ p->domain = DOMAIN_KERNEL;
+ p->prot_read = 1;
+ p->prot_write = 0;
+ p->cacheable = 1;
+ p->bufferable = 0;
+
+ p ++;
#endif
- for (i = 0; i < meminfo.nr_banks; i++) {
- init_map[i+1].physical = meminfo.bank[i].start;
- init_map[i+1].virtual = meminfo.bank[i].start +
- PAGE_OFFSET - PHYS_OFFSET;
- init_map[i+1].length = meminfo.bank[i].size;
- }
+ /*
+ * We may have a mapping in virtual address 0.
+ * Clear it out.
+ */
+ clear_mapping(0);
/*
* Go through the initial mappings, but clear out any
@@ -347,18 +359,16 @@ void __init pagetable_init(void)
*/
i = 0;
do {
- if (address < init_map[i].virtual || i == NR_INIT_MAPS) {
- free_init_section(address);
+ if (address < init_maps->virtual || init_maps == p) {
+ clear_mapping(address);
address += PGDIR_SIZE;
} else {
- create_mapping(init_map + i);
+ create_mapping(init_maps);
- address = init_map[i].virtual + init_map[i].length;
+ address = init_maps->virtual + init_maps->length;
address = (address + PGDIR_SIZE - 1) & PGDIR_MASK;
- do {
- i += 1;
- } while (init_map[i].length == 0 && i < NR_INIT_MAPS);
+ init_maps ++;
}
} while (address != 0);
@@ -382,6 +392,7 @@ void __init create_memmap_holes(void)
unsigned int i;
#define PFN(x) (((x) - PHYS_OFFSET) >> PAGE_SHIFT)
+#define free_bootmem(s,sz) free_bootmem(((s)<<PAGE_SHIFT)+PHYS_OFFSET, (sz)<<PAGE_SHIFT)
for (i = 0; i < meminfo.nr_banks; i++) {
if (meminfo.bank[i].size == 0)
@@ -409,7 +420,7 @@ void __init create_memmap_holes(void)
end_pfn = PFN(meminfo.bank[i].start + meminfo.bank[i].size);
- if (end_pfn != meminfo.end >> PAGE_SHIFT)
+ if (end_pfn != PFN(meminfo.end))
pg = mem_map + end_pfn;
}
diff --git a/arch/arm/mm/mm-sa1100.c b/arch/arm/mm/mm-sa1100.c
index eba2984b6..c6f9f2e8b 100644
--- a/arch/arm/mm/mm-sa1100.c
+++ b/arch/arm/mm/mm-sa1100.c
@@ -6,11 +6,11 @@
* Copyright (C) 1998-1999 Russell King
* Copyright (C) 1999 Hugo Fiennes
*
- * 1999/09/12 Nicolas Pitre <nico@visuaide.com>
- * Specific RAM implementation details are in
- * linux/include/asm/arch-sa1100/memory.h now.
- * Allows for better macro optimisations when possible.
+ * 1999/12/04 Nicolas Pitre <nico@cam.org>
+ * Converted memory definition for struct meminfo initialisations.
+ * Memory is listed physically now.
*/
+
#include <linux/config.h>
#include <linux/mm.h>
#include <linux/init.h>
@@ -22,33 +22,37 @@
#define SIZE(x) (sizeof(x) / sizeof(x[0]))
+
/*
- * These are the memory size mappings for the
- * SA1100. Note that LART is a special case -
- * it doesn't use physical address A23 on the
- * DRAM, so we effectively have 4 * 8MB in
- * two banks.
+ * These are the RAM memory mappings for SA1100 implementations.
+ * Note that LART is a special case - it doesn't use physical
+ * address line A23 on the DRAM, so we effectively have 4 * 8MB
+ * in two banks.
*/
-struct mem_desc mem_desc[] __initdata = {
- /* virt start virt end */
+struct mem_desc {
+ unsigned long phys_start;
+ unsigned long length;
+} mem_desc[] __initdata = {
#if defined(CONFIG_SA1100_BRUTUS)
- { 0xc0000000, 0xc0400000 }, /* 4MB */
- { 0xc1000000, 0xc1400000 }, /* 4MB */
- { 0xc2000000, 0xc2400000 }, /* 4MB */
- { 0xc3000000, 0xc3400000 } /* 4MB */
+ { 0xc0000000, 0x00400000 }, /* 4MB */
+ { 0xc8000000, 0x00400000 }, /* 4MB */
+#if 0 /* only two banks until the bootmem stuff is fixed... */
+ { 0xd0000000, 0x00400000 }, /* 4MB */
+ { 0xd8000000, 0x00400000 } /* 4MB */
+#endif
#elif defined(CONFIG_SA1100_EMPEG)
- { 0xc0000000, 0xc0400000 }, /* 4MB */
- { 0xc1000000, 0xc1400000 } /* 4MB */
+ { 0xc0000000, 0x00400000 }, /* 4MB */
+ { 0xc8000000, 0x00400000 } /* 4MB */
#elif defined(CONFIG_SA1100_LART)
- { 0xc0000000, 0xc0800000 }, /* 16MB */
- { 0xc1000000, 0xc1800000 },
- { 0xc2000000, 0xc2800000 }, /* 16MB */
- { 0xc3000000, 0xc3800000 }
+ { 0xc0000000, 0x00800000 }, /* 8MB */
+ { 0xc1000000, 0x00800000 }, /* 8MB */
+ { 0xc8000000, 0x00800000 }, /* 8MB */
+ { 0xc9000000, 0x00800000 } /* 8MB */
#elif defined(CONFIG_SA1100_VICTOR)
- { 0xc0000000, 0xc0400000 } /* 4MB */
+ { 0xc0000000, 0x00400000 } /* 4MB */
#elif defined(CONFIG_SA1100_TIFON)
- { 0xc0000000, 0xc1000000 }, /* 16MB */
- { 0xc1000000, 0xc2000000 } /* 16MB */
+ { 0xc0000000, 0x01000000 }, /* 16MB */
+ { 0xc8000000, 0x01000000 } /* 16MB */
#else
#error missing memory configuration
#endif
@@ -56,6 +60,7 @@ struct mem_desc mem_desc[] __initdata = {
unsigned int __initdata mem_desc_size = SIZE(mem_desc);
+
struct map_desc io_desc[] __initdata = {
/* virtual physical length domain r w c b */
#if defined(CONFIG_SA1100_VICTOR)
diff --git a/arch/arm/mm/proc-arm6,7.S b/arch/arm/mm/proc-arm6,7.S
index d453269d2..23508c197 100644
--- a/arch/arm/mm/proc-arm6,7.S
+++ b/arch/arm/mm/proc-arm6,7.S
@@ -134,14 +134,10 @@ ENTRY(cpu_arm7_data_abort)
b Ldata_simple @ ldc rd, [rn, #m]
b Ldata_unknown
Ldata_unknown: @ Part of jumptable
- ldr r3, [sp, #15 * 4] @ Get PC
- str r3, [sp, #-4]!
- mov r1, r1, lsr #2
- mov r3, r4
- mov r2, r0
- adr r0, Lukabttxt
- bl SYMBOL_NAME(panic)
-Lstop: b Lstop
+ mov r0, r1
+ mov r1, r4
+ mov r2, r3
+ b baddataabort
Ldata_ldmstm: tst r4, #1 << 21 @ check writeback bit
beq Ldata_simple
@@ -468,7 +464,7 @@ ENTRY(arm6_processor_functions)
.word cpu_arm6_cache_wback_area
.word cpu_arm6_cache_purge_area
.word cpu_arm6_flush_tlb_page
- .word cpu_arm7_do_idle
+ .word cpu_arm6_do_idle
.size arm6_processor_functions, . - arm6_processor_functions
/*
diff --git a/arch/arm/mm/proc-sa110.S b/arch/arm/mm/proc-sa110.S
index 2d57b1030..5431f14a0 100644
--- a/arch/arm/mm/proc-sa110.S
+++ b/arch/arm/mm/proc-sa110.S
@@ -16,6 +16,7 @@
* is larger than this, then we flush the whole cache
*/
#define MAX_AREA_SIZE 32768
+#define FLUSH_OFFSET 32768
.macro flush_110_dcache rd, ra, re
add \re, \ra, #16384 @ only necessary for 16k
@@ -56,7 +57,7 @@ cpu_sa110_flush_cache_all_r2:
ands r1, r1, #1
eor r1, r1, #1
str r1, [r3]
- addne ip, ip, #32768
+ addne ip, ip, #FLUSH_OFFSET
flush_110_dcache r3, ip, r1
mov ip, #0
teq r2, #0
@@ -74,7 +75,7 @@ cpu_sa1100_flush_cache_all_r2:
ands r1, r1, #1
eor r1, r1, #1
str r1, [r3]
- addne ip, ip, #32768
+ addne ip, ip, #FLUSH_OFFSET
flush_1100_dcache r3, ip, r1
mov ip, #0
teq r2, #0
@@ -321,7 +322,7 @@ ENTRY(cpu_sa110_set_pgd)
ands r2, r2, #1
eor r2, r2, #1
str r2, [r3]
- addne ip, ip, #32768
+ addne ip, ip, #FLUSH_OFFSET
flush_110_dcache r3, ip, r1
mov r1, #0
mcr p15, 0, r1, c7, c5, 0 @ flush I cache
@@ -338,7 +339,7 @@ ENTRY(cpu_sa1100_set_pgd)
ands r2, r2, #1
eor r2, r2, #1
str r2, [r3]
- addne ip, ip, #32768
+ addne ip, ip, #FLUSH_OFFSET
flush_1100_dcache r3, ip, r1
mov r1, #0
mcr p15, 0, r1, c7, c5, 0 @ flush I cache
@@ -430,8 +431,12 @@ ENTRY(cpu_sa110_do_idle)
ENTRY(cpu_sa1100_do_idle)
mov r0, #0
mcr p15, 0, r0, c15, c2, 2 @ Disable clock switching
- @ load from uncacheable loc?
- mcr p15, 0, r0, c15, c8, 2 @ Wait for interrupt
+ ldr r1, =FLUSH_BASE+FLUSH_OFFSET*2 @ load from uncacheable loc
+ ldr r1, [r1, #0]
+ b 1f
+
+ .align 5
+1: mcr p15, 0, r0, c15, c8, 2 @ Wait for interrupt
mcr p15, 0, r0, c15, c1, 2 @ Enable clock switching
mov pc, lr