This commit was manufactured by cvs2svn to create branch 'vserver'.
[linux-2.6.git] / arch / m32r / kernel / io_mappi2.c
1 /*
2  *  linux/arch/m32r/kernel/io_mappi2.c
3  *
4  *  Typical I/O routines for Mappi2 board.
5  *
6  *  Copyright (c) 2001-2003  Hiroyuki Kondo, Hirokazu Takata,
7  *                            Hitoshi Yamamoto, Mamoru Sakugawa
8  */
9
10 /* $Id:$ */
11
12 #include <linux/config.h>
13 #include <asm/m32r.h>
14 #include <asm/page.h>
15 #include <asm/io.h>
16
17 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
18 #include <linux/types.h>
19
20 #define M32R_PCC_IOMAP_SIZE 0x1000
21
22 #define M32R_PCC_IOSTART0 0x1000
23 #define M32R_PCC_IOEND0   (M32R_PCC_IOSTART0 + M32R_PCC_IOMAP_SIZE - 1)
24
25 extern void pcc_ioread_byte(int, unsigned long, void *, size_t, size_t, int);
26 extern void pcc_ioread_word(int, unsigned long, void *, size_t, size_t, int);
27 extern void pcc_iowrite_byte(int, unsigned long, void *, size_t, size_t, int);
28 extern void pcc_iowrite_word(int, unsigned long, void *, size_t, size_t, int);
29 #endif /* CONFIG_PCMCIA && CONFIG_MAPPI2_CFC */
30
31 #define PORT2ADDR(port)      _port2addr(port)
32 #define PORT2ADDR_NE(port)   _port2addr_ne(port)
33 #define PORT2ADDR_USB(port)  _port2addr_usb(port)
34
35 static __inline__ void *_port2addr(unsigned long port)
36 {
37         return (void *)(port + NONCACHE_OFFSET);
38 }
39
40 #define LAN_IOSTART     0x300
41 #define LAN_IOEND       0x320
42 #ifdef CONFIG_CHIP_OPSP
43 static __inline__ void *_port2addr_ne(unsigned long port)
44 {
45         return (void *)(port + NONCACHE_OFFSET + 0x10000000);
46 }
47 #else
48 static __inline__ void *_port2addr_ne(unsigned long port)
49 {
50         return (void *)(port + NONCACHE_OFFSET + 0x04000000);
51 }
52 #endif
53 static __inline__ void *_port2addr_usb(unsigned long port)
54 {
55         return (void *)(port + NONCACHE_OFFSET + 0x14000000);
56 }
57 static __inline__ void delay(void)
58 {
59         __asm__ __volatile__ ("push r0; \n\t pop r0;" : : :"memory");
60 }
61
62 /*
63  * NIC I/O function
64  */
65
66 static __inline__ unsigned char _ne_inb(void *portp)
67 {
68         return (unsigned char) *(volatile unsigned char *)portp;
69 }
70
71 static __inline__ unsigned short _ne_inw(void *portp)
72 {
73 #if 1  /* byte swap */
74         unsigned short tmp,tmp2;
75         tmp = *(volatile unsigned short *)portp;
76         tmp2 = (tmp>>8|tmp<<8);
77         return tmp2;
78 #else
79         return *(volatile unsigned short *)portp;
80 #endif
81 }
82
83 static __inline__ void _ne_insb(void *portp, void * addr, unsigned long count)
84 {
85         unsigned short tmp;
86         unsigned char *buf = addr;
87
88         tmp = *(volatile unsigned char *)portp;
89         while (count--) *buf++ = *(volatile unsigned char *)portp;
90 }
91
92 static __inline__ void _ne_outb(unsigned char b, void *portp)
93 {
94         *(volatile unsigned char *)portp = (unsigned char)b;
95 }
96
97 static __inline__ void _ne_outw(unsigned short w, void *portp)
98 {
99         *(volatile unsigned short *)portp = (w>>8|w<<8);
100 }
101
102 unsigned char _inb(unsigned long port)
103 {
104         if (port >= LAN_IOSTART && port < LAN_IOEND)
105                 return _ne_inb(PORT2ADDR_NE(port));
106 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
107         else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
108            unsigned char b;
109            pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
110            return b;
111         } else
112 #endif
113
114         return *(volatile unsigned char *)PORT2ADDR(port);
115 }
116
117 unsigned short _inw(unsigned long port)
118 {
119         if (port >= LAN_IOSTART && port < LAN_IOEND)
120                 return _ne_inw(PORT2ADDR_NE(port));
121 #if defined(CONFIG_USB)
122         else if (port >= 0x340 && port < 0x3a0)
123           return *(volatile unsigned short *)PORT2ADDR_USB(port);
124 #endif
125
126 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
127           else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
128            unsigned short w;
129            pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
130            return w;
131         } else
132 #endif
133         return *(volatile unsigned short *)PORT2ADDR(port);
134 }
135
136 unsigned long _inl(unsigned long port)
137 {
138 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
139         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
140            unsigned long l;
141            pcc_ioread_word(0, port, &l, sizeof(l), 1, 0);
142            return l;
143         } else
144 #endif
145         return *(volatile unsigned long *)PORT2ADDR(port);
146 }
147
148 unsigned char _inb_p(unsigned long port)
149 {
150         unsigned char  v;
151
152         if (port >= 0x300 && port < 0x320)
153                 v = _ne_inb(PORT2ADDR_NE(port));
154         else
155 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
156         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
157            unsigned char b;
158            pcc_ioread_byte(0, port, &b, sizeof(b), 1, 0);
159            return b;
160         } else
161 #endif
162                 v = *(volatile unsigned char *)PORT2ADDR(port);
163
164         delay();
165         return (v);
166 }
167
168 unsigned short _inw_p(unsigned long port)
169 {
170         unsigned short  v;
171
172         if (port >= 0x300 && port < 0x320)
173                 v = _ne_inw(PORT2ADDR_NE(port));
174         else
175 #if defined(CONFIG_USB)
176           if (port >= 0x340 && port < 0x3a0)
177                 v = *(volatile unsigned short *)PORT2ADDR_USB(port);
178           else
179 #endif
180 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
181         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
182            unsigned short w;
183            pcc_ioread_word(0, port, &w, sizeof(w), 1, 0);
184            return w;
185         } else
186 #endif
187                 v = *(volatile unsigned short *)PORT2ADDR(port);
188
189         delay();
190         return (v);
191 }
192
193 unsigned long _inl_p(unsigned long port)
194 {
195         unsigned long  v;
196
197         v = *(volatile unsigned long *)PORT2ADDR(port);
198         delay();
199         return (v);
200 }
201
202 void _outb(unsigned char b, unsigned long port)
203 {
204         if (port >= LAN_IOSTART && port < LAN_IOEND)
205                 _ne_outb(b, PORT2ADDR_NE(port));
206         else
207 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
208         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
209            pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
210         } else
211 #endif
212                 *(volatile unsigned char *)PORT2ADDR(port) = b;
213 }
214
215 void _outw(unsigned short w, unsigned long port)
216 {
217         if (port >= LAN_IOSTART && port < LAN_IOEND)
218                 _ne_outw(w, PORT2ADDR_NE(port));
219         else
220 #if defined(CONFIG_USB)
221           if (port >= 0x340 && port < 0x3a0)
222             *(volatile unsigned short *)PORT2ADDR_USB(port) = w;
223         else
224 #endif
225 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
226         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
227            pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
228         } else
229 #endif
230                 *(volatile unsigned short *)PORT2ADDR(port) = w;
231 }
232
233 void _outl(unsigned long l, unsigned long port)
234 {
235 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
236         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
237            pcc_iowrite_word(0, port, &l, sizeof(l), 1, 0);
238         } else
239 #endif
240         *(volatile unsigned long *)PORT2ADDR(port) = l;
241 }
242
243 void _outb_p(unsigned char b, unsigned long port)
244 {
245         if (port >= LAN_IOSTART && port < LAN_IOEND)
246                 _ne_outb(b, PORT2ADDR_NE(port));
247         else
248 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
249         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
250            pcc_iowrite_byte(0, port, &b, sizeof(b), 1, 0);
251         } else
252 #endif
253                 *(volatile unsigned char *)PORT2ADDR(port) = b;
254
255         delay();
256 }
257
258 void _outw_p(unsigned short w, unsigned long port)
259 {
260         if (port >= LAN_IOSTART && port < LAN_IOEND)
261                 _ne_outw(w, PORT2ADDR_NE(port));
262         else
263 #if defined(CONFIG_USB)
264           if (port >= 0x340 && port < 0x3a0)
265                 *(volatile unsigned short *)PORT2ADDR_USB(port) = w;
266         else
267 #endif
268 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
269         if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
270            pcc_iowrite_word(0, port, &w, sizeof(w), 1, 0);
271         } else
272 #endif
273                 *(volatile unsigned short *)PORT2ADDR(port) = w;
274
275         delay();
276 }
277
278 void _outl_p(unsigned long l, unsigned long port)
279 {
280         *(volatile unsigned long *)PORT2ADDR(port) = l;
281         delay();
282 }
283
284 void _insb(unsigned int port, void * addr, unsigned long count)
285 {
286         if (port >= LAN_IOSTART && port < LAN_IOEND)
287                 _ne_insb(PORT2ADDR_NE(port), addr, count);
288 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
289           else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
290            pcc_ioread_byte(0, port, (void *)addr, sizeof(unsigned char), count, 1);
291         }
292 #endif
293         else {
294                 unsigned char *buf = addr;
295                 unsigned char *portp = PORT2ADDR(port);
296                 while(count--) *buf++ = *(volatile unsigned char *)portp;
297         }
298 }
299
300 void _insw(unsigned int port, void * addr, unsigned long count)
301 {
302         unsigned short *buf = addr;
303         unsigned short *portp;
304
305         if (port >= LAN_IOSTART && port < LAN_IOEND)
306                 portp = PORT2ADDR_NE(port);
307                 while (count--) *buf++ = *(volatile unsigned short *)portp;
308 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
309         } else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
310            pcc_ioread_word(9, port, (void *)addr, sizeof(unsigned short), count, 1);
311 #endif
312         } else {
313                 portp = PORT2ADDR(port);
314                 while (count--) *buf++ = *(volatile unsigned short *)portp;
315         }
316 }
317
318 void _insl(unsigned int port, void * addr, unsigned long count)
319 {
320         unsigned long *buf = addr;
321         unsigned long *portp;
322
323         portp = PORT2ADDR(port);
324         while (count--) *buf++ = *(volatile unsigned long *)portp;
325 }
326
327 void _outsb(unsigned int port, const void * addr, unsigned long count)
328 {
329         const unsigned char *buf = addr;
330         unsigned char *portp;
331
332         if (port >= LAN_IOSTART && port < LAN_IOEND)
333                 portp = PORT2ADDR_NE(port);
334                 while (count--) _ne_outb(*buf++, portp);
335 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
336         } else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
337            pcc_iowrite_byte(0, port, (void *)addr, sizeof(unsigned char), count, 1);
338 #endif
339         } else {
340                 portp = PORT2ADDR(port);
341                 while(count--) *(volatile unsigned char *)portp = *buf++;
342         }
343 }
344
345 void _outsw(unsigned int port, const void * addr, unsigned long count)
346 {
347         const unsigned short *buf = addr;
348         unsigned short *portp;
349
350         if (port >= LAN_IOSTART && port < LAN_IOEND)
351                 portp = PORT2ADDR_NE(port);
352                 while (count--) *(volatile unsigned short *)portp = *buf++;
353 #if defined(CONFIG_PCMCIA) && defined(CONFIG_M32R_CFC)
354         } else if (port >= M32R_PCC_IOSTART0 && port <= M32R_PCC_IOEND0) {
355            pcc_iowrite_word(9, port, (void *)addr, sizeof(unsigned short), count, 1);
356 #endif
357         } else {
358                 portp = PORT2ADDR(port);
359                 while(count--) *(volatile unsigned short *)portp = *buf++;
360         }
361 }
362
363 void _outsl(unsigned int port, const void * addr, unsigned long count)
364 {
365         const unsigned long *buf = addr;
366         unsigned char *portp;
367
368         portp = PORT2ADDR(port);
369         while(count--) *(volatile unsigned long *)portp = *buf++;
370 }