aboutsummaryrefslogtreecommitdiffstats
path: root/arch/sh/drivers/pci/pci.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/sh/drivers/pci/pci.c')
-rw-r--r--arch/sh/drivers/pci/pci.c279
1 files changed, 233 insertions, 46 deletions
diff --git a/arch/sh/drivers/pci/pci.c b/arch/sh/drivers/pci/pci.c
index 0d6ac7a1db49..54d77cbb8b39 100644
--- a/arch/sh/drivers/pci/pci.c
+++ b/arch/sh/drivers/pci/pci.c
@@ -1,67 +1,156 @@
1/* 1/*
2 * arch/sh/drivers/pci/pci.c 2 * New-style PCI core.
3 * 3 *
4 * Copyright (c) 2002 M. R. Brown <mrbrown@linux-sh.org> 4 * Copyright (c) 2004 - 2009 Paul Mundt
5 * Copyright (c) 2004 - 2006 Paul Mundt <lethal@linux-sh.org> 5 * Copyright (c) 2002 M. R. Brown
6 * 6 *
7 * These functions are collected here to reduce duplication of common 7 * Modelled after arch/mips/pci/pci.c:
8 * code amongst the many platform-specific PCI support code files. 8 * Copyright (C) 2003, 04 Ralf Baechle (ralf@linux-mips.org)
9 *
10 * These routines require the following board-specific routines:
11 * void pcibios_fixup_irqs();
12 *
13 * See include/asm-sh/pci.h for more information.
14 * 9 *
15 * This file is subject to the terms and conditions of the GNU General Public 10 * This file is subject to the terms and conditions of the GNU General Public
16 * License. See the file "COPYING" in the main directory of this archive 11 * License. See the file "COPYING" in the main directory of this archive
17 * for more details. 12 * for more details.
18 */ 13 */
19#include <linux/kernel.h> 14#include <linux/kernel.h>
15#include <linux/mm.h>
20#include <linux/pci.h> 16#include <linux/pci.h>
21#include <linux/init.h> 17#include <linux/init.h>
18#include <linux/types.h>
22#include <linux/dma-debug.h> 19#include <linux/dma-debug.h>
23#include <asm/io.h> 20#include <linux/io.h>
21#include <linux/mutex.h>
24 22
25static int __init pcibios_init(void) 23unsigned long PCIBIOS_MIN_IO = 0x0000;
24unsigned long PCIBIOS_MIN_MEM = 0;
25
26/*
27 * The PCI controller list.
28 */
29static struct pci_channel *hose_head, **hose_tail = &hose_head;
30
31static int pci_initialized;
32
33static void __devinit pcibios_scanbus(struct pci_channel *hose)
26{ 34{
27 struct pci_channel *p; 35 static int next_busno;
28 struct pci_bus *bus; 36 struct pci_bus *bus;
29 int busno;
30 37
31#ifdef CONFIG_PCI_AUTO 38 bus = pci_scan_bus(next_busno, hose->pci_ops, hose);
32 /* assign resources */ 39 if (bus) {
33 busno = 0; 40 next_busno = bus->subordinate + 1;
34 for (p = board_pci_channels; p->pci_ops != NULL; p++) 41 /* Don't allow 8-bit bus number overflow inside the hose -
35 busno = pciauto_assign_resources(busno, p) + 1; 42 reserve some space for bridges. */
36#endif 43 if (next_busno > 224)
44 next_busno = 0;
45
46 pci_bus_size_bridges(bus);
47 pci_bus_assign_resources(bus);
48 pci_enable_bridges(bus);
49 }
50}
51
52static DEFINE_MUTEX(pci_scan_mutex);
37 53
38 /* scan the buses */ 54void __devinit register_pci_controller(struct pci_channel *hose)
39 busno = 0; 55{
40 for (p = board_pci_channels; p->pci_ops != NULL; p++) { 56 if (request_resource(&iomem_resource, hose->mem_resource) < 0)
41 bus = pci_scan_bus(busno, p->pci_ops, p); 57 goto out;
42 busno = bus->subordinate + 1; 58 if (request_resource(&ioport_resource, hose->io_resource) < 0) {
59 release_resource(hose->mem_resource);
60 goto out;
43 } 61 }
44 62
63 *hose_tail = hose;
64 hose_tail = &hose->next;
65
66 /*
67 * Do not panic here but later - this might hapen before console init.
68 */
69 if (!hose->io_map_base) {
70 printk(KERN_WARNING
71 "registering PCI controller with io_map_base unset\n");
72 }
73
74 /*
75 * Scan the bus if it is register after the PCI subsystem
76 * initialization.
77 */
78 if (pci_initialized) {
79 mutex_lock(&pci_scan_mutex);
80 pcibios_scanbus(hose);
81 mutex_unlock(&pci_scan_mutex);
82 }
83
84 return;
85
86out:
87 printk(KERN_WARNING
88 "Skipping PCI bus scan due to resource conflict\n");
89}
90
91static int __init pcibios_init(void)
92{
93 struct pci_channel *hose;
94
95 /* Scan all of the recorded PCI controllers. */
96 for (hose = hose_head; hose; hose = hose->next)
97 pcibios_scanbus(hose);
98
45 pci_fixup_irqs(pci_common_swizzle, pcibios_map_platform_irq); 99 pci_fixup_irqs(pci_common_swizzle, pcibios_map_platform_irq);
46 100
47 dma_debug_add_bus(&pci_bus_type); 101 dma_debug_add_bus(&pci_bus_type);
48 102
103 pci_initialized = 1;
104
49 return 0; 105 return 0;
50} 106}
51subsys_initcall(pcibios_init); 107subsys_initcall(pcibios_init);
52 108
109static void pcibios_fixup_device_resources(struct pci_dev *dev,
110 struct pci_bus *bus)
111{
112 /* Update device resources. */
113 struct pci_channel *hose = bus->sysdata;
114 unsigned long offset = 0;
115 int i;
116
117 for (i = 0; i < PCI_NUM_RESOURCES; i++) {
118 if (!dev->resource[i].start)
119 continue;
120 if (dev->resource[i].flags & IORESOURCE_PCI_FIXED)
121 continue;
122 if (dev->resource[i].flags & IORESOURCE_IO)
123 offset = hose->io_offset;
124 else if (dev->resource[i].flags & IORESOURCE_MEM)
125 offset = hose->mem_offset;
126
127 dev->resource[i].start += offset;
128 dev->resource[i].end += offset;
129 }
130}
131
53/* 132/*
54 * Called after each bus is probed, but before its children 133 * Called after each bus is probed, but before its children
55 * are examined. 134 * are examined.
56 */ 135 */
57void __devinit __weak pcibios_fixup_bus(struct pci_bus *bus) 136void __devinit pcibios_fixup_bus(struct pci_bus *bus)
58{ 137{
59 pci_read_bridge_bases(bus); 138 struct pci_dev *dev = bus->self;
60} 139 struct list_head *ln;
140 struct pci_channel *chan = bus->sysdata;
61 141
62void pcibios_align_resource(void *data, struct resource *res, 142 if (!dev) {
63 resource_size_t size, resource_size_t align) 143 bus->resource[0] = chan->io_resource;
64 __attribute__ ((weak)); 144 bus->resource[1] = chan->mem_resource;
145 }
146
147 for (ln = bus->devices.next; ln != &bus->devices; ln = ln->next) {
148 dev = pci_dev_b(ln);
149
150 if ((dev->class >> 8) != PCI_CLASS_BRIDGE_PCI)
151 pcibios_fixup_device_resources(dev, bus);
152 }
153}
65 154
66/* 155/*
67 * We need to avoid collisions with `mirrored' VGA ports 156 * We need to avoid collisions with `mirrored' VGA ports
@@ -72,14 +161,58 @@ void pcibios_align_resource(void *data, struct resource *res,
72void pcibios_align_resource(void *data, struct resource *res, 161void pcibios_align_resource(void *data, struct resource *res,
73 resource_size_t size, resource_size_t align) 162 resource_size_t size, resource_size_t align)
74{ 163{
164 struct pci_dev *dev = data;
165 struct pci_channel *chan = dev->sysdata;
166 resource_size_t start = res->start;
167
75 if (res->flags & IORESOURCE_IO) { 168 if (res->flags & IORESOURCE_IO) {
76 resource_size_t start = res->start; 169 if (start < PCIBIOS_MIN_IO + chan->io_resource->start)
170 start = PCIBIOS_MIN_IO + chan->io_resource->start;
77 171
172 /*
173 * Put everything into 0x00-0xff region modulo 0x400.
174 */
78 if (start & 0x300) { 175 if (start & 0x300) {
79 start = (start + 0x3ff) & ~0x3ff; 176 start = (start + 0x3ff) & ~0x3ff;
80 res->start = start; 177 res->start = start;
81 } 178 }
179 } else if (res->flags & IORESOURCE_MEM) {
180 if (start < PCIBIOS_MIN_MEM + chan->mem_resource->start)
181 start = PCIBIOS_MIN_MEM + chan->mem_resource->start;
82 } 182 }
183
184 res->start = start;
185}
186
187void pcibios_resource_to_bus(struct pci_dev *dev, struct pci_bus_region *region,
188 struct resource *res)
189{
190 struct pci_channel *hose = dev->sysdata;
191 unsigned long offset = 0;
192
193 if (res->flags & IORESOURCE_IO)
194 offset = hose->io_offset;
195 else if (res->flags & IORESOURCE_MEM)
196 offset = hose->mem_offset;
197
198 region->start = res->start - offset;
199 region->end = res->end - offset;
200}
201
202void __devinit
203pcibios_bus_to_resource(struct pci_dev *dev, struct resource *res,
204 struct pci_bus_region *region)
205{
206 struct pci_channel *hose = dev->sysdata;
207 unsigned long offset = 0;
208
209 if (res->flags & IORESOURCE_IO)
210 offset = hose->io_offset;
211 else if (res->flags & IORESOURCE_MEM)
212 offset = hose->mem_offset;
213
214 res->start = region->start + offset;
215 res->end = region->end + offset;
83} 216}
84 217
85int pcibios_enable_device(struct pci_dev *dev, int mask) 218int pcibios_enable_device(struct pci_dev *dev, int mask)
@@ -90,13 +223,21 @@ int pcibios_enable_device(struct pci_dev *dev, int mask)
90 223
91 pci_read_config_word(dev, PCI_COMMAND, &cmd); 224 pci_read_config_word(dev, PCI_COMMAND, &cmd);
92 old_cmd = cmd; 225 old_cmd = cmd;
93 for(idx=0; idx<6; idx++) { 226 for (idx=0; idx < PCI_NUM_RESOURCES; idx++) {
94 if (!(mask & (1 << idx))) 227 /* Only set up the requested stuff */
228 if (!(mask & (1<<idx)))
95 continue; 229 continue;
230
96 r = &dev->resource[idx]; 231 r = &dev->resource[idx];
232 if (!(r->flags & (IORESOURCE_IO | IORESOURCE_MEM)))
233 continue;
234 if ((idx == PCI_ROM_RESOURCE) &&
235 (!(r->flags & IORESOURCE_ROM_ENABLE)))
236 continue;
97 if (!r->start && r->end) { 237 if (!r->start && r->end) {
98 printk(KERN_ERR "PCI: Device %s not available because " 238 printk(KERN_ERR "PCI: Device %s not available "
99 "of resource collisions\n", pci_name(dev)); 239 "because of resource collisions\n",
240 pci_name(dev));
100 return -EINVAL; 241 return -EINVAL;
101 } 242 }
102 if (r->flags & IORESOURCE_IO) 243 if (r->flags & IORESOURCE_IO)
@@ -104,10 +245,8 @@ int pcibios_enable_device(struct pci_dev *dev, int mask)
104 if (r->flags & IORESOURCE_MEM) 245 if (r->flags & IORESOURCE_MEM)
105 cmd |= PCI_COMMAND_MEMORY; 246 cmd |= PCI_COMMAND_MEMORY;
106 } 247 }
107 if (dev->resource[PCI_ROM_RESOURCE].start)
108 cmd |= PCI_COMMAND_MEMORY;
109 if (cmd != old_cmd) { 248 if (cmd != old_cmd) {
110 printk(KERN_INFO "PCI: Enabling device %s (%04x -> %04x)\n", 249 printk("PCI: Enabling device %s (%04x -> %04x)\n",
111 pci_name(dev), old_cmd, cmd); 250 pci_name(dev), old_cmd, cmd);
112 pci_write_config_word(dev, PCI_COMMAND, cmd); 251 pci_write_config_word(dev, PCI_COMMAND, cmd);
113 } 252 }
@@ -140,6 +279,43 @@ void __init pcibios_update_irq(struct pci_dev *dev, int irq)
140 pci_write_config_byte(dev, PCI_INTERRUPT_LINE, irq); 279 pci_write_config_byte(dev, PCI_INTERRUPT_LINE, irq);
141} 280}
142 281
282char * __devinit pcibios_setup(char *str)
283{
284 return str;
285}
286
287int pci_mmap_page_range(struct pci_dev *dev, struct vm_area_struct *vma,
288 enum pci_mmap_state mmap_state, int write_combine)
289{
290 /*
291 * I/O space can be accessed via normal processor loads and stores on
292 * this platform but for now we elect not to do this and portable
293 * drivers should not do this anyway.
294 */
295 if (mmap_state == pci_mmap_io)
296 return -EINVAL;
297
298 /*
299 * Ignore write-combine; for now only return uncached mappings.
300 */
301 vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
302
303 return remap_pfn_range(vma, vma->vm_start, vma->vm_pgoff,
304 vma->vm_end - vma->vm_start,
305 vma->vm_page_prot);
306}
307
308static void __iomem *ioport_map_pci(struct pci_dev *dev,
309 unsigned long port, unsigned int nr)
310{
311 struct pci_channel *chan = dev->sysdata;
312
313 if (!chan->io_map_base)
314 chan->io_map_base = generic_io_base;
315
316 return (void __iomem *)(chan->io_map_base + port);
317}
318
143void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen) 319void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen)
144{ 320{
145 resource_size_t start = pci_resource_start(dev, bar); 321 resource_size_t start = pci_resource_start(dev, bar);
@@ -151,20 +327,24 @@ void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen)
151 if (maxlen && len > maxlen) 327 if (maxlen && len > maxlen)
152 len = maxlen; 328 len = maxlen;
153 329
330 if (flags & IORESOURCE_IO)
331 return ioport_map_pci(dev, start, len);
332
154 /* 333 /*
155 * Presently the IORESOURCE_MEM case is a bit special, most 334 * Presently the IORESOURCE_MEM case is a bit special, most
156 * SH7751 style PCI controllers have PCI memory at a fixed 335 * SH7751 style PCI controllers have PCI memory at a fixed
157 * location in the address space where no remapping is desired 336 * location in the address space where no remapping is desired.
158 * (typically at 0xfd000000, but is_pci_memaddr() will know 337 * With the IORESOURCE_MEM case more care has to be taken
159 * best). With the IORESOURCE_MEM case more care has to be taken
160 * to inhibit page table mapping for legacy cores, but this is 338 * to inhibit page table mapping for legacy cores, but this is
161 * punted off to __ioremap(). 339 * punted off to __ioremap().
162 * -- PFM. 340 * -- PFM.
163 */ 341 */
164 if (flags & IORESOURCE_IO) 342 if (flags & IORESOURCE_MEM) {
165 return ioport_map(start, len); 343 if (flags & IORESOURCE_CACHEABLE)
166 if (flags & IORESOURCE_MEM) 344 return ioremap(start, len);
167 return ioremap(start, len); 345
346 return ioremap_nocache(start, len);
347 }
168 348
169 return NULL; 349 return NULL;
170} 350}
@@ -175,3 +355,10 @@ void pci_iounmap(struct pci_dev *dev, void __iomem *addr)
175 iounmap(addr); 355 iounmap(addr);
176} 356}
177EXPORT_SYMBOL(pci_iounmap); 357EXPORT_SYMBOL(pci_iounmap);
358
359#ifdef CONFIG_HOTPLUG
360EXPORT_SYMBOL(pcibios_resource_to_bus);
361EXPORT_SYMBOL(pcibios_bus_to_resource);
362EXPORT_SYMBOL(PCIBIOS_MIN_IO);
363EXPORT_SYMBOL(PCIBIOS_MIN_MEM);
364#endif