diff options
author | Jacob Pan <jacob.jun.pan@linux.intel.com> | 2010-07-16 13:19:22 -0400 |
---|---|---|
committer | Jesse Barnes <jbarnes@virtuousgeek.org> | 2010-07-30 12:29:35 -0400 |
commit | 253d2e549818f5a4a52e2db0aba3dacee21e5b38 (patch) | |
tree | 535ff224cb89860809fa5d948e19e1f3342cf7b3 /drivers/pci/probe.c | |
parent | fcd097f31a6ee207cc0c3da9cccd2a86d4334785 (diff) |
PCI: disable mmio during bar sizing
It is a known issue that mmio decoding shall be disabled while doing PCI
bar sizing. Host bridge and other devices (PCI PIC) shall be excluded for
certain platforms. This patch mainly comes from Mathew Willcox's
patch in http://kerneltrap.org/mailarchive/linux-kernel/2007/9/13/258969.
A new flag bit "mmio_alway_on" is added to pci_dev with the intention that
devices with their mmio decoding cannot be disabled during BAR sizing shall
have this bit set, preferrablly in their quirks.
Without this patch, Intel Moorestown platform graphics unit will be
corrupted during bar sizing activities.
Signed-off-by: Jacob Pan <jacob.jun.pan@linux.intel.com>
Signed-off-by: Jesse Barnes <jbarnes@virtuousgeek.org>
Diffstat (limited to 'drivers/pci/probe.c')
-rw-r--r-- | drivers/pci/probe.c | 10 |
1 files changed, 10 insertions, 0 deletions
diff --git a/drivers/pci/probe.c b/drivers/pci/probe.c index f4adba2d1dd3..12625d90f8b5 100644 --- a/drivers/pci/probe.c +++ b/drivers/pci/probe.c | |||
@@ -163,9 +163,16 @@ int __pci_read_base(struct pci_dev *dev, enum pci_bar_type type, | |||
163 | struct resource *res, unsigned int pos) | 163 | struct resource *res, unsigned int pos) |
164 | { | 164 | { |
165 | u32 l, sz, mask; | 165 | u32 l, sz, mask; |
166 | u16 orig_cmd; | ||
166 | 167 | ||
167 | mask = type ? PCI_ROM_ADDRESS_MASK : ~0; | 168 | mask = type ? PCI_ROM_ADDRESS_MASK : ~0; |
168 | 169 | ||
170 | if (!dev->mmio_always_on) { | ||
171 | pci_read_config_word(dev, PCI_COMMAND, &orig_cmd); | ||
172 | pci_write_config_word(dev, PCI_COMMAND, | ||
173 | orig_cmd & ~(PCI_COMMAND_MEMORY | PCI_COMMAND_IO)); | ||
174 | } | ||
175 | |||
169 | res->name = pci_name(dev); | 176 | res->name = pci_name(dev); |
170 | 177 | ||
171 | pci_read_config_dword(dev, pos, &l); | 178 | pci_read_config_dword(dev, pos, &l); |
@@ -173,6 +180,9 @@ int __pci_read_base(struct pci_dev *dev, enum pci_bar_type type, | |||
173 | pci_read_config_dword(dev, pos, &sz); | 180 | pci_read_config_dword(dev, pos, &sz); |
174 | pci_write_config_dword(dev, pos, l); | 181 | pci_write_config_dword(dev, pos, l); |
175 | 182 | ||
183 | if (!dev->mmio_always_on) | ||
184 | pci_write_config_word(dev, PCI_COMMAND, orig_cmd); | ||
185 | |||
176 | /* | 186 | /* |
177 | * All bits set in sz means the device isn't working properly. | 187 | * All bits set in sz means the device isn't working properly. |
178 | * If the BAR isn't implemented, all bits must be 0. If it's a | 188 | * If the BAR isn't implemented, all bits must be 0. If it's a |