Commit 41b9eb264c8407655db57b60b4457fe1b2ec9977

Authored by Stefan Assmann
Committed by Ingo Molnar
1 parent 3e370b29d3

x86, pci: introduce config option for pci reroute quirks (was: [PATCH 0/3] Boot …

…IRQ quirks for Broadcom and AMD/ATI)

This is against linux-2.6-tip, branch pci-ioapic-boot-irq-quirks.

From: Stefan Assmann <sassmann@suse.de>
Subject: Introduce config option for pci reroute quirks

The config option X86_REROUTE_FOR_BROKEN_BOOT_IRQS is introduced to
enable (or disable) the redirection of the interrupt handler to the boot
interrupt line by default. Depending on the existence of interrupt
masking / threaded interrupt handling in the kernel (vanilla, rt, ...)
and the maturity of the rerouting patch, users can enable or disable the
redirection by default.

This means that the reroute quirk can be applied to any kernel without
changing it.

Interrupt sharing could be increased if this option is enabled. However this
option is vital for threaded interrupt handling, as done by the RT kernel.
It should simplify the consolidation with the RT kernel.

The option can be overridden by either pci=ioapicreroute or
pci=noioapicreroute.

Signed-off-by: Stefan Assmann <sassmann@suse.de>
Signed-off-by: Olaf Dabrunz <od@suse.de>
Cc: Jesse Barnes <jbarnes@virtuousgeek.org>
Cc: Jon Masters <jonathan@jonmasters.org>
Cc: Ihno Krumreich <ihno@suse.de>
Cc: Sven Dietrich <sdietrich@suse.de>
Cc: Daniel Gollub <dgollub@suse.de>
Cc: Felix Foerster <ffoerster@suse.de>
Signed-off-by: Ingo Molnar <mingo@elte.hu>

Showing 5 changed files with 38 additions and 2 deletions Side-by-side Diff

Documentation/kernel-parameters.txt
... ... @@ -1536,6 +1536,10 @@
1536 1536 primary IO-APIC for bridges that cannot disable
1537 1537 boot IRQs. This fixes a source of spurious IRQs
1538 1538 when the system masks IRQs.
  1539 + noioapicreroute [APIC] Disable workaround that uses the
  1540 + boot IRQ equivalent of an IRQ that connects to
  1541 + a chipset where boot IRQs cannot be disabled.
  1542 + The opposite of ioapicreroute.
1539 1543 biosirq [X86-32] Use PCI BIOS calls to get the interrupt
1540 1544 routing table. These calls are known to be buggy
1541 1545 on several machines and they hang the machine
... ... @@ -665,6 +665,30 @@
665 665 def_bool y
666 666 depends on X86_32 && X86_VISWS
667 667  
  668 +config X86_REROUTE_FOR_BROKEN_BOOT_IRQS
  669 + bool "Reroute for broken boot IRQs"
  670 + default n
  671 + depends on X86_IO_APIC
  672 + help
  673 + This option enables a workaround that fixes a source of
  674 + spurious interrupts. This is recommended when threaded
  675 + interrupt handling is used on systems where the generation of
  676 + superfluous "boot interrupts" cannot be disabled.
  677 +
  678 + Some chipsets generate a legacy INTx "boot IRQ" when the IRQ
  679 + entry in the chipset's IO-APIC is masked (as, e.g. the RT
  680 + kernel does during interrupt handling). On chipsets where this
  681 + boot IRQ generation cannot be disabled, this workaround keeps
  682 + the original IRQ line masked so that only the equivalent "boot
  683 + IRQ" is delivered to the CPUs. The workaround also tells the
  684 + kernel to set up the IRQ handler on the boot IRQ line. In this
  685 + way only one interrupt is delivered to the kernel. Otherwise
  686 + the spurious second interrupt may cause the kernel to bring
  687 + down (vital) interrupt lines.
  688 +
  689 + Only affects "broken" chipsets. Interrupt sharing may be
  690 + increased on these systems.
  691 +
668 692 config X86_MCE
669 693 bool "Machine Check Exception"
670 694 depends on !X86_VOYAGER
arch/x86/pci/common.c
... ... @@ -24,7 +24,11 @@
24 24 static int pci_bf_sort;
25 25 int pci_routeirq;
26 26 int noioapicquirk;
  27 +#ifdef CONFIG_X86_REROUTE_FOR_BROKEN_BOOT_IRQS
  28 +int noioapicreroute = 0;
  29 +#else
27 30 int noioapicreroute = 1;
  31 +#endif
28 32 int pcibios_last_bus = -1;
29 33 unsigned long pirq_table_addr;
30 34 struct pci_bus *pci_root_bus;
... ... @@ -527,6 +531,10 @@
527 531 } else if (!strcmp(str, "ioapicreroute")) {
528 532 if (noioapicreroute != -1)
529 533 noioapicreroute = 0;
  534 + return NULL;
  535 + } else if (!strcmp(str, "noioapicreroute")) {
  536 + if (noioapicreroute != -1)
  537 + noioapicreroute = 1;
530 538 return NULL;
531 539 }
532 540 return str;
drivers/pci/quirks.c
... ... @@ -1397,7 +1397,7 @@
1397 1397 */
1398 1398 static void quirk_reroute_to_boot_interrupts_intel(struct pci_dev *dev)
1399 1399 {
1400   - if (noioapicquirk)
  1400 + if (noioapicquirk || noioapicreroute)
1401 1401 return;
1402 1402  
1403 1403 dev->irq_reroute_variant = INTEL_IRQ_REROUTE_VARIANT;
include/asm-x86/pci.h
... ... @@ -20,7 +20,7 @@
20 20  
21 21 extern int pci_routeirq;
22 22 extern int noioapicquirk;
23   -extern int ioapicreroute;
  23 +extern int noioapicreroute;
24 24  
25 25 /* scan a bus after allocating a pci_sysdata for it */
26 26 extern struct pci_bus *pci_scan_bus_on_node(int busno, struct pci_ops *ops,