PCI bus conflict hang: how to avoid the allocation of an I/O range.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



After commit 

commit 12c22d6ef299ccf0955e5756eb57d90d7577ac68
Author: Linus Torvalds <torvalds@xxxxxxxxxxxxxxxxxxxx>
Date:   Wed Mar 26 11:22:40 2008 -0700

    Revert "PCI: remove transparent bridge sizing"


My laptop began hanging when booting, and I filed
http://bugzilla.kernel.org/show_bug.cgi?id=11054.


I had to disable the sizing of transparent bridges until, after a
conversation in the kernel mailing list, I think I've found the root of
the problem.

A CardBus bridge is on the secondary bus of a transparent bridge. By
default it gets assigned two I/O ranges: 0x1000-0x10ff and
0x-1400-0x14ff, which is translated to the transparent bridge positively
forwarding the range 0x1000-0x1fff. There are no more I/O resources
allocated behind the transparent PCI to PCI bridge.

I suspect there's "something" (some device unknown by the kernel)
decoding I/O accesses in the primary PCI bus, in the 0x1000-0x1fff
range. This device must be causing bus conflicts with the range
allocated to the PCI to PCI bridge. Not sizing the transparent bridge
wouldn't configure any I/O range in it for positive decoding, thus
avoiding the conflict.

The system hangs when the bridge register for the IO base/limit (lower
16 bits, since it's 16 bit only) gets written to with the value
0x????0101.

If I force the range to be allocated to be above 0x4000, everything
works flawlessly. I've been able to do so by two means:

1. Changing the definition of PCIBIOS_MIN_IO in
arch/x86/include/asm/pci.h from 0x1000 to 0x4000. This forces the
CardBus ranges to be allocated above the problematic area, making the
bridge forward 0x4000-0x4fff I/O addresses. BTW, PCIBIOS_MIN_CARDBUS_IO
is defined to be 0x4000 in the same header, but it's only used in
drivers/pcmcia/yenta_socket.c, not apparently when assigning resources
to the CardBus bridge in the functions pci_setup_cardbus() or
pci_bus_size_cardbus() in drivers/pci/setup-bus.c. I suppose that making
the CardBus bridge I/O range allocation respect the defined
PCIBIOS_MIN_CARDBUS_IO limit would fix my issue, but I don't know
whether that's "the right fix" (TM).

2. I've managed to boot a stock Ubuntu Intrepid Ibex x86_64 kernel by
supplying the parameter "pci=cbiosize=8k" to the grub command line. It
doesn't work with a smaller size. With 8k the CardBus bridge I/O ranges
are big enough that they have to be allocated above the "problem area"
because of natural alignment restrictions.


So far I've got what I really wanted (to be able to use my laptop with
modern distributions without having to recompile each kernel version),
although to do so I'm depending on the fact that a kernel parameter
intended for a different use will alter I/O range alignment one PCI to
PCI bridge away.

I write to ask whether the definition of PCIBIOS_MIN_CARDBUS_IO was
indeed intended to affect my case too (in which case what is happening
is the result of a kernel bug that should be fixed) or not. And if it's
not a bug, I'd like to know if there exists any reliable way to
pre-allocate a given I/O range (0x1000-0x1fff in my case) so that it
won't be assigned to PCI busses/devices (without the need to recompile
every kernel version).


Regards, and thanks in advance,

   Juan Jesus.
--
To unsubscribe from this list: send the line "unsubscribe linux-pci" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [DMA Engine]     [Linux Coverity]     [Linux USB]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Greybus]

  Powered by Linux