Should message signaled interrupts (MSI) work with Intel GMA 950?
Roland Dreier
roland.list at gmail.com
Tue Sep 4 13:56:31 PDT 2007
I have a Lenovo X60s laptop with Intel GMA 950 (945GM) graphics, and
for the fun of it I decided to try enabling message signaled
interrupts for the graphics controller in the i915 drm module, since
the internal graphics device's PCI header contains an MSI capability.
(And MSI is nice with powertop, because it avoids shared interrupts
that make it impossible to see who is really causing a wakeup)
Unfortunately, although my patch seems to work enough so MSI gets
enabled, and X also seems to work OK, I don't see any interrupts.
Using 2.6.23-rc5 without the patch (so using INTx) I see a steady
stream of (vblank?) interrupts. (My patch testing is on top of an
otherwise completely vanilla 2.6.23-rc5 kernel)
Does anyone (probably from Intel) know whether MSI is supposed to work
with this graphics controller and if there's something else that needs
to be poked to get it to work? I couldn't find anything in the 945GM
datasheet or spec update that indicated that MSI was broken, but I
also couldn't find a definitive statement in the datasheet that said
that MSI is supposed to work for the internal graphics.
All the other MSI capable devices in the laptop (ahci, e1000, iwl3945
and HDA sound) work well with MSI:
CPU0 CPU1
0: 102397 2 IO-APIC-edge timer
1: 2289 0 IO-APIC-edge i8042
8: 3 0 IO-APIC-edge rtc
9: 1613 0 IO-APIC-fasteoi acpi
12: 6695 0 IO-APIC-edge i8042
14: 0 0 IO-APIC-edge libata
15: 0 0 IO-APIC-edge libata
20: 0 0 IO-APIC-fasteoi uhci_hcd:usb1, yenta
21: 3 0 IO-APIC-fasteoi uhci_hcd:usb2, ohci1394
22: 0 0 IO-APIC-fasteoi uhci_hcd:usb3,
sdhci:slot0
23: 39 0 IO-APIC-fasteoi uhci_hcd:usb4,
ehci_hcd:usb5
215: 0 0 PCI-MSI-edge i915 at pci:0000:00:02.0
216: 118 0 PCI-MSI-edge HDA Intel
217: 642 0 PCI-MSI-edge iwl3945
218: 4430 0 PCI-MSI-edge eth0
219: 15242 0 PCI-MSI-edge ahci
NMI: 0 0
LOC: 11615 59013
ERR: 0
MIS: 0
And here's lspci output (with MSI enabled; the MSI address and data
look completely sane to me):
00:02.0 VGA compatible controller [0300]: Intel Corporation
Mobile 945GM/GMS/940GML Express Integrated Graphics Controller
[8086:27a2] (rev 03) (prog-if 00 [VGA])
Subsystem: Lenovo Thinkpad R60e model 0657 [17aa:201a]
Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop-
ParErr- Stepping- SERR- FastB2B-
Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=fast
>TAbort- <TAbort- <MAbort- >SERR- <PERR-
Latency: 0
Interrupt: pin A routed to IRQ 215
Region 0: Memory at ee100000 (32-bit, non-prefetchable) [size=512K]
Region 1: I/O ports at 1800 [size=8]
Region 2: Memory at d0000000 (32-bit, prefetchable) [size=256M]
Region 3: Memory at ee200000 (32-bit, non-prefetchable) [size=256K]
Capabilities: [90] Message Signalled Interrupts: Mask- 64bit-
Queue=0/0 Enable+
Address: fee0300c Data: 416a
Capabilities: [d0] Power Management version 2
Flags: PMEClk- DSI+ D1- D2- AuxCurrent=0mA
PME(D0-,D1-,D2-,D3hot-,D3cold-)
Status: D0 PME-Enable- DSel=0 DScale=0 PME-
00:02.1 Display controller [0380]: Intel Corporation Mobile
945GM/GMS/940GML Express Integrated Graphics Controller [8086:27a6]
(rev 03)
Subsystem: Lenovo Thinkpad R60e model 0657 [17aa:201a]
Control: I/O+ Mem+ BusMaster- SpecCycle- MemWINV- VGASnoop-
ParErr- Stepping- SERR- FastB2B-
Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=fast
>TAbort- <TAbort- <MAbort- >SERR- <PERR-
Region 0: Memory at ee180000 (32-bit, non-prefetchable) [size=512K]
Capabilities: [d0] Power Management version 2
Flags: PMEClk- DSI+ D1- D2- AuxCurrent=0mA
PME(D0-,D1-,D2-,D3hot-,D3cold-)
Status: D0 PME-Enable- DSel=0 DScale=0 PME-
Finally, here's the exact patch I tried (probably space mangled by
gmail); someone adventurous could try this with GMA 3000 or 3100
graphics and see if it actually generates interrupts.
Thanks,
Roland
diff --git a/drivers/char/drm/drmP.h b/drivers/char/drm/drmP.h
index 0df87fc..d6f8aba 100644
--- a/drivers/char/drm/drmP.h
+++ b/drivers/char/drm/drmP.h
@@ -100,6 +100,7 @@
#define DRIVER_DMA_QUEUE 0x200
#define DRIVER_FB_DMA 0x400
#define DRIVER_IRQ_VBL2 0x800
+#define DRIVER_USE_MSI 0x1000
/***********************************************************************/
/** \name Begin the DRM... */
diff --git a/drivers/char/drm/drm_stub.c b/drivers/char/drm/drm_stub.c
index ee83ff9..a2d9f0a 100644
--- a/drivers/char/drm/drm_stub.c
+++ b/drivers/char/drm/drm_stub.c
@@ -78,6 +78,14 @@ static int drm_fill_in_dev(struct drm_device * dev,
struct pci_dev *pdev,
dev->pci_device = pdev->device;
dev->pci_vendor = pdev->vendor;
+ dev->driver = driver;
+
+ if (drm_core_check_feature(dev, DRIVER_USE_MSI))
+ if (!pci_enable_msi(pdev)) {
+ printk(KERN_ERR "DRM: Enabled MSI\n");
+ dev->driver->driver_features &= ~DRIVER_IRQ_SHARED;
+ }
+
#ifdef __alpha__
dev->hose = pdev->sysdata;
#endif
@@ -96,8 +104,6 @@ static int drm_fill_in_dev(struct drm_device * dev,
struct pci_dev *pdev,
dev->types[4] = _DRM_STAT_LOCKS;
dev->types[5] = _DRM_STAT_UNLOCKS;
- dev->driver = driver;
-
if (dev->driver->load)
if ((retcode = dev->driver->load(dev, ent->driver_data)))
goto error_out_unreg;
diff --git a/drivers/char/drm/i915_drv.c b/drivers/char/drm/i915_drv.c
index 85bcc27..1d7a200 100644
--- a/drivers/char/drm/i915_drv.c
+++ b/drivers/char/drm/i915_drv.c
@@ -45,7 +45,7 @@ static struct drm_driver driver = {
.driver_features =
DRIVER_USE_AGP | DRIVER_REQUIRE_AGP | /* DRIVER_USE_MTRR |*/
DRIVER_HAVE_IRQ | DRIVER_IRQ_SHARED | DRIVER_IRQ_VBL |
- DRIVER_IRQ_VBL2,
+ DRIVER_IRQ_VBL2 | DRIVER_USE_MSI,
.load = i915_driver_load,
.lastclose = i915_driver_lastclose,
.preclose = i915_driver_preclose,
More information about the xorg
mailing list