86d77a666458bae80c60f94c9fc405dca5f8459c
[~shefty/rdma-dev.git] / arch / mips / pci / pci-ar724x.c
1 /*
2  *  Atheros AR724X PCI host controller driver
3  *
4  *  Copyright (C) 2011 RenĂ© Bolldorf <xsecute@googlemail.com>
5  *  Copyright (C) 2009-2011 Gabor Juhos <juhosg@openwrt.org>
6  *
7  *  This program is free software; you can redistribute it and/or modify it
8  *  under the terms of the GNU General Public License version 2 as published
9  *  by the Free Software Foundation.
10  */
11
12 #include <linux/irq.h>
13 #include <linux/pci.h>
14 #include <asm/mach-ath79/ath79.h>
15 #include <asm/mach-ath79/ar71xx_regs.h>
16 #include <asm/mach-ath79/pci.h>
17
18 #define AR724X_PCI_CFG_BASE     0x14000000
19 #define AR724X_PCI_CFG_SIZE     0x1000
20 #define AR724X_PCI_CTRL_BASE    (AR71XX_APB_BASE + 0x000f0000)
21 #define AR724X_PCI_CTRL_SIZE    0x100
22
23 #define AR724X_PCI_MEM_BASE     0x10000000
24 #define AR724X_PCI_MEM_SIZE     0x08000000
25
26 #define AR724X_PCI_REG_RESET            0x18
27 #define AR724X_PCI_REG_INT_STATUS       0x4c
28 #define AR724X_PCI_REG_INT_MASK         0x50
29
30 #define AR724X_PCI_RESET_LINK_UP        BIT(0)
31
32 #define AR724X_PCI_INT_DEV0             BIT(14)
33
34 #define AR724X_PCI_IRQ_COUNT            1
35
36 #define AR7240_BAR0_WAR_VALUE   0xffff
37
38 static DEFINE_SPINLOCK(ar724x_pci_lock);
39 static void __iomem *ar724x_pci_devcfg_base;
40 static void __iomem *ar724x_pci_ctrl_base;
41
42 static u32 ar724x_pci_bar0_value;
43 static bool ar724x_pci_bar0_is_cached;
44 static bool ar724x_pci_link_up;
45
46 static inline bool ar724x_pci_check_link(void)
47 {
48         u32 reset;
49
50         reset = __raw_readl(ar724x_pci_ctrl_base + AR724X_PCI_REG_RESET);
51         return reset & AR724X_PCI_RESET_LINK_UP;
52 }
53
54 static int ar724x_pci_read(struct pci_bus *bus, unsigned int devfn, int where,
55                             int size, uint32_t *value)
56 {
57         unsigned long flags;
58         void __iomem *base;
59         u32 data;
60
61         if (!ar724x_pci_link_up)
62                 return PCIBIOS_DEVICE_NOT_FOUND;
63
64         if (devfn)
65                 return PCIBIOS_DEVICE_NOT_FOUND;
66
67         base = ar724x_pci_devcfg_base;
68
69         spin_lock_irqsave(&ar724x_pci_lock, flags);
70         data = __raw_readl(base + (where & ~3));
71
72         switch (size) {
73         case 1:
74                 if (where & 1)
75                         data >>= 8;
76                 if (where & 2)
77                         data >>= 16;
78                 data &= 0xff;
79                 break;
80         case 2:
81                 if (where & 2)
82                         data >>= 16;
83                 data &= 0xffff;
84                 break;
85         case 4:
86                 break;
87         default:
88                 spin_unlock_irqrestore(&ar724x_pci_lock, flags);
89
90                 return PCIBIOS_BAD_REGISTER_NUMBER;
91         }
92
93         spin_unlock_irqrestore(&ar724x_pci_lock, flags);
94
95         if (where == PCI_BASE_ADDRESS_0 && size == 4 &&
96             ar724x_pci_bar0_is_cached) {
97                 /* use the cached value */
98                 *value = ar724x_pci_bar0_value;
99         } else {
100                 *value = data;
101         }
102
103         return PCIBIOS_SUCCESSFUL;
104 }
105
106 static int ar724x_pci_write(struct pci_bus *bus, unsigned int devfn, int where,
107                              int size, uint32_t value)
108 {
109         unsigned long flags;
110         void __iomem *base;
111         u32 data;
112         int s;
113
114         if (!ar724x_pci_link_up)
115                 return PCIBIOS_DEVICE_NOT_FOUND;
116
117         if (devfn)
118                 return PCIBIOS_DEVICE_NOT_FOUND;
119
120         if (soc_is_ar7240() && where == PCI_BASE_ADDRESS_0 && size == 4) {
121                 if (value != 0xffffffff) {
122                         /*
123                          * WAR for a hw issue. If the BAR0 register of the
124                          * device is set to the proper base address, the
125                          * memory space of the device is not accessible.
126                          *
127                          * Cache the intended value so it can be read back,
128                          * and write a SoC specific constant value to the
129                          * BAR0 register in order to make the device memory
130                          * accessible.
131                          */
132                         ar724x_pci_bar0_is_cached = true;
133                         ar724x_pci_bar0_value = value;
134
135                         value = AR7240_BAR0_WAR_VALUE;
136                 } else {
137                         ar724x_pci_bar0_is_cached = false;
138                 }
139         }
140
141         base = ar724x_pci_devcfg_base;
142
143         spin_lock_irqsave(&ar724x_pci_lock, flags);
144         data = __raw_readl(base + (where & ~3));
145
146         switch (size) {
147         case 1:
148                 s = ((where & 3) * 8);
149                 data &= ~(0xff << s);
150                 data |= ((value & 0xff) << s);
151                 break;
152         case 2:
153                 s = ((where & 2) * 8);
154                 data &= ~(0xffff << s);
155                 data |= ((value & 0xffff) << s);
156                 break;
157         case 4:
158                 data = value;
159                 break;
160         default:
161                 spin_unlock_irqrestore(&ar724x_pci_lock, flags);
162
163                 return PCIBIOS_BAD_REGISTER_NUMBER;
164         }
165
166         __raw_writel(data, base + (where & ~3));
167         /* flush write */
168         __raw_readl(base + (where & ~3));
169         spin_unlock_irqrestore(&ar724x_pci_lock, flags);
170
171         return PCIBIOS_SUCCESSFUL;
172 }
173
174 static struct pci_ops ar724x_pci_ops = {
175         .read   = ar724x_pci_read,
176         .write  = ar724x_pci_write,
177 };
178
179 static struct resource ar724x_io_resource = {
180         .name   = "PCI IO space",
181         .start  = 0,
182         .end    = 0,
183         .flags  = IORESOURCE_IO,
184 };
185
186 static struct resource ar724x_mem_resource = {
187         .name   = "PCI memory space",
188         .start  = AR724X_PCI_MEM_BASE,
189         .end    = AR724X_PCI_MEM_BASE + AR724X_PCI_MEM_SIZE - 1,
190         .flags  = IORESOURCE_MEM,
191 };
192
193 static struct pci_controller ar724x_pci_controller = {
194         .pci_ops        = &ar724x_pci_ops,
195         .io_resource    = &ar724x_io_resource,
196         .mem_resource   = &ar724x_mem_resource,
197 };
198
199 static void ar724x_pci_irq_handler(unsigned int irq, struct irq_desc *desc)
200 {
201         void __iomem *base;
202         u32 pending;
203
204         base = ar724x_pci_ctrl_base;
205
206         pending = __raw_readl(base + AR724X_PCI_REG_INT_STATUS) &
207                   __raw_readl(base + AR724X_PCI_REG_INT_MASK);
208
209         if (pending & AR724X_PCI_INT_DEV0)
210                 generic_handle_irq(ATH79_PCI_IRQ(0));
211
212         else
213                 spurious_interrupt();
214 }
215
216 static void ar724x_pci_irq_unmask(struct irq_data *d)
217 {
218         void __iomem *base;
219         u32 t;
220
221         base = ar724x_pci_ctrl_base;
222
223         switch (d->irq) {
224         case ATH79_PCI_IRQ(0):
225                 t = __raw_readl(base + AR724X_PCI_REG_INT_MASK);
226                 __raw_writel(t | AR724X_PCI_INT_DEV0,
227                              base + AR724X_PCI_REG_INT_MASK);
228                 /* flush write */
229                 __raw_readl(base + AR724X_PCI_REG_INT_MASK);
230         }
231 }
232
233 static void ar724x_pci_irq_mask(struct irq_data *d)
234 {
235         void __iomem *base;
236         u32 t;
237
238         base = ar724x_pci_ctrl_base;
239
240         switch (d->irq) {
241         case ATH79_PCI_IRQ(0):
242                 t = __raw_readl(base + AR724X_PCI_REG_INT_MASK);
243                 __raw_writel(t & ~AR724X_PCI_INT_DEV0,
244                              base + AR724X_PCI_REG_INT_MASK);
245
246                 /* flush write */
247                 __raw_readl(base + AR724X_PCI_REG_INT_MASK);
248
249                 t = __raw_readl(base + AR724X_PCI_REG_INT_STATUS);
250                 __raw_writel(t | AR724X_PCI_INT_DEV0,
251                              base + AR724X_PCI_REG_INT_STATUS);
252
253                 /* flush write */
254                 __raw_readl(base + AR724X_PCI_REG_INT_STATUS);
255         }
256 }
257
258 static struct irq_chip ar724x_pci_irq_chip = {
259         .name           = "AR724X PCI ",
260         .irq_mask       = ar724x_pci_irq_mask,
261         .irq_unmask     = ar724x_pci_irq_unmask,
262         .irq_mask_ack   = ar724x_pci_irq_mask,
263 };
264
265 static void __init ar724x_pci_irq_init(int irq)
266 {
267         void __iomem *base;
268         int i;
269
270         base = ar724x_pci_ctrl_base;
271
272         __raw_writel(0, base + AR724X_PCI_REG_INT_MASK);
273         __raw_writel(0, base + AR724X_PCI_REG_INT_STATUS);
274
275         BUILD_BUG_ON(ATH79_PCI_IRQ_COUNT < AR724X_PCI_IRQ_COUNT);
276
277         for (i = ATH79_PCI_IRQ_BASE;
278              i < ATH79_PCI_IRQ_BASE + AR724X_PCI_IRQ_COUNT; i++)
279                 irq_set_chip_and_handler(i, &ar724x_pci_irq_chip,
280                                          handle_level_irq);
281
282         irq_set_chained_handler(irq, ar724x_pci_irq_handler);
283 }
284
285 int __init ar724x_pcibios_init(int irq)
286 {
287         int ret;
288
289         ret = -ENOMEM;
290
291         ar724x_pci_devcfg_base = ioremap(AR724X_PCI_CFG_BASE,
292                                          AR724X_PCI_CFG_SIZE);
293         if (ar724x_pci_devcfg_base == NULL)
294                 goto err;
295
296         ar724x_pci_ctrl_base = ioremap(AR724X_PCI_CTRL_BASE,
297                                        AR724X_PCI_CTRL_SIZE);
298         if (ar724x_pci_ctrl_base == NULL)
299                 goto err_unmap_devcfg;
300
301         ar724x_pci_link_up = ar724x_pci_check_link();
302         if (!ar724x_pci_link_up)
303                 pr_warn("ar724x: PCIe link is down\n");
304
305         ar724x_pci_irq_init(irq);
306         register_pci_controller(&ar724x_pci_controller);
307
308         return PCIBIOS_SUCCESSFUL;
309
310 err_unmap_devcfg:
311         iounmap(ar724x_pci_devcfg_base);
312 err:
313         return ret;
314 }