diff options
author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-07-16 20:58:08 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-07-16 20:58:08 -0400 |
commit | 489de30259e667d7bc47da9da44a0270b050cd97 (patch) | |
tree | 6807814f443fe2c5d041c3bc3fe3ca8d22a955ca /arch/powerpc/kernel/pci_64.c | |
parent | 1f1c2881f673671539b25686df463518d69c4649 (diff) | |
parent | bf22f6fe2d72b4d7e9035be8ceb340414cf490e3 (diff) |
Merge branch 'merge' of git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc
* 'merge' of git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc: (209 commits)
[POWERPC] Create add_rtc() function to enable the RTC CMOS driver
[POWERPC] Add H_ILLAN_ATTRIBUTES hcall number
[POWERPC] xilinxfb: Parameterize xilinxfb platform device registration
[POWERPC] Oprofile support for Power 5++
[POWERPC] Enable arbitary speed tty ioctls and split input/output speed
[POWERPC] Make drivers/char/hvc_console.c:khvcd() static
[POWERPC] Remove dead code for preventing pread() and pwrite() calls
[POWERPC] Remove unnecessary #undef printk from prom.c
[POWERPC] Fix typo in Ebony default DTS
[POWERPC] Check for NULL ppc_md.init_IRQ() before calling
[POWERPC] Remove extra return statement
[POWERPC] pasemi: Don't auto-select CONFIG_EMBEDDED
[POWERPC] pasemi: Rename platform
[POWERPC] arch/powerpc/kernel/sysfs.c: Move NUMA exports
[POWERPC] Add __read_mostly support for powerpc
[POWERPC] Modify sched_clock() to make CONFIG_PRINTK_TIME more sane
[POWERPC] Create a dummy zImage if no valid platform has been selected
[POWERPC] PS3: Bootwrapper support.
[POWERPC] powermac i2c: Use mutex
[POWERPC] Schedule removal of arch/ppc
...
Fixed up conflicts manually in:
Documentation/feature-removal-schedule.txt
arch/powerpc/kernel/pci_32.c
arch/powerpc/kernel/pci_64.c
include/asm-powerpc/pci.h
and asked the powerpc people to double-check the result..
Diffstat (limited to 'arch/powerpc/kernel/pci_64.c')
-rw-r--r-- | arch/powerpc/kernel/pci_64.c | 750 |
1 files changed, 126 insertions, 624 deletions
diff --git a/arch/powerpc/kernel/pci_64.c b/arch/powerpc/kernel/pci_64.c index e3009a43ac56..a97e23ac1976 100644 --- a/arch/powerpc/kernel/pci_64.c +++ b/arch/powerpc/kernel/pci_64.c | |||
@@ -22,6 +22,7 @@ | |||
22 | #include <linux/list.h> | 22 | #include <linux/list.h> |
23 | #include <linux/syscalls.h> | 23 | #include <linux/syscalls.h> |
24 | #include <linux/irq.h> | 24 | #include <linux/irq.h> |
25 | #include <linux/vmalloc.h> | ||
25 | 26 | ||
26 | #include <asm/processor.h> | 27 | #include <asm/processor.h> |
27 | #include <asm/io.h> | 28 | #include <asm/io.h> |
@@ -41,35 +42,23 @@ | |||
41 | 42 | ||
42 | unsigned long pci_probe_only = 1; | 43 | unsigned long pci_probe_only = 1; |
43 | int pci_assign_all_buses = 0; | 44 | int pci_assign_all_buses = 0; |
44 | static int pci_initial_scan_done; | ||
45 | 45 | ||
46 | static void fixup_resource(struct resource *res, struct pci_dev *dev); | 46 | static void fixup_resource(struct resource *res, struct pci_dev *dev); |
47 | static void do_bus_setup(struct pci_bus *bus); | 47 | static void do_bus_setup(struct pci_bus *bus); |
48 | static void phbs_remap_io(void); | ||
49 | 48 | ||
50 | /* pci_io_base -- the base address from which io bars are offsets. | 49 | /* pci_io_base -- the base address from which io bars are offsets. |
51 | * This is the lowest I/O base address (so bar values are always positive), | 50 | * This is the lowest I/O base address (so bar values are always positive), |
52 | * and it *must* be the start of ISA space if an ISA bus exists because | 51 | * and it *must* be the start of ISA space if an ISA bus exists because |
53 | * ISA drivers use hard coded offsets. If no ISA bus exists a dummy | 52 | * ISA drivers use hard coded offsets. If no ISA bus exists nothing |
54 | * page is mapped and isa_io_limit prevents access to it. | 53 | * is mapped on the first 64K of IO space |
55 | */ | 54 | */ |
56 | unsigned long isa_io_base; /* NULL if no ISA bus */ | 55 | unsigned long pci_io_base = ISA_IO_BASE; |
57 | EXPORT_SYMBOL(isa_io_base); | ||
58 | unsigned long pci_io_base; | ||
59 | EXPORT_SYMBOL(pci_io_base); | 56 | EXPORT_SYMBOL(pci_io_base); |
60 | 57 | ||
61 | void iSeries_pcibios_init(void); | ||
62 | |||
63 | LIST_HEAD(hose_list); | 58 | LIST_HEAD(hose_list); |
64 | 59 | ||
65 | static struct dma_mapping_ops *pci_dma_ops; | 60 | static struct dma_mapping_ops *pci_dma_ops; |
66 | 61 | ||
67 | int global_phb_number; /* Global phb counter */ | ||
68 | |||
69 | /* Cached ISA bridge dev. */ | ||
70 | struct pci_dev *ppc64_isabridge_dev = NULL; | ||
71 | EXPORT_SYMBOL_GPL(ppc64_isabridge_dev); | ||
72 | |||
73 | void set_pci_dma_ops(struct dma_mapping_ops *dma_ops) | 62 | void set_pci_dma_ops(struct dma_mapping_ops *dma_ops) |
74 | { | 63 | { |
75 | pci_dma_ops = dma_ops; | 64 | pci_dma_ops = dma_ops; |
@@ -100,7 +89,7 @@ void pcibios_resource_to_bus(struct pci_dev *dev, struct pci_bus_region *region | |||
100 | return; | 89 | return; |
101 | 90 | ||
102 | if (res->flags & IORESOURCE_IO) | 91 | if (res->flags & IORESOURCE_IO) |
103 | offset = (unsigned long)hose->io_base_virt - pci_io_base; | 92 | offset = (unsigned long)hose->io_base_virt - _IO_BASE; |
104 | 93 | ||
105 | if (res->flags & IORESOURCE_MEM) | 94 | if (res->flags & IORESOURCE_MEM) |
106 | offset = hose->pci_mem_offset; | 95 | offset = hose->pci_mem_offset; |
@@ -119,7 +108,7 @@ void pcibios_bus_to_resource(struct pci_dev *dev, struct resource *res, | |||
119 | return; | 108 | return; |
120 | 109 | ||
121 | if (res->flags & IORESOURCE_IO) | 110 | if (res->flags & IORESOURCE_IO) |
122 | offset = (unsigned long)hose->io_base_virt - pci_io_base; | 111 | offset = (unsigned long)hose->io_base_virt - _IO_BASE; |
123 | 112 | ||
124 | if (res->flags & IORESOURCE_MEM) | 113 | if (res->flags & IORESOURCE_MEM) |
125 | offset = hose->pci_mem_offset; | 114 | offset = hose->pci_mem_offset; |
@@ -156,7 +145,7 @@ void pcibios_align_resource(void *data, struct resource *res, | |||
156 | 145 | ||
157 | if (res->flags & IORESOURCE_IO) { | 146 | if (res->flags & IORESOURCE_IO) { |
158 | unsigned long offset = (unsigned long)hose->io_base_virt - | 147 | unsigned long offset = (unsigned long)hose->io_base_virt - |
159 | pci_io_base; | 148 | _IO_BASE; |
160 | /* Make sure we start at our min on all hoses */ | 149 | /* Make sure we start at our min on all hoses */ |
161 | if (start - offset < PCIBIOS_MIN_IO) | 150 | if (start - offset < PCIBIOS_MIN_IO) |
162 | start = PCIBIOS_MIN_IO + offset; | 151 | start = PCIBIOS_MIN_IO + offset; |
@@ -180,55 +169,6 @@ void pcibios_align_resource(void *data, struct resource *res, | |||
180 | res->start = start; | 169 | res->start = start; |
181 | } | 170 | } |
182 | 171 | ||
183 | static DEFINE_SPINLOCK(hose_spinlock); | ||
184 | |||
185 | /* | ||
186 | * pci_controller(phb) initialized common variables. | ||
187 | */ | ||
188 | static void __devinit pci_setup_pci_controller(struct pci_controller *hose) | ||
189 | { | ||
190 | memset(hose, 0, sizeof(struct pci_controller)); | ||
191 | |||
192 | spin_lock(&hose_spinlock); | ||
193 | hose->global_number = global_phb_number++; | ||
194 | list_add_tail(&hose->list_node, &hose_list); | ||
195 | spin_unlock(&hose_spinlock); | ||
196 | } | ||
197 | |||
198 | struct pci_controller * pcibios_alloc_controller(struct device_node *dev) | ||
199 | { | ||
200 | struct pci_controller *phb; | ||
201 | |||
202 | if (mem_init_done) | ||
203 | phb = kmalloc(sizeof(struct pci_controller), GFP_KERNEL); | ||
204 | else | ||
205 | phb = alloc_bootmem(sizeof (struct pci_controller)); | ||
206 | if (phb == NULL) | ||
207 | return NULL; | ||
208 | pci_setup_pci_controller(phb); | ||
209 | phb->arch_data = dev; | ||
210 | phb->is_dynamic = mem_init_done; | ||
211 | if (dev) { | ||
212 | int nid = of_node_to_nid(dev); | ||
213 | |||
214 | if (nid < 0 || !node_online(nid)) | ||
215 | nid = -1; | ||
216 | |||
217 | PHB_SET_NODE(phb, nid); | ||
218 | } | ||
219 | return phb; | ||
220 | } | ||
221 | |||
222 | void pcibios_free_controller(struct pci_controller *phb) | ||
223 | { | ||
224 | spin_lock(&hose_spinlock); | ||
225 | list_del(&phb->list_node); | ||
226 | spin_unlock(&hose_spinlock); | ||
227 | |||
228 | if (phb->is_dynamic) | ||
229 | kfree(phb); | ||
230 | } | ||
231 | |||
232 | void __devinit pcibios_claim_one_bus(struct pci_bus *b) | 172 | void __devinit pcibios_claim_one_bus(struct pci_bus *b) |
233 | { | 173 | { |
234 | struct pci_dev *dev; | 174 | struct pci_dev *dev; |
@@ -291,7 +231,6 @@ static unsigned int pci_parse_of_flags(u32 addr0) | |||
291 | return flags; | 231 | return flags; |
292 | } | 232 | } |
293 | 233 | ||
294 | #define GET_64BIT(prop, i) ((((u64) (prop)[(i)]) << 32) | (prop)[(i)+1]) | ||
295 | 234 | ||
296 | static void pci_parse_of_addrs(struct device_node *node, struct pci_dev *dev) | 235 | static void pci_parse_of_addrs(struct device_node *node, struct pci_dev *dev) |
297 | { | 236 | { |
@@ -310,8 +249,8 @@ static void pci_parse_of_addrs(struct device_node *node, struct pci_dev *dev) | |||
310 | flags = pci_parse_of_flags(addrs[0]); | 249 | flags = pci_parse_of_flags(addrs[0]); |
311 | if (!flags) | 250 | if (!flags) |
312 | continue; | 251 | continue; |
313 | base = GET_64BIT(addrs, 1); | 252 | base = of_read_number(&addrs[1], 2); |
314 | size = GET_64BIT(addrs, 3); | 253 | size = of_read_number(&addrs[3], 2); |
315 | if (!size) | 254 | if (!size) |
316 | continue; | 255 | continue; |
317 | i = addrs[0] & 0xff; | 256 | i = addrs[0] & 0xff; |
@@ -479,7 +418,7 @@ void __devinit of_scan_pci_bridge(struct device_node *node, | |||
479 | i = 1; | 418 | i = 1; |
480 | for (; len >= 32; len -= 32, ranges += 8) { | 419 | for (; len >= 32; len -= 32, ranges += 8) { |
481 | flags = pci_parse_of_flags(ranges[0]); | 420 | flags = pci_parse_of_flags(ranges[0]); |
482 | size = GET_64BIT(ranges, 6); | 421 | size = of_read_number(&ranges[6], 2); |
483 | if (flags == 0 || size == 0) | 422 | if (flags == 0 || size == 0) |
484 | continue; | 423 | continue; |
485 | if (flags & IORESOURCE_IO) { | 424 | if (flags & IORESOURCE_IO) { |
@@ -498,7 +437,7 @@ void __devinit of_scan_pci_bridge(struct device_node *node, | |||
498 | res = bus->resource[i]; | 437 | res = bus->resource[i]; |
499 | ++i; | 438 | ++i; |
500 | } | 439 | } |
501 | res->start = GET_64BIT(ranges, 1); | 440 | res->start = of_read_number(&ranges[1], 2); |
502 | res->end = res->start + size - 1; | 441 | res->end = res->start + size - 1; |
503 | res->flags = flags; | 442 | res->flags = flags; |
504 | fixup_resource(res, dev); | 443 | fixup_resource(res, dev); |
@@ -537,10 +476,16 @@ void __devinit scan_phb(struct pci_controller *hose) | |||
537 | bus->secondary = hose->first_busno; | 476 | bus->secondary = hose->first_busno; |
538 | hose->bus = bus; | 477 | hose->bus = bus; |
539 | 478 | ||
479 | if (!firmware_has_feature(FW_FEATURE_ISERIES)) | ||
480 | pcibios_map_io_space(bus); | ||
481 | |||
540 | bus->resource[0] = res = &hose->io_resource; | 482 | bus->resource[0] = res = &hose->io_resource; |
541 | if (res->flags && request_resource(&ioport_resource, res)) | 483 | if (res->flags && request_resource(&ioport_resource, res)) { |
542 | printk(KERN_ERR "Failed to request PCI IO region " | 484 | printk(KERN_ERR "Failed to request PCI IO region " |
543 | "on PCI domain %04x\n", hose->global_number); | 485 | "on PCI domain %04x\n", hose->global_number); |
486 | DBG("res->start = 0x%016lx, res->end = 0x%016lx\n", | ||
487 | res->start, res->end); | ||
488 | } | ||
544 | 489 | ||
545 | for (i = 0; i < 3; ++i) { | 490 | for (i = 0; i < 3; ++i) { |
546 | res = &hose->mem_resources[i]; | 491 | res = &hose->mem_resources[i]; |
@@ -598,17 +543,6 @@ static int __init pcibios_init(void) | |||
598 | if (ppc_md.pcibios_fixup) | 543 | if (ppc_md.pcibios_fixup) |
599 | ppc_md.pcibios_fixup(); | 544 | ppc_md.pcibios_fixup(); |
600 | 545 | ||
601 | /* Cache the location of the ISA bridge (if we have one) */ | ||
602 | ppc64_isabridge_dev = pci_get_class(PCI_CLASS_BRIDGE_ISA << 8, NULL); | ||
603 | if (ppc64_isabridge_dev != NULL) | ||
604 | printk(KERN_DEBUG "ISA bridge at %s\n", pci_name(ppc64_isabridge_dev)); | ||
605 | |||
606 | if (!firmware_has_feature(FW_FEATURE_ISERIES)) | ||
607 | /* map in PCI I/O space */ | ||
608 | phbs_remap_io(); | ||
609 | |||
610 | pci_initial_scan_done = 1; | ||
611 | |||
612 | printk(KERN_DEBUG "PCI: Probing PCI hardware done\n"); | 546 | printk(KERN_DEBUG "PCI: Probing PCI hardware done\n"); |
613 | 547 | ||
614 | return 0; | 548 | return 0; |
@@ -616,11 +550,6 @@ static int __init pcibios_init(void) | |||
616 | 550 | ||
617 | subsys_initcall(pcibios_init); | 551 | subsys_initcall(pcibios_init); |
618 | 552 | ||
619 | char __init *pcibios_setup(char *str) | ||
620 | { | ||
621 | return str; | ||
622 | } | ||
623 | |||
624 | int pcibios_enable_device(struct pci_dev *dev, int mask) | 553 | int pcibios_enable_device(struct pci_dev *dev, int mask) |
625 | { | 554 | { |
626 | u16 cmd, oldcmd; | 555 | u16 cmd, oldcmd; |
@@ -651,22 +580,6 @@ int pcibios_enable_device(struct pci_dev *dev, int mask) | |||
651 | return 0; | 580 | return 0; |
652 | } | 581 | } |
653 | 582 | ||
654 | /* | ||
655 | * Return the domain number for this bus. | ||
656 | */ | ||
657 | int pci_domain_nr(struct pci_bus *bus) | ||
658 | { | ||
659 | if (firmware_has_feature(FW_FEATURE_ISERIES)) | ||
660 | return 0; | ||
661 | else { | ||
662 | struct pci_controller *hose = pci_bus_to_host(bus); | ||
663 | |||
664 | return hose->global_number; | ||
665 | } | ||
666 | } | ||
667 | |||
668 | EXPORT_SYMBOL(pci_domain_nr); | ||
669 | |||
670 | /* Decide whether to display the domain number in /proc */ | 583 | /* Decide whether to display the domain number in /proc */ |
671 | int pci_proc_domain(struct pci_bus *bus) | 584 | int pci_proc_domain(struct pci_bus *bus) |
672 | { | 585 | { |
@@ -678,281 +591,6 @@ int pci_proc_domain(struct pci_bus *bus) | |||
678 | } | 591 | } |
679 | } | 592 | } |
680 | 593 | ||
681 | /* | ||
682 | * Platform support for /proc/bus/pci/X/Y mmap()s, | ||
683 | * modelled on the sparc64 implementation by Dave Miller. | ||
684 | * -- paulus. | ||
685 | */ | ||
686 | |||
687 | /* | ||
688 | * Adjust vm_pgoff of VMA such that it is the physical page offset | ||
689 | * corresponding to the 32-bit pci bus offset for DEV requested by the user. | ||
690 | * | ||
691 | * Basically, the user finds the base address for his device which he wishes | ||
692 | * to mmap. They read the 32-bit value from the config space base register, | ||
693 | * add whatever PAGE_SIZE multiple offset they wish, and feed this into the | ||
694 | * offset parameter of mmap on /proc/bus/pci/XXX for that device. | ||
695 | * | ||
696 | * Returns negative error code on failure, zero on success. | ||
697 | */ | ||
698 | static struct resource *__pci_mmap_make_offset(struct pci_dev *dev, | ||
699 | resource_size_t *offset, | ||
700 | enum pci_mmap_state mmap_state) | ||
701 | { | ||
702 | struct pci_controller *hose = pci_bus_to_host(dev->bus); | ||
703 | unsigned long io_offset = 0; | ||
704 | int i, res_bit; | ||
705 | |||
706 | if (hose == 0) | ||
707 | return NULL; /* should never happen */ | ||
708 | |||
709 | /* If memory, add on the PCI bridge address offset */ | ||
710 | if (mmap_state == pci_mmap_mem) { | ||
711 | #if 0 /* See comment in pci_resource_to_user() for why this is disabled */ | ||
712 | *offset += hose->pci_mem_offset; | ||
713 | #endif | ||
714 | res_bit = IORESOURCE_MEM; | ||
715 | } else { | ||
716 | io_offset = (unsigned long)hose->io_base_virt - pci_io_base; | ||
717 | *offset += io_offset; | ||
718 | res_bit = IORESOURCE_IO; | ||
719 | } | ||
720 | |||
721 | /* | ||
722 | * Check that the offset requested corresponds to one of the | ||
723 | * resources of the device. | ||
724 | */ | ||
725 | for (i = 0; i <= PCI_ROM_RESOURCE; i++) { | ||
726 | struct resource *rp = &dev->resource[i]; | ||
727 | int flags = rp->flags; | ||
728 | |||
729 | /* treat ROM as memory (should be already) */ | ||
730 | if (i == PCI_ROM_RESOURCE) | ||
731 | flags |= IORESOURCE_MEM; | ||
732 | |||
733 | /* Active and same type? */ | ||
734 | if ((flags & res_bit) == 0) | ||
735 | continue; | ||
736 | |||
737 | /* In the range of this resource? */ | ||
738 | if (*offset < (rp->start & PAGE_MASK) || *offset > rp->end) | ||
739 | continue; | ||
740 | |||
741 | /* found it! construct the final physical address */ | ||
742 | if (mmap_state == pci_mmap_io) | ||
743 | *offset += hose->io_base_phys - io_offset; | ||
744 | return rp; | ||
745 | } | ||
746 | |||
747 | return NULL; | ||
748 | } | ||
749 | |||
750 | /* | ||
751 | * Set vm_page_prot of VMA, as appropriate for this architecture, for a pci | ||
752 | * device mapping. | ||
753 | */ | ||
754 | static pgprot_t __pci_mmap_set_pgprot(struct pci_dev *dev, struct resource *rp, | ||
755 | pgprot_t protection, | ||
756 | enum pci_mmap_state mmap_state, | ||
757 | int write_combine) | ||
758 | { | ||
759 | unsigned long prot = pgprot_val(protection); | ||
760 | |||
761 | /* Write combine is always 0 on non-memory space mappings. On | ||
762 | * memory space, if the user didn't pass 1, we check for a | ||
763 | * "prefetchable" resource. This is a bit hackish, but we use | ||
764 | * this to workaround the inability of /sysfs to provide a write | ||
765 | * combine bit | ||
766 | */ | ||
767 | if (mmap_state != pci_mmap_mem) | ||
768 | write_combine = 0; | ||
769 | else if (write_combine == 0) { | ||
770 | if (rp->flags & IORESOURCE_PREFETCH) | ||
771 | write_combine = 1; | ||
772 | } | ||
773 | |||
774 | /* XXX would be nice to have a way to ask for write-through */ | ||
775 | prot |= _PAGE_NO_CACHE; | ||
776 | if (write_combine) | ||
777 | prot &= ~_PAGE_GUARDED; | ||
778 | else | ||
779 | prot |= _PAGE_GUARDED; | ||
780 | |||
781 | return __pgprot(prot); | ||
782 | } | ||
783 | |||
784 | /* | ||
785 | * This one is used by /dev/mem and fbdev who have no clue about the | ||
786 | * PCI device, it tries to find the PCI device first and calls the | ||
787 | * above routine | ||
788 | */ | ||
789 | pgprot_t pci_phys_mem_access_prot(struct file *file, | ||
790 | unsigned long pfn, | ||
791 | unsigned long size, | ||
792 | pgprot_t protection) | ||
793 | { | ||
794 | struct pci_dev *pdev = NULL; | ||
795 | struct resource *found = NULL; | ||
796 | unsigned long prot = pgprot_val(protection); | ||
797 | unsigned long offset = pfn << PAGE_SHIFT; | ||
798 | int i; | ||
799 | |||
800 | if (page_is_ram(pfn)) | ||
801 | return __pgprot(prot); | ||
802 | |||
803 | prot |= _PAGE_NO_CACHE | _PAGE_GUARDED; | ||
804 | |||
805 | for_each_pci_dev(pdev) { | ||
806 | for (i = 0; i <= PCI_ROM_RESOURCE; i++) { | ||
807 | struct resource *rp = &pdev->resource[i]; | ||
808 | int flags = rp->flags; | ||
809 | |||
810 | /* Active and same type? */ | ||
811 | if ((flags & IORESOURCE_MEM) == 0) | ||
812 | continue; | ||
813 | /* In the range of this resource? */ | ||
814 | if (offset < (rp->start & PAGE_MASK) || | ||
815 | offset > rp->end) | ||
816 | continue; | ||
817 | found = rp; | ||
818 | break; | ||
819 | } | ||
820 | if (found) | ||
821 | break; | ||
822 | } | ||
823 | if (found) { | ||
824 | if (found->flags & IORESOURCE_PREFETCH) | ||
825 | prot &= ~_PAGE_GUARDED; | ||
826 | pci_dev_put(pdev); | ||
827 | } | ||
828 | |||
829 | DBG("non-PCI map for %lx, prot: %lx\n", offset, prot); | ||
830 | |||
831 | return __pgprot(prot); | ||
832 | } | ||
833 | |||
834 | |||
835 | /* | ||
836 | * Perform the actual remap of the pages for a PCI device mapping, as | ||
837 | * appropriate for this architecture. The region in the process to map | ||
838 | * is described by vm_start and vm_end members of VMA, the base physical | ||
839 | * address is found in vm_pgoff. | ||
840 | * The pci device structure is provided so that architectures may make mapping | ||
841 | * decisions on a per-device or per-bus basis. | ||
842 | * | ||
843 | * Returns a negative error code on failure, zero on success. | ||
844 | */ | ||
845 | int pci_mmap_page_range(struct pci_dev *dev, struct vm_area_struct *vma, | ||
846 | enum pci_mmap_state mmap_state, int write_combine) | ||
847 | { | ||
848 | resource_size_t offset = vma->vm_pgoff << PAGE_SHIFT; | ||
849 | struct resource *rp; | ||
850 | int ret; | ||
851 | |||
852 | rp = __pci_mmap_make_offset(dev, &offset, mmap_state); | ||
853 | if (rp == NULL) | ||
854 | return -EINVAL; | ||
855 | |||
856 | vma->vm_pgoff = offset >> PAGE_SHIFT; | ||
857 | vma->vm_page_prot = __pci_mmap_set_pgprot(dev, rp, | ||
858 | vma->vm_page_prot, | ||
859 | mmap_state, write_combine); | ||
860 | |||
861 | ret = remap_pfn_range(vma, vma->vm_start, vma->vm_pgoff, | ||
862 | vma->vm_end - vma->vm_start, vma->vm_page_prot); | ||
863 | |||
864 | return ret; | ||
865 | } | ||
866 | |||
867 | static ssize_t pci_show_devspec(struct device *dev, | ||
868 | struct device_attribute *attr, char *buf) | ||
869 | { | ||
870 | struct pci_dev *pdev; | ||
871 | struct device_node *np; | ||
872 | |||
873 | pdev = to_pci_dev (dev); | ||
874 | np = pci_device_to_OF_node(pdev); | ||
875 | if (np == NULL || np->full_name == NULL) | ||
876 | return 0; | ||
877 | return sprintf(buf, "%s", np->full_name); | ||
878 | } | ||
879 | static DEVICE_ATTR(devspec, S_IRUGO, pci_show_devspec, NULL); | ||
880 | |||
881 | int pcibios_add_platform_entries(struct pci_dev *pdev) | ||
882 | { | ||
883 | return device_create_file(&pdev->dev, &dev_attr_devspec); | ||
884 | } | ||
885 | |||
886 | #define ISA_SPACE_MASK 0x1 | ||
887 | #define ISA_SPACE_IO 0x1 | ||
888 | |||
889 | static void __devinit pci_process_ISA_OF_ranges(struct device_node *isa_node, | ||
890 | unsigned long phb_io_base_phys, | ||
891 | void __iomem * phb_io_base_virt) | ||
892 | { | ||
893 | /* Remove these asap */ | ||
894 | |||
895 | struct pci_address { | ||
896 | u32 a_hi; | ||
897 | u32 a_mid; | ||
898 | u32 a_lo; | ||
899 | }; | ||
900 | |||
901 | struct isa_address { | ||
902 | u32 a_hi; | ||
903 | u32 a_lo; | ||
904 | }; | ||
905 | |||
906 | struct isa_range { | ||
907 | struct isa_address isa_addr; | ||
908 | struct pci_address pci_addr; | ||
909 | unsigned int size; | ||
910 | }; | ||
911 | |||
912 | const struct isa_range *range; | ||
913 | unsigned long pci_addr; | ||
914 | unsigned int isa_addr; | ||
915 | unsigned int size; | ||
916 | int rlen = 0; | ||
917 | |||
918 | range = of_get_property(isa_node, "ranges", &rlen); | ||
919 | if (range == NULL || (rlen < sizeof(struct isa_range))) { | ||
920 | printk(KERN_ERR "no ISA ranges or unexpected isa range size," | ||
921 | "mapping 64k\n"); | ||
922 | __ioremap_explicit(phb_io_base_phys, | ||
923 | (unsigned long)phb_io_base_virt, | ||
924 | 0x10000, _PAGE_NO_CACHE | _PAGE_GUARDED); | ||
925 | return; | ||
926 | } | ||
927 | |||
928 | /* From "ISA Binding to 1275" | ||
929 | * The ranges property is laid out as an array of elements, | ||
930 | * each of which comprises: | ||
931 | * cells 0 - 1: an ISA address | ||
932 | * cells 2 - 4: a PCI address | ||
933 | * (size depending on dev->n_addr_cells) | ||
934 | * cell 5: the size of the range | ||
935 | */ | ||
936 | if ((range->isa_addr.a_hi && ISA_SPACE_MASK) == ISA_SPACE_IO) { | ||
937 | isa_addr = range->isa_addr.a_lo; | ||
938 | pci_addr = (unsigned long) range->pci_addr.a_mid << 32 | | ||
939 | range->pci_addr.a_lo; | ||
940 | |||
941 | /* Assume these are both zero */ | ||
942 | if ((pci_addr != 0) || (isa_addr != 0)) { | ||
943 | printk(KERN_ERR "unexpected isa to pci mapping: %s\n", | ||
944 | __FUNCTION__); | ||
945 | return; | ||
946 | } | ||
947 | |||
948 | size = PAGE_ALIGN(range->size); | ||
949 | |||
950 | __ioremap_explicit(phb_io_base_phys, | ||
951 | (unsigned long) phb_io_base_virt, | ||
952 | size, _PAGE_NO_CACHE | _PAGE_GUARDED); | ||
953 | } | ||
954 | } | ||
955 | |||
956 | void __devinit pci_process_bridge_OF_ranges(struct pci_controller *hose, | 594 | void __devinit pci_process_bridge_OF_ranges(struct pci_controller *hose, |
957 | struct device_node *dev, int prim) | 595 | struct device_node *dev, int prim) |
958 | { | 596 | { |
@@ -1047,155 +685,122 @@ void __devinit pci_process_bridge_OF_ranges(struct pci_controller *hose, | |||
1047 | } | 685 | } |
1048 | } | 686 | } |
1049 | 687 | ||
1050 | void __devinit pci_setup_phb_io(struct pci_controller *hose, int primary) | 688 | #ifdef CONFIG_HOTPLUG |
689 | |||
690 | int pcibios_unmap_io_space(struct pci_bus *bus) | ||
1051 | { | 691 | { |
1052 | unsigned long size = hose->pci_io_size; | 692 | struct pci_controller *hose; |
1053 | unsigned long io_virt_offset; | ||
1054 | struct resource *res; | ||
1055 | struct device_node *isa_dn; | ||
1056 | 693 | ||
1057 | if (size == 0) | 694 | WARN_ON(bus == NULL); |
1058 | return; | ||
1059 | 695 | ||
1060 | hose->io_base_virt = reserve_phb_iospace(size); | 696 | /* If this is not a PHB, we only flush the hash table over |
1061 | DBG("phb%d io_base_phys 0x%lx io_base_virt 0x%lx\n", | 697 | * the area mapped by this bridge. We don't play with the PTE |
1062 | hose->global_number, hose->io_base_phys, | 698 | * mappings since we might have to deal with sub-page alignemnts |
1063 | (unsigned long) hose->io_base_virt); | 699 | * so flushing the hash table is the only sane way to make sure |
1064 | 700 | * that no hash entries are covering that removed bridge area | |
1065 | if (primary) { | 701 | * while still allowing other busses overlapping those pages |
1066 | pci_io_base = (unsigned long)hose->io_base_virt; | 702 | */ |
1067 | isa_dn = of_find_node_by_type(NULL, "isa"); | 703 | if (bus->self) { |
1068 | if (isa_dn) { | 704 | struct resource *res = bus->resource[0]; |
1069 | isa_io_base = pci_io_base; | ||
1070 | pci_process_ISA_OF_ranges(isa_dn, hose->io_base_phys, | ||
1071 | hose->io_base_virt); | ||
1072 | of_node_put(isa_dn); | ||
1073 | } | ||
1074 | } | ||
1075 | 705 | ||
1076 | io_virt_offset = (unsigned long)hose->io_base_virt - pci_io_base; | 706 | DBG("IO unmapping for PCI-PCI bridge %s\n", |
1077 | res = &hose->io_resource; | 707 | pci_name(bus->self)); |
1078 | res->start += io_virt_offset; | ||
1079 | res->end += io_virt_offset; | ||
1080 | 708 | ||
1081 | /* If this is called after the initial PCI scan, then we need to | 709 | __flush_hash_table_range(&init_mm, res->start + _IO_BASE, |
1082 | * proceed to IO mappings now | 710 | res->end - res->start + 1); |
1083 | */ | 711 | return 0; |
1084 | if (pci_initial_scan_done) | 712 | } |
1085 | __ioremap_explicit(hose->io_base_phys, | ||
1086 | (unsigned long)hose->io_base_virt, | ||
1087 | hose->pci_io_size, | ||
1088 | _PAGE_NO_CACHE | _PAGE_GUARDED); | ||
1089 | } | ||
1090 | 713 | ||
1091 | void __devinit pci_setup_phb_io_dynamic(struct pci_controller *hose, | 714 | /* Get the host bridge */ |
1092 | int primary) | 715 | hose = pci_bus_to_host(bus); |
1093 | { | ||
1094 | unsigned long size = hose->pci_io_size; | ||
1095 | unsigned long io_virt_offset; | ||
1096 | struct resource *res; | ||
1097 | 716 | ||
1098 | if (size == 0) | 717 | /* Check if we have IOs allocated */ |
1099 | return; | 718 | if (hose->io_base_alloc == 0) |
719 | return 0; | ||
1100 | 720 | ||
1101 | hose->io_base_virt = __ioremap(hose->io_base_phys, size, | 721 | DBG("IO unmapping for PHB %s\n", |
1102 | _PAGE_NO_CACHE | _PAGE_GUARDED); | 722 | ((struct device_node *)hose->arch_data)->full_name); |
1103 | DBG("phb%d io_base_phys 0x%lx io_base_virt 0x%lx\n", | 723 | DBG(" alloc=0x%p\n", hose->io_base_alloc); |
1104 | hose->global_number, hose->io_base_phys, | ||
1105 | (unsigned long) hose->io_base_virt); | ||
1106 | 724 | ||
1107 | if (primary) | 725 | /* This is a PHB, we fully unmap the IO area */ |
1108 | pci_io_base = (unsigned long)hose->io_base_virt; | 726 | vunmap(hose->io_base_alloc); |
1109 | 727 | ||
1110 | io_virt_offset = (unsigned long)hose->io_base_virt - pci_io_base; | 728 | return 0; |
1111 | res = &hose->io_resource; | ||
1112 | res->start += io_virt_offset; | ||
1113 | res->end += io_virt_offset; | ||
1114 | } | 729 | } |
730 | EXPORT_SYMBOL_GPL(pcibios_unmap_io_space); | ||
1115 | 731 | ||
732 | #endif /* CONFIG_HOTPLUG */ | ||
1116 | 733 | ||
1117 | static int get_bus_io_range(struct pci_bus *bus, unsigned long *start_phys, | 734 | int __devinit pcibios_map_io_space(struct pci_bus *bus) |
1118 | unsigned long *start_virt, unsigned long *size) | ||
1119 | { | 735 | { |
1120 | struct pci_controller *hose = pci_bus_to_host(bus); | 736 | struct vm_struct *area; |
1121 | struct resource *res; | 737 | unsigned long phys_page; |
1122 | 738 | unsigned long size_page; | |
1123 | if (bus->self) | 739 | unsigned long io_virt_offset; |
1124 | res = bus->resource[0]; | 740 | struct pci_controller *hose; |
1125 | else | ||
1126 | /* Root Bus */ | ||
1127 | res = &hose->io_resource; | ||
1128 | |||
1129 | if (res->end == 0 && res->start == 0) | ||
1130 | return 1; | ||
1131 | 741 | ||
1132 | *start_virt = pci_io_base + res->start; | 742 | WARN_ON(bus == NULL); |
1133 | *start_phys = *start_virt + hose->io_base_phys | ||
1134 | - (unsigned long) hose->io_base_virt; | ||
1135 | 743 | ||
1136 | if (res->end > res->start) | 744 | /* If this not a PHB, nothing to do, page tables still exist and |
1137 | *size = res->end - res->start + 1; | 745 | * thus HPTEs will be faulted in when needed |
1138 | else { | 746 | */ |
1139 | printk("%s(): unexpected region 0x%lx->0x%lx\n", | 747 | if (bus->self) { |
1140 | __FUNCTION__, res->start, res->end); | 748 | DBG("IO mapping for PCI-PCI bridge %s\n", |
1141 | return 1; | 749 | pci_name(bus->self)); |
750 | DBG(" virt=0x%016lx...0x%016lx\n", | ||
751 | bus->resource[0]->start + _IO_BASE, | ||
752 | bus->resource[0]->end + _IO_BASE); | ||
753 | return 0; | ||
1142 | } | 754 | } |
1143 | 755 | ||
1144 | return 0; | 756 | /* Get the host bridge */ |
1145 | } | 757 | hose = pci_bus_to_host(bus); |
1146 | 758 | phys_page = _ALIGN_DOWN(hose->io_base_phys, PAGE_SIZE); | |
1147 | int unmap_bus_range(struct pci_bus *bus) | 759 | size_page = _ALIGN_UP(hose->pci_io_size, PAGE_SIZE); |
1148 | { | ||
1149 | unsigned long start_phys; | ||
1150 | unsigned long start_virt; | ||
1151 | unsigned long size; | ||
1152 | 760 | ||
1153 | if (!bus) { | 761 | /* Make sure IO area address is clear */ |
1154 | printk(KERN_ERR "%s() expected bus\n", __FUNCTION__); | 762 | hose->io_base_alloc = NULL; |
1155 | return 1; | ||
1156 | } | ||
1157 | |||
1158 | if (get_bus_io_range(bus, &start_phys, &start_virt, &size)) | ||
1159 | return 1; | ||
1160 | if (__iounmap_explicit((void __iomem *) start_virt, size)) | ||
1161 | return 1; | ||
1162 | |||
1163 | return 0; | ||
1164 | } | ||
1165 | EXPORT_SYMBOL(unmap_bus_range); | ||
1166 | 763 | ||
1167 | int remap_bus_range(struct pci_bus *bus) | 764 | /* If there's no IO to map on that bus, get away too */ |
1168 | { | 765 | if (hose->pci_io_size == 0 || hose->io_base_phys == 0) |
1169 | unsigned long start_phys; | 766 | return 0; |
1170 | unsigned long start_virt; | ||
1171 | unsigned long size; | ||
1172 | 767 | ||
1173 | if (!bus) { | 768 | /* Let's allocate some IO space for that guy. We don't pass |
1174 | printk(KERN_ERR "%s() expected bus\n", __FUNCTION__); | 769 | * VM_IOREMAP because we don't care about alignment tricks that |
1175 | return 1; | 770 | * the core does in that case. Maybe we should due to stupid card |
1176 | } | 771 | * with incomplete address decoding but I'd rather not deal with |
1177 | 772 | * those outside of the reserved 64K legacy region. | |
1178 | 773 | */ | |
1179 | if (get_bus_io_range(bus, &start_phys, &start_virt, &size)) | 774 | area = __get_vm_area(size_page, 0, PHB_IO_BASE, PHB_IO_END); |
1180 | return 1; | 775 | if (area == NULL) |
1181 | if (start_phys == 0) | 776 | return -ENOMEM; |
1182 | return 1; | 777 | hose->io_base_alloc = area->addr; |
1183 | printk(KERN_DEBUG "mapping IO %lx -> %lx, size: %lx\n", start_phys, start_virt, size); | 778 | hose->io_base_virt = (void __iomem *)(area->addr + |
1184 | if (__ioremap_explicit(start_phys, start_virt, size, | 779 | hose->io_base_phys - phys_page); |
1185 | _PAGE_NO_CACHE | _PAGE_GUARDED)) | 780 | |
1186 | return 1; | 781 | DBG("IO mapping for PHB %s\n", |
782 | ((struct device_node *)hose->arch_data)->full_name); | ||
783 | DBG(" phys=0x%016lx, virt=0x%p (alloc=0x%p)\n", | ||
784 | hose->io_base_phys, hose->io_base_virt, hose->io_base_alloc); | ||
785 | DBG(" size=0x%016lx (alloc=0x%016lx)\n", | ||
786 | hose->pci_io_size, size_page); | ||
787 | |||
788 | /* Establish the mapping */ | ||
789 | if (__ioremap_at(phys_page, area->addr, size_page, | ||
790 | _PAGE_NO_CACHE | _PAGE_GUARDED) == NULL) | ||
791 | return -ENOMEM; | ||
792 | |||
793 | /* Fixup hose IO resource */ | ||
794 | io_virt_offset = (unsigned long)hose->io_base_virt - _IO_BASE; | ||
795 | hose->io_resource.start += io_virt_offset; | ||
796 | hose->io_resource.end += io_virt_offset; | ||
797 | |||
798 | DBG(" hose->io_resource=0x%016lx...0x%016lx\n", | ||
799 | hose->io_resource.start, hose->io_resource.end); | ||
1187 | 800 | ||
1188 | return 0; | 801 | return 0; |
1189 | } | 802 | } |
1190 | EXPORT_SYMBOL(remap_bus_range); | 803 | EXPORT_SYMBOL_GPL(pcibios_map_io_space); |
1191 | |||
1192 | static void phbs_remap_io(void) | ||
1193 | { | ||
1194 | struct pci_controller *hose, *tmp; | ||
1195 | |||
1196 | list_for_each_entry_safe(hose, tmp, &hose_list, list_node) | ||
1197 | remap_bus_range(hose->bus); | ||
1198 | } | ||
1199 | 804 | ||
1200 | static void __devinit fixup_resource(struct resource *res, struct pci_dev *dev) | 805 | static void __devinit fixup_resource(struct resource *res, struct pci_dev *dev) |
1201 | { | 806 | { |
@@ -1203,8 +808,7 @@ static void __devinit fixup_resource(struct resource *res, struct pci_dev *dev) | |||
1203 | unsigned long offset; | 808 | unsigned long offset; |
1204 | 809 | ||
1205 | if (res->flags & IORESOURCE_IO) { | 810 | if (res->flags & IORESOURCE_IO) { |
1206 | offset = (unsigned long)hose->io_base_virt - pci_io_base; | 811 | offset = (unsigned long)hose->io_base_virt - _IO_BASE; |
1207 | |||
1208 | res->start += offset; | 812 | res->start += offset; |
1209 | res->end += offset; | 813 | res->end += offset; |
1210 | } else if (res->flags & IORESOURCE_MEM) { | 814 | } else if (res->flags & IORESOURCE_MEM) { |
@@ -1219,9 +823,20 @@ void __devinit pcibios_fixup_device_resources(struct pci_dev *dev, | |||
1219 | /* Update device resources. */ | 823 | /* Update device resources. */ |
1220 | int i; | 824 | int i; |
1221 | 825 | ||
1222 | for (i = 0; i < PCI_NUM_RESOURCES; i++) | 826 | DBG("%s: Fixup resources:\n", pci_name(dev)); |
1223 | if (dev->resource[i].flags) | 827 | for (i = 0; i < PCI_NUM_RESOURCES; i++) { |
1224 | fixup_resource(&dev->resource[i], dev); | 828 | struct resource *res = &dev->resource[i]; |
829 | if (!res->flags) | ||
830 | continue; | ||
831 | |||
832 | DBG(" 0x%02x < %08lx:0x%016lx...0x%016lx\n", | ||
833 | i, res->flags, res->start, res->end); | ||
834 | |||
835 | fixup_resource(res, dev); | ||
836 | |||
837 | DBG(" > %08lx:0x%016lx...0x%016lx\n", | ||
838 | res->flags, res->start, res->end); | ||
839 | } | ||
1225 | } | 840 | } |
1226 | EXPORT_SYMBOL(pcibios_fixup_device_resources); | 841 | EXPORT_SYMBOL(pcibios_fixup_device_resources); |
1227 | 842 | ||
@@ -1291,119 +906,6 @@ void __devinit pcibios_fixup_bus(struct pci_bus *bus) | |||
1291 | } | 906 | } |
1292 | EXPORT_SYMBOL(pcibios_fixup_bus); | 907 | EXPORT_SYMBOL(pcibios_fixup_bus); |
1293 | 908 | ||
1294 | /* | ||
1295 | * Reads the interrupt pin to determine if interrupt is use by card. | ||
1296 | * If the interrupt is used, then gets the interrupt line from the | ||
1297 | * openfirmware and sets it in the pci_dev and pci_config line. | ||
1298 | */ | ||
1299 | int pci_read_irq_line(struct pci_dev *pci_dev) | ||
1300 | { | ||
1301 | struct of_irq oirq; | ||
1302 | unsigned int virq; | ||
1303 | |||
1304 | DBG("Try to map irq for %s...\n", pci_name(pci_dev)); | ||
1305 | |||
1306 | #ifdef DEBUG | ||
1307 | memset(&oirq, 0xff, sizeof(oirq)); | ||
1308 | #endif | ||
1309 | /* Try to get a mapping from the device-tree */ | ||
1310 | if (of_irq_map_pci(pci_dev, &oirq)) { | ||
1311 | u8 line, pin; | ||
1312 | |||
1313 | /* If that fails, lets fallback to what is in the config | ||
1314 | * space and map that through the default controller. We | ||
1315 | * also set the type to level low since that's what PCI | ||
1316 | * interrupts are. If your platform does differently, then | ||
1317 | * either provide a proper interrupt tree or don't use this | ||
1318 | * function. | ||
1319 | */ | ||
1320 | if (pci_read_config_byte(pci_dev, PCI_INTERRUPT_PIN, &pin)) | ||
1321 | return -1; | ||
1322 | if (pin == 0) | ||
1323 | return -1; | ||
1324 | if (pci_read_config_byte(pci_dev, PCI_INTERRUPT_LINE, &line) || | ||
1325 | line == 0xff) { | ||
1326 | return -1; | ||
1327 | } | ||
1328 | DBG(" -> no map ! Using irq line %d from PCI config\n", line); | ||
1329 | |||
1330 | virq = irq_create_mapping(NULL, line); | ||
1331 | if (virq != NO_IRQ) | ||
1332 | set_irq_type(virq, IRQ_TYPE_LEVEL_LOW); | ||
1333 | } else { | ||
1334 | DBG(" -> got one, spec %d cells (0x%08x 0x%08x...) on %s\n", | ||
1335 | oirq.size, oirq.specifier[0], oirq.specifier[1], | ||
1336 | oirq.controller->full_name); | ||
1337 | |||
1338 | virq = irq_create_of_mapping(oirq.controller, oirq.specifier, | ||
1339 | oirq.size); | ||
1340 | } | ||
1341 | if(virq == NO_IRQ) { | ||
1342 | DBG(" -> failed to map !\n"); | ||
1343 | return -1; | ||
1344 | } | ||
1345 | |||
1346 | DBG(" -> mapped to linux irq %d\n", virq); | ||
1347 | |||
1348 | pci_dev->irq = virq; | ||
1349 | |||
1350 | return 0; | ||
1351 | } | ||
1352 | EXPORT_SYMBOL(pci_read_irq_line); | ||
1353 | |||
1354 | void pci_resource_to_user(const struct pci_dev *dev, int bar, | ||
1355 | const struct resource *rsrc, | ||
1356 | resource_size_t *start, resource_size_t *end) | ||
1357 | { | ||
1358 | struct pci_controller *hose = pci_bus_to_host(dev->bus); | ||
1359 | resource_size_t offset = 0; | ||
1360 | |||
1361 | if (hose == NULL) | ||
1362 | return; | ||
1363 | |||
1364 | if (rsrc->flags & IORESOURCE_IO) | ||
1365 | offset = (unsigned long)hose->io_base_virt - pci_io_base; | ||
1366 | |||
1367 | /* We pass a fully fixed up address to userland for MMIO instead of | ||
1368 | * a BAR value because X is lame and expects to be able to use that | ||
1369 | * to pass to /dev/mem ! | ||
1370 | * | ||
1371 | * That means that we'll have potentially 64 bits values where some | ||
1372 | * userland apps only expect 32 (like X itself since it thinks only | ||
1373 | * Sparc has 64 bits MMIO) but if we don't do that, we break it on | ||
1374 | * 32 bits CHRPs :-( | ||
1375 | * | ||
1376 | * Hopefully, the sysfs insterface is immune to that gunk. Once X | ||
1377 | * has been fixed (and the fix spread enough), we can re-enable the | ||
1378 | * 2 lines below and pass down a BAR value to userland. In that case | ||
1379 | * we'll also have to re-enable the matching code in | ||
1380 | * __pci_mmap_make_offset(). | ||
1381 | * | ||
1382 | * BenH. | ||
1383 | */ | ||
1384 | #if 0 | ||
1385 | else if (rsrc->flags & IORESOURCE_MEM) | ||
1386 | offset = hose->pci_mem_offset; | ||
1387 | #endif | ||
1388 | |||
1389 | *start = rsrc->start - offset; | ||
1390 | *end = rsrc->end - offset; | ||
1391 | } | ||
1392 | |||
1393 | struct pci_controller* pci_find_hose_for_OF_device(struct device_node* node) | ||
1394 | { | ||
1395 | if (!have_of) | ||
1396 | return NULL; | ||
1397 | while(node) { | ||
1398 | struct pci_controller *hose, *tmp; | ||
1399 | list_for_each_entry_safe(hose, tmp, &hose_list, list_node) | ||
1400 | if (hose->arch_data == node) | ||
1401 | return hose; | ||
1402 | node = node->parent; | ||
1403 | } | ||
1404 | return NULL; | ||
1405 | } | ||
1406 | |||
1407 | unsigned long pci_address_to_pio(phys_addr_t address) | 909 | unsigned long pci_address_to_pio(phys_addr_t address) |
1408 | { | 910 | { |
1409 | struct pci_controller *hose, *tmp; | 911 | struct pci_controller *hose, *tmp; |
@@ -1412,7 +914,7 @@ unsigned long pci_address_to_pio(phys_addr_t address) | |||
1412 | if (address >= hose->io_base_phys && | 914 | if (address >= hose->io_base_phys && |
1413 | address < (hose->io_base_phys + hose->pci_io_size)) { | 915 | address < (hose->io_base_phys + hose->pci_io_size)) { |
1414 | unsigned long base = | 916 | unsigned long base = |
1415 | (unsigned long)hose->io_base_virt - pci_io_base; | 917 | (unsigned long)hose->io_base_virt - _IO_BASE; |
1416 | return base + (address - hose->io_base_phys); | 918 | return base + (address - hose->io_base_phys); |
1417 | } | 919 | } |
1418 | } | 920 | } |