diff options
author | Keir Fraser <keir.fraser@citrix.com> | 2009-10-21 08:50:23 +0100 |
---|---|---|
committer | Keir Fraser <keir.fraser@citrix.com> | 2009-10-21 08:50:23 +0100 |
commit | d9e4801c022e6a503454e23d8eef3ff90f30ed6f (patch) | |
tree | 68e9258de91fd50ba3de7854bb14fa96a0fb5104 /xen/arch/x86/msi.c | |
parent | 9266eb0ef8f0774fef7d23a1a38d38a4101f6007 (diff) | |
download | xen-d9e4801c022e6a503454e23d8eef3ff90f30ed6f.tar.gz xen-d9e4801c022e6a503454e23d8eef3ff90f30ed6f.tar.bz2 xen-d9e4801c022e6a503454e23d8eef3ff90f30ed6f.zip |
x86: MSI: Mask/unmask msi irq during the window which programs msi.
When program msi, it has to mask it first, otherwise, it
may generate inconsistent interrupts. According to spec,
if not masked, the interrupt generation behaviour is undefined.
Signed-off-by: Xiantao Zhang <xiantao.zhang@intel.com>
Diffstat (limited to 'xen/arch/x86/msi.c')
-rw-r--r-- | xen/arch/x86/msi.c | 4 |
1 files changed, 4 insertions, 0 deletions
diff --git a/xen/arch/x86/msi.c b/xen/arch/x86/msi.c index 261da58185..6bf4e6ef69 100644 --- a/xen/arch/x86/msi.c +++ b/xen/arch/x86/msi.c @@ -231,6 +231,7 @@ static void write_msi_msg(struct msi_desc *entry, struct msi_msg *msg) u8 slot = PCI_SLOT(dev->devfn); u8 func = PCI_FUNC(dev->devfn); + mask_msi_irq(entry->irq); pci_conf_write32(bus, slot, func, msi_lower_address_reg(pos), msg->address_lo); if ( entry->msi_attrib.is_64 ) @@ -243,6 +244,7 @@ static void write_msi_msg(struct msi_desc *entry, struct msi_msg *msg) else pci_conf_write16(bus, slot, func, msi_data_reg(pos, 0), msg->data); + unmask_msi_irq(entry->irq); break; } case PCI_CAP_ID_MSIX: @@ -250,11 +252,13 @@ static void write_msi_msg(struct msi_desc *entry, struct msi_msg *msg) void __iomem *base; base = entry->mask_base; + mask_msi_irq(entry->irq); writel(msg->address_lo, base + PCI_MSIX_ENTRY_LOWER_ADDR_OFFSET); writel(msg->address_hi, base + PCI_MSIX_ENTRY_UPPER_ADDR_OFFSET); writel(msg->data, base + PCI_MSIX_ENTRY_DATA_OFFSET); + unmask_msi_irq(entry->irq); break; } default: |