diff options
author | Muli Ben-Yehuda <muli@il.ibm.com> | 2006-09-26 04:52:31 -0400 |
---|---|---|
committer | Andi Kleen <andi@basil.nowhere.org> | 2006-09-26 04:52:31 -0400 |
commit | f38db651d5da5e10235fd7dd31095969fb7ef6fb (patch) | |
tree | 4df8d0921b5c4e392adad94eec8407e39e9ffae0 /arch/x86_64/kernel/pci-calgary.c | |
parent | 5f4a7a93886ce1a4327f6028cc05d423f39eebf0 (diff) |
[PATCH] Calgary IOMMU: consolidate per bus data structures
Move the tce_table_kva array, disabled bitmap and bus_to_phb array
into a new per bus 'struct calgary_bus_info'. Also slightly reorganize
build_tce_table and tce_table_setparms to avoid exporting bus_info to
tce.c.
Signed-off-by: Muli Ben-Yehuda <muli@il.ibm.com>
Signed-off-by: Jon Mason <jdmason@us.ibm.com>
Signed-off-by: Andi Kleen <ak@suse.de>
Diffstat (limited to 'arch/x86_64/kernel/pci-calgary.c')
-rw-r--r-- | arch/x86_64/kernel/pci-calgary.c | 53 |
1 files changed, 28 insertions, 25 deletions
diff --git a/arch/x86_64/kernel/pci-calgary.c b/arch/x86_64/kernel/pci-calgary.c index 146924ba5df5..96f6a866afad 100644 --- a/arch/x86_64/kernel/pci-calgary.c +++ b/arch/x86_64/kernel/pci-calgary.c | |||
@@ -111,17 +111,17 @@ static const unsigned long phb_offsets[] = { | |||
111 | 0xB000 /* PHB3 */ | 111 | 0xB000 /* PHB3 */ |
112 | }; | 112 | }; |
113 | 113 | ||
114 | static char bus_to_phb[MAX_PHB_BUS_NUM]; | ||
115 | void* tce_table_kva[MAX_PHB_BUS_NUM]; | ||
116 | unsigned int specified_table_size = TCE_TABLE_SIZE_UNSPECIFIED; | 114 | unsigned int specified_table_size = TCE_TABLE_SIZE_UNSPECIFIED; |
117 | static int translate_empty_slots __read_mostly = 0; | 115 | static int translate_empty_slots __read_mostly = 0; |
118 | static int calgary_detected __read_mostly = 0; | 116 | static int calgary_detected __read_mostly = 0; |
119 | 117 | ||
120 | /* | 118 | struct calgary_bus_info { |
121 | * the bitmap of PHBs the user requested that we disable | 119 | void *tce_space; |
122 | * translation on. | 120 | int translation_disabled; |
123 | */ | 121 | signed char phbid; |
124 | static DECLARE_BITMAP(translation_disabled, MAX_PHB_BUS_NUM); | 122 | }; |
123 | |||
124 | static struct calgary_bus_info bus_info[MAX_PHB_BUS_NUM] = { { NULL, 0, 0 }, }; | ||
125 | 125 | ||
126 | static void tce_cache_blast(struct iommu_table *tbl); | 126 | static void tce_cache_blast(struct iommu_table *tbl); |
127 | 127 | ||
@@ -149,7 +149,7 @@ static inline unsigned int num_dma_pages(unsigned long dma, unsigned int dmalen) | |||
149 | 149 | ||
150 | static inline int translate_phb(struct pci_dev* dev) | 150 | static inline int translate_phb(struct pci_dev* dev) |
151 | { | 151 | { |
152 | int disabled = test_bit(dev->bus->number, translation_disabled); | 152 | int disabled = bus_info[dev->bus->number].translation_disabled; |
153 | return !disabled; | 153 | return !disabled; |
154 | } | 154 | } |
155 | 155 | ||
@@ -454,7 +454,7 @@ static struct dma_mapping_ops calgary_dma_ops = { | |||
454 | 454 | ||
455 | static inline int busno_to_phbid(unsigned char num) | 455 | static inline int busno_to_phbid(unsigned char num) |
456 | { | 456 | { |
457 | return bus_to_phb[num]; | 457 | return bus_info[num].phbid; |
458 | } | 458 | } |
459 | 459 | ||
460 | static inline unsigned long split_queue_offset(unsigned char num) | 460 | static inline unsigned long split_queue_offset(unsigned char num) |
@@ -631,6 +631,10 @@ static int __init calgary_setup_tar(struct pci_dev *dev, void __iomem *bbar) | |||
631 | if (ret) | 631 | if (ret) |
632 | return ret; | 632 | return ret; |
633 | 633 | ||
634 | tbl = dev->sysdata; | ||
635 | tbl->it_base = (unsigned long)bus_info[dev->bus->number].tce_space; | ||
636 | tce_free(tbl, 0, tbl->it_size); | ||
637 | |||
634 | calgary_reserve_regions(dev); | 638 | calgary_reserve_regions(dev); |
635 | 639 | ||
636 | /* set TARs for each PHB */ | 640 | /* set TARs for each PHB */ |
@@ -824,7 +828,7 @@ static int __init calgary_init(void) | |||
824 | calgary_init_one_nontraslated(dev); | 828 | calgary_init_one_nontraslated(dev); |
825 | continue; | 829 | continue; |
826 | } | 830 | } |
827 | if (!tce_table_kva[dev->bus->number] && !translate_empty_slots) { | 831 | if (!bus_info[dev->bus->number].tce_space && !translate_empty_slots) { |
828 | pci_dev_put(dev); | 832 | pci_dev_put(dev); |
829 | continue; | 833 | continue; |
830 | } | 834 | } |
@@ -844,7 +848,7 @@ error: | |||
844 | pci_dev_put(dev); | 848 | pci_dev_put(dev); |
845 | continue; | 849 | continue; |
846 | } | 850 | } |
847 | if (!tce_table_kva[dev->bus->number] && !translate_empty_slots) | 851 | if (!bus_info[dev->bus->number].tce_space && !translate_empty_slots) |
848 | continue; | 852 | continue; |
849 | calgary_disable_translation(dev); | 853 | calgary_disable_translation(dev); |
850 | calgary_free_tar(dev); | 854 | calgary_free_tar(dev); |
@@ -894,9 +898,8 @@ void __init detect_calgary(void) | |||
894 | 898 | ||
895 | for (bus = 0; bus < MAX_PHB_BUS_NUM; bus++) { | 899 | for (bus = 0; bus < MAX_PHB_BUS_NUM; bus++) { |
896 | int dev; | 900 | int dev; |
897 | 901 | struct calgary_bus_info *info = &bus_info[bus]; | |
898 | tce_table_kva[bus] = NULL; | 902 | info->phbid = -1; |
899 | bus_to_phb[bus] = -1; | ||
900 | 903 | ||
901 | if (read_pci_config(bus, 0, 0, 0) != PCI_VENDOR_DEVICE_ID_CALGARY) | 904 | if (read_pci_config(bus, 0, 0, 0) != PCI_VENDOR_DEVICE_ID_CALGARY) |
902 | continue; | 905 | continue; |
@@ -907,12 +910,9 @@ void __init detect_calgary(void) | |||
907 | */ | 910 | */ |
908 | phb = (phb + 1) % PHBS_PER_CALGARY; | 911 | phb = (phb + 1) % PHBS_PER_CALGARY; |
909 | 912 | ||
910 | if (test_bit(bus, translation_disabled)) { | 913 | if (info->translation_disabled) |
911 | printk(KERN_INFO "Calgary: translation is disabled for " | ||
912 | "PHB 0x%x\n", bus); | ||
913 | /* skip this phb, don't allocate a tbl for it */ | ||
914 | continue; | 914 | continue; |
915 | } | 915 | |
916 | /* | 916 | /* |
917 | * Scan the slots of the PCI bus to see if there is a device present. | 917 | * Scan the slots of the PCI bus to see if there is a device present. |
918 | * The parent bus will be the zero-ith device, so start at 1. | 918 | * The parent bus will be the zero-ith device, so start at 1. |
@@ -923,8 +923,8 @@ void __init detect_calgary(void) | |||
923 | tbl = alloc_tce_table(); | 923 | tbl = alloc_tce_table(); |
924 | if (!tbl) | 924 | if (!tbl) |
925 | goto cleanup; | 925 | goto cleanup; |
926 | tce_table_kva[bus] = tbl; | 926 | info->tce_space = tbl; |
927 | bus_to_phb[bus] = phb; | 927 | info->phbid = phb; |
928 | calgary_found = 1; | 928 | calgary_found = 1; |
929 | break; | 929 | break; |
930 | } | 930 | } |
@@ -940,9 +940,12 @@ void __init detect_calgary(void) | |||
940 | return; | 940 | return; |
941 | 941 | ||
942 | cleanup: | 942 | cleanup: |
943 | for (--bus; bus >= 0; --bus) | 943 | for (--bus; bus >= 0; --bus) { |
944 | if (tce_table_kva[bus]) | 944 | struct calgary_bus_info *info = &bus_info[bus]; |
945 | free_tce_table(tce_table_kva[bus]); | 945 | |
946 | if (info->tce_space) | ||
947 | free_tce_table(info->tce_space); | ||
948 | } | ||
946 | } | 949 | } |
947 | 950 | ||
948 | int __init calgary_iommu_init(void) | 951 | int __init calgary_iommu_init(void) |
@@ -1016,7 +1019,7 @@ static int __init calgary_parse_options(char *p) | |||
1016 | if (bridge < MAX_PHB_BUS_NUM) { | 1019 | if (bridge < MAX_PHB_BUS_NUM) { |
1017 | printk(KERN_INFO "Calgary: disabling " | 1020 | printk(KERN_INFO "Calgary: disabling " |
1018 | "translation for PHB 0x%x\n", bridge); | 1021 | "translation for PHB 0x%x\n", bridge); |
1019 | set_bit(bridge, translation_disabled); | 1022 | bus_info[bridge].translation_disabled = 1; |
1020 | } | 1023 | } |
1021 | } | 1024 | } |
1022 | 1025 | ||