IRQ routing [Was: Re: Using the "best available" driver]

Jean Tourrilhes jt at hpl.hp.com
Wed Dec 7 16:29:01 EST 2005


On Wed, Dec 07, 2005 at 10:16:00PM +0100, Dominik Brodowski wrote:
> Hi,
> 
> On Wed, Dec 07, 2005 at 01:02:46PM -0800, Jean Tourrilhes wrote:
> > http://marc.theaimsgroup.com/?t=106971885300002&r=1&w=2
> > http://marc.theaimsgroup.com/?l=linux-kernel&m=106981189506433&w=2
> > 
> > 	Note this is why I'm still using the external Pcmcia package
> > on some of my boxes.
> 
> Did you re-test with recent kernels? A lot of stuff has changed since
> 2.6.0-testX in this regard, mostly due to Daniel Ritz's excellent work in
> this area.

	No changes. Linus did say "no manual overrides".

> > For my other boxes, I just use my hackish patch, well, when the BIOS
> > doesn't refuse to allocate ISA regions.
> 
> Could you elaborate on that, please?

	The second link includes a patch at the bottom of the
e-mail. That's what I use (updated for newer kernel). Patch attached.

> Let's squash bugs...

	Well, this one is messy.

> 	Dominik

	Jean
-------------- next part --------------
diff -u -p linux/arch/i386/pci/irq.j1.c linux/arch/i386/pci/irq.c
--- linux/arch/i386/pci/irq.j1.c	Tue Nov 25 10:36:45 2003
+++ linux/arch/i386/pci/irq.c	Tue Nov 25 17:35:44 2003
@@ -693,6 +693,43 @@ static int pcibios_lookup_irq(struct pci
 	return 1;
 }
 
+#define MAX_MIRQS 4
+int manual_irq_entries[MAX_MIRQS][3];		/* bus/slot/irq */
+int manual_irqs_enabled;	/* = 0 */
+
+static int __init manual_irq_setup(char *str)
+{
+	int i, max;
+	int ints[(MAX_MIRQS*3)+1];
+
+	get_options(str, ARRAY_SIZE(ints), ints);
+
+	for (i = 0; i < MAX_MIRQS; i++)
+		manual_irq_entries[i][0] = -1;
+
+	manual_irqs_enabled = 1;
+
+	max = MAX_MIRQS * 3;
+	if (ints[0] < max)
+		max = ints[0];
+	max = max / 3;
+
+	for (i = 0; i < max; i++) {
+		/* Fill our mapping table */
+		manual_irq_entries[i][0] = ints[(3*i) + 1];
+		manual_irq_entries[i][1] = ints[(3*i) + 2];
+		manual_irq_entries[i][2] = ints[(3*i) + 3];
+
+		printk(KERN_DEBUG "Manual PCI %d:%d -> IRQ %d\n",
+		       manual_irq_entries[i][0],
+		       manual_irq_entries[i][1],
+		       manual_irq_entries[i][2]);
+	}
+	return 1;
+}
+
+__setup("manual_pci_irq=", manual_irq_setup);
+
 static void __init pcibios_fixup_irqs(void)
 {
 	struct pci_dev *dev = NULL;
@@ -757,6 +794,30 @@ static void __init pcibios_fixup_irqs(vo
 		 */
 		if (pin && !dev->irq)
 			pcibios_lookup_irq(dev, 0);
+
+		/*
+		 * Manual fixups. Use at your own risks. Jean II
+		 * This assume that the PCI IRQ routing is done right,
+		 * and it's just the BIOS that ignore the card. If you
+		 * need to also fixup the PCI IRQ routing, you will
+		 * probably need to use the "pirq=" option.
+		 * I use this hack to get a PCI-CardBus add-on adapter
+		 * to be recognised on my destktop.
+		 * Jean II
+		 */
+		if (manual_irqs_enabled) {
+			int i;
+			for(i = 0; i < MAX_MIRQS; i++)
+				if ((dev->bus->number ==
+				     manual_irq_entries[i][0])
+				    && (PCI_SLOT(dev->devfn) ==
+					manual_irq_entries[i][1])) {
+					printk(KERN_INFO "PCI->APIC IRQ manual fixup: (B%d,I%d) -> %d\n",
+						dev->bus->number, PCI_SLOT(dev->devfn), manual_irq_entries[i][2]);
+					dev->irq = manual_irq_entries[i][2];
+					pci_write_config_byte(dev, PCI_INTERRUPT_LINE, manual_irq_entries[i][2]);
+				}
+		}
 	}
 }
 


More information about the linux-pcmcia mailing list