aboutsummaryrefslogtreecommitdiffstats
path: root/arch/sh
diff options
context:
space:
mode:
authorPaul Mundt <lethal@linux-sh.org>2006-09-27 02:16:42 -0400
committerPaul Mundt <lethal@linux-sh.org>2006-09-27 02:16:42 -0400
commitd7cdc9e8ac82c43fdcd4fde6b5b53d2dcba7f707 (patch)
tree2489b1831a1b5818af0927e4d3c8933bf7d05f31 /arch/sh
parent26ff6c11ef38e08990c1e417c299246e6ab18ff7 (diff)
sh: ioremap() overhaul.
ioremap() overhaul. Add support for transparent PMB mapping, get rid of p3_ioremap(), etc. Also drop ioremap() and iounmap() routines from the machvec, as everyone can use the generic ioremap() API instead. For PCI memory apertures and other special cases, use the pci_iomap() API, as boards are already required to get the mapping right there. Signed-off-by: Paul Mundt <lethal@linux-sh.org>
Diffstat (limited to 'arch/sh')
-rw-r--r--arch/sh/boards/landisk/io.c236
-rw-r--r--arch/sh/boards/landisk/setup.c237
-rw-r--r--arch/sh/boards/renesas/hs7751rvoip/io.c9
-rw-r--r--arch/sh/boards/renesas/hs7751rvoip/setup.c1
-rw-r--r--arch/sh/boards/renesas/rts7751r2d/io.c9
-rw-r--r--arch/sh/boards/renesas/rts7751r2d/mach.c2
-rw-r--r--arch/sh/boards/titan/io.c9
-rw-r--r--arch/sh/boards/titan/setup.c1
-rw-r--r--arch/sh/drivers/pci/pci.c21
-rw-r--r--arch/sh/kernel/cf-enabler.c5
-rw-r--r--arch/sh/kernel/sh_ksyms.c1
-rw-r--r--arch/sh/mm/Makefile7
-rw-r--r--arch/sh/mm/pmb.c145
13 files changed, 361 insertions, 322 deletions
diff --git a/arch/sh/boards/landisk/io.c b/arch/sh/boards/landisk/io.c
index 1f1679af09d0..aa6b145c9e8f 100644
--- a/arch/sh/boards/landisk/io.c
+++ b/arch/sh/boards/landisk/io.c
@@ -17,9 +17,9 @@
17 17
18#include <linux/kernel.h> 18#include <linux/kernel.h>
19#include <linux/types.h> 19#include <linux/types.h>
20#include <asm/io.h>
21#include <asm/landisk/iodata_landisk.h> 20#include <asm/landisk/iodata_landisk.h>
22#include <asm/addrspace.h> 21#include <asm/addrspace.h>
22#include <asm/io.h>
23 23
24#include <linux/module.h> 24#include <linux/module.h>
25#include <linux/pci.h> 25#include <linux/pci.h>
@@ -42,10 +42,6 @@ extern void *area6_io_base; /* Area 6 I/O Base address */
42 42
43#define PCI_IOMAP(adr) (PCI_IO_AREA + (adr & ~SH7751_PCIIOBR_MASK)) 43#define PCI_IOMAP(adr) (PCI_IO_AREA + (adr & ~SH7751_PCIIOBR_MASK))
44 44
45#define maybebadio(name,port) \
46 printk("bad PC-like io %s for port 0x%lx at 0x%08x\n", \
47 #name, (port), (__u32) __builtin_return_address(0))
48
49static inline void delay(void) 45static inline void delay(void)
50{ 46{
51 ctrl_inw(0xa0000000); 47 ctrl_inw(0xa0000000);
@@ -66,7 +62,7 @@ static inline unsigned long port2adr(unsigned int port)
66 return ((unsigned long)area6_io_base + PA_SIDE_OFFSET + 62 return ((unsigned long)area6_io_base + PA_SIDE_OFFSET +
67 ((port - 0x170) << 1)); 63 ((port - 0x170) << 1));
68 else 64 else
69 maybebadio(port2adr, (unsigned long)port); 65 maybebadio((unsigned long)port);
70 66
71 return port; 67 return port;
72} 68}
@@ -89,234 +85,200 @@ static inline unsigned long port2adr(unsigned int port)
89 * should be way beyond the window, and is used w/o translation for 85 * should be way beyond the window, and is used w/o translation for
90 * compatibility. 86 * compatibility.
91 */ 87 */
92unsigned char landisk_inb(unsigned long port) 88u8 landisk_inb(unsigned long port)
93{ 89{
94 if (PXSEG(port)) 90 if (PXSEG(port))
95 return *(volatile unsigned char *)port; 91 return ctrl_inb(port);
96 else if (CHECK_SH7751_PCIIO(port)) 92 else if (CHECK_SH7751_PCIIO(port))
97 return *(volatile unsigned char *)PCI_IOMAP(port); 93 return ctrl_inb(PCI_IOMAP(port));
98 else 94
99 return (*(volatile unsigned short *)port2adr(port) & 0xff); 95 return ctrl_inw(port2adr(port)) & 0xff;
100} 96}
101 97
102unsigned char landisk_inb_p(unsigned long port) 98u8 landisk_inb_p(unsigned long port)
103{ 99{
104 unsigned char v; 100 u8 v;
105 101
106 if (PXSEG(port)) 102 if (PXSEG(port))
107 v = *(volatile unsigned char *)port; 103 v = ctrl_inb(port);
108 else if (CHECK_SH7751_PCIIO(port)) 104 else if (CHECK_SH7751_PCIIO(port))
109 v = *(volatile unsigned char *)PCI_IOMAP(port); 105 v = ctrl_inb(PCI_IOMAP(port));
110 else 106 else
111 v = (*(volatile unsigned short *)port2adr(port) & 0xff); 107 v = ctrl_inw(port2adr(port)) & 0xff;
108
112 delay(); 109 delay();
113 110
114 return v; 111 return v;
115} 112}
116 113
117unsigned short landisk_inw(unsigned long port) 114u16 landisk_inw(unsigned long port)
118{ 115{
119 if (PXSEG(port)) 116 if (PXSEG(port))
120 return *(volatile unsigned short *)port; 117 return ctrl_inw(port);
121 else if (CHECK_SH7751_PCIIO(port)) 118 else if (CHECK_SH7751_PCIIO(port))
122 return *(volatile unsigned short *)PCI_IOMAP(port); 119 return ctrl_inw(PCI_IOMAP(port));
123 else 120 else
124 maybebadio(inw, port); 121 maybebadio(port);
125 122
126 return 0; 123 return 0;
127} 124}
128 125
129unsigned int landisk_inl(unsigned long port) 126u32 landisk_inl(unsigned long port)
130{ 127{
131 if (PXSEG(port)) 128 if (PXSEG(port))
132 return *(volatile unsigned long *)port; 129 return ctrl_inl(port);
133 else if (CHECK_SH7751_PCIIO(port)) 130 else if (CHECK_SH7751_PCIIO(port))
134 return *(volatile unsigned long *)PCI_IOMAP(port); 131 return ctrl_inl(PCI_IOMAP(port));
135 else 132 else
136 maybebadio(inl, port); 133 maybebadio(port);
137 134
138 return 0; 135 return 0;
139} 136}
140 137
141void landisk_outb(unsigned char value, unsigned long port) 138void landisk_outb(u8 value, unsigned long port)
142{ 139{
143
144 if (PXSEG(port)) 140 if (PXSEG(port))
145 *(volatile unsigned char *)port = value; 141 ctrl_outb(value, port);
146 else if (CHECK_SH7751_PCIIO(port)) 142 else if (CHECK_SH7751_PCIIO(port))
147 *(volatile unsigned char *)PCI_IOMAP(port) = value; 143 ctrl_outb(value, PCI_IOMAP(port));
148 else 144 else
149 *(volatile unsigned short *)port2adr(port) = value; 145 ctrl_outw(value, port2adr(port));
150} 146}
151 147
152void landisk_outb_p(unsigned char value, unsigned long port) 148void landisk_outb_p(u8 value, unsigned long port)
153{ 149{
154 if (PXSEG(port)) 150 if (PXSEG(port))
155 *(volatile unsigned char *)port = value; 151 ctrl_outb(value, port);
156 else if (CHECK_SH7751_PCIIO(port)) 152 else if (CHECK_SH7751_PCIIO(port))
157 *(volatile unsigned char *)PCI_IOMAP(port) = value; 153 ctrl_outb(value, PCI_IOMAP(port));
158 else 154 else
159 *(volatile unsigned short *)port2adr(port) = value; 155 ctrl_outw(value, port2adr(port));
160 delay(); 156 delay();
161} 157}
162 158
163void landisk_outw(unsigned short value, unsigned long port) 159void landisk_outw(u16 value, unsigned long port)
164{ 160{
165 if (PXSEG(port)) 161 if (PXSEG(port))
166 *(volatile unsigned short *)port = value; 162 ctrl_outw(value, port);
167 else if (CHECK_SH7751_PCIIO(port)) 163 else if (CHECK_SH7751_PCIIO(port))
168 *(volatile unsigned short *)PCI_IOMAP(port) = value; 164 ctrl_outw(value, PCI_IOMAP(port));
169 else 165 else
170 maybebadio(outw, port); 166 maybebadio(port);
171} 167}
172 168
173void landisk_outl(unsigned int value, unsigned long port) 169void landisk_outl(u32 value, unsigned long port)
174{ 170{
175 if (PXSEG(port)) 171 if (PXSEG(port))
176 *(volatile unsigned long *)port = value; 172 ctrl_outl(value, port);
177 else if (CHECK_SH7751_PCIIO(port)) 173 else if (CHECK_SH7751_PCIIO(port))
178 *(volatile unsigned long *)PCI_IOMAP(port) = value; 174 ctrl_outl(value, PCI_IOMAP(port));
179 else 175 else
180 maybebadio(outl, port); 176 maybebadio(port);
181} 177}
182 178
183void landisk_insb(unsigned long port, void *addr, unsigned long count) 179void landisk_insb(unsigned long port, void *dst, unsigned long count)
184{ 180{
185 if (PXSEG(port)) 181 volatile u16 *p;
186 while (count--) 182 u8 *buf = dst;
187 *((unsigned char *)addr)++ =
188 *(volatile unsigned char *)port;
189 else if (CHECK_SH7751_PCIIO(port)) {
190 volatile __u8 *bp = (__u8 *) PCI_IOMAP(port);
191 183
192 while (count--) 184 if (PXSEG(port)) {
193 *((volatile unsigned char *)addr)++ = *bp; 185 while (count--)
194 } else { 186 *buf++ = *(volatile u8 *)port;
195 volatile __u16 *p = (volatile unsigned short *)port2adr(port); 187 } else if (CHECK_SH7751_PCIIO(port)) {
188 volatile u8 *bp = (volatile u8 *)PCI_IOMAP(port);
196 189
197 while (count--) 190 while (count--)
198 *((unsigned char *)addr)++ = *p; 191 *buf++ = *bp;
192 } else {
193 p = (volatile u16 *)port2adr(port);
194 while (count--)
195 *buf++ = *p & 0xff;
199 } 196 }
200} 197}
201 198
202void landisk_insw(unsigned long port, void *addr, unsigned long count) 199void landisk_insw(unsigned long port, void *dst, unsigned long count)
203{ 200{
204 volatile __u16 *p; 201 volatile u16 *p;
202 u16 *buf = dst;
205 203
206 if (PXSEG(port)) 204 if (PXSEG(port))
207 p = (volatile unsigned short *)port; 205 p = (volatile u16 *)port;
208 else if (CHECK_SH7751_PCIIO(port)) 206 else if (CHECK_SH7751_PCIIO(port))
209 p = (volatile unsigned short *)PCI_IOMAP(port); 207 p = (volatile u16 *)PCI_IOMAP(port);
210 else 208 else
211 p = (volatile unsigned short *)port2adr(port); 209 p = (volatile u16 *)port2adr(port);
212 while (count--) 210 while (count--)
213 *((__u16 *) addr)++ = *p; 211 *buf++ = *p;
214} 212}
215 213
216void landisk_insl(unsigned long port, void *addr, unsigned long count) 214void landisk_insl(unsigned long port, void *dst, unsigned long count)
217{ 215{
216 u32 *buf = dst;
217
218 if (CHECK_SH7751_PCIIO(port)) { 218 if (CHECK_SH7751_PCIIO(port)) {
219 volatile __u32 *p = (__u32 *) PCI_IOMAP(port); 219 volatile u32 *p = (volatile u32 *)PCI_IOMAP(port);
220 220
221 while (count--) 221 while (count--)
222 *((__u32 *) addr)++ = *p; 222 *buf++ = *p;
223 } else 223 } else
224 maybebadio(insl, port); 224 maybebadio(port);
225} 225}
226 226
227void landisk_outsb(unsigned long port, const void *addr, unsigned long count) 227void landisk_outsb(unsigned long port, const void *src, unsigned long count)
228{ 228{
229 volatile u16 *p;
230 const u8 *buf = src;
231
229 if (PXSEG(port)) 232 if (PXSEG(port))
230 while (count--) 233 while (count--)
231 *(volatile unsigned char *)port = 234 ctrl_outb(*buf++, port);
232 *((unsigned char *)addr)++;
233 else if (CHECK_SH7751_PCIIO(port)) { 235 else if (CHECK_SH7751_PCIIO(port)) {
234 volatile __u8 *bp = (__u8 *) PCI_IOMAP(port); 236 volatile u8 *bp = (volatile u8 *)PCI_IOMAP(port);
235 237
236 while (count--) 238 while (count--)
237 *bp = *((volatile unsigned char *)addr)++; 239 *bp = *buf++;
238 } else { 240 } else {
239 volatile __u16 *p = (volatile unsigned short *)port2adr(port); 241 p = (volatile u16 *)port2adr(port);
240 242 while (count--)
241 while (count--) 243 *p = *buf++;
242 *p = *((unsigned char *)addr)++;
243 } 244 }
244} 245}
245 246
246void landisk_outsw(unsigned long port, const void *addr, unsigned long count) 247void landisk_outsw(unsigned long port, const void *src, unsigned long count)
247{ 248{
248 volatile __u16 *p; 249 volatile u16 *p;
250 const u16 *buf = src;
249 251
250 if (PXSEG(port)) 252 if (PXSEG(port))
251 p = (volatile unsigned short *)port; 253 p = (volatile u16 *)port;
252 else if (CHECK_SH7751_PCIIO(port)) 254 else if (CHECK_SH7751_PCIIO(port))
253 p = (volatile unsigned short *)PCI_IOMAP(port); 255 p = (volatile u16 *)PCI_IOMAP(port);
254 else 256 else
255 p = (volatile unsigned short *)port2adr(port); 257 p = (volatile u16 *)port2adr(port);
256 while (count--)
257 *p = *((__u16 *) addr)++;
258}
259 258
260void landisk_outsl(unsigned long port, const void *addr, unsigned long count) 259 while (count--)
261{ 260 *p = *buf++;
262 if (CHECK_SH7751_PCIIO(port)) {
263 volatile __u32 *p = (__u32 *) PCI_IOMAP(port);
264
265 while (count--)
266 *p = *((__u32 *) addr)++;
267 } else
268 maybebadio(outsl, port);
269} 261}
270 262
271/* For read/write calls, just copy generic (pass-thru); PCIMBR is */ 263void landisk_outsl(unsigned long port, const void *src, unsigned long count)
272/* already set up. For a larger memory space, these would need to */
273/* reset PCIMBR as needed on a per-call basis... */
274
275unsigned char landisk_readb(unsigned long addr)
276{ 264{
277 return *(volatile unsigned char *)addr; 265 const u32 *buf = src;
278}
279 266
280unsigned short landisk_readw(unsigned long addr) 267 if (CHECK_SH7751_PCIIO(port)) {
281{ 268 volatile u32 *p = (volatile u32 *)PCI_IOMAP(port);
282 return *(volatile unsigned short *)addr;
283}
284
285unsigned int landisk_readl(unsigned long addr)
286{
287 return *(volatile unsigned long *)addr;
288}
289
290void landisk_writeb(unsigned char b, unsigned long addr)
291{
292 *(volatile unsigned char *)addr = b;
293}
294
295void landisk_writew(unsigned short b, unsigned long addr)
296{
297 *(volatile unsigned short *)addr = b;
298}
299
300void landisk_writel(unsigned int b, unsigned long addr)
301{
302 *(volatile unsigned long *)addr = b;
303}
304 269
305void *landisk_ioremap(unsigned long offset, unsigned long size) 270 while (count--)
306{ 271 *p = *buf++;
307 if (offset >= 0xfd000000) 272 } else
308 return (void *)offset; 273 maybebadio(port);
309 else
310 return (void *)P2SEGADDR(offset);
311} 274}
312 275
313void landisk_iounmap(void *addr) 276void __iomem *landisk_ioport_map(unsigned long port, unsigned int size)
314{ 277{
315} 278 if (PXSEG(port))
279 return (void __iomem *)port;
280 else if (CHECK_SH7751_PCIIO(port))
281 return (void __iomem *)PCI_IOMAP(port);
316 282
317/* Map ISA bus address to the real address. Only for PCMCIA. */ 283 return (void __iomem *)port2adr(port);
318
319unsigned long landisk_isa_port2addr(unsigned long offset)
320{
321 return port2adr(offset);
322} 284}
diff --git a/arch/sh/boards/landisk/setup.c b/arch/sh/boards/landisk/setup.c
index 0c60eaa10ba7..3a795cfb1eda 100644
--- a/arch/sh/boards/landisk/setup.c
+++ b/arch/sh/boards/landisk/setup.c
@@ -1,157 +1,52 @@
1/* 1/*
2 * arch/sh/boards/landisk/setup.c 2 * arch/sh/boards/landisk/setup.c
3 * 3 *
4 * Copyright (C) 2000 Kazumoto Kojima
4 * Copyright (C) 2002 Paul Mundt 5 * Copyright (C) 2002 Paul Mundt
5 * 6 *
6 * May be copied or modified under the terms of the GNU General Public
7 * License. See linux/COPYING for more information.
8 *
9 * Setup code for an unknown machine (internal peripherials only)
10 */
11/*
12 * linux/arch/sh/kernel/setup_landisk.c
13 *
14 * Copyright (C) 2000 Kazumoto Kojima
15 *
16 * I-O DATA Device, Inc. LANDISK Support. 7 * I-O DATA Device, Inc. LANDISK Support.
17 * 8 *
18 * Modified for LANDISK by 9 * Modified for LANDISK by
19 * Atom Create Engineering Co., Ltd. 2002. 10 * Atom Create Engineering Co., Ltd. 2002.
20 */ 11 *
21/*
22 * modifed by kogiidena 12 * modifed by kogiidena
23 * 2005.09.16 13 * 2005.09.16
14 *
15 * This file is subject to the terms and conditions of the GNU General Public
16 * License. See the file "COPYING" in the main directory of this archive
17 * for more details.
24 */ 18 */
25
26#include <linux/config.h> 19#include <linux/config.h>
27#include <linux/init.h> 20#include <linux/init.h>
28#include <linux/irq.h>
29#include <linux/pm.h> 21#include <linux/pm.h>
30 22#include <linux/mm.h>
31#include <linux/hdreg.h>
32#include <linux/ide.h>
33#include <linux/pci.h>
34
35#include <asm/machvec.h> 23#include <asm/machvec.h>
36#include <asm/rtc.h> 24#include <asm/rtc.h>
37#include <asm/machvec_init.h>
38#include <asm/io.h>
39#include <asm/landisk/iodata_landisk.h> 25#include <asm/landisk/iodata_landisk.h>
40#include <asm/landisk/io.h> 26#include <asm/io.h>
41
42#include <linux/mm.h>
43#include <linux/vmalloc.h>
44 27
45extern void (*board_time_init) (void);
46void landisk_time_init(void); 28void landisk_time_init(void);
47extern void init_landisk_IRQ(void); 29void init_landisk_IRQ(void);
48 30
49int landisk_ledparam; 31int landisk_ledparam;
50int landisk_buzzerparam; 32int landisk_buzzerparam;
51int landisk_arch; 33int landisk_arch;
52 34
53/* defined in mm/ioremap.c */ 35/* cycle the led's in the clasic knightrider/sun pattern */
54extern void *p3_ioremap(unsigned long phys_addr, unsigned long size, 36static void heartbeat_landisk(void)
55 unsigned long flags);
56
57/*
58 * Initialize the board
59 */
60
61const char *get_system_type(void)
62{
63 return "LANDISK";
64}
65
66static void landisk_power_off(void)
67{
68 ctrl_outb(0x01, PA_SHUTDOWN);
69}
70
71void check_usl5p(void)
72{
73 volatile unsigned char *p = (volatile unsigned char *)PA_LED;
74 unsigned char tmp1, tmp2;
75 tmp1 = *p;
76 *p = 0x40;
77 tmp2 = *p;
78 *p = tmp1;
79 landisk_arch = (tmp2 == 0x40) ? 1 : 0;
80 if (landisk_arch == 1) { /* arch == usl-5p */
81 landisk_ledparam = 0x00000380;
82 landisk_ledparam |= (tmp1 & 0x07c);
83 } else { /* arch == landisk */
84 landisk_ledparam = 0x02000180;
85 landisk_ledparam |= 0x04;
86 }
87 return;
88}
89
90void __init platform_setup(void)
91{
92
93 landisk_buzzerparam = 0;
94 check_usl5p();
95
96 printk(KERN_INFO "I-O DATA DEVICE, INC. \"LANDISK Series\" support.\n");
97 board_time_init = landisk_time_init;
98 pm_power_off = landisk_power_off;
99
100}
101
102void *area5_io_base;
103void *area6_io_base;
104
105int __init cf_init(void)
106{
107 pgprot_t prot;
108 unsigned long paddrbase, psize;
109
110 /* open I/O area window */
111 paddrbase = virt_to_phys((void *)PA_AREA5_IO);
112 psize = PAGE_SIZE;
113 prot = PAGE_KERNEL_PCC(1, _PAGE_PCC_IO16);
114 area5_io_base = p3_ioremap(paddrbase, psize, prot.pgprot);
115 if (!area5_io_base) {
116 printk("allocate_cf_area : can't open CF I/O window!\n");
117 return -ENOMEM;
118 }
119
120 paddrbase = virt_to_phys((void *)PA_AREA6_IO);
121 psize = PAGE_SIZE;
122 prot = PAGE_KERNEL_PCC(0, _PAGE_PCC_IO16);
123 area6_io_base = p3_ioremap(paddrbase, psize, prot.pgprot);
124 if (!area6_io_base) {
125 printk("allocate_cf_area : can't open HDD I/O window!\n");
126 return -ENOMEM;
127 }
128
129 printk(KERN_INFO "Allocate Area5/6 success.\n");
130
131 /* XXX : do we need attribute and common-memory area also? */
132
133 return 0;
134}
135
136__initcall(cf_init);
137
138#include <linux/sched.h>
139
140/* Cycle the LED's in the clasic knightrider/Sun pattern */
141
142void heartbeat_landisk(void)
143{ 37{
144 static unsigned int cnt = 0, blink = 0x00, period = 25; 38 static unsigned int cnt = 0, blink = 0x00, period = 25;
145 volatile unsigned char *p = (volatile unsigned char *)PA_LED; 39 volatile u8 *p = (volatile u8 *)PA_LED;
146 char data; 40 char data;
147 41
148 if ((landisk_ledparam & 0x080) == 0) { 42 if ((landisk_ledparam & 0x080) == 0)
149 return; 43 return;
150 } 44
151 cnt += 1; 45 cnt += 1;
152 if (cnt < period) { 46
47 if (cnt < period)
153 return; 48 return;
154 } 49
155 cnt = 0; 50 cnt = 0;
156 blink++; 51 blink++;
157 52
@@ -167,17 +62,16 @@ void heartbeat_landisk(void)
167 } 62 }
168 *p = data; 63 *p = data;
169 64
170 if (((landisk_ledparam & 0x007f7f00) == 0) 65 if (((landisk_ledparam & 0x007f7f00) == 0) &&
171 && (landisk_buzzerparam == 0)) { 66 (landisk_buzzerparam == 0))
172 landisk_ledparam &= (~0x0080); 67 landisk_ledparam &= (~0x0080);
173 } 68
174 landisk_buzzerparam >>= 1; 69 landisk_buzzerparam >>= 1;
175} 70}
176 71
177/* 72/*
178 * The Machine Vector 73 * The Machine Vector
179 */ 74 */
180
181struct sh_machine_vector mv_landisk __initmv = { 75struct sh_machine_vector mv_landisk __initmv = {
182 .mv_nr_irqs = 72, 76 .mv_nr_irqs = 72,
183 .mv_inb = landisk_inb, 77 .mv_inb = landisk_inb,
@@ -198,21 +92,88 @@ struct sh_machine_vector mv_landisk __initmv = {
198 .mv_outsb = landisk_outsb, 92 .mv_outsb = landisk_outsb,
199 .mv_outsw = landisk_outsw, 93 .mv_outsw = landisk_outsw,
200 .mv_outsl = landisk_outsl, 94 .mv_outsl = landisk_outsl,
201 .mv_readb = landisk_readb, 95 .mv_ioport_map = landisk_ioport_map,
202 .mv_readw = landisk_readw,
203 .mv_readl = landisk_readl,
204 .mv_writeb = landisk_writeb,
205 .mv_writew = landisk_writew,
206 .mv_writel = landisk_writel,
207 .mv_ioremap = landisk_ioremap,
208 .mv_iounmap = landisk_iounmap,
209 .mv_isa_port2addr = landisk_isa_port2addr,
210 .mv_init_irq = init_landisk_IRQ, 96 .mv_init_irq = init_landisk_IRQ,
211
212#ifdef CONFIG_HEARTBEAT 97#ifdef CONFIG_HEARTBEAT
213 .mv_heartbeat = heartbeat_landisk, 98 .mv_heartbeat = heartbeat_landisk,
214#endif 99#endif
215
216}; 100};
217
218ALIAS_MV(landisk) 101ALIAS_MV(landisk)
102
103const char *get_system_type(void)
104{
105 return "LANDISK";
106}
107
108static void landisk_power_off(void)
109{
110 ctrl_outb(0x01, PA_SHUTDOWN);
111}
112
113static void check_usl5p(void)
114{
115 volatile u8 *p = (volatile u8 *)PA_LED;
116 u8 tmp1, tmp2;
117
118 tmp1 = *p;
119 *p = 0x40;
120 tmp2 = *p;
121 *p = tmp1;
122
123 landisk_arch = (tmp2 == 0x40);
124 if (landisk_arch == 1) {
125 /* arch == usl-5p */
126 landisk_ledparam = 0x00000380;
127 landisk_ledparam |= (tmp1 & 0x07c);
128 } else {
129 /* arch == landisk */
130 landisk_ledparam = 0x02000180;
131 landisk_ledparam |= 0x04;
132 }
133}
134
135void __init platform_setup(void)
136{
137 landisk_buzzerparam = 0;
138 check_usl5p();
139
140 printk(KERN_INFO "I-O DATA DEVICE, INC. \"LANDISK Series\" support.\n");
141 board_time_init = landisk_time_init;
142 pm_power_off = landisk_power_off;
143}
144
145void *area5_io_base;
146void *area6_io_base;
147
148static int __init landisk_cf_init(void)
149{
150 pgprot_t prot;
151 unsigned long paddrbase, psize;
152
153 /* open I/O area window */
154 paddrbase = virt_to_phys((void *)PA_AREA5_IO);
155 psize = PAGE_SIZE;
156 prot = PAGE_KERNEL_PCC(1, _PAGE_PCC_IO16);
157 area5_io_base = p3_ioremap(paddrbase, psize, prot.pgprot);
158 if (!area5_io_base) {
159 printk("allocate_cf_area : can't open CF I/O window!\n");
160 return -ENOMEM;
161 }
162
163 paddrbase = virt_to_phys((void *)PA_AREA6_IO);
164 psize = PAGE_SIZE;
165 prot = PAGE_KERNEL_PCC(0, _PAGE_PCC_IO16);
166 area6_io_base = p3_ioremap(paddrbase, psize, prot.pgprot);
167 if (!area6_io_base) {
168 printk("allocate_cf_area : can't open HDD I/O window!\n");
169 return -ENOMEM;
170 }
171
172 printk(KERN_INFO "Allocate Area5/6 success.\n");
173
174 /* XXX : do we need attribute and common-memory area also? */
175
176 return 0;
177}
178
179__initcall(landisk_cf_init);
diff --git a/arch/sh/boards/renesas/hs7751rvoip/io.c b/arch/sh/boards/renesas/hs7751rvoip/io.c
index 09fb77ffb835..edecf107fc13 100644
--- a/arch/sh/boards/renesas/hs7751rvoip/io.c
+++ b/arch/sh/boards/renesas/hs7751rvoip/io.c
@@ -294,15 +294,6 @@ void hs7751rvoip_outsl(unsigned long port, const void *addr, unsigned long count
294 maybebadio(outsl, port); 294 maybebadio(outsl, port);
295} 295}
296 296
297void *hs7751rvoip_ioremap(unsigned long offset, unsigned long size)
298{
299 if (offset >= 0xfd000000)
300 return (void *)offset;
301 else
302 return (void *)P2SEGADDR(offset);
303}
304EXPORT_SYMBOL(hs7751rvoip_ioremap);
305
306unsigned long hs7751rvoip_isa_port2addr(unsigned long offset) 297unsigned long hs7751rvoip_isa_port2addr(unsigned long offset)
307{ 298{
308 return port2adr(offset); 299 return port2adr(offset);
diff --git a/arch/sh/boards/renesas/hs7751rvoip/setup.c b/arch/sh/boards/renesas/hs7751rvoip/setup.c
index 813fc4d5862a..aa51bda931f6 100644
--- a/arch/sh/boards/renesas/hs7751rvoip/setup.c
+++ b/arch/sh/boards/renesas/hs7751rvoip/setup.c
@@ -60,7 +60,6 @@ struct sh_machine_vector mv_hs7751rvoip __initmv = {
60 .mv_outsw = hs7751rvoip_outsw, 60 .mv_outsw = hs7751rvoip_outsw,
61 .mv_outsl = hs7751rvoip_outsl, 61 .mv_outsl = hs7751rvoip_outsl,
62 62
63 .mv_ioremap = hs7751rvoip_ioremap,
64 .mv_isa_port2addr = hs7751rvoip_isa_port2addr, 63 .mv_isa_port2addr = hs7751rvoip_isa_port2addr,
65 .mv_init_irq = hs7751rvoip_init_irq, 64 .mv_init_irq = hs7751rvoip_init_irq,
66}; 65};
diff --git a/arch/sh/boards/renesas/rts7751r2d/io.c b/arch/sh/boards/renesas/rts7751r2d/io.c
index 9e7fa726a86d..8dc2a2e2e5df 100644
--- a/arch/sh/boards/renesas/rts7751r2d/io.c
+++ b/arch/sh/boards/renesas/rts7751r2d/io.c
@@ -321,15 +321,6 @@ void rts7751r2d_outsl(unsigned long port, const void *addr, unsigned long count)
321 maybebadio(port); 321 maybebadio(port);
322} 322}
323 323
324void *rts7751r2d_ioremap(unsigned long offset, unsigned long size)
325{
326 if (offset >= 0xfd000000)
327 return (void *)offset;
328 else
329 return (void *)P2SEGADDR(offset);
330}
331EXPORT_SYMBOL(rts7751r2d_ioremap);
332
333unsigned long rts7751r2d_isa_port2addr(unsigned long offset) 324unsigned long rts7751r2d_isa_port2addr(unsigned long offset)
334{ 325{
335 return port2adr(offset); 326 return port2adr(offset);
diff --git a/arch/sh/boards/renesas/rts7751r2d/mach.c b/arch/sh/boards/renesas/rts7751r2d/mach.c
index 175a93d726e8..fe3e8735e9f8 100644
--- a/arch/sh/boards/renesas/rts7751r2d/mach.c
+++ b/arch/sh/boards/renesas/rts7751r2d/mach.c
@@ -19,7 +19,6 @@
19 19
20extern void heartbeat_rts7751r2d(void); 20extern void heartbeat_rts7751r2d(void);
21extern void init_rts7751r2d_IRQ(void); 21extern void init_rts7751r2d_IRQ(void);
22extern void *rts7751r2d_ioremap(unsigned long, unsigned long);
23extern int rts7751r2d_irq_demux(int irq); 22extern int rts7751r2d_irq_demux(int irq);
24 23
25extern void *voyagergx_consistent_alloc(struct device *, size_t, dma_addr_t *, gfp_t); 24extern void *voyagergx_consistent_alloc(struct device *, size_t, dma_addr_t *, gfp_t);
@@ -53,7 +52,6 @@ struct sh_machine_vector mv_rts7751r2d __initmv = {
53 .mv_outsw = rts7751r2d_outsw, 52 .mv_outsw = rts7751r2d_outsw,
54 .mv_outsl = rts7751r2d_outsl, 53 .mv_outsl = rts7751r2d_outsl,
55 54
56 .mv_ioremap = rts7751r2d_ioremap,
57 .mv_init_irq = init_rts7751r2d_IRQ, 55 .mv_init_irq = init_rts7751r2d_IRQ,
58#ifdef CONFIG_HEARTBEAT 56#ifdef CONFIG_HEARTBEAT
59 .mv_heartbeat = heartbeat_rts7751r2d, 57 .mv_heartbeat = heartbeat_rts7751r2d,
diff --git a/arch/sh/boards/titan/io.c b/arch/sh/boards/titan/io.c
index d66900c99a11..b886fd233a66 100644
--- a/arch/sh/boards/titan/io.c
+++ b/arch/sh/boards/titan/io.c
@@ -138,19 +138,12 @@ void titan_outsl(unsigned long port, const void *src, unsigned long count)
138 maybebadio(port); 138 maybebadio(port);
139} 139}
140 140
141void *titan_ioremap(unsigned long offset, unsigned long size) {
142 if (CHECK_SH7751_PCIIO(offset) || CHECK_SH7751_PCIMEMIO(offset))
143 return (void *)offset;
144}
145
146void __iomem *titan_ioport_map(unsigned long port, unsigned int size) 141void __iomem *titan_ioport_map(unsigned long port, unsigned int size)
147{ 142{
148 if (PXSEG(port)) 143 if (PXSEG(port) || CHECK_SH7751_PCIMEMIO(port))
149 return (void __iomem *)port; 144 return (void __iomem *)port;
150 else if (CHECK_SH7751_PCIIO(port)) 145 else if (CHECK_SH7751_PCIIO(port))
151 return (void __iomem *)PCI_IOMAP(port); 146 return (void __iomem *)PCI_IOMAP(port);
152 147
153 return (void __iomem *)port2adr(port); 148 return (void __iomem *)port2adr(port);
154} 149}
155
156EXPORT_SYMBOL(titan_ioremap);
diff --git a/arch/sh/boards/titan/setup.c b/arch/sh/boards/titan/setup.c
index 6ac5c8d7b3fb..c8b431c1d0fd 100644
--- a/arch/sh/boards/titan/setup.c
+++ b/arch/sh/boards/titan/setup.c
@@ -51,7 +51,6 @@ struct sh_machine_vector mv_titan __initmv = {
51 .mv_insl = titan_insl, 51 .mv_insl = titan_insl,
52 .mv_outsl = titan_outsl, 52 .mv_outsl = titan_outsl,
53 53
54 .mv_ioremap = titan_ioremap,
55 .mv_ioport_map = titan_ioport_map, 54 .mv_ioport_map = titan_ioport_map,
56 55
57 .mv_init_irq = init_titan_irq, 56 .mv_init_irq = init_titan_irq,
diff --git a/arch/sh/drivers/pci/pci.c b/arch/sh/drivers/pci/pci.c
index 1f5e23e8b163..285dffd12bd8 100644
--- a/arch/sh/drivers/pci/pci.c
+++ b/arch/sh/drivers/pci/pci.c
@@ -2,7 +2,7 @@
2 * arch/sh/drivers/pci/pci.c 2 * arch/sh/drivers/pci/pci.c
3 * 3 *
4 * Copyright (c) 2002 M. R. Brown <mrbrown@linux-sh.org> 4 * Copyright (c) 2002 M. R. Brown <mrbrown@linux-sh.org>
5 * Copyright (c) 2004, 2005 Paul Mundt <lethal@linux-sh.org> 5 * Copyright (c) 2004 - 2006 Paul Mundt <lethal@linux-sh.org>
6 * 6 *
7 * These functions are collected here to reduce duplication of common 7 * These functions are collected here to reduce duplication of common
8 * code amongst the many platform-specific PCI support code files. 8 * code amongst the many platform-specific PCI support code files.
@@ -172,10 +172,23 @@ void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen)
172 return NULL; 172 return NULL;
173 if (maxlen && len > maxlen) 173 if (maxlen && len > maxlen)
174 len = maxlen; 174 len = maxlen;
175 if (flags & IORESOURCE_IO) 175
176 /*
177 * Presently the IORESOURCE_MEM case is a bit special, most
178 * SH7751 style PCI controllers have PCI memory at a fixed
179 * location in the address space where no remapping is desired
180 * (traditionally at 0xfd000000). Once this changes, the
181 * IORESOURCE_MEM case will have to switch to using ioremap() and
182 * more care will have to be taken to inhibit page table mapping
183 * for legacy cores.
184 *
185 * For now everything wraps to ioport_map(), since boards that
186 * have PCI will be able to check the address range properly on
187 * their own.
188 * -- PFM.
189 */
190 if (flags & (IORESOURCE_IO | IORESOURCE_MEM))
176 return ioport_map(start, len); 191 return ioport_map(start, len);
177 if (flags & IORESOURCE_MEM)
178 return ioremap(start, len);
179 192
180 return NULL; 193 return NULL;
181} 194}
diff --git a/arch/sh/kernel/cf-enabler.c b/arch/sh/kernel/cf-enabler.c
index f1f9ab87f0b0..c9b823d1d073 100644
--- a/arch/sh/kernel/cf-enabler.c
+++ b/arch/sh/kernel/cf-enabler.c
@@ -41,9 +41,6 @@
41#define slot_no 1 41#define slot_no 1
42#endif 42#endif
43 43
44/* defined in mm/ioremap.c */
45extern void * p3_ioremap(unsigned long phys_addr, unsigned long size, unsigned long flags);
46
47/* use this pointer to access to directly connected compact flash io area*/ 44/* use this pointer to access to directly connected compact flash io area*/
48void *cf_io_base; 45void *cf_io_base;
49 46
@@ -62,7 +59,7 @@ static int __init allocate_cf_area(void)
62 return -ENOMEM; 59 return -ENOMEM;
63 } 60 }
64/* printk("p3_ioremap(paddr=0x%08lx, psize=0x%08lx, prot=0x%08lx)=0x%08lx\n", 61/* printk("p3_ioremap(paddr=0x%08lx, psize=0x%08lx, prot=0x%08lx)=0x%08lx\n",
65 paddrbase, psize, prot.pgprot, cf_io_base);*/ 62 paddrbase, psize, prot.pgprot, cf_io_base);*/
66 63
67 /* XXX : do we need attribute and common-memory area also? */ 64 /* XXX : do we need attribute and common-memory area also? */
68 65
diff --git a/arch/sh/kernel/sh_ksyms.c b/arch/sh/kernel/sh_ksyms.c
index 8a6dd06fd071..b73feafcd06e 100644
--- a/arch/sh/kernel/sh_ksyms.c
+++ b/arch/sh/kernel/sh_ksyms.c
@@ -27,7 +27,6 @@ EXPORT_SYMBOL(sh_mv);
27 27
28/* platform dependent support */ 28/* platform dependent support */
29EXPORT_SYMBOL(dump_fpu); 29EXPORT_SYMBOL(dump_fpu);
30EXPORT_SYMBOL(iounmap);
31EXPORT_SYMBOL(enable_irq); 30EXPORT_SYMBOL(enable_irq);
32EXPORT_SYMBOL(disable_irq); 31EXPORT_SYMBOL(disable_irq);
33EXPORT_SYMBOL(probe_irq_mask); 32EXPORT_SYMBOL(probe_irq_mask);
diff --git a/arch/sh/mm/Makefile b/arch/sh/mm/Makefile
index d90906367c5f..87a7c07265c0 100644
--- a/arch/sh/mm/Makefile
+++ b/arch/sh/mm/Makefile
@@ -12,13 +12,14 @@ obj-$(CONFIG_DMA_PAGE_OPS) += pg-dma.o
12obj-$(CONFIG_HUGETLB_PAGE) += hugetlbpage.o 12obj-$(CONFIG_HUGETLB_PAGE) += hugetlbpage.o
13 13
14mmu-y := fault-nommu.o tlb-nommu.o pg-nommu.o 14mmu-y := fault-nommu.o tlb-nommu.o pg-nommu.o
15mmu-$(CONFIG_MMU) := fault.o clear_page.o copy_page.o tlb-flush.o 15mmu-$(CONFIG_MMU) := fault.o clear_page.o copy_page.o tlb-flush.o \
16 ioremap.o
16 17
17obj-y += $(mmu-y) 18obj-y += $(mmu-y)
18 19
19ifdef CONFIG_MMU 20ifdef CONFIG_MMU
20obj-$(CONFIG_CPU_SH3) += tlb-sh3.o 21obj-$(CONFIG_CPU_SH3) += tlb-sh3.o
21obj-$(CONFIG_CPU_SH4) += tlb-sh4.o ioremap.o 22obj-$(CONFIG_CPU_SH4) += tlb-sh4.o
22obj-$(CONFIG_SH7705_CACHE_32KB) += pg-sh7705.o 23obj-$(CONFIG_SH7705_CACHE_32KB) += pg-sh7705.o
23endif 24endif
24 25
diff --git a/arch/sh/mm/pmb.c b/arch/sh/mm/pmb.c
index ff5bde745647..819fd0faf022 100644
--- a/arch/sh/mm/pmb.c
+++ b/arch/sh/mm/pmb.c
@@ -3,7 +3,7 @@
3 * 3 *
4 * Privileged Space Mapping Buffer (PMB) Support. 4 * Privileged Space Mapping Buffer (PMB) Support.
5 * 5 *
6 * Copyright (C) 2005 Paul Mundt 6 * Copyright (C) 2005, 2006 Paul Mundt
7 * 7 *
8 * P1/P2 Section mapping definitions from map32.h, which was: 8 * P1/P2 Section mapping definitions from map32.h, which was:
9 * 9 *
@@ -24,6 +24,7 @@
24#include <linux/err.h> 24#include <linux/err.h>
25#include <asm/system.h> 25#include <asm/system.h>
26#include <asm/uaccess.h> 26#include <asm/uaccess.h>
27#include <asm/pgtable.h>
27#include <asm/mmu.h> 28#include <asm/mmu.h>
28#include <asm/io.h> 29#include <asm/io.h>
29 30
@@ -127,11 +128,15 @@ repeat:
127 return 0; 128 return 0;
128} 129}
129 130
130void set_pmb_entry(struct pmb_entry *pmbe) 131int set_pmb_entry(struct pmb_entry *pmbe)
131{ 132{
133 int ret;
134
132 jump_to_P2(); 135 jump_to_P2();
133 __set_pmb_entry(pmbe->vpn, pmbe->ppn, pmbe->flags, &pmbe->entry); 136 ret = __set_pmb_entry(pmbe->vpn, pmbe->ppn, pmbe->flags, &pmbe->entry);
134 back_to_P1(); 137 back_to_P1();
138
139 return ret;
135} 140}
136 141
137void clear_pmb_entry(struct pmb_entry *pmbe) 142void clear_pmb_entry(struct pmb_entry *pmbe)
@@ -162,11 +167,141 @@ void clear_pmb_entry(struct pmb_entry *pmbe)
162 clear_bit(entry, &pmb_map); 167 clear_bit(entry, &pmb_map);
163} 168}
164 169
170static DEFINE_SPINLOCK(pmb_list_lock);
171static struct pmb_entry *pmb_list;
172
173static inline void pmb_list_add(struct pmb_entry *pmbe)
174{
175 struct pmb_entry **p, *tmp;
176
177 p = &pmb_list;
178 while ((tmp = *p) != NULL)
179 p = &tmp->next;
180
181 pmbe->next = tmp;
182 *p = pmbe;
183}
184
185static inline void pmb_list_del(struct pmb_entry *pmbe)
186{
187 struct pmb_entry **p, *tmp;
188
189 for (p = &pmb_list; (tmp = *p); p = &tmp->next)
190 if (tmp == pmbe) {
191 *p = tmp->next;
192 return;
193 }
194}
195
196static struct {
197 unsigned long size;
198 int flag;
199} pmb_sizes[] = {
200 { .size = 0x20000000, .flag = PMB_SZ_512M, },
201 { .size = 0x08000000, .flag = PMB_SZ_128M, },
202 { .size = 0x04000000, .flag = PMB_SZ_64M, },
203 { .size = 0x01000000, .flag = PMB_SZ_16M, },
204};
205
206long pmb_remap(unsigned long vaddr, unsigned long phys,
207 unsigned long size, unsigned long flags)
208{
209 struct pmb_entry *pmbp;
210 unsigned long wanted;
211 int pmb_flags, i;
212
213 /* Convert typical pgprot value to the PMB equivalent */
214 if (flags & _PAGE_CACHABLE) {
215 if (flags & _PAGE_WT)
216 pmb_flags = PMB_WT;
217 else
218 pmb_flags = PMB_C;
219 } else
220 pmb_flags = PMB_WT | PMB_UB;
221
222 pmbp = NULL;
223 wanted = size;
224
225again:
226 for (i = 0; i < ARRAY_SIZE(pmb_sizes); i++) {
227 struct pmb_entry *pmbe;
228 int ret;
229
230 if (size < pmb_sizes[i].size)
231 continue;
232
233 pmbe = pmb_alloc(vaddr, phys, pmb_flags | pmb_sizes[i].flag);
234 if (IS_ERR(pmbe))
235 return PTR_ERR(pmbe);
236
237 ret = set_pmb_entry(pmbe);
238 if (ret != 0) {
239 pmb_free(pmbe);
240 return -EBUSY;
241 }
242
243 phys += pmb_sizes[i].size;
244 vaddr += pmb_sizes[i].size;
245 size -= pmb_sizes[i].size;
246
247 /*
248 * Link adjacent entries that span multiple PMB entries
249 * for easier tear-down.
250 */
251 if (likely(pmbp))
252 pmbp->link = pmbe;
253
254 pmbp = pmbe;
255 }
256
257 if (size >= 0x1000000)
258 goto again;
259
260 return wanted - size;
261}
262
263void pmb_unmap(unsigned long addr)
264{
265 struct pmb_entry **p, *pmbe;
266
267 for (p = &pmb_list; (pmbe = *p); p = &pmbe->next)
268 if (pmbe->vpn == addr)
269 break;
270
271 if (unlikely(!pmbe))
272 return;
273
274 WARN_ON(!test_bit(pmbe->entry, &pmb_map));
275
276 do {
277 struct pmb_entry *pmblink = pmbe;
278
279 clear_pmb_entry(pmbe);
280 pmbe = pmblink->link;
281
282 pmb_free(pmblink);
283 } while (pmbe);
284}
285
165static void pmb_cache_ctor(void *pmb, kmem_cache_t *cachep, unsigned long flags) 286static void pmb_cache_ctor(void *pmb, kmem_cache_t *cachep, unsigned long flags)
166{ 287{
288 struct pmb_entry *pmbe = pmb;
289
167 memset(pmb, 0, sizeof(struct pmb_entry)); 290 memset(pmb, 0, sizeof(struct pmb_entry));
168 291
169 ((struct pmb_entry *)pmb)->entry = PMB_NO_ENTRY; 292 spin_lock_irq(&pmb_list_lock);
293
294 pmbe->entry = PMB_NO_ENTRY;
295 pmb_list_add(pmbe);
296
297 spin_unlock_irq(&pmb_list_lock);
298}
299
300static void pmb_cache_dtor(void *pmb, kmem_cache_t *cachep, unsigned long flags)
301{
302 spin_lock_irq(&pmb_list_lock);
303 pmb_list_del(pmb);
304 spin_unlock_irq(&pmb_list_lock);
170} 305}
171 306
172static int __init pmb_init(void) 307static int __init pmb_init(void)
@@ -177,7 +312,7 @@ static int __init pmb_init(void)
177 BUG_ON(unlikely(nr_entries >= NR_PMB_ENTRIES)); 312 BUG_ON(unlikely(nr_entries >= NR_PMB_ENTRIES));
178 313
179 pmb_cache = kmem_cache_create("pmb", sizeof(struct pmb_entry), 314 pmb_cache = kmem_cache_create("pmb", sizeof(struct pmb_entry),
180 0, 0, pmb_cache_ctor, NULL); 315 0, 0, pmb_cache_ctor, pmb_cache_dtor);
181 BUG_ON(!pmb_cache); 316 BUG_ON(!pmb_cache);
182 317
183 jump_to_P2(); 318 jump_to_P2();