diff options
Diffstat (limited to 'include/asm-sparc/io_32.h')
-rw-r--r-- | include/asm-sparc/io_32.h | 325 |
1 files changed, 325 insertions, 0 deletions
diff --git a/include/asm-sparc/io_32.h b/include/asm-sparc/io_32.h new file mode 100644 index 000000000000..c43af722ae8c --- /dev/null +++ b/include/asm-sparc/io_32.h | |||
@@ -0,0 +1,325 @@ | |||
1 | #ifndef __SPARC_IO_H | ||
2 | #define __SPARC_IO_H | ||
3 | |||
4 | #include <linux/kernel.h> | ||
5 | #include <linux/types.h> | ||
6 | #include <linux/ioport.h> /* struct resource */ | ||
7 | |||
8 | #include <asm/page.h> /* IO address mapping routines need this */ | ||
9 | #include <asm/system.h> | ||
10 | |||
11 | #define page_to_phys(page) (((page) - mem_map) << PAGE_SHIFT) | ||
12 | |||
13 | static inline u32 flip_dword (u32 l) | ||
14 | { | ||
15 | return ((l&0xff)<<24) | (((l>>8)&0xff)<<16) | (((l>>16)&0xff)<<8)| ((l>>24)&0xff); | ||
16 | } | ||
17 | |||
18 | static inline u16 flip_word (u16 w) | ||
19 | { | ||
20 | return ((w&0xff) << 8) | ((w>>8)&0xff); | ||
21 | } | ||
22 | |||
23 | #define mmiowb() | ||
24 | |||
25 | /* | ||
26 | * Memory mapped I/O to PCI | ||
27 | */ | ||
28 | |||
29 | static inline u8 __raw_readb(const volatile void __iomem *addr) | ||
30 | { | ||
31 | return *(__force volatile u8 *)addr; | ||
32 | } | ||
33 | |||
34 | static inline u16 __raw_readw(const volatile void __iomem *addr) | ||
35 | { | ||
36 | return *(__force volatile u16 *)addr; | ||
37 | } | ||
38 | |||
39 | static inline u32 __raw_readl(const volatile void __iomem *addr) | ||
40 | { | ||
41 | return *(__force volatile u32 *)addr; | ||
42 | } | ||
43 | |||
44 | static inline void __raw_writeb(u8 b, volatile void __iomem *addr) | ||
45 | { | ||
46 | *(__force volatile u8 *)addr = b; | ||
47 | } | ||
48 | |||
49 | static inline void __raw_writew(u16 w, volatile void __iomem *addr) | ||
50 | { | ||
51 | *(__force volatile u16 *)addr = w; | ||
52 | } | ||
53 | |||
54 | static inline void __raw_writel(u32 l, volatile void __iomem *addr) | ||
55 | { | ||
56 | *(__force volatile u32 *)addr = l; | ||
57 | } | ||
58 | |||
59 | static inline u8 __readb(const volatile void __iomem *addr) | ||
60 | { | ||
61 | return *(__force volatile u8 *)addr; | ||
62 | } | ||
63 | |||
64 | static inline u16 __readw(const volatile void __iomem *addr) | ||
65 | { | ||
66 | return flip_word(*(__force volatile u16 *)addr); | ||
67 | } | ||
68 | |||
69 | static inline u32 __readl(const volatile void __iomem *addr) | ||
70 | { | ||
71 | return flip_dword(*(__force volatile u32 *)addr); | ||
72 | } | ||
73 | |||
74 | static inline void __writeb(u8 b, volatile void __iomem *addr) | ||
75 | { | ||
76 | *(__force volatile u8 *)addr = b; | ||
77 | } | ||
78 | |||
79 | static inline void __writew(u16 w, volatile void __iomem *addr) | ||
80 | { | ||
81 | *(__force volatile u16 *)addr = flip_word(w); | ||
82 | } | ||
83 | |||
84 | static inline void __writel(u32 l, volatile void __iomem *addr) | ||
85 | { | ||
86 | *(__force volatile u32 *)addr = flip_dword(l); | ||
87 | } | ||
88 | |||
89 | #define readb(__addr) __readb(__addr) | ||
90 | #define readw(__addr) __readw(__addr) | ||
91 | #define readl(__addr) __readl(__addr) | ||
92 | #define readb_relaxed(__addr) readb(__addr) | ||
93 | #define readw_relaxed(__addr) readw(__addr) | ||
94 | #define readl_relaxed(__addr) readl(__addr) | ||
95 | |||
96 | #define writeb(__b, __addr) __writeb((__b),(__addr)) | ||
97 | #define writew(__w, __addr) __writew((__w),(__addr)) | ||
98 | #define writel(__l, __addr) __writel((__l),(__addr)) | ||
99 | |||
100 | /* | ||
101 | * I/O space operations | ||
102 | * | ||
103 | * Arrangement on a Sun is somewhat complicated. | ||
104 | * | ||
105 | * First of all, we want to use standard Linux drivers | ||
106 | * for keyboard, PC serial, etc. These drivers think | ||
107 | * they access I/O space and use inb/outb. | ||
108 | * On the other hand, EBus bridge accepts PCI *memory* | ||
109 | * cycles and converts them into ISA *I/O* cycles. | ||
110 | * Ergo, we want inb & outb to generate PCI memory cycles. | ||
111 | * | ||
112 | * If we want to issue PCI *I/O* cycles, we do this | ||
113 | * with a low 64K fixed window in PCIC. This window gets | ||
114 | * mapped somewhere into virtual kernel space and we | ||
115 | * can use inb/outb again. | ||
116 | */ | ||
117 | #define inb_local(__addr) __readb((void __iomem *)(unsigned long)(__addr)) | ||
118 | #define inb(__addr) __readb((void __iomem *)(unsigned long)(__addr)) | ||
119 | #define inw(__addr) __readw((void __iomem *)(unsigned long)(__addr)) | ||
120 | #define inl(__addr) __readl((void __iomem *)(unsigned long)(__addr)) | ||
121 | |||
122 | #define outb_local(__b, __addr) __writeb(__b, (void __iomem *)(unsigned long)(__addr)) | ||
123 | #define outb(__b, __addr) __writeb(__b, (void __iomem *)(unsigned long)(__addr)) | ||
124 | #define outw(__w, __addr) __writew(__w, (void __iomem *)(unsigned long)(__addr)) | ||
125 | #define outl(__l, __addr) __writel(__l, (void __iomem *)(unsigned long)(__addr)) | ||
126 | |||
127 | #define inb_p(__addr) inb(__addr) | ||
128 | #define outb_p(__b, __addr) outb(__b, __addr) | ||
129 | #define inw_p(__addr) inw(__addr) | ||
130 | #define outw_p(__w, __addr) outw(__w, __addr) | ||
131 | #define inl_p(__addr) inl(__addr) | ||
132 | #define outl_p(__l, __addr) outl(__l, __addr) | ||
133 | |||
134 | void outsb(unsigned long addr, const void *src, unsigned long cnt); | ||
135 | void outsw(unsigned long addr, const void *src, unsigned long cnt); | ||
136 | void outsl(unsigned long addr, const void *src, unsigned long cnt); | ||
137 | void insb(unsigned long addr, void *dst, unsigned long count); | ||
138 | void insw(unsigned long addr, void *dst, unsigned long count); | ||
139 | void insl(unsigned long addr, void *dst, unsigned long count); | ||
140 | |||
141 | #define IO_SPACE_LIMIT 0xffffffff | ||
142 | |||
143 | /* | ||
144 | * SBus accessors. | ||
145 | * | ||
146 | * SBus has only one, memory mapped, I/O space. | ||
147 | * We do not need to flip bytes for SBus of course. | ||
148 | */ | ||
149 | static inline u8 _sbus_readb(const volatile void __iomem *addr) | ||
150 | { | ||
151 | return *(__force volatile u8 *)addr; | ||
152 | } | ||
153 | |||
154 | static inline u16 _sbus_readw(const volatile void __iomem *addr) | ||
155 | { | ||
156 | return *(__force volatile u16 *)addr; | ||
157 | } | ||
158 | |||
159 | static inline u32 _sbus_readl(const volatile void __iomem *addr) | ||
160 | { | ||
161 | return *(__force volatile u32 *)addr; | ||
162 | } | ||
163 | |||
164 | static inline void _sbus_writeb(u8 b, volatile void __iomem *addr) | ||
165 | { | ||
166 | *(__force volatile u8 *)addr = b; | ||
167 | } | ||
168 | |||
169 | static inline void _sbus_writew(u16 w, volatile void __iomem *addr) | ||
170 | { | ||
171 | *(__force volatile u16 *)addr = w; | ||
172 | } | ||
173 | |||
174 | static inline void _sbus_writel(u32 l, volatile void __iomem *addr) | ||
175 | { | ||
176 | *(__force volatile u32 *)addr = l; | ||
177 | } | ||
178 | |||
179 | /* | ||
180 | * The only reason for #define's is to hide casts to unsigned long. | ||
181 | */ | ||
182 | #define sbus_readb(__addr) _sbus_readb(__addr) | ||
183 | #define sbus_readw(__addr) _sbus_readw(__addr) | ||
184 | #define sbus_readl(__addr) _sbus_readl(__addr) | ||
185 | #define sbus_writeb(__b, __addr) _sbus_writeb(__b, __addr) | ||
186 | #define sbus_writew(__w, __addr) _sbus_writew(__w, __addr) | ||
187 | #define sbus_writel(__l, __addr) _sbus_writel(__l, __addr) | ||
188 | |||
189 | static inline void sbus_memset_io(volatile void __iomem *__dst, int c, __kernel_size_t n) | ||
190 | { | ||
191 | while(n--) { | ||
192 | sbus_writeb(c, __dst); | ||
193 | __dst++; | ||
194 | } | ||
195 | } | ||
196 | |||
197 | static inline void | ||
198 | _memset_io(volatile void __iomem *dst, int c, __kernel_size_t n) | ||
199 | { | ||
200 | volatile void __iomem *d = dst; | ||
201 | |||
202 | while (n--) { | ||
203 | writeb(c, d); | ||
204 | d++; | ||
205 | } | ||
206 | } | ||
207 | |||
208 | #define memset_io(d,c,sz) _memset_io(d,c,sz) | ||
209 | |||
210 | static inline void | ||
211 | _memcpy_fromio(void *dst, const volatile void __iomem *src, __kernel_size_t n) | ||
212 | { | ||
213 | char *d = dst; | ||
214 | |||
215 | while (n--) { | ||
216 | char tmp = readb(src); | ||
217 | *d++ = tmp; | ||
218 | src++; | ||
219 | } | ||
220 | } | ||
221 | |||
222 | #define memcpy_fromio(d,s,sz) _memcpy_fromio(d,s,sz) | ||
223 | |||
224 | static inline void | ||
225 | _memcpy_toio(volatile void __iomem *dst, const void *src, __kernel_size_t n) | ||
226 | { | ||
227 | const char *s = src; | ||
228 | volatile void __iomem *d = dst; | ||
229 | |||
230 | while (n--) { | ||
231 | char tmp = *s++; | ||
232 | writeb(tmp, d); | ||
233 | d++; | ||
234 | } | ||
235 | } | ||
236 | |||
237 | #define memcpy_toio(d,s,sz) _memcpy_toio(d,s,sz) | ||
238 | |||
239 | #ifdef __KERNEL__ | ||
240 | |||
241 | /* | ||
242 | * Bus number may be embedded in the higher bits of the physical address. | ||
243 | * This is why we have no bus number argument to ioremap(). | ||
244 | */ | ||
245 | extern void __iomem *ioremap(unsigned long offset, unsigned long size); | ||
246 | #define ioremap_nocache(X,Y) ioremap((X),(Y)) | ||
247 | extern void iounmap(volatile void __iomem *addr); | ||
248 | |||
249 | #define ioread8(X) readb(X) | ||
250 | #define ioread16(X) readw(X) | ||
251 | #define ioread32(X) readl(X) | ||
252 | #define iowrite8(val,X) writeb(val,X) | ||
253 | #define iowrite16(val,X) writew(val,X) | ||
254 | #define iowrite32(val,X) writel(val,X) | ||
255 | |||
256 | static inline void ioread8_rep(void __iomem *port, void *buf, unsigned long count) | ||
257 | { | ||
258 | insb((unsigned long __force)port, buf, count); | ||
259 | } | ||
260 | static inline void ioread16_rep(void __iomem *port, void *buf, unsigned long count) | ||
261 | { | ||
262 | insw((unsigned long __force)port, buf, count); | ||
263 | } | ||
264 | |||
265 | static inline void ioread32_rep(void __iomem *port, void *buf, unsigned long count) | ||
266 | { | ||
267 | insl((unsigned long __force)port, buf, count); | ||
268 | } | ||
269 | |||
270 | static inline void iowrite8_rep(void __iomem *port, const void *buf, unsigned long count) | ||
271 | { | ||
272 | outsb((unsigned long __force)port, buf, count); | ||
273 | } | ||
274 | |||
275 | static inline void iowrite16_rep(void __iomem *port, const void *buf, unsigned long count) | ||
276 | { | ||
277 | outsw((unsigned long __force)port, buf, count); | ||
278 | } | ||
279 | |||
280 | static inline void iowrite32_rep(void __iomem *port, const void *buf, unsigned long count) | ||
281 | { | ||
282 | outsl((unsigned long __force)port, buf, count); | ||
283 | } | ||
284 | |||
285 | /* Create a virtual mapping cookie for an IO port range */ | ||
286 | extern void __iomem *ioport_map(unsigned long port, unsigned int nr); | ||
287 | extern void ioport_unmap(void __iomem *); | ||
288 | |||
289 | /* Create a virtual mapping cookie for a PCI BAR (memory or IO) */ | ||
290 | struct pci_dev; | ||
291 | extern void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long max); | ||
292 | extern void pci_iounmap(struct pci_dev *dev, void __iomem *); | ||
293 | |||
294 | /* | ||
295 | * Bus number may be in res->flags... somewhere. | ||
296 | */ | ||
297 | extern void __iomem *sbus_ioremap(struct resource *res, unsigned long offset, | ||
298 | unsigned long size, char *name); | ||
299 | extern void sbus_iounmap(volatile void __iomem *vaddr, unsigned long size); | ||
300 | |||
301 | |||
302 | /* | ||
303 | * At the moment, we do not use CMOS_READ anywhere outside of rtc.c, | ||
304 | * so rtc_port is static in it. This should not change unless a new | ||
305 | * hardware pops up. | ||
306 | */ | ||
307 | #define RTC_PORT(x) (rtc_port + (x)) | ||
308 | #define RTC_ALWAYS_BCD 0 | ||
309 | |||
310 | #endif | ||
311 | |||
312 | #define __ARCH_HAS_NO_PAGE_ZERO_MAPPED 1 | ||
313 | |||
314 | /* | ||
315 | * Convert a physical pointer to a virtual kernel pointer for /dev/mem | ||
316 | * access | ||
317 | */ | ||
318 | #define xlate_dev_mem_ptr(p) __va(p) | ||
319 | |||
320 | /* | ||
321 | * Convert a virtual cached pointer to an uncached pointer | ||
322 | */ | ||
323 | #define xlate_dev_kmem_ptr(p) p | ||
324 | |||
325 | #endif /* !(__SPARC_IO_H) */ | ||