aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/parisc/lba_pci.c56
1 files changed, 56 insertions, 0 deletions
diff --git a/drivers/parisc/lba_pci.c b/drivers/parisc/lba_pci.c
index 1f05913ae677..19f6f70c67d3 100644
--- a/drivers/parisc/lba_pci.c
+++ b/drivers/parisc/lba_pci.c
@@ -613,6 +613,54 @@ truncate_pat_collision(struct resource *root, struct resource *new)
613 return 0; /* truncation successful */ 613 return 0; /* truncation successful */
614} 614}
615 615
616/*
617 * extend_lmmio_len: extend lmmio range to maximum length
618 *
619 * This is needed at least on C8000 systems to get the ATI FireGL card
620 * working. On other systems we will currently not extend the lmmio space.
621 */
622static unsigned long
623extend_lmmio_len(unsigned long start, unsigned long end, unsigned long lba_len)
624{
625 struct resource *tmp;
626
627 pr_debug("LMMIO mismatch: PAT length = 0x%lx, MASK register = 0x%lx\n",
628 end - start, lba_len);
629
630 lba_len = min(lba_len+1, 256UL*1024*1024); /* limit to 256 MB */
631
632 pr_debug("LBA: lmmio_space [0x%lx-0x%lx] - original\n", start, end);
633
634 if (boot_cpu_data.cpu_type < mako) {
635 pr_info("LBA: Not a C8000 system - not extending LMMIO range.\n");
636 return end;
637 }
638
639 end += lba_len;
640 if (end < start) /* fix overflow */
641 end = -1ULL;
642
643 pr_debug("LBA: lmmio_space [0x%lx-0x%lx] - current\n", start, end);
644
645 /* first overlap */
646 for (tmp = iomem_resource.child; tmp; tmp = tmp->sibling) {
647 pr_debug("LBA: testing %pR\n", tmp);
648 if (tmp->start == start)
649 continue; /* ignore ourself */
650 if (tmp->end < start)
651 continue;
652 if (tmp->start > end)
653 continue;
654 if (end >= tmp->start)
655 end = tmp->start - 1;
656 }
657
658 pr_info("LBA: lmmio_space [0x%lx-0x%lx] - new\n", start, end);
659
660 /* return new end */
661 return end;
662}
663
616#else 664#else
617#define truncate_pat_collision(r,n) (0) 665#define truncate_pat_collision(r,n) (0)
618#endif 666#endif
@@ -994,6 +1042,14 @@ lba_pat_resources(struct parisc_device *pa_dev, struct lba_device *lba_dev)
994 case PAT_LMMIO: 1042 case PAT_LMMIO:
995 /* used to fix up pre-initialized MEM BARs */ 1043 /* used to fix up pre-initialized MEM BARs */
996 if (!lba_dev->hba.lmmio_space.flags) { 1044 if (!lba_dev->hba.lmmio_space.flags) {
1045 unsigned long lba_len;
1046
1047 lba_len = ~READ_REG32(lba_dev->hba.base_addr
1048 + LBA_LMMIO_MASK);
1049 if ((p->end - p->start) != lba_len)
1050 p->end = extend_lmmio_len(p->start,
1051 p->end, lba_len);
1052
997 sprintf(lba_dev->hba.lmmio_name, 1053 sprintf(lba_dev->hba.lmmio_name,
998 "PCI%02x LMMIO", 1054 "PCI%02x LMMIO",
999 (int)lba_dev->hba.bus_num.start); 1055 (int)lba_dev->hba.bus_num.start);