OvmfPkg: set ActiveHigh polarity for the SCI with a dedicated link device

We cannot specify a pin-GSI connection for the SCI directly in the _PRT
because that implies ActiveLow polarity, clashing with both qemu and the
MADT we prepare.

With this patch the RHEL-6 guest logs the following:

    ACPI: PCI Interrupt Routing Table [\_SB_.PCI0._PRT]
    ACPI: PCI Interrupt Link [LNKS] (IRQs *9)
    ACPI: PCI Interrupt Link [LNKA] (IRQs 5 10 *11)
    ACPI: PCI Interrupt Link [LNKB] (IRQs 5 10 *11)
    ACPI: PCI Interrupt Link [LNKC] (IRQs 5 *10 11)
    ACPI: PCI Interrupt Link [LNKD] (IRQs 5 *10 11)

The patch amends svn rev 13625. Testing it in a RHEL-6 guest, the problems
described in
<http://sourceforge.net/mailarchive/message.php?msg_id=29660862> do not
reappear.

The code is derived from Paolo Bonzini's patch (originally appearing as
SeaBIOS commit f64a472a, "acpi: reintroduce LNKS"). Said original patch is
copyrighted by Red Hat (our common employer), and it has been relicensed
<http://sourceforge.net/mailarchive/message.php?msg_id=30393854> to form
the basis of this derived patch for edk2. The latter is therefore

Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: Laszlo Ersek <lersek@redhat.com>
Reviewed-by: Jordan Justen <jordan.l.justen@intel.com>

git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@14111 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
jljusten 2013-01-28 16:55:38 +00:00
parent f940fea8b1
commit 0c504abf90
1 changed files with 44 additions and 2 deletions

View File

@ -203,10 +203,28 @@ DefinitionBlock ("Dsdt.aml", "DSDT", 1, "INTEL ", "OVMF ", 4) {
Package () {0x0000FFFF, 0x02, \_SB.PCI0.LPC.LNKB, 0x00}, Package () {0x0000FFFF, 0x02, \_SB.PCI0.LPC.LNKB, 0x00},
Package () {0x0000FFFF, 0x03, \_SB.PCI0.LPC.LNKC, 0x00}, Package () {0x0000FFFF, 0x03, \_SB.PCI0.LPC.LNKC, 0x00},
Package () {0x0001FFFF, 0x00, 0x00, 0x09},
// //
// list of IRQs occupied thus far: 9 // Bus 0, Device 1, Pin 0 (INTA) is special; it corresponds to the
// internally generated SCI (System Control Interrupt), which is
// always routed to GSI 9. By setting the third (= Source) field to
// zero, we could use the fourth (= Source Index) field to hardwire
// the pin to GSI 9 directly.
// //
// That way however, in accordance with the ACPI spec's description
// of SCI, the interrupt would be treated as "active low,
// shareable, level", and that doesn't match qemu.
//
// In QemuInstallAcpiMadtTable() [OvmfPkg/AcpiPlatformDxe/Qemu.c]
// we install an Interrupt Override Structure for the identity
// mapped IRQ#9 / GSI 9 (the corresponding bit being set in
// Pcd8259LegacyModeEdgeLevel), which describes the correct
// polarity (active high). As a consequence, some OS'en (eg. Linux)
// override the default (active low) polarity originating from the
// _PRT; others (eg. FreeBSD) don't. Therefore we need a separate
// link device just to specify a polarity that matches the MADT.
//
Package () {0x0001FFFF, 0x00, \_SB.PCI0.LPC.LNKS, 0x00},
Package () {0x0001FFFF, 0x01, \_SB.PCI0.LPC.LNKB, 0x00}, Package () {0x0001FFFF, 0x01, \_SB.PCI0.LPC.LNKB, 0x00},
Package () {0x0001FFFF, 0x02, \_SB.PCI0.LPC.LNKC, 0x00}, Package () {0x0001FFFF, 0x02, \_SB.PCI0.LPC.LNKC, 0x00},
Package () {0x0001FFFF, 0x03, \_SB.PCI0.LPC.LNKD, 0x00}, Package () {0x0001FFFF, 0x03, \_SB.PCI0.LPC.LNKD, 0x00},
@ -291,6 +309,30 @@ DefinitionBlock ("Dsdt.aml", "DSDT", 1, "INTEL ", "OVMF ", 4) {
Device (LPC) { Device (LPC) {
Name (_ADR, 0x00010000) Name (_ADR, 0x00010000)
//
// The SCI cannot be rerouted or disabled with PIRQRC[A:D]; we only
// need this link device in order to specify the polarity.
//
Device (LNKS) {
Name (_HID, EISAID("PNP0C0F"))
Name (_UID, 0)
Name (_STA, 0xB) // 0x1: device present
// 0x2: enabled and decoding resources
// 0x8: functioning properly
Method (_SRS, 1, NotSerialized) { /* no-op */ }
Method (_DIS, 0, NotSerialized) { /* no-op */ }
Name (_PRS, ResourceTemplate () {
Interrupt (ResourceConsumer, Level, ActiveHigh, Shared) { 9 }
//
// list of IRQs occupied thus far: 9
//
})
Method (_CRS, 0, NotSerialized) { Return (_PRS) }
}
// //
// PCI Interrupt Routing Configuration Registers, PIRQRC[A:D] // PCI Interrupt Routing Configuration Registers, PIRQRC[A:D]
// //