x86, intr-remap: enable interrupt remapping early

Currently, when x2apic is not enabled, interrupt remapping
will be enabled in init_dmars(), where it is too late to remap
ioapic interrupts, that is, ioapic interrupts are really in
compatibility mode, not remappable mode.

This patch always enables interrupt remapping before ioapic
setup, it guarantees all interrupts will be remapped when
interrupt remapping is enabled. Thus it doesn't need to set
the compatibility interrupt bit.

[ Impact: refactor intr-remap init sequence, enable fuller remap mode ]

Signed-off-by: Suresh Siddha <[email protected]>
Signed-off-by: Weidong Han <[email protected]>
Acked-by: David Woodhouse <[email protected]>
Cc: [email protected]
Cc: [email protected]
Cc: [email protected]
LKML-Reference: <[email protected]>
Signed-off-by: Ingo Molnar <[email protected]>
This commit is contained in:
Weidong Han 2009-04-17 16:42:14 +08:00 • committed by Ingo Molnar
commit 937582382c
5 changed files with 54 additions and 67 deletions

View file

@ -1968,15 +1968,6 @@ static int __init init_dmars(void)
}
}
#ifdef CONFIG_INTR_REMAP
if (!intr_remapping_enabled) {
ret = enable_intr_remapping(0);
if (ret)
printk(KERN_ERR
"IOMMU: enable interrupt remapping failed\n");
}
#endif
/*
* For each rmrr
* for each dev attached to rmrr

View file

@ -423,20 +423,6 @@ static void iommu_set_intr_remapping(struct intel_iommu *iommu, int mode)
readl, (sts & DMA_GSTS_IRTPS), sts);
spin_unlock_irqrestore(&iommu->register_lock, flags);
if (mode == 0) {
spin_lock_irqsave(&iommu->register_lock, flags);
/* enable comaptiblity format interrupt pass through */
cmd = iommu->gcmd | DMA_GCMD_CFI;
iommu->gcmd |= DMA_GCMD_CFI;
writel(cmd, iommu->reg + DMAR_GCMD_REG);
IOMMU_WAIT_OP(iommu, DMAR_GSTS_REG,
readl, (sts & DMA_GSTS_CFIS), sts);
spin_unlock_irqrestore(&iommu->register_lock, flags);
}
/*
* global invalidation of interrupt entry cache before enabling
* interrupt-remapping.
@ -516,6 +502,20 @@ end:
spin_unlock_irqrestore(&iommu->register_lock, flags);
}
int __init intr_remapping_supported(void)
{
struct dmar_drhd_unit *drhd;
for_each_drhd_unit(drhd) {
struct intel_iommu *iommu = drhd->iommu;
if (!ecap_ir_support(iommu->ecap))
return 0;
}
return 1;
}
int __init enable_intr_remapping(int eim)
{
struct dmar_drhd_unit *drhd;