PReP and generic PCI resource assignment

6 messages, 4 authors, 2001-08-09 · open the first message on its own page

PReP and generic PCI resource assignment

From: Hollis <hidden>
Date: 2001-08-08 05:11:20

I'm trying to boot _2_4_devel on a Thinkpad 850. The only problem comes when
the video controller's PCI resource 1 (mapped by the firmware to
0x0..0x00ffffff) is relocated to 0xc1000000..0xc1ffffff. [The symptom is that
all new VGA text is drawn backwards-endian, which I would not have expected
but is very visible.] That's way out of bounds for PReP IO memory, which in
bus addresses can only be 0x0..0x40000000 (in CPU addresses that's
0xc0000000..0xfeffffff or so).

How did it get moved that drastically? The problem comes from generic PCI
code, starting with pci_assign_resource (called from
pcibios_assign_resources). The actual bad line of code is in
kernel/resource.c find_resource():
	new->start = root->start;
where it starts the new resource at the bottom of the parent resource's
range.

The problem is that root in this case is the PCI memory resource of the host
bridge, which correctly starts at 0xc0000000... but NOT in bus terms. In bus
terms it starts at 0x0. (CPU physical 0xc0000000 = PCI bus 0x0 [IO mem].) So
the new resource is assigned 0xc1000000, which is written back to the BAR
with pcibios_update_resource... which is way wrong.

Now if resources could be assigned properly in the first place this code path
wouldn't be taken, but quite a few things fail (request_resource's and
pci_find_parent_resource's) and it's proving difficult to track down why
(maybe I've been staring at this too long).

Anyways, when I change "root->start" above to be 0, the symptom is fixed, but
that's clearly a hack. I don't see how anything PReP (system IO nor IO
memory) could escape generic resource assignment unscathed though.

Thoughts?

-Hollis

** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/

Re: PReP and generic PCI resource assignment

From: ashish anand <hidden>
Date: 2001-08-08 05:43:46

if I remember correctly there should be some a board specific variable like pci_dram_offset
it is zero for your case.
0xc1000000 is a virtual address ..while pci bar should be programmed with bus address .
your case bios is not apropiately updating the resource assignment with 0xc0000000 , the kernel_base.

Hollis wrote:
I'm trying to boot _2_4_devel on a Thinkpad 850. The only problem comes when
the video controller's PCI resource 1 (mapped by the firmware to
0x0..0x00ffffff) is relocated to 0xc1000000..0xc1ffffff. [The symptom is that
all new VGA text is drawn backwards-endian, which I would not have expected
but is very visible.] That's way out of bounds for PReP IO memory, which in
bus addresses can only be 0x0..0x40000000 (in CPU addresses that's
0xc0000000..0xfeffffff or so).

How did it get moved that drastically? The problem comes from generic PCI
code, starting with pci_assign_resource (called from
pcibios_assign_resources). The actual bad line of code is in
kernel/resource.c find_resource():
        new->start = root->start;
where it starts the new resource at the bottom of the parent resource's
range.

The problem is that root in this case is the PCI memory resource of the host
bridge, which correctly starts at 0xc0000000... but NOT in bus terms. In bus
terms it starts at 0x0. (CPU physical 0xc0000000 = PCI bus 0x0 [IO mem].) So
the new resource is assigned 0xc1000000, which is written back to the BAR
with pcibios_update_resource... which is way wrong.

Now if resources could be assigned properly in the first place this code path
wouldn't be taken, but quite a few things fail (request_resource's and
pci_find_parent_resource's) and it's proving difficult to track down why
(maybe I've been staring at this too long).

Anyways, when I change "root->start" above to be 0, the symptom is fixed, but
that's clearly a hack. I don't see how anything PReP (system IO nor IO
memory) could escape generic resource assignment unscathed though.

Thoughts?

-Hollis
** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/

Re: PReP and generic PCI resource assignment

From: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Date: 2001-08-08 10:27:31

The problem is that root in this case is the PCI memory resource of the host
bridge, which correctly starts at 0xc0000000... but NOT in bus terms. In bus
terms it starts at 0x0. (CPU physical 0xc0000000 = PCI bus 0x0 [IO mem].) So
the new resource is assigned 0xc1000000, which is written back to the BAR
with pcibios_update_resource... which is way wrong.
The resource is in CPU space. The problem must be with
pcibios_update_resource, which is responsible for doing the proper
offset. If you look closely, it substracts hose->pci_mem_offset from the
resource before writing it to the BAR.
If your hose pci_mem_offset is wrong, then it can't work. It should be
0xc0000000 on PReP.
Now if resources could be assigned properly in the first place this code path
wouldn't be taken, but quite a few things fail (request_resource's and
pci_find_parent_resource's) and it's proving difficult to track down why
(maybe I've been staring at this too long).

Anyways, when I change "root->start" above to be 0, the symptom is fixed, but
that's clearly a hack. I don't see how anything PReP (system IO nor IO
memory) could escape generic resource assignment unscathed though.
The fix is to have pci_mem_offset set properly when setting up the
pci_controller structure.

ben.


** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/

Re: PReP and generic PCI resource assignment

From: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Date: 2001-08-08 12:23:52

if I remember correctly there should be some a board specific variable
like pci_dram_offset
it is zero for your case.
0xc1000000 is a virtual address ..while pci bar should be programmed with
bus address .
your case bios is not apropiately updating the resource assignment with
0xc0000000 , the kernel_base.
pci_dram_offset is the offset of system memory as seen by PCI devices,
what Hollis needs to look at is the pci_controller's pci_mem_offset.

Ben.


** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/

Re: PReP and generic PCI resource assignment

From: Hollis <hidden>
Date: 2001-08-09 01:34:30

On Wednesday 08 August 2001 05:27, Benjamin Herrenschmidt wrote:
quoted
The problem is that root in this case is the PCI memory resource of the
host bridge, which correctly starts at 0xc0000000... but NOT in bus
terms. In bus terms it starts at 0x0. (CPU physical 0xc0000000 = PCI bus
0x0 [IO mem].) So the new resource is assigned 0xc1000000, which is
written back to the BAR with pcibios_update_resource... which is way
wrong.
The resource is in CPU space. The problem must be with
pcibios_update_resource, which is responsible for doing the proper
offset. If you look closely, it substracts hose->pci_mem_offset from the
resource before writing it to the BAR.
If your hose pci_mem_offset is wrong, then it can't work. It should be
0xc0000000 on PReP.
Yes, it is. I misinterpretted my debug output... :/

At any rate, relocating PCI resource 1 on this controller from 0x0 to
0x01000000 causes my VGA console to go backwards endian. I don't know why
this would be the case... Re-moving it back to 0x0 fixes the symptom. Any
ideas on why this could happen? I think VGA is all IO, no memory at all?

I'm curious about PCIBIOS_MIN_MEM... Why does that exist, and why was it
given that value?

-Hollis

** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/

Re: PReP and generic PCI resource assignment

From: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Date: 2001-08-09 10:18:33

At any rate, relocating PCI resource 1 on this controller from 0x0 to
0x01000000 causes my VGA console to go backwards endian. I don't know why
this would be the case... Re-moving it back to 0x0 fixes the symptom. Any
ideas on why this could happen? I think VGA is all IO, no memory at all?
VGA is both IO and memory. It's possible that your VGA card is so broken
that it only use the low-order bits of addresses and use the high addresses
as flags, for example to access a "bug endian" aperture :) That would suck
as it would mean you actually have address aliasing going on on the bus,
possiby causing weird conflicts.
I'm curious about PCIBIOS_MIN_MEM... Why does that exist, and why was it
given that value?
Note sure, I don't really like the way it's used and hard coded....

Ben.


** Sent via the linuxppc-dev mail list. See http://lists.linuxppc.org/
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help