PCI/MSI: Deal with devices lying about their MSI mask capability

It appears that some devices are lying about their mask capability,
pretending that they don't have it, while they actually do.
The net result is that now that we don't enable MSIs on such
endpoint.

Add a new per-device flag to deal with this. Further patches will
make use of it, sadly.

Signed-off-by: Marc Zyngier <maz@kernel.org>
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Reviewed-by: Thomas Gleixner <tglx@linutronix.de>
Link: https://lore.kernel.org/r/20211104180130.3825416-2-maz@kernel.org
Cc: Bjorn Helgaas <helgaas@kernel.org>

authored by Marc Zyngier and committed by Thomas Gleixner 2226667a 9c8e9c96

+5
+3
drivers/pci/msi.c
··· 477 goto out; 478 479 pci_read_config_word(dev, dev->msi_cap + PCI_MSI_FLAGS, &control); 480 481 entry->msi_attrib.is_msix = 0; 482 entry->msi_attrib.is_64 = !!(control & PCI_MSI_FLAGS_64BIT);
··· 477 goto out; 478 479 pci_read_config_word(dev, dev->msi_cap + PCI_MSI_FLAGS, &control); 480 + /* Lies, damned lies, and MSIs */ 481 + if (dev->dev_flags & PCI_DEV_FLAGS_HAS_MSI_MASKING) 482 + control |= PCI_MSI_FLAGS_MASKBIT; 483 484 entry->msi_attrib.is_msix = 0; 485 entry->msi_attrib.is_64 = !!(control & PCI_MSI_FLAGS_64BIT);
+2
include/linux/pci.h
··· 233 PCI_DEV_FLAGS_NO_FLR_RESET = (__force pci_dev_flags_t) (1 << 10), 234 /* Don't use Relaxed Ordering for TLPs directed at this device */ 235 PCI_DEV_FLAGS_NO_RELAXED_ORDERING = (__force pci_dev_flags_t) (1 << 11), 236 }; 237 238 enum pci_irq_reroute_variant {
··· 233 PCI_DEV_FLAGS_NO_FLR_RESET = (__force pci_dev_flags_t) (1 << 10), 234 /* Don't use Relaxed Ordering for TLPs directed at this device */ 235 PCI_DEV_FLAGS_NO_RELAXED_ORDERING = (__force pci_dev_flags_t) (1 << 11), 236 + /* Device does honor MSI masking despite saying otherwise */ 237 + PCI_DEV_FLAGS_HAS_MSI_MASKING = (__force pci_dev_flags_t) (1 << 12), 238 }; 239 240 enum pci_irq_reroute_variant {