blob: 6df9743270ec0e74c2ada443e0c910f3c7dd04b1 [file] [log] [blame]
Sam Ravnborgf5e706a2008-07-17 21:55:51 -07001#ifndef __SPARC64_IO_H
2#define __SPARC64_IO_H
3
4#include <linux/kernel.h>
5#include <linux/compiler.h>
6#include <linux/types.h>
7
8#include <asm/page.h> /* IO address mapping routines need this */
Sam Ravnborgf5e706a2008-07-17 21:55:51 -07009#include <asm/asi.h>
Michael S. Tsirkina21a2fd2011-11-24 21:10:12 +020010#include <asm-generic/pci_iomap.h>
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070011
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070012/* BIO layer definitions. */
13extern unsigned long kern_base, kern_size;
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070014
Sam Ravnborg79294d72014-07-20 13:39:00 +020015#define inb inb
16static inline u8 inb(unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070017{
18 u8 ret;
19
20 __asm__ __volatile__("lduba\t[%1] %2, %0\t/* pci_inb */"
21 : "=r" (ret)
22 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
23 : "memory");
24
25 return ret;
26}
27
Sam Ravnborg79294d72014-07-20 13:39:00 +020028#define inw inw
29static inline u16 inw(unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070030{
31 u16 ret;
32
33 __asm__ __volatile__("lduha\t[%1] %2, %0\t/* pci_inw */"
34 : "=r" (ret)
35 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
36 : "memory");
37
38 return ret;
39}
40
Sam Ravnborg79294d72014-07-20 13:39:00 +020041#define inl inl
42static inline u32 inl(unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070043{
44 u32 ret;
45
46 __asm__ __volatile__("lduwa\t[%1] %2, %0\t/* pci_inl */"
47 : "=r" (ret)
48 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
49 : "memory");
50
51 return ret;
52}
53
Sam Ravnborg79294d72014-07-20 13:39:00 +020054#define outb outb
55static inline void outb(u8 b, unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070056{
57 __asm__ __volatile__("stba\t%r0, [%1] %2\t/* pci_outb */"
58 : /* no outputs */
59 : "Jr" (b), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
60 : "memory");
61}
62
Sam Ravnborg79294d72014-07-20 13:39:00 +020063#define outw outw
64static inline void outw(u16 w, unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070065{
66 __asm__ __volatile__("stha\t%r0, [%1] %2\t/* pci_outw */"
67 : /* no outputs */
68 : "Jr" (w), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
69 : "memory");
70}
71
Sam Ravnborg79294d72014-07-20 13:39:00 +020072#define outl outl
73static inline void outl(u32 l, unsigned long addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070074{
75 __asm__ __volatile__("stwa\t%r0, [%1] %2\t/* pci_outl */"
76 : /* no outputs */
77 : "Jr" (l), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
78 : "memory");
79}
80
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070081
82#define inb_p(__addr) inb(__addr)
83#define outb_p(__b, __addr) outb(__b, __addr)
84#define inw_p(__addr) inw(__addr)
85#define outw_p(__w, __addr) outw(__w, __addr)
86#define inl_p(__addr) inl(__addr)
87#define outl_p(__l, __addr) outl(__l, __addr)
88
Sam Ravnborgf05a6862014-05-16 23:25:50 +020089void outsb(unsigned long, const void *, unsigned long);
90void outsw(unsigned long, const void *, unsigned long);
91void outsl(unsigned long, const void *, unsigned long);
92void insb(unsigned long, void *, unsigned long);
93void insw(unsigned long, void *, unsigned long);
94void insl(unsigned long, void *, unsigned long);
Sam Ravnborgf5e706a2008-07-17 21:55:51 -070095
96static inline void ioread8_rep(void __iomem *port, void *buf, unsigned long count)
97{
98 insb((unsigned long __force)port, buf, count);
99}
100static inline void ioread16_rep(void __iomem *port, void *buf, unsigned long count)
101{
102 insw((unsigned long __force)port, buf, count);
103}
104
105static inline void ioread32_rep(void __iomem *port, void *buf, unsigned long count)
106{
107 insl((unsigned long __force)port, buf, count);
108}
109
110static inline void iowrite8_rep(void __iomem *port, const void *buf, unsigned long count)
111{
112 outsb((unsigned long __force)port, buf, count);
113}
114
115static inline void iowrite16_rep(void __iomem *port, const void *buf, unsigned long count)
116{
117 outsw((unsigned long __force)port, buf, count);
118}
119
120static inline void iowrite32_rep(void __iomem *port, const void *buf, unsigned long count)
121{
122 outsl((unsigned long __force)port, buf, count);
123}
124
125/* Memory functions, same as I/O accesses on Ultra. */
Sam Ravnborg79294d72014-07-20 13:39:00 +0200126#define readb readb
127static inline u8 readb(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700128{ u8 ret;
129
130 __asm__ __volatile__("lduba\t[%1] %2, %0\t/* pci_readb */"
131 : "=r" (ret)
132 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
133 : "memory");
134 return ret;
135}
136
Sam Ravnborg79294d72014-07-20 13:39:00 +0200137#define readw readw
138static inline u16 readw(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700139{ u16 ret;
140
141 __asm__ __volatile__("lduha\t[%1] %2, %0\t/* pci_readw */"
142 : "=r" (ret)
143 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
144 : "memory");
145
146 return ret;
147}
148
Sam Ravnborg79294d72014-07-20 13:39:00 +0200149#define readl readl
150static inline u32 readl(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700151{ u32 ret;
152
153 __asm__ __volatile__("lduwa\t[%1] %2, %0\t/* pci_readl */"
154 : "=r" (ret)
155 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
156 : "memory");
157
158 return ret;
159}
160
Sam Ravnborg79294d72014-07-20 13:39:00 +0200161#define readq readq
162static inline u64 readq(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700163{ u64 ret;
164
165 __asm__ __volatile__("ldxa\t[%1] %2, %0\t/* pci_readq */"
166 : "=r" (ret)
167 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
168 : "memory");
169
170 return ret;
171}
172
Sam Ravnborg79294d72014-07-20 13:39:00 +0200173#define writeb writeb
174static inline void writeb(u8 b, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700175{
176 __asm__ __volatile__("stba\t%r0, [%1] %2\t/* pci_writeb */"
177 : /* no outputs */
178 : "Jr" (b), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
179 : "memory");
180}
181
Sam Ravnborg79294d72014-07-20 13:39:00 +0200182#define writew writew
183static inline void writew(u16 w, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700184{
185 __asm__ __volatile__("stha\t%r0, [%1] %2\t/* pci_writew */"
186 : /* no outputs */
187 : "Jr" (w), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
188 : "memory");
189}
190
Sam Ravnborg79294d72014-07-20 13:39:00 +0200191#define writel writel
192static inline void writel(u32 l, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700193{
194 __asm__ __volatile__("stwa\t%r0, [%1] %2\t/* pci_writel */"
195 : /* no outputs */
196 : "Jr" (l), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
197 : "memory");
198}
199
Sam Ravnborg79294d72014-07-20 13:39:00 +0200200#define writeq writeq
201static inline void writeq(u64 q, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700202{
203 __asm__ __volatile__("stxa\t%r0, [%1] %2\t/* pci_writeq */"
204 : /* no outputs */
205 : "Jr" (q), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E_L)
206 : "memory");
207}
208
Sam Ravnborg79294d72014-07-20 13:39:00 +0200209#define readb_relaxed(__addr) readb(__addr)
210#define readw_relaxed(__addr) readw(__addr)
211#define readl_relaxed(__addr) readl(__addr)
212#define readq_relaxed(__addr) readq(__addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700213
214/* Now versions without byte-swapping. */
Sam Ravnborg79294d72014-07-20 13:39:00 +0200215#define __raw_readb __raw_readb
216static inline u8 __raw_readb(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700217{
218 u8 ret;
219
220 __asm__ __volatile__("lduba\t[%1] %2, %0\t/* pci_raw_readb */"
221 : "=r" (ret)
222 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
223
224 return ret;
225}
226
Sam Ravnborg79294d72014-07-20 13:39:00 +0200227#define __raw_readw __raw_readw
228static inline u16 __raw_readw(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700229{
230 u16 ret;
231
232 __asm__ __volatile__("lduha\t[%1] %2, %0\t/* pci_raw_readw */"
233 : "=r" (ret)
234 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
235
236 return ret;
237}
238
Sam Ravnborg79294d72014-07-20 13:39:00 +0200239#define __raw_readl __raw_readl
240static inline u32 __raw_readl(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700241{
242 u32 ret;
243
244 __asm__ __volatile__("lduwa\t[%1] %2, %0\t/* pci_raw_readl */"
245 : "=r" (ret)
246 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
247
248 return ret;
249}
250
Sam Ravnborg79294d72014-07-20 13:39:00 +0200251#define __raw_readq __raw_readq
252static inline u64 __raw_readq(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700253{
254 u64 ret;
255
256 __asm__ __volatile__("ldxa\t[%1] %2, %0\t/* pci_raw_readq */"
257 : "=r" (ret)
258 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
259
260 return ret;
261}
262
Sam Ravnborg79294d72014-07-20 13:39:00 +0200263#define __raw_writeb __raw_writeb
264static inline void __raw_writeb(u8 b, const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700265{
266 __asm__ __volatile__("stba\t%r0, [%1] %2\t/* pci_raw_writeb */"
267 : /* no outputs */
268 : "Jr" (b), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
269}
270
Sam Ravnborg79294d72014-07-20 13:39:00 +0200271#define __raw_writew __raw_writew
272static inline void __raw_writew(u16 w, const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700273{
274 __asm__ __volatile__("stha\t%r0, [%1] %2\t/* pci_raw_writew */"
275 : /* no outputs */
276 : "Jr" (w), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
277}
278
Sam Ravnborg79294d72014-07-20 13:39:00 +0200279#define __raw_writel __raw_writel
280static inline void __raw_writel(u32 l, const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700281{
282 __asm__ __volatile__("stwa\t%r0, [%1] %2\t/* pci_raw_writel */"
283 : /* no outputs */
284 : "Jr" (l), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
285}
286
Sam Ravnborg79294d72014-07-20 13:39:00 +0200287#define __raw_writeq __raw_writeq
288static inline void __raw_writeq(u64 q, const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700289{
290 __asm__ __volatile__("stxa\t%r0, [%1] %2\t/* pci_raw_writeq */"
291 : /* no outputs */
292 : "Jr" (q), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E));
293}
294
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700295
296/* Valid I/O Space regions are anywhere, because each PCI bus supported
297 * can live in an arbitrary area of the physical address range.
298 */
299#define IO_SPACE_LIMIT 0xffffffffffffffffUL
300
301/* Now, SBUS variants, only difference from PCI is that we do
302 * not use little-endian ASIs.
303 */
Sam Ravnborg79294d72014-07-20 13:39:00 +0200304static inline u8 sbus_readb(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700305{
306 u8 ret;
307
308 __asm__ __volatile__("lduba\t[%1] %2, %0\t/* sbus_readb */"
309 : "=r" (ret)
310 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
311 : "memory");
312
313 return ret;
314}
315
Sam Ravnborg79294d72014-07-20 13:39:00 +0200316static inline u16 sbus_readw(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700317{
318 u16 ret;
319
320 __asm__ __volatile__("lduha\t[%1] %2, %0\t/* sbus_readw */"
321 : "=r" (ret)
322 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
323 : "memory");
324
325 return ret;
326}
327
Sam Ravnborg79294d72014-07-20 13:39:00 +0200328static inline u32 sbus_readl(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700329{
330 u32 ret;
331
332 __asm__ __volatile__("lduwa\t[%1] %2, %0\t/* sbus_readl */"
333 : "=r" (ret)
334 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
335 : "memory");
336
337 return ret;
338}
339
Sam Ravnborg79294d72014-07-20 13:39:00 +0200340static inline u64 sbus_readq(const volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700341{
342 u64 ret;
343
344 __asm__ __volatile__("ldxa\t[%1] %2, %0\t/* sbus_readq */"
345 : "=r" (ret)
346 : "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
347 : "memory");
348
349 return ret;
350}
351
Sam Ravnborg79294d72014-07-20 13:39:00 +0200352static inline void sbus_writeb(u8 b, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700353{
354 __asm__ __volatile__("stba\t%r0, [%1] %2\t/* sbus_writeb */"
355 : /* no outputs */
356 : "Jr" (b), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
357 : "memory");
358}
359
Sam Ravnborg79294d72014-07-20 13:39:00 +0200360static inline void sbus_writew(u16 w, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700361{
362 __asm__ __volatile__("stha\t%r0, [%1] %2\t/* sbus_writew */"
363 : /* no outputs */
364 : "Jr" (w), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
365 : "memory");
366}
367
Sam Ravnborg79294d72014-07-20 13:39:00 +0200368static inline void sbus_writel(u32 l, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700369{
370 __asm__ __volatile__("stwa\t%r0, [%1] %2\t/* sbus_writel */"
371 : /* no outputs */
372 : "Jr" (l), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
373 : "memory");
374}
375
Sam Ravnborg79294d72014-07-20 13:39:00 +0200376static inline void sbus_writeq(u64 l, volatile void __iomem *addr)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700377{
378 __asm__ __volatile__("stxa\t%r0, [%1] %2\t/* sbus_writeq */"
379 : /* no outputs */
380 : "Jr" (l), "r" (addr), "i" (ASI_PHYS_BYPASS_EC_E)
381 : "memory");
382}
383
Sam Ravnborg79294d72014-07-20 13:39:00 +0200384static inline void sbus_memset_io(volatile void __iomem *dst, int c, __kernel_size_t n)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700385{
386 while(n--) {
387 sbus_writeb(c, dst);
388 dst++;
389 }
390}
391
Sam Ravnborg79294d72014-07-20 13:39:00 +0200392static inline void memset_io(volatile void __iomem *dst, int c, __kernel_size_t n)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700393{
394 volatile void __iomem *d = dst;
395
396 while (n--) {
397 writeb(c, d);
398 d++;
399 }
400}
401
Sam Ravnborg79294d72014-07-20 13:39:00 +0200402static inline void sbus_memcpy_fromio(void *dst, const volatile void __iomem *src,
403 __kernel_size_t n)
James Hoganf11b4782010-10-27 15:33:28 -0700404{
405 char *d = dst;
406
407 while (n--) {
408 char tmp = sbus_readb(src);
409 *d++ = tmp;
410 src++;
411 }
412}
413
James Hoganf11b4782010-10-27 15:33:28 -0700414
Sam Ravnborg79294d72014-07-20 13:39:00 +0200415static inline void memcpy_fromio(void *dst, const volatile void __iomem *src,
416 __kernel_size_t n)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700417{
418 char *d = dst;
419
420 while (n--) {
421 char tmp = readb(src);
422 *d++ = tmp;
423 src++;
424 }
425}
426
Sam Ravnborg79294d72014-07-20 13:39:00 +0200427static inline void sbus_memcpy_toio(volatile void __iomem *dst, const void *src,
428 __kernel_size_t n)
James Hoganf11b4782010-10-27 15:33:28 -0700429{
430 const char *s = src;
431 volatile void __iomem *d = dst;
432
433 while (n--) {
434 char tmp = *s++;
435 sbus_writeb(tmp, d);
436 d++;
437 }
438}
439
Sam Ravnborg79294d72014-07-20 13:39:00 +0200440static inline void memcpy_toio(volatile void __iomem *dst, const void *src,
441 __kernel_size_t n)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700442{
443 const char *s = src;
444 volatile void __iomem *d = dst;
445
446 while (n--) {
447 char tmp = *s++;
448 writeb(tmp, d);
449 d++;
450 }
451}
452
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700453#define mmiowb()
454
455#ifdef __KERNEL__
456
457/* On sparc64 we have the whole physical IO address space accessible
458 * using physically addressed loads and stores, so this does nothing.
459 */
460static inline void __iomem *ioremap(unsigned long offset, unsigned long size)
461{
462 return (void __iomem *)offset;
463}
464
465#define ioremap_nocache(X,Y) ioremap((X),(Y))
David S. Miller428695b2008-07-22 14:30:55 -0700466#define ioremap_wc(X,Y) ioremap((X),(Y))
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700467
468static inline void iounmap(volatile void __iomem *addr)
469{
470}
471
472#define ioread8(X) readb(X)
473#define ioread16(X) readw(X)
David S. Miller1bff4db2010-03-03 02:30:37 -0800474#define ioread16be(X) __raw_readw(X)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700475#define ioread32(X) readl(X)
David S. Miller1bff4db2010-03-03 02:30:37 -0800476#define ioread32be(X) __raw_readl(X)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700477#define iowrite8(val,X) writeb(val,X)
478#define iowrite16(val,X) writew(val,X)
David S. Miller1bff4db2010-03-03 02:30:37 -0800479#define iowrite16be(val,X) __raw_writew(val,X)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700480#define iowrite32(val,X) writel(val,X)
David S. Miller1bff4db2010-03-03 02:30:37 -0800481#define iowrite32be(val,X) __raw_writel(val,X)
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700482
483/* Create a virtual mapping cookie for an IO port range */
Sam Ravnborgf05a6862014-05-16 23:25:50 +0200484void __iomem *ioport_map(unsigned long port, unsigned int nr);
485void ioport_unmap(void __iomem *);
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700486
487/* Create a virtual mapping cookie for a PCI BAR (memory or IO) */
488struct pci_dev;
Sam Ravnborgf05a6862014-05-16 23:25:50 +0200489void pci_iounmap(struct pci_dev *dev, void __iomem *);
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700490
David S. Miller63237ee2008-08-26 23:33:42 -0700491static inline int sbus_can_dma_64bit(void)
492{
493 return 1;
494}
495static inline int sbus_can_burst64(void)
496{
497 return 1;
498}
499struct device;
Sam Ravnborgf05a6862014-05-16 23:25:50 +0200500void sbus_set_sbus64(struct device *, int);
David S. Miller63237ee2008-08-26 23:33:42 -0700501
Sam Ravnborgf5e706a2008-07-17 21:55:51 -0700502/*
503 * Convert a physical pointer to a virtual kernel pointer for /dev/mem
504 * access
505 */
506#define xlate_dev_mem_ptr(p) __va(p)
507
508/*
509 * Convert a virtual cached pointer to an uncached pointer
510 */
511#define xlate_dev_kmem_ptr(p) p
512
513#endif
514
515#endif /* !(__SPARC64_IO_H) */