From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([208.118.235.92]:48556) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1S2hyd-0001CQ-Lr for qemu-devel@nongnu.org; Wed, 29 Feb 2012 06:45:53 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1S2hy6-0002IT-Dj for qemu-devel@nongnu.org; Wed, 29 Feb 2012 06:45:47 -0500 Received: from mx1.redhat.com ([209.132.183.28]:3117) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1S2hy6-0002I1-58 for qemu-devel@nongnu.org; Wed, 29 Feb 2012 06:45:14 -0500 From: Gerd Hoffmann Date: Wed, 29 Feb 2012 12:45:06 +0100 Message-Id: <1330515910-725-3-git-send-email-kraxel@redhat.com> In-Reply-To: <1330515910-725-1-git-send-email-kraxel@redhat.com> References: <1330515910-725-1-git-send-email-kraxel@redhat.com> Subject: [Qemu-devel] [PATCH v2 2/6] pci: split device discovery into multiple steps List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: seabios@seabios.org Cc: qemu-devel@nongnu.org, Gerd Hoffmann First bridge init, next pci bar discovery, finally pci bar ressource allocation. Needed because we need to figure whenever we can map 64bit bars above 4G before doing ressource allocation. Signed-off-by: Gerd Hoffmann --- src/pciinit.c | 39 ++++++++++++++++++++++++++++++++------- 1 files changed, 32 insertions(+), 7 deletions(-) diff --git a/src/pciinit.c b/src/pciinit.c index 9f3fdd4..652564c 100644 --- a/src/pciinit.c +++ b/src/pciinit.c @@ -368,22 +368,28 @@ static void pci_bios_check_devices(struct pci_bus *busses) { dprintf(1, "PCI: check devices\n"); - // Calculate resources needed for regular (non-bus) devices. struct pci_device *pci; + struct pci_bus *bus; + int i; + + // init pci bridges foreachpci(pci) { - if (pci->class == PCI_CLASS_BRIDGE_PCI) { - busses[pci->secondary_bus].bus_dev = pci; + if (pci->class != PCI_CLASS_BRIDGE_PCI) + continue; + bus = &busses[pci->secondary_bus]; + bus->bus_dev = pci; + } + + // discover pci bars + foreachpci(pci) { + if (pci->class == PCI_CLASS_BRIDGE_PCI) continue; - } - struct pci_bus *bus = &busses[pci_bdf_to_bus(pci->bdf)]; - int i; for (i = 0; i < PCI_NUM_REGIONS; i++) { u32 val, size; pci_bios_get_bar(pci, i, &val, &size); if (val == 0) continue; - pci_bios_bus_reserve(bus, pci_addr_to_type(val), size); pci->bars[i].addr = val; pci->bars[i].size = size; pci->bars[i].is64 = (!(val & PCI_BASE_ADDRESS_SPACE_IO) && @@ -395,6 +401,25 @@ static void pci_bios_check_devices(struct pci_bus *busses) } } + // alloc ressources for pci bars + foreachpci(pci) { + if (pci->class == PCI_CLASS_BRIDGE_PCI) + continue; + bus = &busses[pci_bdf_to_bus(pci->bdf)]; + for (i = 0; i < PCI_NUM_REGIONS; i++) { + enum pci_region_type type; + if (pci->bars[i].addr == 0) + continue; + + type = pci_addr_to_type(pci->bars[i].addr); + pci_bios_bus_reserve(bus, type, + pci->bars[i].size); + + if (pci->bars[i].is64) + i++; + } + } + // Propagate required bus resources to parent busses. int secondary_bus; for (secondary_bus=MaxPCIBus; secondary_bus>0; secondary_bus--) { -- 1.7.1