Root/target/linux/ubicom32/files/arch/ubicom32/mach-common/io.c

1/*
2 * arch/ubicom32/mach-common/io.c
3 * PCI I/O memory read/write support functions.
4 *
5 * (C) Copyright 2009, Ubicom, Inc.
6 *
7 * This file is part of the Ubicom32 Linux Kernel Port.
8 *
9 * The Ubicom32 Linux Kernel Port is free software: you can redistribute
10 * it and/or modify it under the terms of the GNU General Public License
11 * as published by the Free Software Foundation, either version 2 of the
12 * License, or (at your option) any later version.
13 *
14 * The Ubicom32 Linux Kernel Port is distributed in the hope that it
15 * will be useful, but WITHOUT ANY WARRANTY; without even the implied
16 * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
17 * the GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with the Ubicom32 Linux Kernel Port. If not,
21 * see <http://www.gnu.org/licenses/>.
22 *
23 * Ubicom32 implementation derived from (with many thanks):
24 * arch/m68knommu
25 * arch/blackfin
26 * arch/parisc
27 */
28#include <linux/module.h>
29#include <linux/kernel.h>
30#include <linux/io.h>
31
32#ifdef CONFIG_PCI
33unsigned char ioread8(void __iomem *addr)
34{
35    if (IS_PCI_ADDRESS(addr))
36        return ubi32_pci_read_u8(addr);
37    else
38        return (unsigned char)(*(volatile unsigned char *)addr);
39}
40EXPORT_SYMBOL(ioread8);
41
42unsigned short ioread16(void __iomem *addr)
43{
44    if (IS_PCI_ADDRESS(addr))
45        return ubi32_pci_read_u16(addr);
46    else
47        return (unsigned short)(*(volatile unsigned short *)addr);
48}
49EXPORT_SYMBOL(ioread16);
50
51unsigned int ioread32(void __iomem *addr)
52{
53    if (IS_PCI_ADDRESS(addr))
54        return ubi32_pci_read_u32(addr);
55    else
56        return (unsigned int)(*(volatile unsigned int *)addr);
57}
58EXPORT_SYMBOL(ioread32);
59
60void iowrite32(unsigned int val, void __iomem *addr)
61{
62    if (IS_PCI_ADDRESS(addr))
63        ubi32_pci_write_u32(val, addr);
64    else
65        *(volatile unsigned int *)addr = val;
66}
67EXPORT_SYMBOL(iowrite32);
68
69void iowrite16(unsigned short val, void __iomem *addr)
70{
71    if (IS_PCI_ADDRESS(addr))
72        ubi32_pci_write_u16(val, addr);
73    else
74        *(volatile unsigned short *)addr = val;
75}
76EXPORT_SYMBOL(iowrite16);
77
78void iowrite8(unsigned char val, void __iomem *addr)
79{
80    if (IS_PCI_ADDRESS(addr))
81        ubi32_pci_write_u8(val, addr);
82    else
83        *(volatile unsigned char *)addr = val;
84}
85EXPORT_SYMBOL(iowrite8);
86
87void memcpy_fromio(void *to, const volatile void __iomem *from, unsigned len)
88{
89    if (IS_PCI_ADDRESS(from)) {
90        if ((((u32_t)from & 0x3) == 0) && (((u32_t)to & 0x3) == 0)) {
91            while ((int)len >= 4) {
92                *(u32_t *)to = ubi32_pci_read_u32(from);
93                to += 4;
94                from += 4;
95                len -= 4;
96            }
97        } else if ((((u32_t)from & 0x1) == 0) &&
98               (((u32_t)to & 0x1) == 0)) {
99            while ((int)len >= 2) {
100                 *(u16_t *)to = ubi32_pci_read_u16(from);
101                 to += 2;
102                 from += 2;
103                 len -= 2;
104            }
105        }
106
107        while (len) {
108            *(u8_t *)to = ubi32_pci_read_u8(from);
109            to++;
110            from++;
111            len--;
112        }
113    } else
114        memcpy(to, (void *)from, len);
115}
116EXPORT_SYMBOL(memcpy_fromio);
117
118void memcpy_toio(volatile void __iomem *to, const void *from, unsigned len)
119{
120    if (IS_PCI_ADDRESS(to)) {
121        if ((((u32_t)from & 0x3) == 0) && (((u32_t)to & 0x3) == 0)) {
122            while ((int)len >= 4) {
123                ubi32_pci_write_u32(*(u32_t *)from, to);
124                to += 4;
125                from += 4;
126                len -= 4;
127            }
128        } else if ((((u32_t)from & 0x1) == 0) &&
129               (((u32_t)to & 0x1) == 0)) {
130            while ((int)len >= 2) {
131                ubi32_pci_write_u16(*(u16_t *)from, to);
132                to += 2;
133                from += 2;
134                len -= 2;
135            }
136        }
137
138        while (len) {
139            ubi32_pci_write_u8(*(u8_t *)from, to);
140            from++;
141            to++;
142            len--;
143        }
144    } else
145        memcpy((void *)to, from, len);
146
147}
148EXPORT_SYMBOL(memcpy_toio);
149
150void memset_io(volatile void __iomem *addr, int val, size_t len)
151{
152    if (IS_PCI_ADDRESS(addr)) {
153        while (len) {
154            ubi32_pci_write_u8((unsigned char)val, addr);
155            addr++;
156            len--;
157        }
158    } else
159        memset((void *)addr, val, len);
160
161}
162EXPORT_SYMBOL(memset_io);
163
164void ioread8_rep(void __iomem *port, void *buf, unsigned long count)
165{
166    if (IS_PCI_ADDRESS(port)) {
167        while (count) {
168            *(u8_t *)buf = ioread8(port);
169            buf++;
170            count--;
171        }
172    } else {
173        insb((unsigned int)port, buf, count);
174    }
175
176}
177EXPORT_SYMBOL(ioread8_rep);
178
179void ioread16_rep(void __iomem *port, void *buf, unsigned long count)
180{
181    if (IS_PCI_ADDRESS(port)) {
182        while (count) {
183            *(u16_t *)buf = ioread16(port);
184            buf += 2;
185            count--;
186        }
187    } else {
188        insw((unsigned int)port, buf, count);
189    }
190}
191EXPORT_SYMBOL(ioread16_rep);
192
193void ioread32_rep(void __iomem *port, void *buf, unsigned long count)
194{
195     if (IS_PCI_ADDRESS(port)) {
196        while (count) {
197            *(u32_t *)buf = ioread32(port);
198            buf += 4;
199            count--;
200        }
201    } else {
202        insl((unsigned int)port, buf, count);
203    }
204}
205EXPORT_SYMBOL(ioread32_rep);
206
207void iowrite8_rep(void __iomem *port, const void *buf, unsigned long count)
208{
209      if (IS_PCI_ADDRESS(port)) {
210        while (count) {
211            iowrite8(*(u8_t *)buf, port);
212            buf++;
213            count--;
214        }
215    } else {
216        outsb((unsigned int)port, buf, count);
217    }
218
219}
220EXPORT_SYMBOL(iowrite8_rep);
221
222void iowrite16_rep(void __iomem *port, const void *buf, unsigned long count)
223{
224    if (IS_PCI_ADDRESS(port)) {
225        while (count) {
226            iowrite16(*(u16_t *)buf, port);
227            buf += 2;
228            count--;
229        }
230    } else {
231        outsw((unsigned int)port, buf, count);
232    }
233}
234EXPORT_SYMBOL(iowrite16_rep);
235
236void iowrite32_rep(void __iomem *port, const void *buf, unsigned long count)
237{
238    if (IS_PCI_ADDRESS(port)) {
239        while (count) {
240            iowrite32(*(u32_t *)buf, port);
241            buf += 4;
242            count--;
243        }
244    } else {
245        outsl((unsigned int)port, buf, count);
246    }
247}
248EXPORT_SYMBOL(iowrite32_rep);
249
250#endif /* CONFIG_PCI */
251

Archive Download this file



interactive