source: GPL/trunk/include/asm/io.h@ 689

Last change on this file since 689 was 442, checked in by Paul Smedley, 16 years ago

Reorganise code to make maintenance easier

File size: 5.0 KB
Line 
1#ifndef _ASM_IO_H
2#define _ASM_IO_H
3
4#include <asm/pgtable.h>
5/*
6 * This file contains the definitions for the x86 IO instructions
7 * inb/inw/inl/outb/outw/outl and the "string versions" of the same
8 * (insb/insw/insl/outsb/outsw/outsl). You can also use "pausing"
9 * versions of the single-IO instructions (inb_p/inw_p/..).
10 *
11 * This file is not meant to be obfuscating: it's just complicated
12 * to (a) handle it all in a way that makes gcc able to optimize it
13 * as well as possible and (b) trying to avoid writing the same thing
14 * over and over again with slight variations and possibly making a
15 * mistake somewhere.
16 */
17
18extern void * __ioremap(unsigned long offset, unsigned long size, unsigned long flags);
19
20#define ioremap(offset, size) __ioremap(offset, size, 0)
21
22/*
23 * This one maps high address device memory and turns off caching for that area.
24 * it's useful if some control registers are in such an area and write combining
25 * or read caching is not desirable:
26 */
27#define ioremap_nocache(offset, size) __ioremap(offset, size, _PAGE_PCD)
28
29extern void iounmap(void *addr);
30
31/*
32 * readX/writeX() are used to access memory mapped devices. On some
33 * architectures the memory mapped IO stuff needs to be accessed
34 * differently. On the x86 architecture, we just read/write the
35 * memory location directly.
36 */
37
38#define readb(addr) (*(volatile unsigned char *) __io_virt(addr))
39#define readw(addr) (*(volatile unsigned short *) __io_virt(addr))
40#define readl(addr) (*(volatile unsigned int *) __io_virt(addr))
41#define __raw_readb readb
42#define __raw_readw readw
43#define __raw_readl readl
44
45#define writeb(b,addr) (*(volatile unsigned char *) __io_virt(addr) = (b))
46#define writew(b,addr) (*(volatile unsigned short *) __io_virt(addr) = (b))
47#define writel(b,addr) (*(volatile unsigned int *) __io_virt(addr) = (b))
48#define __raw_writeb writeb
49#define __raw_writew writew
50#define __raw_writel writel
51
52#define __io_virt(x) ((void *)(x))
53#define memset_io(a,b,c) memset(__io_virt(a),(b),(c))
54#define memcpy_fromio(a,b,c) memcpy((a),__io_virt(b),(c))
55#define memcpy_toio(a,b,c) memcpy(__io_virt(a),(b),(c))
56
57unsigned int ioread8(void __iomem *addr);
58unsigned int ioread16(void __iomem *addr);
59unsigned int ioread32(void __iomem *addr);
60void iowrite8(u8 val, void __iomem *addr);
61void iowrite16(u16 val, void __iomem *addr);
62void iowrite32(u32 val, void __iomem *addr);
63void __iomem *ioport_map(unsigned long port, unsigned int nr);
64void ioport_unmap(void __iomem *addr);
65void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen);
66void pci_iounmap(struct pci_dev *dev, void __iomem * addr);
67
68/*
69 * Thanks to James van Artsdalen for a better timing-fix than
70 * the two short jumps: using outb's to a nonexistent port seems
71 * to guarantee better timings even on fast machines.
72 *
73 * On the other hand, I'd like to be sure of a non-existent port:
74 * I feel a bit unsafe about using 0x80 (should be safe, though)
75 *
76 * Linus
77 */
78
79 /*
80 * Bit simplified and optimized by Jan Hubicka
81 * Support of BIGMEM added by Gerhard Wichert, Siemens AG, July 1999.
82 *
83 * isa_memset_io, isa_memcpy_fromio, isa_memcpy_toio added,
84 * isa_read[wl] and isa_write[wl] fixed
85 * - Arnaldo Carvalho de Melo <acme@conectiva.com.br>
86 */
87
88#ifdef SLOW_IO_BY_JUMPING
89#define __SLOW_DOWN_IO "\njmp 1f\n1:\tjmp 1f\n1:"
90#else
91#define __SLOW_DOWN_IO "\noutb %%al,$0x80"
92#endif
93
94#ifdef REALLY_SLOW_IO
95#define __FULL_SLOW_DOWN_IO __SLOW_DOWN_IO __SLOW_DOWN_IO __SLOW_DOWN_IO __SLOW_DOWN_IO
96#else
97#define __FULL_SLOW_DOWN_IO __SLOW_DOWN_IO
98#endif
99
100/*
101 * Talk about misusing macros..
102 */
103#define __OUT1(s,x) \
104extern inline void out##s(unsigned x value, unsigned short port) {
105
106
107#define __IN1(s) \
108extern inline RETURN_TYPE in##s(unsigned short port) { RETURN_TYPE _v;
109
110
111void outb(unsigned char data, unsigned short port);
112#pragma aux outb = \
113 "out dx, al" \
114 parm [al] [dx];
115
116void outsb(unsigned short port, char *buffer, int size);
117#pragma aux outsb = \
118 "outsb" \
119 parm [dx] [esi] [ecx];
120
121#if 1
122unsigned char inb(unsigned short port);
123#pragma aux inb = \
124 "in al,dx" \
125 parm [dx] \
126 value [al];
127#endif
128
129void insb(unsigned short port, char *buffer, int size);
130#pragma aux insb = \
131 "insb" \
132 parm [dx] [esi] [ecx];
133
134void outw(unsigned short data, unsigned short port);
135#pragma aux outw = \
136 "out dx, ax" \
137 parm [ax] [dx];
138
139void outsw(unsigned short port, void *buffer, int size);
140#pragma aux outsw = \
141 "outsw" \
142 parm [dx] [edi] [ecx];
143
144unsigned short inw(unsigned short port);
145#pragma aux inw = \
146 "in ax,dx" \
147 parm [dx] \
148 value [ax];
149
150void outl(unsigned long data, unsigned short port);
151#pragma aux outl = \
152 "out dx, eax" \
153 parm [eax] [dx];
154
155unsigned long inl(unsigned short port);
156#pragma aux inl = \
157 "in eax,dx" \
158 parm [dx] \
159 value [eax];
160
161#endif
Note: See TracBrowser for help on using the repository browser.