From cb4e75d3ebefcb87cee402f56144caae7d11a8f5 Mon Sep 17 00:00:00 2001 From: Michael Lotz Date: Sun, 22 May 2011 12:06:17 +0000 Subject: [PATCH] * When configuring a link device failed, fall back and keep the currently active config and update the info for the remaining shared link device entries. Seen on KVM for the (PCI) ACPI interrupt, but happens where there is no _SRS method for a device (as this one is optional). I find that a bit strange however as in such a case no _PRS (possible resources) should be present either, especially not one advertising a config different from the current one. * Print the routing table later, after enabling irq routing, so that possible changes due to such a fallback are included. * Fix a typo. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@41652 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/system/kernel/arch/x86/ioapic.cpp | 11 ++++++++--- src/system/kernel/arch/x86/irq_routing_table.cpp | 15 +++++++++++++-- 2 files changed, 21 insertions(+), 5 deletions(-) diff --git a/src/system/kernel/arch/x86/ioapic.cpp b/src/system/kernel/arch/x86/ioapic.cpp index 7b7b237de3..5b5e52f910 100644 --- a/src/system/kernel/arch/x86/ioapic.cpp +++ b/src/system/kernel/arch/x86/ioapic.cpp @@ -246,7 +246,7 @@ static void ioapic_enable_io_interrupt(int32 gsi) { // If enabling an overriden source is attempted, enable the override entry - // instead. An interrupt handler was installed at the override GSI to rely + // instead. An interrupt handler was installed at the override GSI to relay // interrupts to the overriden source. if (gsi < ISA_INTERRUPT_COUNT && sSourceOverrides[gsi] != 0) gsi = sSourceOverrides[gsi]; @@ -709,8 +709,6 @@ ioapic_init(kernel_args* args) return; } - print_irq_routing_table(table); - // use the boot CPU as the target for all interrupts uint8 targetAPIC = args->arch_args.cpu_apic_id[0]; @@ -726,6 +724,11 @@ ioapic_init(kernel_args* args) current = current->next; } +#ifdef TRACE_IOAPIC + dprintf("trying interrupt routing:\n"); + print_irq_routing_table(table); +#endif + status = enable_irq_routing(acpiModule, table); if (status != B_OK) { panic("failed to enable IRQ routing"); @@ -734,6 +737,8 @@ ioapic_init(kernel_args* args) return; } + print_irq_routing_table(table); + // configure the source overrides, but let the PCI config below override it acpi_configure_source_overrides(madt); diff --git a/src/system/kernel/arch/x86/irq_routing_table.cpp b/src/system/kernel/arch/x86/irq_routing_table.cpp index ce93bdc84a..160e1ebe30 100644 --- a/src/system/kernel/arch/x86/irq_routing_table.cpp +++ b/src/system/kernel/arch/x86/irq_routing_table.cpp @@ -312,8 +312,19 @@ configure_link_devices(acpi_module_info* acpi, IRQRoutingTable& routingTable) status_t status = set_current_irq(acpi, irqEntry.source, configuration); if (status != B_OK) { - panic("failed to set irq on link device"); - return status; + dprintf("failed to set irq on link device, keeping current\n"); + print_irq_descriptor(configuration); + + // we failed to set the resource, fall back to current + read_current_irq(acpi, irqEntry.source, configuration); + for (int j = i; j < routingTable.Count(); j++) { + irq_routing_entry& other = routingTable.ElementAt(j); + if (other.source == irqEntry.source) { + other.irq = configuration.irq; + other.polarity = configuration.polarity; + other.trigger_mode = configuration.trigger_mode; + } + } } irqEntry.needs_configuration = false;