coreboot
Threads by month
- ----- 2025 -----
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2009 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2008 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2007 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2006 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2005 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2004 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2003 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2002 -----
- December
- November
- October
- September
- August
December 2008
- 77 participants
- 330 discussions
This patch fixes up qemu to work with the new resource allocation code.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Thanks,
Myles
file-by-file changes:
dts:
There are no bus devices, remove it. Add the northbridge devices.
Fix susbsytem_vendor and subsystem_device.
southbridge/intel/i82371eb/ide:
Make the ide enabled by default.
northbridge/intel/i440bxemulation/i440bx.c:
1. Split ops into domain and northbridge
A. Domain should have bus ops, scan_bus, etc.
B. Northbridge should have ops for its own registers.
In this case it only needs read and set resources.
functions:
i440bx_read_resources - set up the IO and VGA resources. VGA is fixed.
i440bx_ram_resources - this should be called after resource assignment.
i440bx_set_resources - call pci_set_resources then i440bx_ram_resources.
i440bx_domain_read_resources - Set up system-wide resources, and
reserve space for the local APIC. I put the IOAPIC here too,
but it belongs somewhere in the southbridge.
i440bx_domain_set_resources - Mark the domain-specific resources as
stored (In a real device you'd probably need to set some
registers here.) Call phase4_set_resources for children.
southbridge/intel/i82371eb/i82371eb.c:
1. Add ISA read and set resources to reserve legacy IO space.
- Note that since it's subtractively decoded, it doesn't need
to be stored anywhere. It needs to be marked stored so
pci_set_resource doesn't try to store it.
1
1
This patch fixes up geode for the new resource allocator. This is the
bare minimum. I think the functions of the northbridge should be split
based
on whether they are domain-specific or not.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Thanks,
Myles
1
1

r1093 - in coreboot-v3: mainboard/kontron/986lcd-m northbridge/intel/i945
by svn@coreboot.org Dec. 31, 2008
by svn@coreboot.org Dec. 31, 2008
Dec. 31, 2008
Author: myles
Date: 2008-12-31 21:02:03 +0100 (Wed, 31 Dec 2008)
New Revision: 1093
Modified:
coreboot-v3/mainboard/kontron/986lcd-m/dts
coreboot-v3/northbridge/intel/i945/northbridge.c
coreboot-v3/northbridge/intel/i945/northbridge.dts
Log:
This patch fixes up kontron for the new resource allocator. More
could be done.
northbridge/intel/i945/northbridge.dts
Remove bridge flag. Northbridges don't have children. The domains
they implement do.
northbridge/intel/i945/northbridge.c
Add IORESOURCE_BRIDGE flags and change the limit for MMIO to avoid ROM.
mainboard/kontron/986lcd-m/dts
Make PCI devices children of the domain and add a few devices.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Acked-by: Ronald G. Minnich <rminnich(a)gmail.com>
Modified: coreboot-v3/mainboard/kontron/986lcd-m/dts
===================================================================
--- coreboot-v3/mainboard/kontron/986lcd-m/dts 2008-12-31 20:00:30 UTC (rev 1092)
+++ coreboot-v3/mainboard/kontron/986lcd-m/dts 2008-12-31 20:02:03 UTC (rev 1093)
@@ -145,55 +145,90 @@
};
domain@0 {
/config/("northbridge/intel/i945/northbridge.dts");
- /* guesses; we need a real lspci */
- pci@0,0 {
- pci@1b,0 {
- /config/("southbridge/intel/i82801gx/ac97audio.dts");
- };
- pci@1c,0 {
- /config/("southbridge/intel/i82801gx/pcie1.dts");
- };
- pci@1c,1 {
- /config/("southbridge/intel/i82801gx/pcie2.dts");
- };
- pci@1c,2{
- /config/("southbridge/intel/i82801gx/pcie3.dts");
- };
- pci@1d,0{
- /config/("southbridge/intel/i82801gx/usb1.dts");
- };
- pci@1d,1{
- /config/("southbridge/intel/i82801gx/usb2.dts");
- };
- pci@1d,2{
- /config/("southbridge/intel/i82801gx/usb3.dts");
- };
- pci@1d,3{
- /config/("southbridge/intel/i82801gx/usb4.dts");
- };
- pci@1d,7{
- /config/("southbridge/intel/i82801gx/usb_ehci.dts");
- };
- pci@1e,0{
- /config/("southbridge/intel/i82801gx/pci.dts");
- };
- pci@1f,0{/* which ich? */
- /config/("southbridge/intel/i82801gx/ich7m_dh_lpc.dts");
- };
- pci@1f,1{
- /config/("southbridge/intel/i82801gx/ide.dts");
- };
- pci@1f,2{
- /config/("southbridge/intel/i82801gx/sata.dts");
- };
- pci@1f,3{
- /config/("southbridge/intel/i82801gx/smbus.dts");
- };
-
+ pci@0,0 {
+ /config/("northbridge/intel/i945/mc.dts");
};
- ioport@2e {
- /config/("superio/winbond/w83627thg/dts");
- com1enable = "1";
+ pci@1,0 { /* PCIe */
+ disabled;
};
+ pci@2,0 { /* Onboard VGA. */
+ rom_address = "0xfff00000"; /* Shouldn't this be a lar path? */
+ };
+ pci@2,1 { /* Display controller. */
+ };
+ pci@1b,0 {
+ /config/("southbridge/intel/i82801gx/ac97audio.dts");
+ };
+ pci@1c,0 {
+ /config/("southbridge/intel/i82801gx/pcie1.dts");
+ };
+ pci@1c,1 {
+ /config/("southbridge/intel/i82801gx/pcie2.dts");
+ };
+ pci@1c,2{
+ /config/("southbridge/intel/i82801gx/pcie3.dts");
+ };
+ pci@1c,3{ disabled; }; /* PCIe port 4 */
+ pci@1c,4{ disabled; }; /* PCIe port 5 */
+ pci@1c,5{ disabled; }; /* PCIe port 6 */
+ pci@1d,0{
+ /config/("southbridge/intel/i82801gx/usb1.dts");
+ };
+ pci@1d,1{
+ /config/("southbridge/intel/i82801gx/usb2.dts");
+ };
+ pci@1d,2{
+ /config/("southbridge/intel/i82801gx/usb3.dts");
+ };
+ pci@1d,3{
+ /config/("southbridge/intel/i82801gx/usb4.dts");
+ };
+ pci@1d,7{
+ /config/("southbridge/intel/i82801gx/usb_ehci.dts");
+ };
+ pci@1e,0{
+ /config/("southbridge/intel/i82801gx/pci.dts");
+ };
+ pci@1e,2{ disabled; }; /* AC'97 Audio */
+ pci@1e,3{ disabled; }; /* AC'97 Modem */
+ pci@1f,0{/* which ich? */
+ /config/("southbridge/intel/i82801gx/ich7m_dh_lpc.dts");
+ ioport@2e {
+ /config/("superio/winbond/w83627thg/dts");
+ com1enable = "1";
+ com2enable = "1";
+ kbenable = "1";
+ /* irq 0xf1 = 4 # set IRMODE 0 # XXX not an irq */
+ gameenable = "1";
+ gpio2enable = "1";
+ gpio34enable = "1";
+ hwmenable = "1";
+ };
+ ioport@4e {
+ /config/("superio/winbond/w83627thg/dts");
+ com1enable = "1";
+ com1io = "0x3e8";
+ com1irq = "11";
+ com2enable = "1";
+ com2io = "0x2e8";
+ com2irq = "10";
+ };
+ };
+ pci@1f,1{ /* Disabled and commented out in v2. */
+ /config/("southbridge/intel/i82801gx/ide.dts");
+ disabled;
+ };
+ pci@1f,2{
+ /config/("southbridge/intel/i82801gx/sata.dts");
+ };
+ pci@1f,3{
+ /config/("southbridge/intel/i82801gx/smbus.dts");
+ };
+ /* Disabled and commented out in v2.
+ * pci@1f,4{
+ * /config/("southbridge/intel/i82801gx/codec.dts");
+ * disabled;
+ * };
+ */
};
};
Modified: coreboot-v3/northbridge/intel/i945/northbridge.c
===================================================================
--- coreboot-v3/northbridge/intel/i945/northbridge.c 2008-12-31 20:00:30 UTC (rev 1092)
+++ coreboot-v3/northbridge/intel/i945/northbridge.c 2008-12-31 20:02:03 UTC (rev 1093)
@@ -51,8 +51,8 @@
resource->align = 0;
resource->gran = 0;
resource->limit = 0xffffUL;
- resource->flags =
- IORESOURCE_IO | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ resource->flags = IORESOURCE_IO | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_BRIDGE;
/* Initialize the system wide memory resources constraints */
resource = new_resource(dev, IOINDEX_SUBTRACTIVE(1, 0));
@@ -60,9 +60,10 @@
resource->size = 0;
resource->align = 0;
resource->gran = 0;
- resource->limit = 0xffffffffUL;
- resource->flags =
- IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ /* This is a hack. I don't know all the right reserved regions. */
+ resource->limit = 0xfeffffffUL;
+ resource->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_BRIDGE;
}
static void tolm_test(void *gp, struct device *dev, struct resource *new)
Modified: coreboot-v3/northbridge/intel/i945/northbridge.dts
===================================================================
--- coreboot-v3/northbridge/intel/i945/northbridge.dts 2008-12-31 20:00:30 UTC (rev 1092)
+++ coreboot-v3/northbridge/intel/i945/northbridge.dts 2008-12-31 20:02:03 UTC (rev 1093)
@@ -19,4 +19,5 @@
*/
{
device_operations = "i945_pci_domain_ops";
+ bridge;
};
1
0

r1092 - in coreboot-v3: mainboard/emulation/qemu-x86 northbridge/intel/i440bxemulation southbridge/intel/i82371eb
by svn@coreboot.org Dec. 31, 2008
by svn@coreboot.org Dec. 31, 2008
Dec. 31, 2008
Author: myles
Date: 2008-12-31 21:00:30 +0100 (Wed, 31 Dec 2008)
New Revision: 1092
Added:
coreboot-v3/northbridge/intel/i440bxemulation/northbridge
coreboot-v3/southbridge/intel/i82371eb/acpi
coreboot-v3/southbridge/intel/i82371eb/isa
Modified:
coreboot-v3/mainboard/emulation/qemu-x86/dts
coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c
coreboot-v3/northbridge/intel/i440bxemulation/i440bx.h
coreboot-v3/southbridge/intel/i82371eb/i82371eb.c
coreboot-v3/southbridge/intel/i82371eb/ide
Log:
This patch should serve as a porting help for other northbridges for the new resource allocator.
file-by-file changes:
dts:
There are no bus devices, remove it. Add the northbridge devices.
Fix susbsytem_vendor and subsystem_device.
southbridge/intel/i82371eb/ide:
Make the ide enabled by default.
northbridge/intel/i440bxemulation/i440bx.c:
1. Split ops into domain and northbridge
A. Domain should have bus ops, scan_bus, etc.
B. Northbridge should have ops for its own registers.
In this case it only needs read and set resources.
functions:
i440bx_read_resources - set up the IO and VGA resources. VGA is fixed.
i440bx_ram_resources - this should be called after resource assignment.
i440bx_set_resources - call pci_set_resources then i440bx_ram_resources.
i440bx_domain_read_resources - Set up system-wide resources, and
reserve space for the local APIC. I put the IOAPIC here too,
but it belongs somewhere in the southbridge.
i440bx_domain_set_resources - Mark the domain-specific resources as
stored (In a real device you'd probably need to set some
registers here.) Call phase4_set_resources for children.
southbridge/intel/i82371eb/i82371eb.c:
1. Add ISA read and set resources to reserve legacy IO space.
- Note that since it's subtractively decoded, it doesn't need
to be stored anywhere. It needs to be marked stored so
pci_set_resource doesn't try to store it.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Acked-by: Ronald G. Minnich <rminnich(a)gmail.com>
Modified: coreboot-v3/mainboard/emulation/qemu-x86/dts
===================================================================
--- coreboot-v3/mainboard/emulation/qemu-x86/dts 2008-12-31 19:56:11 UTC (rev 1091)
+++ coreboot-v3/mainboard/emulation/qemu-x86/dts 2008-12-31 20:00:30 UTC (rev 1092)
@@ -21,21 +21,25 @@
/{
mainboard_vendor = "Emulation";
mainboard_name = "QEMU x86";
- mainboard_pci_subsystem_vendor = "0x15ad";
- mainboard_pci_subsystem_device = "0x1976";
+ subsystem_vendor = "0x15ad";
+ subsystem_device = "0x1976";
device_operations = "qemuvga_pci_ops_dev";
cpus {};
domain@0 {
/config/("northbridge/intel/i440bxemulation/domain");
- bus@0 {
- pci@0,0 {
- };
- pci@1,1 {
- /config/("southbridge/intel/i82371eb/ide");
- subsystem_vendor = "0x15ad";
- subsystem_device = "0x1976";
- on_mainboard;
- };
+ pci@0,0 {
+ /config/("northbridge/intel/i440bxemulation/northbridge");
};
+ pci@1,0 {
+ /config/("southbridge/intel/i82371eb/isa");
+ };
+ pci@1,1 {
+ /config/("southbridge/intel/i82371eb/ide");
+ };
+ pci@1,3 {
+ /config/("southbridge/intel/i82371eb/acpi");
+ };
+ /* PCI 2.0 and 3.0 are plugged in. */
+ /* 2.0 is the Cirrus VGA card. 3.0 is a nic. */
};
};
Modified: coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c
===================================================================
--- coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c 2008-12-31 19:56:11 UTC (rev 1091)
+++ coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c 2008-12-31 20:00:30 UTC (rev 1092)
@@ -56,30 +56,103 @@
return inb(0x71);
}
-static void pci_domain_set_resources(struct device *dev)
+static void no_op(struct device *dev)
{
- struct device *mc_dev;
+}
+
+static void i440bx_read_resources(struct device *dev)
+{
+ struct resource *res;
+
+ /* Hole for VGA (0xA0000-0xAFFFF) graphics and text mode
+ * graphics (0xB8000-0xBFFFF) */
+ res = new_resource(dev, 1);
+ res->base = 0xA0000UL;
+ res->size = 0x20000UL;
+ res->limit = 0xBFFFUL;
+ res->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_FIXED;
+
+}
+
+static void i440bx_ram_resources(struct device *dev)
+{
u32 tolmk; /* Top of low mem, Kbytes. */
int idx;
- /* read large mem memory descriptor
- for <16 MB read the more detailed small mem descriptor
- all values in kbytes */
+
+ /* Read the large mem memory descriptor. If that value is <16 MB, read
+ * the more detailed small mem descriptor. All values are in kbytes.
+ */
tolmk = ((inb_cmos(0x35)<<8) |inb_cmos(0x34)) * 64;
if (tolmk <= 16 * 1024) {
tolmk = (inb_cmos(0x31)<<8) |inb_cmos(0x30);
}
- printk(BIOS_WARNING, "Ignoring chipset specified RAM size. Using dts "
- "settings of %d kB instead.\n", tolmk);
- mc_dev = dev->link[0].children;
- if (mc_dev) {
- idx = 10;
- /* 0 .. 640 kB */
- ram_resource(dev, idx++, 0, 640);
- /* Hole for VGA (0xA0000-0xAFFFF) graphics and text mode
- * graphics (0xB8000-0xBFFFF) */
- /* 768 kB .. Systop (in KB) */
- ram_resource(dev, idx++, 768, tolmk - 768);
- }
+
+ printk(BIOS_WARNING, "Using CMOS settings of %d kB RAM.\n", tolmk);
+ idx = 10;
+
+ /* 0 .. 640 kB */
+ ram_resource(dev, idx++, 0, 640);
+
+ /* 768 kB .. Systop (in KB) */
+ ram_resource(dev, idx++, 768, tolmk - 768);
+}
+
+static void i440bx_set_resources(struct device *dev)
+{
+ /* If there were any NB-specific resources that were not part of the
+ * domain, they would get set here.
+ */
+
+ pci_set_resources(dev);
+
+ /* Add RAM resources. They are not part of resource allocation. */
+ i440bx_ram_resources(dev);
+
+ /* If RAM values need to be set, do it here. */
+}
+
+static void i440bx_domain_read_resources(struct device *dev)
+{
+ struct resource *res;
+
+ pci_domain_read_resources(dev);
+
+ /* Reserve space for the IOAPIC. This should be in the Southbridge,
+ * but I couldn't tell which device to put it in. */
+ res = new_resource(dev, 2);
+ res->base = 0xfec00000UL;
+ res->size = 0x100000UL;
+ res->limit = 0xffffffffUL;
+ res->flags = IORESOURCE_MEM | IORESOURCE_FIXED | IORESOURCE_STORED |
+ IORESOURCE_ASSIGNED;
+
+ /* Reserve space for the LAPIC. There's one in every processor, but
+ * the space only needs to be reserved once, so we do it here. */
+ res = new_resource(dev, 3);
+ res->base = 0xfee00000UL;
+ res->size = 0x10000UL;
+ res->limit = 0xffffffffUL;
+ res->flags = IORESOURCE_MEM | IORESOURCE_FIXED | IORESOURCE_STORED |
+ IORESOURCE_ASSIGNED;
+}
+
+static void i440bx_domain_set_resources(struct device *dev)
+{
+ struct resource *res;
+
+ /* If the domain needs these resources set in BARs, do it here. */
+
+ /* Domain I/O resource. */
+ res = probe_resource(dev,0);
+ if (res)
+ res->flags |= IORESOURCE_STORED;
+
+ /* Domain Memory resource. */
+ res = probe_resource(dev,1);
+ if (res)
+ res->flags |= IORESOURCE_STORED;
+
phase4_set_resources(&dev->link[0]);
}
@@ -90,10 +163,24 @@
{.pci_domain = {.vendor = 0x8086,.device = 0x7190}}},
.constructor = default_device_constructor,
.phase3_scan = pci_domain_scan_bus,
- .phase4_read_resources = pci_domain_read_resources,
- .phase4_set_resources = pci_domain_set_resources,
+ .phase4_read_resources = i440bx_domain_read_resources,
+ .phase4_set_resources = i440bx_domain_set_resources,
.phase5_enable_resources = enable_childrens_resources,
- .phase6_init = 0,
+ .phase6_init = no_op,
.ops_pci_bus = &pci_cf8_conf1,
};
+
+/* Here are the operations for the northbridge. */
+struct device_operations i440bx_northbridge = {
+ .id = {.type = DEVICE_ID_PCI,
+ {.pci = {.vendor = 0x8086,.device = 0x1237}}},
+ .constructor = default_device_constructor,
+ .phase3_scan = NULL,
+ .phase4_read_resources = i440bx_read_resources,
+ .phase4_set_resources = i440bx_set_resources,
+ .phase5_enable_resources = no_op,
+ .phase6_init = no_op,
+ .ops_pci_bus = &pci_cf8_conf1,
+
+};
Modified: coreboot-v3/northbridge/intel/i440bxemulation/i440bx.h
===================================================================
--- coreboot-v3/northbridge/intel/i440bxemulation/i440bx.h 2008-12-31 19:56:11 UTC (rev 1091)
+++ coreboot-v3/northbridge/intel/i440bxemulation/i440bx.h 2008-12-31 20:00:30 UTC (rev 1092)
@@ -92,6 +92,4 @@
#define PAM5 0x5e
#define PAM6 0x5f
-unsigned int i440bx_scan_root_bus(struct device *root, unsigned int max);
-
#endif /* NORTHBRIDGE_INTEL_I440BXEMULATION_I440BX_H */
Added: coreboot-v3/northbridge/intel/i440bxemulation/northbridge
===================================================================
--- coreboot-v3/northbridge/intel/i440bxemulation/northbridge (rev 0)
+++ coreboot-v3/northbridge/intel/i440bxemulation/northbridge 2008-12-31 20:00:30 UTC (rev 1092)
@@ -0,0 +1,23 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2007 Ronald G. Minnich <rminnich(a)gmail.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+{
+ device_operations = "i440bx_northbridge";
+};
Added: coreboot-v3/southbridge/intel/i82371eb/acpi
===================================================================
--- coreboot-v3/southbridge/intel/i82371eb/acpi (rev 0)
+++ coreboot-v3/southbridge/intel/i82371eb/acpi 2008-12-31 20:00:30 UTC (rev 1092)
@@ -0,0 +1,23 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2007 Ronald G. Minnich <rminnich(a)gmail.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+{
+ device_operations = "i82371eb_acpi";
+};
Modified: coreboot-v3/southbridge/intel/i82371eb/i82371eb.c
===================================================================
--- coreboot-v3/southbridge/intel/i82371eb/i82371eb.c 2008-12-31 19:56:11 UTC (rev 1091)
+++ coreboot-v3/southbridge/intel/i82371eb/i82371eb.c 2008-12-31 20:00:30 UTC (rev 1092)
@@ -83,6 +83,25 @@
pci_write_config8(dev, 0x80, 1);
}
+static void i82371eb_isa_read_resources(struct device *dev)
+{
+ struct resource *res;
+ res = new_resource(dev, 0);
+ res->base = 0x0UL;
+ res->size = 0x1000UL;
+ res->flags = IORESOURCE_IO | IORESOURCE_ASSIGNED | IORESOURCE_FIXED |
+ IORESOURCE_STORED;
+}
+
+static void i82371eb_isa_set_resources(struct device *dev)
+{
+ /* If the isa resource needed to be set somehow in hardware, we would do
+ * it here. We would call probe_resource(dev,0), then set it in
+ * hardware before calling pci_set_resources.
+ */
+ pci_set_resources(dev);
+}
+
/*NOTE: We need our own read and set resources for this part! It has
* BARS that are not in the normal place (such as SMBUS)
*/
@@ -92,8 +111,8 @@
{.pci = {.vendor = 0x8086,.device = 0x7000}}},
.constructor = default_device_constructor,
.phase3_scan = 0,
- .phase4_read_resources = pci_dev_read_resources,
- .phase4_set_resources = pci_set_resources,
+ .phase4_read_resources = i82371eb_isa_read_resources,
+ .phase4_set_resources = i82371eb_isa_set_resources,
.phase5_enable_resources = pci_dev_enable_resources,
.phase6_init = i82371eb_isa_init,
.ops_pci = &pci_dev_ops_pci,
Modified: coreboot-v3/southbridge/intel/i82371eb/ide
===================================================================
--- coreboot-v3/southbridge/intel/i82371eb/ide 2008-12-31 19:56:11 UTC (rev 1091)
+++ coreboot-v3/southbridge/intel/i82371eb/ide 2008-12-31 20:00:30 UTC (rev 1092)
@@ -19,7 +19,7 @@
*/
{
- ide0_enable = "0";
- ide1_enable = "0";
+ ide0_enable = "1";
+ ide1_enable = "1";
device_operations = "i82371eb_ide";
};
Added: coreboot-v3/southbridge/intel/i82371eb/isa
===================================================================
--- coreboot-v3/southbridge/intel/i82371eb/isa (rev 0)
+++ coreboot-v3/southbridge/intel/i82371eb/isa 2008-12-31 20:00:30 UTC (rev 1092)
@@ -0,0 +1,23 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2007 Ronald G. Minnich <rminnich(a)gmail.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+{
+ device_operations = "i82371eb_isa";
+};
1
0
These two patches are the resource allocator I've been working on. The
biggest thing it does is simplify the resource allocator by splitting it
into distinct phases:
1. read resources
2. constrain resources around fixed resources
3. sum resource needs
4. assign values
This means that there are no more calls to compute_allocate_resources from
specific devices, which makes the process easier to follow.
Boot tested (with patches that will be coming shortly) on qemu, serengeti,
kontron, and dbe62.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Thanks,
Myles
I split it into two patches: one which implements most of the changes, and
the other which updates device code.
resource-allocation.diff:
device/device.c:
Remove references to have_resources.
Remove read_resources from compute allocate resources.
Split compute_allocate_resources into two
1. compute_resource_needs
A. Traverse the tree depth first
B. Sum resources
C. Adjust limits and bases
D. Update bridge resources sizes
2. assign_resource_values
A. Traverse the tree breadth first
B. Assign resource values
device/device_util.c:
Remove references to have_resources.
device/pci_device.c:
Remove saved values stubs (they're not needed now.)
1. Sizing function restores values
Fix 64-bit flag masking.
Add an error message for an invalid value.
Update pci_record_bridge_resource:
1. remove compute_allocate_resource call
2. remove pci_set_resource call
Update pci_bus_read_resources to read children's too.
Update pci_set_resource:
1. change logic for setting zero-size resources
A. Set range to [limit->limit-2^gran]
(Could have been any range with base > limit)
2. remove compute_allocate_resource calls
3. Change phase4_assign_resources ->phase4_set_resources
device/pci_ops.c:
Change an error message to be more helpful.
device/root_device.c:
Remove code for read_resources and set resources.
Add a .id to the ops.
include/device/device.h:
Remove have_resources.
Comment out assign_resources. I think we could comment out more here.
Add debugging function prototypes.
Change phase4_assign_resources to phase4_set_resources.
include/device/resource.h
Add a IORESOURCE_BRIDGE flag.
device/cardbus_device.c
Remove compute_allocate_resource call.
Use probe_resource (doesn't die) instead of find_resource.
specific-resources.diff:
This patch makes specific devices use the updated resource allocation code.
The changes necessary are:
1. Remove all calls to compute_allocate_resources.
2. Don't store resources except in phase4_set_resources.
northbridge/amd/k8/pci.c:
Remove calls to compute_allocate_resource.
Change phase4_assign_resources to phase4_set_resources
southbridge/amd/amd8132/amd8132_bridge.c:
Remove NPUML and NPUMB.
Add a warning for bus disabling.
Remove bridge_{read|set}_resources (they were there for NPUML)
southbridge/nvidia/mcp55/lpc.c:
southbridge/amd/sb600/lpc.c:
Remove references to have_resources.
southbridge/amd/amd8111/lpc.c:
Add resources for subtractive IO and ROM.
northbridge/amd/k8/domain.c:
northbridge/intel/i440bxemulation/i440bx.c:
northbridge/amd/geodelx/geodelx.c:
northbridge/intel/i945/northbridge.c:
northbridge/via/cn700/stage2.c:
Change phase4_assign_resources->phase4_set_resources.
2
7
Author: myles
Date: 2008-12-31 20:56:11 +0100 (Wed, 31 Dec 2008)
New Revision: 1091
Modified:
coreboot-v3/southbridge/amd/cs5536/cs5536.c
Log:
patch: geodelx.diff
This patch fixes up geode for the new resource allocator. This is the
bare minimum. I think the functions of the northbridge should be split based
on whether they are domain-specific or not.
southbridge/amd/cs5536/cs5536.c:
Change read resources to add a fixed IO resource for legacy decoding.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Acked-by: Ronald G. Minnich <rminnich(a)gmail.com>
Modified: coreboot-v3/southbridge/amd/cs5536/cs5536.c
===================================================================
--- coreboot-v3/southbridge/amd/cs5536/cs5536.c 2008-12-31 19:46:14 UTC (rev 1090)
+++ coreboot-v3/southbridge/amd/cs5536/cs5536.c 2008-12-31 19:56:11 UTC (rev 1091)
@@ -676,6 +676,25 @@
}
/**
+ * A slightly different read resources. We add fixed resources.
+ *
+ * @param dev The device to use.
+ */
+static void cs5536_read_resources(struct device *dev)
+{
+ /* This is a fixed IO resource for legacy decoding. Its presence moves
+ * other allocations out of this location. */
+ struct resource *res;
+ res = new_resource(dev, 0);
+ res->base = 0x0UL;
+ res->size = 0x1000UL;
+ res->flags = IORESOURCE_IO | IORESOURCE_ASSIGNED | IORESOURCE_FIXED |
+ IORESOURCE_STORED;
+
+ pci_dev_read_resources(dev);
+}
+
+/**
* A slightly different enable resources than the standard.
* We grab control here as VSA has played in this chip as well.
*
@@ -695,7 +714,7 @@
.device = PCI_DEVICE_ID_AMD_CS5536_ISA}}},
.constructor = default_device_constructor,
.phase3_scan = scan_static_bus,
- .phase4_read_resources = pci_dev_read_resources,
+ .phase4_read_resources = cs5536_read_resources,
.phase4_set_resources = pci_set_resources,
.phase5_enable_resources = cs5536_pci_dev_enable_resources,
.phase6_init = southbridge_init,
@@ -706,7 +725,6 @@
{.pci = {.vendor = PCI_VENDOR_ID_AMD,
.device = PCI_DEVICE_ID_AMD_CS5536_B0_IDE}}},
.constructor = default_device_constructor,
-#warning FIXME: what has to go in phase3_scan?
.phase3_scan = 0,
.phase4_read_resources = pci_dev_read_resources,
.phase4_set_resources = pci_set_resources,
1
0

r1090 - in coreboot-v3: northbridge/amd/geodelx northbridge/amd/k8 northbridge/intel/i440bxemulation northbridge/intel/i945 southbridge/amd/amd8111 southbridge/amd/amd8132 southbridge/amd/sb600 southbridge/nvidia/mcp55
by svn@coreboot.org Dec. 31, 2008
by svn@coreboot.org Dec. 31, 2008
Dec. 31, 2008
Author: myles
Date: 2008-12-31 20:46:14 +0100 (Wed, 31 Dec 2008)
New Revision: 1090
Modified:
coreboot-v3/northbridge/amd/geodelx/geodelx.c
coreboot-v3/northbridge/amd/k8/domain.c
coreboot-v3/northbridge/amd/k8/pci.c
coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c
coreboot-v3/northbridge/intel/i945/northbridge.c
coreboot-v3/southbridge/amd/amd8111/lpc.c
coreboot-v3/southbridge/amd/amd8132/amd8132_bridge.c
coreboot-v3/southbridge/amd/sb600/lpc.c
coreboot-v3/southbridge/nvidia/mcp55/lpc.c
Log:
specific-resources.diff:
This patch makes specific devices use the updated resource allocation code.
The changes necessary are:
1. Remove all calls to compute_allocate_resources.
2. Don't store resources except in phase4_set_resources.
northbridge/amd/k8/pci.c:
Remove calls to compute_allocate_resource.
Change phase4_assign_resources to phase4_set_resources
southbridge/amd/amd8132/amd8132_bridge.c:
Remove NPUML and NPUMB.
Add a warning for bus disabling.
Remove bridge_{read|set}_resources (they were there for NPUML)
southbridge/nvidia/mcp55/lpc.c:
southbridge/amd/sb600/lpc.c:
Remove references to have_resources.
southbridge/amd/amd8111/lpc.c:
Add resources for subtractive IO and ROM.
northbridge/amd/k8/domain.c:
northbridge/intel/i440bxemulation/i440bx.c:
northbridge/amd/geodelx/geodelx.c:
northbridge/intel/i945/northbridge.c:
northbridge/via/cn700/stage2.c:
Change phase4_assign_resources->phase4_set_resources.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Acked-by: Ronald G. Minnich <rminnich(a)gmail.com>
Modified: coreboot-v3/northbridge/amd/geodelx/geodelx.c
===================================================================
--- coreboot-v3/northbridge/amd/geodelx/geodelx.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/northbridge/amd/geodelx/geodelx.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -111,8 +111,8 @@
for (link = 0; link < dev->links; link++) {
bus = &dev->link[link];
if (bus->children) {
- printk(BIOS_DEBUG, "my_dev_set_resources: phase4_assign_resources %p\n", bus);
- phase4_assign_resources(bus);
+ printk(BIOS_DEBUG, "my_dev_set_resources: phase4_set_resources %p\n", bus);
+ phase4_set_resources(bus);
}
}
@@ -161,7 +161,7 @@
(get_systop(nb_dm) / 1024) - 1024);
}
- phase4_assign_resources(&dev->link[0]);
+ phase4_set_resources(&dev->link[0]);
}
/**
Modified: coreboot-v3/northbridge/amd/k8/domain.c
===================================================================
--- coreboot-v3/northbridge/amd/k8/domain.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/northbridge/amd/k8/domain.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -44,12 +44,8 @@
#include <device/hypertransport.h>
#include <mc146818rtc.h>
#include <lib.h>
-#include <lapic.h>
+#include <lapic.h>
-#ifdef CONFIG_PCI_64BIT_PREF_MEM
-#define BRIDGE_IO_MASK (IORESOURCE_IO | IORESOURCE_MEM | IORESOURCE_PREFETCH)
-#endif
-
#define FX_DEVS 8
extern struct device * __f0_dev[FX_DEVS];
u32 f1_read_config32(unsigned int reg);
@@ -140,24 +136,16 @@
resource->base = 0x400;
resource->limit = 0xffffUL;
resource->flags = IORESOURCE_IO;
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_IO, IORESOURCE_IO);
/* Initialize the system-wide prefetchable memory resource constraints */
resource = new_resource(dev, 1);
resource->limit = 0xfcffffffffULL;
resource->flags = IORESOURCE_MEM | IORESOURCE_PREFETCH;
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM | IORESOURCE_PREFETCH);
/* Initialize the system-wide memory resource constraints */
resource = new_resource(dev, 2);
resource->limit = 0xfcffffffffULL;
resource->flags = IORESOURCE_MEM;
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM);
#endif
printk(BIOS_DEBUG, "k8_pci_domain_read_resources done\n");
}
@@ -238,9 +226,6 @@
resource->flags |= IORESOURCE_ASSIGNED;
resource->flags &= ~IORESOURCE_STORED;
#endif
- compute_allocate_resource(&dev->link[0], resource,
- BRIDGE_IO_MASK, resource->flags & BRIDGE_IO_MASK);
-
resource->flags |= IORESOURCE_STORED;
report_resource_stored(dev, resource, "");
@@ -360,7 +345,7 @@
k8_ram_resource(dev, (idx | i), basek, sizek);
idx += 0x10;
}
- phase4_assign_resources(&dev->link[0]);
+ phase4_set_resources(&dev->link[0]);
}
static unsigned int k8_domain_scan_bus(struct device * dev, unsigned int max)
Modified: coreboot-v3/northbridge/amd/k8/pci.c
===================================================================
--- coreboot-v3/northbridge/amd/k8/pci.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/northbridge/amd/k8/pci.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -355,8 +355,6 @@
resource->gran = log2c(HT_IO_HOST_ALIGN);
resource->limit = 0xffffUL;
resource->flags = IORESOURCE_IO;
- compute_allocate_resource(&dev->link[link], resource,
- IORESOURCE_IO, IORESOURCE_IO);
}
/* Initialize the prefetchable memory constraints on the current bus */
@@ -368,9 +366,6 @@
resource->gran = log2c(HT_MEM_HOST_ALIGN);
resource->limit = 0xffffffffffULL;
resource->flags = IORESOURCE_MEM | IORESOURCE_PREFETCH;
- compute_allocate_resource(&dev->link[link], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM | IORESOURCE_PREFETCH);
}
/* Initialize the memory constraints on the current bus */
@@ -382,9 +377,6 @@
resource->gran = log2c(HT_MEM_HOST_ALIGN);
resource->limit = 0xffffffffffULL;
resource->flags = IORESOURCE_MEM;
- compute_allocate_resource(&dev->link[link], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM);
}
}
@@ -441,8 +433,6 @@
if (resource->flags & IORESOURCE_IO) {
u32 base, limit;
- compute_allocate_resource(&dev->link[link], resource,
- IORESOURCE_IO, IORESOURCE_IO);
base = f1_read_config32(reg);
limit = f1_read_config32(reg + 0x4);
base &= 0xfe000fcc;
@@ -467,11 +457,6 @@
f1_write_config32(reg, base);
} else if (resource->flags & IORESOURCE_MEM) {
u32 base, limit;
- compute_allocate_resource(&dev->link[link], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- resource->
- flags & (IORESOURCE_MEM |
- IORESOURCE_PREFETCH));
base = f1_read_config32(reg);
limit = f1_read_config32(reg + 0x4);
base &= 0x000000f0;
@@ -581,7 +566,7 @@
struct bus *bus;
bus = &dev->link[link];
if (bus->children) {
- phase4_assign_resources(bus);
+ phase4_set_resources(bus);
}
}
}
Modified: coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c
===================================================================
--- coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/northbridge/intel/i440bxemulation/i440bx.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -80,7 +80,7 @@
/* 768 kB .. Systop (in KB) */
ram_resource(dev, idx++, 768, tolmk - 768);
}
- phase4_assign_resources(&dev->link[0]);
+ phase4_set_resources(&dev->link[0]);
}
/* Here are the operations for when the northbridge is running a PCI domain. */
Modified: coreboot-v3/northbridge/intel/i945/northbridge.c
===================================================================
--- coreboot-v3/northbridge/intel/i945/northbridge.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/northbridge/intel/i945/northbridge.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -164,7 +164,7 @@
i945_ram_resource(dev, 5, 4096 * 1024, tomk - 4 * 1024 * 1024);
}
- phase4_assign_resources(&dev->link[0]);
+ phase4_set_resources(&dev->link[0]);
}
static unsigned int i945_pci_domain_scan_bus(struct device * dev, unsigned int max)
Modified: coreboot-v3/southbridge/amd/amd8111/lpc.c
===================================================================
--- coreboot-v3/southbridge/amd/amd8111/lpc.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/southbridge/amd/amd8111/lpc.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -184,11 +184,19 @@
pci_dev_read_resources(dev);
/* Add an extra subtractive resource for both memory and I/O */
- res = new_resource(dev, IOINDEX_SUBTRACTIVE(0, 0));
- res->flags = IORESOURCE_IO | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ res = new_resource(dev, 0);
+ res->base = 0x0;
+ res->size = 0x1000;
+ res->limit = 0xffff;
+ res->flags = IORESOURCE_IO | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_FIXED | IORESOURCE_STORED;
- res = new_resource(dev, IOINDEX_SUBTRACTIVE(1, 0));
- res->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ res = new_resource(dev, 1);
+ res->base = 0xff000000UL;
+ res->size = 0x01000000UL;
+ res->limit = 0xffffffffUL;
+ res->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_FIXED | IORESOURCE_STORED;
}
static void amd8111_lpc_enable_resources(struct device * dev)
Modified: coreboot-v3/southbridge/amd/amd8132/amd8132_bridge.c
===================================================================
--- coreboot-v3/southbridge/amd/amd8132/amd8132_bridge.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/southbridge/amd/amd8132/amd8132_bridge.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -31,8 +31,13 @@
#define NMI_OFF 0
-#define NPUML 0xD9 /* Non prefetchable upper memory limit */
-#define NPUMB 0xD8 /* Non prefetchable upper memory base */
+/* We don't implement this because:
+ * 1. There's only one pair of registers for both devices.
+ * - This breaks our model for resource allocation.
+ * 2. The datasheet recommends against it.
+ */
+/* #define NPUML 0xD9 Non prefetchable upper memory limit */
+/* #define NPUMB 0xD8 Non prefetchable upper memory base */
static void amd8132_walk_children(struct bus *bus,
void (*visit)(struct device * dev, void *ptr), void *ptr)
@@ -165,6 +170,7 @@
info.master_devices = 0;
amd8132_walk_children(bus, amd8132_count_dev, &info);
+#warning Bus disabling disabled for amd8132
#if 0
/* Disable the bus if there are no devices on it
*/
@@ -309,40 +315,6 @@
return;
}
-static void bridge_read_resources(struct device *dev)
-{
- struct resource *res;
- pci_bus_read_resources(dev);
- res = probe_resource(dev, PCI_MEMORY_BASE);
- if (res) {
- res->limit = 0xffffffffffULL;
- }
-}
-
-static void bridge_set_resources(struct device *dev)
-{
- struct resource *res;
- res = find_resource(dev, PCI_MEMORY_BASE);
- if (res) {
- resource_t base, end;
- /* set the memory range */
- dev->command |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER;
- res->flags |= IORESOURCE_STORED;
- compute_allocate_resource(&dev->link[0], res,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM);
- base = res->base;
- end = resource_end(res);
- pci_write_config16(dev, PCI_MEMORY_BASE, base >> 16);
- pci_write_config8(dev, NPUML, (base >> 32) & 0xff);
- pci_write_config16(dev, PCI_MEMORY_LIMIT, end >> 16);
- pci_write_config8(dev, NPUMB, (end >> 32) & 0xff);
-
- report_resource_stored(dev, res, "including NPUML");
- }
- pci_set_resources(dev);
-}
-
struct device_operations amd8132_pcix = {
.id = {.type = DEVICE_ID_PCI,
{.pci = {.vendor = PCI_VENDOR_ID_AMD,
@@ -350,8 +322,8 @@
.constructor = default_device_constructor,
.reset_bus = pci_bus_reset,
.phase3_scan = amd8132_scan_bridge,
- .phase4_read_resources = bridge_read_resources,
- .phase4_set_resources = bridge_set_resources,
+ .phase4_read_resources = pci_bus_read_resources,
+ .phase4_set_resources = pci_set_resources,
.phase5_enable_resources = pci_dev_enable_resources,
.phase6_init = amd8132_pcix_init,
.ops_pci = &pci_bus_ops_pci,
Modified: coreboot-v3/southbridge/amd/sb600/lpc.c
===================================================================
--- coreboot-v3/southbridge/amd/sb600/lpc.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/southbridge/amd/sb600/lpc.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -110,8 +110,7 @@
for (child = dev->link[link].children; child;
child = child->sibling) {
dev_phase5(child);
- if (child->have_resources
- && (child->path.type == DEVICE_PATH_PNP)) {
+ if (child->path.type == DEVICE_PATH_PNP) {
for (i = 0; i < child->resources; i++) {
struct resource *res;
unsigned long base, end; /* don't need long long */
Modified: coreboot-v3/southbridge/nvidia/mcp55/lpc.c
===================================================================
--- coreboot-v3/southbridge/nvidia/mcp55/lpc.c 2008-12-31 19:43:34 UTC (rev 1089)
+++ coreboot-v3/southbridge/nvidia/mcp55/lpc.c 2008-12-31 19:46:14 UTC (rev 1090)
@@ -292,7 +292,7 @@
struct device *child;
for (child = dev->link[link].children; child; child = child->sibling) {
dev_phase5(child);
- if(child->have_resources && (child->path.type == DEVICE_PATH_PNP)) {
+ if(child->path.type == DEVICE_PATH_PNP) {
for(i=0;i<child->resources;i++) {
struct resource *res;
unsigned long base, end; // don't need long long
1
0
Author: myles
Date: 2008-12-31 20:43:34 +0100 (Wed, 31 Dec 2008)
New Revision: 1089
Modified:
coreboot-v3/device/cardbus_device.c
coreboot-v3/device/device.c
coreboot-v3/device/device_util.c
coreboot-v3/device/pci_device.c
coreboot-v3/device/pci_ops.c
coreboot-v3/device/root_device.c
coreboot-v3/include/device/device.h
coreboot-v3/include/device/resource.h
Log:
This patch simplifies the resource allocator by splitting it into distinct
phases. One benefit of this is that it makes the call chain easier to follow.
device/device.c:
Remove references to have_resources.
Remove read_resources from compute allocate resources.
Split compute_allocate_resources into two
1. compute_resource_needs
A. Traverse the tree depth first
B. Sum resources
C. Adjust limits and bases
D. Update bridge resources sizes
2. assign_resource_values
A. Traverse the tree breadth first
B. Assign resource values
device/device_util.c:
Remove references to have_resources.
device/pci_device.c:
Remove saved values stubs (they're not needed now.)
1. Sizing function restores values
Fix 64-bit flag masking.
Add an error message for an invalid value.
Update pci_record_bridge_resource:
1. remove compute_allocate_resource call
2. remove pci_set_resource call
Update pci_bus_read_resources to read children's too.
Update pci_set_resource:
1. change logic for setting zero-size resources
A. Set range to [limit->limit-2^gran]
(Could have been any range with base > limit)
2. remove compute_allocate_resource calls
3. Change phase4_assign_resources ->phase4_set_resources
device/pci_ops.c:
Change an error message to be more helpful.
device/root_device.c:
Remove code for read_resources and set resources.
Add a .id to the ops.
include/device/device.h:
Remove have_resources.
Comment out assign_resources. I think we could comment out more here.
Add debugging function prototypes.
Change phase4_assign_resources to phase4_set_resources.
include/device/resource.h
Add a IORESOURCE_BRIDGE flag.
device/cardbus_device.c
Remove compute_allocate_resource call.
Use probe_resource (doesn't die) instead of find_resource.
Signed-off-by: Myles Watson <mylesgw(a)gmail.com>
Acked-by: Ronald G. Minnich <rminnich(a)gmail.com>
Modified: coreboot-v3/device/cardbus_device.c
===================================================================
--- coreboot-v3/device/cardbus_device.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/cardbus_device.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -75,11 +75,10 @@
{
struct resource *resource;
resource_t min_size;
- resource = find_resource(dev, index);
+ resource = probe_resource(dev, index);
if (resource) {
min_size = resource->size;
- compute_allocate_resource(&dev->link[0], resource,
- resource->flags, resource->flags);
+
/* Always allocate at least the minimum size to a
* cardbus bridge in case a new card is plugged in.
*/
Modified: coreboot-v3/device/device.c
===================================================================
--- coreboot-v3/device/device.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/device.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -13,6 +13,7 @@
* (Written by Yinghai Lu for Tyan)
* Copyright (C) 2005-2006 Stefan Reinauer <stepan(a)openbios.org>
* Copyright (C) 2007 coresystems GmbH
+ * Copyright (C) 2008 Myles Watson <mylesgw(a)gmail.com>
*/
/*
@@ -48,18 +49,6 @@
struct device **last_dev_p;
/**
- * The upper limit of MEM resource of the devices.
- * Reserve 20M for the system.
- */
-#define DEVICE_MEM_HIGH 0xFEBFFFFFUL
-
-/**
- * The lower limit of I/O resource of the devices.
- * Reserve 4K for ISA/Legacy devices.
- */
-#define DEVICE_IO_START 0x1000
-
-/**
* device memory. All the device tree wil live here
*/
@@ -110,7 +99,7 @@
/**
* Given a path, locate the device_operations for it from all_device_operations.
*
- * @param id TODO
+ * @param id a device ID to match
* @return Pointer to the ops or 0, if none found.
* @see device_path
*/
@@ -127,7 +116,8 @@
printk(BIOS_SPEW, "%s: cons id %s\n",
__func__, dev_id_string(&c->id));
if (id_eq(&c->id, id)) {
- printk(BIOS_SPEW, "%s: match\n", __func__);
+ printk(BIOS_SPEW, "%s: match %s\n",
+ __func__, dev_id_string(&c->id));
return c;
}
}
@@ -138,10 +128,9 @@
/**
* Initialization tasks for the device tree code.
*
- * Sets up last_dev_p, which used to be done by
- * Fucking Magic (FM) in the config tool. Also, for each of the
- * devices, tries to find the constructor, and from there, the ops,
- * for the device.
+ * Sets up last_dev_p, which used to be done by magic in the config tool. Also,
+ * for each of the devices, tries to find the constructor, and from there, the
+ * ops, for the device.
*/
void dev_init(void)
{
@@ -206,7 +195,7 @@
*
* @param parent Parent bus the newly created device is attached to.
* @param path Path to the device to be created.
- * @param devid TODO
+ * @param devid ID of the device we want allocated.
* @return Pointer to the newly created device structure.
* @see device_path
*/
@@ -254,7 +243,7 @@
last_dev_p = &dev->next;
/* Give the device a name. */
- if (dev->id.type == DEVICE_ID_PNP &&
+ if (dev->id.type == DEVICE_ID_PNP &&
parent->dev->id.type == DEVICE_ID_PNP)
sprintf(dev->dtsname, "%s_pnp_child_%d", parent->dev->dtsname,
dev->path.pnp.device);
@@ -292,17 +281,12 @@
/* Walk through all devices and find which resources they need. */
for (curdev = bus->children; curdev; curdev = curdev->sibling) {
- unsigned int links;
int i;
printk(BIOS_SPEW,
- "%s: %s(%s) dtsname %s have_resources %d enabled %d\n",
+ "%s: %s(%s) dtsname %s enabled %d\n",
__func__, bus->dev ? bus->dev->dtsname : "NOBUSDEV",
bus->dev ? dev_path(bus->dev) : "NOBUSDEV",
- curdev->dtsname,
- curdev->have_resources, curdev->enabled);
- if (curdev->have_resources) {
- continue;
- }
+ curdev->dtsname, curdev->enabled);
if (!curdev->enabled) {
continue;
}
@@ -313,28 +297,10 @@
continue;
}
curdev->ops->phase4_read_resources(curdev);
- curdev->have_resources = 1;
- /* Read in subtractive resources behind the current device. */
- links = 0;
- for (i = 0; i < curdev->resources && (curdev->links > 0); i++) {
- struct resource *resource;
- unsigned int link;
- resource = &curdev->resource[i];
- if (!(resource->flags & IORESOURCE_SUBTRACTIVE))
- continue;
- link = IOINDEX_SUBTRACTIVE_LINK(resource->index);
- if (link > MAX_LINKS) {
- printk(BIOS_ERR,
- "%s subtractive index on link: %d\n",
- dev_path(curdev), link);
- continue;
- }
- if (!(links & (1 << link))) {
- links |= (1 << link);
- read_resources(&curdev->link[link]);
- }
- }
+ /* Read in children's resources behind the current device. */
+ for (i = 0; i< curdev->links; i++)
+ read_resources(&curdev->link[i]);
}
printk(BIOS_SPEW, "%s: %s(%s) read_resources bus %d link: %d done\n",
__func__, bus->dev->dtsname, dev_path(bus->dev), bus->secondary,
@@ -398,7 +364,7 @@
}
/**
- * This function is the guts of the resource allocator.
+ * This function is the first part of the resource allocator.
*
* The problem.
* - Allocate resource locations for every device.
@@ -424,85 +390,199 @@
* a device with a couple of resources, and not need to special case it in
* the allocator. Also this allows handling of other types of bridges.
*
- * @param bus TODO
- * @param bridge TODO
- * @param type_mask TODO
- * @param type TODO
+ * - This function calculates how large the resources are behind the bridges.
+ *
+ * @param bus The bus we are traversing.
+ * @param bridge The bridge resource which will contain the bus' resources.
+ * @param type_mask This value gets anded with the resource type.
+ * @param type This value must match the result of the and.
*/
-void compute_allocate_resource(struct bus *bus, struct resource *bridge,
+void compute_resource_needs(struct bus *bus, struct resource *bridge,
unsigned long type_mask, unsigned long type)
{
struct device *dev;
struct resource *resource;
resource_t base;
- unsigned long align, min_align;
- min_align = 0;
- base = bridge->base;
+ base = align_up(bridge->base, bridge->align);
printk(BIOS_SPEW,
- "%s compute_allocate_%s: base: %08llx size: %08llx align: %d gran: %d limit: %08llx\n",
- dev_path(bus->dev),
- (bridge->flags & IORESOURCE_IO) ? "io" : (bridge->flags &
- IORESOURCE_PREFETCH) ?
- "prefmem" : "mem", base, bridge->size, bridge->align,
+ "%s %s_%s: base: %llx size: %llx align: %d gran: %d limit: %llx\n",
+ dev_path(bus->dev), __func__,
+ (type & IORESOURCE_IO) ? "io" : (type & IORESOURCE_PREFETCH) ?
+ "prefmem" : "mem",
+ base, bridge->size, bridge->align,
bridge->gran, bridge->limit);
- /* We want different minimum alignments for different kinds of
- * resources. These minimums are not device type specific but
- * resource type specific.
- */
- if (bridge->flags & IORESOURCE_IO) {
- min_align = log2c(DEVICE_IO_ALIGN);
+ /* For each child which is a bridge, compute_resource_needs. */
+ for (dev = bus->children; dev; dev = dev->sibling) {
+ unsigned i;
+ struct resource *child_bridge;
+
+ if (!dev->links)
+ continue;
+
+ /* Find the resources with matching type flags. */
+ for (i=0; i< dev->resources; i++){
+ child_bridge = &dev->resource[i];
+
+ if (!(child_bridge->flags & IORESOURCE_BRIDGE) ||
+ (child_bridge->flags & type_mask) != type)
+ continue;
+
+ /* Split prefetchable memory if combined. Many domains
+ * use the same address space for prefetchable memory
+ * and non-prefetchable memory. Bridges below them
+ * need it separated. Add the PREFETCH flag to the
+ * type_mask and type.
+ */
+ compute_resource_needs(&dev->link[0], child_bridge,
+ type_mask | IORESOURCE_PREFETCH,
+ type | (child_bridge->flags &
+ IORESOURCE_PREFETCH));
+ }
}
- if (bridge->flags & IORESOURCE_MEM) {
- min_align = log2c(DEVICE_MEM_ALIGN);
- }
- /* Make certain we have read in all of the resources. */
- read_resources(bus);
-
/* Remember we haven't found anything yet. */
resource = NULL;
- /* Walk through all the devices on the current bus and
- * compute the addresses.
+ /* Walk through all the resources on the current bus and compute the
+ * amount of address space taken by them. Take granularity and
+ * alignment into account.
*/
while ((dev = largest_resource(bus, &resource, type_mask, type))) {
- resource_t size;
- /* Do NOT, I repeat do not, ignore resources which have zero
- * size. If they need to be ignored dev->read_resources should
- * not even return them. Some resources must be set even when
- * they have no size. PCI bridge resources are a good example
- * of this.
- */
-
- /* Make certain we are dealing with a good minimum size. */
- size = resource->size;
- align = resource->align;
- if (align < min_align) {
- align = min_align;
+ /* Size 0 resources can be skipped. */
+ if (!resource->size) {
+ continue;
}
- /* Propagate the resource alignment to the bridge register */
- if (align > bridge->align) {
- bridge->align = align;
+ /* Propagate the resource alignment to the bridge resource. */
+ if (resource->align > bridge->align) {
+ bridge->align = resource->align;
}
- if (resource->flags & IORESOURCE_FIXED) {
- continue;
- }
-
/* Propagate the resource limit to the bridge register. */
if (bridge->limit > resource->limit) {
bridge->limit = resource->limit;
}
- /* Artificially deny limits between DEVICE_MEM_HIGH and 0xffffffff. */
- if ((bridge->limit > DEVICE_MEM_HIGH)
- && (bridge->limit <= 0xffffffff)) {
- bridge->limit = DEVICE_MEM_HIGH;
+ /* I'm not sure what to do here. I'd really like this to go
+ * away into some PCI-specific file, but I don't see how to do
+ * it. I'm also not sure how to guarantee that larger
+ * allocations don't conflict with this address set.
+ * The example is 0x1000-0x13ff overlaps, but since the base
+ * doesn't, then this check doesn't trigger. It wouldn't do
+ * any good, though, since you can't move it to avoid the
+ * conflict.
+ */
+ if (resource->flags & IORESOURCE_IO) {
+ /* Don't allow potential aliases over the legacy PCI
+ * expansion card addresses. The legacy PCI decodes
+ * only 10 bits, uses 0x100 - 0x3ff. Therefore, only
+ * 0x00 - 0xff can be used out of each 0x400 block of
+ * I/O space.
+ */
+ if ((base & 0x300) != 0) {
+ base = (base & ~0x3ff) + 0x400;
+ }
+ /* Don't allow allocations in the VGA I/O range.
+ * PCI has special cases for that.
+ */
+ else if ((base >= 0x3b0) && (base <= 0x3df)) {
+ base = 0x3e0;
+ }
}
+ /* Base must be aligned. */
+ base = align_up(base, resource->align);
+ resource->base = base;
+ base += resource->size;
+
+ printk(BIOS_SPEW, "%s %02lx * [0x%llx - 0x%llx] %s\n",
+ dev_path(dev), resource->index, resource->base,
+ resource->base + resource->size - 1,
+ (resource->flags & IORESOURCE_IO) ? "io" :
+ (resource-> flags & IORESOURCE_PREFETCH) ? "prefmem" :
+ "mem");
+ }
+ /* Bridge resources have a minimum granularity. Round the size up to
+ * that minimum granularity so we know not to place something else at
+ * an address positively decoded by the bridge.
+ */
+ bridge->size = align_up(base, bridge->gran) -
+ align_up(bridge->base, bridge->align);
+
+ printk(BIOS_SPEW,
+ "%s %s_%s: base: %llx size: %llx align: %d gran: %d limit: %llx done\n",
+ dev_path(bus->dev), __func__,
+ (type & IORESOURCE_IO) ? "io" : (type & IORESOURCE_PREFETCH) ?
+ "prefmem" : "mem",
+ base, bridge->size, bridge->align,
+ bridge->gran, bridge->limit);
+}
+
+/**
+ * This function is the second part of the resource allocator.
+ *
+ * The problem.
+ * - Allocate resource locations for every device.
+ * - Don't overlap, and follow the rules of bridges.
+ * - Don't overlap with resources in fixed locations.
+ * - Be efficient so we don't have ugly strategies.
+ *
+ * The strategy.
+ * - Devices that have fixed addresses are the minority so don't
+ * worry about them too much. Instead only use part of the address
+ * space for devices with programmable addresses. This easily handles
+ * everything except bridges.
+ *
+ * - PCI devices are required to have their sizes and their alignments
+ * equal. In this case an optimal solution to the packing problem
+ * exists. Allocate all devices from highest alignment to least
+ * alignment or vice versa. Use this.
+ *
+ * - So we can handle more than PCI run two allocation passes on bridges. The
+ * first to see how large the resources are behind the bridge, and what
+ * their alignment requirements are. The second to assign a safe address to
+ * the devices behind the bridge. This allows us to treat a bridge as just
+ * a device with a couple of resources, and not need to special case it in
+ * the allocator. Also this allows handling of other types of bridges.
+ *
+ * - This function assigns the resources a value.
+ *
+ * @param bus The bus we are traversing.
+ * @param bridge The bridge resource which must contain the bus' resources.
+ * @param type_mask This value gets anded with the resource type.
+ * @param type This value must match the result of the and.
+ */
+void assign_resource_values(struct bus *bus, struct resource *bridge,
+ unsigned long type_mask, unsigned long type)
+{
+ struct device *dev;
+ struct resource *resource;
+ resource_t base;
+ base = bridge->base;
+
+ printk(BIOS_SPEW,
+ "%s %s_%s: base:%llx size:%llx align:%d gran:%d limit:%llx\n",
+ dev_path(bus->dev), __func__,
+ (type & IORESOURCE_IO) ? "io" : (type & IORESOURCE_PREFETCH) ?
+ "prefmem" : "mem",
+ base, bridge->size, bridge->align,
+ bridge->gran, bridge->limit);
+
+ /* Remember we haven't found anything yet. */
+ resource = NULL;
+
+ /* Walk through all the resources on the current bus and allocate them
+ * address space.
+ */
+ while ((dev = largest_resource(bus, &resource, type_mask, type))) {
+
+ /* Size 0 resources can be skipped. */
+ if (!resource->size) {
+ continue;
+ }
+
if (resource->flags & IORESOURCE_IO) {
/* Don't allow potential aliases over the legacy PCI
* expansion card addresses. The legacy PCI decodes
@@ -520,42 +600,210 @@
base = 0x3e0;
}
}
- if (((align_up(base, align) + size) - 1) <= resource->limit) {
- /* Base must be aligned to size. */
- base = align_up(base, align);
+
+
+ if ((align_up(base, resource->align) + resource->size - 1) <=
+ resource->limit) {
+ /* Base must be aligned. */
+ base = align_up(base, resource->align);
resource->base = base;
resource->flags |= IORESOURCE_ASSIGNED;
resource->flags &= ~IORESOURCE_STORED;
- base += size;
+ base += resource->size;
+ } else {
+ printk(BIOS_ERR, "!! Resource didn't fit !!\n");
+ printk(BIOS_ERR, " aligned base %llx size %llx limit %llx\n",
+ align_up(base, resource->align), resource->size, resource->limit);
+ printk(BIOS_ERR, " %llx needs to be <= %llx (limit)\n",
+ (align_up(base, resource->align)+resource->size)-1, resource->limit);
+ printk(BIOS_ERR, " %s%s %02lx * [0x%llx - 0x%llx] %s\n",
+ (resource->flags & IORESOURCE_ASSIGNED) ? "Assigned: "
+ : "",
+ dev_path(dev), resource->index, resource->base,
+ resource->base + resource->size - 1,
+ (resource->flags & IORESOURCE_IO) ? "io" :
+ (resource-> flags & IORESOURCE_PREFETCH) ? "prefmem" :
+ "mem");
+ }
- printk(BIOS_SPEW,
- "%s %02lx * [0x%08llx - 0x%08llx] %s\n",
- dev_path(dev),
- resource->index,
- resource->base,
- resource->base + resource->size - 1,
- (resource->flags & IORESOURCE_IO) ? "io" :
- (resource->
- flags & IORESOURCE_PREFETCH) ? "prefmem" :
- "mem");
- }
+ printk(BIOS_SPEW, "%s%s %02lx * [0x%llx - 0x%llx] %s\n",
+ (resource->flags & IORESOURCE_ASSIGNED) ? "Assigned: "
+ : "",
+ dev_path(dev), resource->index, resource->base,
+
+ resource->size? resource->base + resource->size - 1 :
+ resource->base,
+
+ (resource->flags & IORESOURCE_IO) ? "io" :
+ (resource-> flags & IORESOURCE_PREFETCH) ? "prefmem" :
+ "mem");
}
/* A PCI bridge resource does not need to be a power of two size, but
* it does have a minimum granularity. Round the size up to that
* minimum granularity so we know not to place something else at an
* address positively decoded by the bridge.
*/
- bridge->size = align_up(base, bridge->gran) - bridge->base;
+ bridge->flags |= IORESOURCE_ASSIGNED;
+
printk(BIOS_SPEW,
- "%s compute_allocate_%s: base: %08llx size: %08llx align: %d gran: %d done\n",
- dev_path(bus->dev),
- (bridge->flags & IORESOURCE_IO) ? "io" : (bridge->flags &
- IORESOURCE_PREFETCH) ?
- "prefmem" : "mem", base, bridge->size, bridge->align,
+ "%s %s_%s: next_base: %llx size: %llx align: %d gran: %d done\n",
+ dev_path(bus->dev), __func__,
+ (type & IORESOURCE_IO) ? "io" : (type & IORESOURCE_PREFETCH) ?
+ "prefmem" : "mem",
+ base, bridge->size, bridge->align,
bridge->gran);
+
+ /* For each child which is a bridge, assign_resource_values. */
+ for (dev = bus->children; dev; dev = dev->sibling) {
+ unsigned i;
+ struct resource *child_bridge;
+
+ if (!dev->links)
+ continue;
+
+ /* Find the resources with matching type flags. */
+ for (i=0; i< dev->resources; i++){
+ child_bridge = &dev->resource[i];
+
+ if (!(child_bridge->flags & IORESOURCE_BRIDGE) ||
+ (child_bridge->flags & type_mask) != type)
+ continue;
+
+ /* Split prefetchable memory if combined. Many domains
+ * use the same address space for prefetchable memory
+ * and non-prefetchable memory. Bridges below them
+ * need it separated. Add the PREFETCH flag to the
+ * type_mask and type.
+ */
+ assign_resource_values(&dev->link[0], child_bridge,
+ type_mask | IORESOURCE_PREFETCH,
+ type | (child_bridge->flags &
+ IORESOURCE_PREFETCH));
+ }
+ }
}
+struct constraints {
+ struct resource pref, io, mem;
+};
+
+static void constrain_resources(struct device *dev, struct constraints* limits)
+{
+ struct device *child;
+ struct resource *res;
+ struct resource *lim;
+ int i;
+
+#ifdef CONFIG_PCI_64BIT_PREF_MEM
+ #define MEM_MASK (IORESOURCE_PREFETCH | IORESOURCE_MEM)
+#else
+ #define MEM_MASK (IORESOURCE_MEM)
+#endif
+#define IO_MASK (IORESOURCE_IO)
+#define PREF_TYPE (IORESOURCE_PREFETCH | IORESOURCE_MEM)
+#define MEM_TYPE (IORESOURCE_MEM)
+#define IO_TYPE (IORESOURCE_IO)
+
+ /* Descend into every child and look for fixed resources. */
+ for (child=dev->link[0].children; child; child = child->sibling) {
+ constrain_resources(child, limits);
+ for (i = 0; i<child->resources; i++) {
+ res = &child->resource[i];
+ if (!(res->flags & IORESOURCE_FIXED))
+ continue;
+
+ /* PREFETCH, MEM, or I/O - skip any others. */
+ if ((res->flags & MEM_MASK) == PREF_TYPE)
+ lim = &limits->pref;
+ else if ((res->flags & MEM_MASK) == MEM_TYPE)
+ lim = &limits->mem;
+ else if ((res->flags & IO_MASK) == IO_TYPE)
+ lim = &limits->io;
+ else
+ continue;
+
+ /* Is it already outside the limits? */
+ if (res->size &&
+ (((res->base + res->size -1) < lim->base) ||
+ (res->base > lim->limit)))
+ continue;
+
+ /* Choose to be above or below fixed resources. This
+ * check is signed so that "negative" amounts of space
+ * are handled correctly.
+ */
+ if ((s64)(lim->limit - (res->base + res->size -1)) >
+ (s64)(res->base - lim->base))
+ lim->base = res->base + res->size;
+ else
+ lim->limit = res->base -1;
+ }
+ }
+}
+
+static void avoid_fixed_resources(struct device *dev)
+{
+ struct constraints limits;
+ struct resource *res;
+ int i;
+
+ /* Initialize constraints to maximum size. */
+
+ limits.pref.base = 0;
+ limits.pref.limit = 0xffffffffffffffffULL;
+ limits.io.base = 0;
+ limits.io.limit = 0xffffffffffffffffULL;
+ limits.mem.base = 0;
+ limits.mem.limit = 0xffffffffffffffffULL;
+
+ /* Constrain the limits to dev's initial resources. */
+ for (i = 0; i<dev->resources; i++) {
+ res = &dev->resource[i];
+ if ((res->flags & IORESOURCE_FIXED) ||
+ !(res->flags & IORESOURCE_BRIDGE))
+ continue;
+ if ((res->flags & MEM_MASK) == PREF_TYPE &&
+ (res->limit < limits.pref.limit))
+ limits.pref.limit = res->limit;
+ if ((res->flags & MEM_MASK) == MEM_TYPE &&
+ (res->limit < limits.mem.limit))
+ limits.mem.limit = res->limit;
+ if ((res->flags & IO_MASK) == IO_TYPE &&
+ (res->limit < limits.io.limit))
+ limits.io.limit = res->limit;
+ }
+
+ /* Look through the tree for fixed resources and update the limits. */
+ constrain_resources(dev, &limits);
+
+ /* Update dev's resources with new limits. */
+ for (i = 0; i<dev->resources; i++) {
+ struct resource *lim;
+ res = &dev->resource[i];
+
+ if ((res->flags & IORESOURCE_FIXED) ||
+ !(res->flags & IORESOURCE_BRIDGE))
+ continue;
+
+ /* PREFETCH, MEM, or I/O - skip any others. */
+ if ((res->flags & MEM_MASK) == PREF_TYPE)
+ lim = &limits.pref;
+ else if ((res->flags & MEM_MASK) == MEM_TYPE)
+ lim = &limits.mem;
+ else if ((res->flags & IO_MASK) == IO_TYPE)
+ lim = &limits.io;
+ else
+ continue;
+
+ /* Is the resource outside the limits? */
+ if ( lim->base > res->base )
+ res->base = lim->base;
+ if ( res->limit > lim->limit )
+ res->limit = lim->limit;
+ }
+}
+
#ifdef CONFIG_PCI_OPTION_ROM_RUN
struct device *vga_pri = 0;
int vga_inited = 0;
@@ -639,16 +887,16 @@
* has to recurse into every down stream buses.
*
* Mutual recursion:
- * assign_resources() -> device_operation::set_resources()
- * device_operation::set_resources() -> assign_resources()
+ * phase4_set_resources() -> device_operation::set_resources()
+ * device_operation::set_resources() -> phase4_set_resources()
*
* @param bus Pointer to the structure for this bus.
*/
-void phase4_assign_resources(struct bus *bus)
+void phase4_set_resources(struct bus *bus)
{
struct device *curdev;
- printk(BIOS_SPEW, "%s(%s) assign_resources, bus %d link: %d\n",
+ printk(BIOS_SPEW, "%s(%s) %s, bus %d link: %d\n", __func__,
bus->dev->dtsname, dev_path(bus->dev), bus->secondary,
bus->link);
@@ -669,7 +917,7 @@
}
curdev->ops->phase4_set_resources(curdev);
}
- printk(BIOS_SPEW, "%s(%s) assign_resources done, bus %d link: %d\n",
+ printk(BIOS_SPEW, "%s(%s) %s done, bus %d link: %d\n", __func__,
bus->dev->dtsname, dev_path(bus->dev), bus->secondary,
bus->link);
}
@@ -895,7 +1143,7 @@
dtsname : "NULL");
for (i = 0; i < root->resources; i++) {
printk(BIOS_DEBUG,
- "%s%s resource base %llx size %llx align %x gran %x limit %llx flags %lx index %lx\n",
+ "%s%s resource base %llx size %llx align %d gran %d limit %llx flags %lx index %lx\n",
indent, dev_path(root), root->resource[i].base,
root->resource[i].size, root->resource[i].align,
root->resource[i].gran, root->resource[i].limit,
@@ -919,129 +1167,140 @@
}
/* Bail if not printing to screen. */
- if (!printk(debug_level, "Show all resources in tree form...%s\n", msg))
+ if (!printk(debug_level, "Show resources in subtree (%s)...%s\n",
+ root->dtsname, msg))
return;
resource_tree(root, debug_level, 0);
}
/**
- * Configure devices on the device tree.
+ * Allocate resources.
*
- * Starting at the root of the device tree, travel it recursively in two
- * passes. In the first pass, we compute and allocate resources (ranges)
- * required by each device. In the second pass, the resources ranges are
- * relocated to their final position and stored to the hardware.
+ * Starting at the root of the device tree, travel it recursively in four
+ * passes. In the first pass, we read all the resources. In the second pass we
+ * compute the resource needs. In the third pass we assign final values to the
+ * resources. In the fourth pass we set them.
*
- * I/O resources start at DEVICE_IO_START and grow upward. MEM resources start
- * at DEVICE_MEM_START and grow downward.
+ * I/O resources start at the bottom of the domain's resource and grow upward.
+ * MEM resources start at the top of the domain's resource and grow downward.
*
- * Since the assignment is hierarchical we set the values into the dev_root
- * struct.
*/
void dev_phase4(void)
{
- struct resource *io, *mem;
+ struct resource *res;
struct device *root;
+ struct device * child;
+ int i;
printk(BIOS_INFO, "Phase 4: Allocating resources...\n");
root = &dev_root;
- if (!root->ops) {
- printk(BIOS_ERR,
- "Phase 4: dev_root missing ops initialization\nPhase 4: Failed.\n");
- return;
- }
- if (!root->ops->phase4_read_resources) {
- printk(BIOS_ERR,
- "dev_root ops missing read_resources\nPhase 4: Failed.\n");
- return;
- }
- if (!root->ops->phase4_set_resources) {
- printk(BIOS_ERR,
- "dev_root ops missing set_resources\nPhase 4: Failed.\n");
- return;
- }
+ /* Each domain should create resources which contain the entire address
+ * space for IO, MEM, and PREFMEM resources in the domain. The
+ * allocation of device resources will be done from this address space.
+ */
printk(BIOS_INFO, "Phase 4: Reading resources...\n");
- root->ops->phase4_read_resources(root);
+
+ /* Read the resources for the entire tree. */
+ read_resources(&root->link[0]);
+
printk(BIOS_INFO, "Phase 4: Done reading resources.\n");
- /* We have read the resources. We now compute the global allocation of
- * resources. We have to create a root resource for the base of the
- * tree. The root resource should contain the entire address space for
- * IO and MEM resources. The allocation of device resources will be done
- * from this resource address space.
- */
+ printk(BIOS_INFO, "Phase 4: Constrain resources.\n");
- /* Allocate a resource from the root device resource pool and initialize
- * the system-wide I/O space constraints.
- */
- io = new_resource(root, 0);
- io->base = 0x400;
- io->size = 0;
- io->align = 0;
- io->gran = 0;
- io->limit = 0xffffUL;
- io->flags = IORESOURCE_IO;
+ /* For all domains. */
+ for (child = root->link[0].children; child;
+ child=child->sibling)
+ if (child->path.type == DEVICE_PATH_PCI_DOMAIN)
+ avoid_fixed_resources(child);
- /* Allocate a resource from the root device resource pool and initialize
- * the system-wide memory resources constraints.
- */
- mem = new_resource(root, 1);
- mem->base = 0;
- mem->size = 0;
- mem->align = 0;
- mem->gran = 0;
- mem->limit = 0xffffffffUL;
- mem->flags = IORESOURCE_MEM;
+ print_resource_tree(root, BIOS_DEBUG, "Original.");
- compute_allocate_resource(&root->link[0], io,
- IORESOURCE_IO, IORESOURCE_IO);
+ /* Compute resources for all domains. */
+ for (child = root->link[0].children; child; child=child->sibling) {
+ if (!(child->path.type == DEVICE_PATH_PCI_DOMAIN))
+ continue;
+ for (i=0; i< child->resources; i++) {
+ res = &child->resource[i];
+ if ( res->flags & IORESOURCE_FIXED )
+ continue;
+ if ( res->flags & IORESOURCE_PREFETCH ) {
+ compute_resource_needs(&child->link[0],
+ res, MEM_MASK, PREF_TYPE);
+ continue;
+ }
+ if ( res->flags & IORESOURCE_MEM ) {
+ compute_resource_needs(&child->link[0],
+ res, MEM_MASK, MEM_TYPE);
+ continue;
+ }
+ if ( res->flags & IORESOURCE_IO ) {
+ compute_resource_needs(&child->link[0],
+ res, IO_MASK, IO_TYPE);
+ continue;
+ }
+ }
+ }
- compute_allocate_resource(&root->link[0], mem,
- IORESOURCE_MEM, IORESOURCE_MEM);
+ print_resource_tree(root, BIOS_DEBUG, "After summations.");
- print_resource_tree(root, BIOS_DEBUG, "After first compute_allocate.");
-
/* Now we need to adjust the resources. The issue is that mem grows
- * downward.
+ * downward. Reallocate the MEM resources with the highest addresses
+ * I can manage.
*/
- /* Make certain the I/O devices are allocated somewhere safe. */
- io->base = DEVICE_IO_START;
- io->flags |= IORESOURCE_ASSIGNED;
- io->flags &= ~IORESOURCE_STORED;
+ for (child = root->link[0].children; child; child=child->sibling) {
+ if (child->path.type != DEVICE_PATH_PCI_DOMAIN)
+ continue;
+ for (i=0; i< child->resources; i++) {
+ res = &child->resource[i];
+ if (!(res->flags & IORESOURCE_MEM) ||
+ res->flags & IORESOURCE_FIXED )
+ continue;
+ res->base = resource_max(res);
+ }
+ }
- /* Now reallocate the PCI resources memory with the
- * highest addresses I can manage.
- */
- mem->base = resource_max(&root->resource[1]);
- mem->flags |= IORESOURCE_ASSIGNED;
- mem->flags &= ~IORESOURCE_STORED;
-
#ifdef CONFIG_PCI_OPTION_ROM_RUN
/* Allocate the VGA I/O resource. */
allocate_vga_resource();
+ print_resource_tree(root, BIOS_DEBUG, "After VGA.");
#endif
- /* now rerun the compute allocate with the adjusted resources */
- compute_allocate_resource(&root->link[0], io,
- IORESOURCE_IO, IORESOURCE_IO);
+ /* Assign values to the resources for all domains. */
+ /* If the domain has a prefetchable memory resource, use it. */
+ for (child = root->link[0].children; child; child=child->sibling) {
+ if (!(child->path.type == DEVICE_PATH_PCI_DOMAIN))
+ continue;
+ for (i=0; i< child->resources; i++) {
+ res = &child->resource[i];
+ if ( res->flags & IORESOURCE_FIXED )
+ continue;
+ if ( res->flags & IORESOURCE_PREFETCH ) {
+ assign_resource_values(&child->link[0],
+ res, MEM_MASK, PREF_TYPE);
+ continue;
+ }
+ if ( res->flags & IORESOURCE_MEM ) {
+ assign_resource_values(&child->link[0],
+ res, MEM_MASK, MEM_TYPE);
+ continue;
+ }
+ if ( res->flags & IORESOURCE_IO ) {
+ assign_resource_values(&child->link[0],
+ res, IO_MASK, IO_TYPE);
+ continue;
+ }
+ }
+ }
- compute_allocate_resource(&root->link[0], mem,
- IORESOURCE_MEM, IORESOURCE_MEM);
+ print_resource_tree(root, BIOS_DEBUG, "After assigning values.");
- print_resource_tree(root, BIOS_DEBUG, "After second compute_allocate.");
-
/* Store the computed resource allocations into device registers. */
printk(BIOS_INFO, "Phase 4: Setting resources...\n");
- root->ops->phase4_set_resources(root);
+ phase4_set_resources(&root->link[0]);
print_resource_tree(root, BIOS_DEBUG, "After setting resources.");
- printk(BIOS_INFO, "Phase 4: Done setting resources.\n");
-#if 0
- mem->flags |= IORESOURCE_STORED;
- report_resource_stored(root, mem, "");
-#endif
printk(BIOS_INFO, "Phase 4: Done allocating resources.\n");
}
@@ -1132,21 +1391,21 @@
return;
for (dev = all_devices; dev; dev = dev->next) {
printk(debug_level,
- "%s(%s): enabled %d have_resources %d\n",
+ "%s(%s): enabled %d, %d resources\n",
dev->dtsname, dev_path(dev), dev->enabled,
- dev->have_resources);
+ dev->resources);
}
}
-void show_one_resource(struct device *dev, struct resource *resource,
- const char *comment)
+void show_one_resource(int debug_level, struct device *dev,
+ struct resource *resource, const char *comment)
{
char buf[10];
unsigned long long base, end;
base = resource->base;
end = resource_end(resource);
buf[0] = '\0';
- if (resource->flags & IORESOURCE_PCI_BRIDGE) {
+ if (resource->flags & IORESOURCE_BRIDGE) {
#if PCI_BUS_SEGN_BITS
sprintf(buf, "bus %04x:%02x ", dev->bus->secondary >> 8,
dev->link[0].secondary & 0xff);
@@ -1154,7 +1413,7 @@
sprintf(buf, "bus %02x ", dev->link[0].secondary);
#endif
}
- printk(BIOS_DEBUG, "%s %02lx <- [0x%010llx - 0x%010llx] "
+ printk(debug_level, "%s %02lx <- [0x%010llx - 0x%010llx] "
"size 0x%08Lx gran 0x%02x %s%s%s\n",
dev_path(dev), resource->index, base, end,
resource->size, resource->gran, buf,
@@ -1162,18 +1421,20 @@
}
-void show_all_devs_resources(void)
+void show_all_devs_resources(int debug_level, const char* msg)
{
struct device *dev;
- printk(BIOS_INFO, "Show all devs...\n");
+ if(!printk(debug_level, "Show all devs with resources...%s\n", msg))
+ return;
+
for (dev = all_devices; dev; dev = dev->next) {
int i;
- printk(BIOS_SPEW,
- "%s(%s): enabled %d have_resources %d\n",
+ printk(debug_level,
+ "%s(%s): enabled %d, %d resources\n",
dev->dtsname, dev_path(dev), dev->enabled,
- dev->have_resources);
+ dev->resources);
for (i = 0; i < dev->resources; i++)
- show_one_resource(dev, &dev->resource[i], "");
+ show_one_resource(debug_level, dev, &dev->resource[i], "");
}
}
Modified: coreboot-v3/device/device_util.c
===================================================================
--- coreboot-v3/device/device_util.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/device_util.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -241,7 +241,7 @@
dev->path.ioport.iobase);
break;
default:
- printk(BIOS_ERR, "%s: Unknown device path type: %d\n",
+ printk(BIOS_ERR, "%s: Unknown device path type: %x\n",
dev->dtsname, dev->path.type);
break;
}
@@ -293,7 +293,7 @@
id->cpu_bus.vendor, id->cpu_bus.device);
break;
default:
- printk(BIOS_ERR, "%s: Unknown device ID type: %d\n",
+ printk(BIOS_ERR, "%s: Unknown device ID type: %x\n",
__func__, id->type);
memcpy(buffer, "Unknown", 8);
break;
@@ -349,8 +349,8 @@
equal = (path1->cpu_bus.id == path2->cpu_bus.id);
break;
default:
- printk(BIOS_ERR, "Unknown device type: %d\n",
- path1->type);
+ printk(BIOS_ERR, "%s: Unknown device type: %x\n",
+ __func__, path1->type);
break;
}
}
@@ -403,8 +403,8 @@
&& (path1->cpu_bus.device == path2->cpu_bus.device);
break;
default:
- printk(BIOS_ERR, "Unknown device type: %d\n",
- path1->type);
+ printk(BIOS_ERR, "%s: Unknown device type: %x\n",
+ __func__, path1->type);
break;
}
}
@@ -615,26 +615,29 @@
void report_resource_stored(struct device *dev, struct resource *resource,
const char *comment)
{
- if (resource->flags & IORESOURCE_STORED) {
- char buf[10];
- unsigned long long base, end;
- base = resource->base;
- end = resource_end(resource);
- buf[0] = '\0';
- if (resource->flags & IORESOURCE_PCI_BRIDGE) {
+ char buf[10];
+ unsigned long long base, end;
+ base = resource->base;
+ end = resource_end(resource);
+ buf[0] = '\0';
+
+ if (!(resource->flags & IORESOURCE_STORED))
+ printk(BIOS_DEBUG, "%s lying: %s(%s) %02lx\n",
+ __func__, dev_path(dev), dev->dtsname, resource->index);
+
+ if (resource->flags & IORESOURCE_BRIDGE) {
#if PCI_BUS_SEGN_BITS
- sprintf(buf, "bus %04x:%02x ", dev->bus->secondary >> 8,
- dev->link[0].secondary & 0xff);
+ sprintf(buf, "bus %04x:%02x ", dev->bus->secondary >> 8,
+ dev->link[0].secondary & 0xff);
#else
- sprintf(buf, "bus %02x ", dev->link[0].secondary);
+ sprintf(buf, "bus %02x ", dev->link[0].secondary);
#endif
- }
- printk(BIOS_DEBUG, "%s %02lx <- [0x%010llx - 0x%010llx] "
- "size 0x%08Lx gran 0x%02x %s%s%s\n",
- dev_path(dev), resource->index, base, end,
- resource->size, resource->gran, buf,
- resource_type(resource), comment);
}
+ printk(BIOS_DEBUG, "%s %02lx <- [0x%010llx - 0x%010llx] "
+ "size 0x%08Lx gran 0x%02x %s%s %s\n",
+ dev_path(dev), resource->index, base, end,
+ resource->size, resource->gran, buf,
+ resource_type(resource), comment);
}
void search_bus_resources(struct bus *bus,
@@ -644,9 +647,6 @@
struct device *curdev;
for (curdev = bus->children; curdev; curdev = curdev->sibling) {
int i;
- /* Ignore disabled devices. */
- if (!curdev->have_resources)
- continue;
for (i = 0; i < curdev->resources; i++) {
struct resource *resource = &curdev->resource[i];
/* If it isn't the right kind of resource ignore it. */
@@ -676,12 +676,8 @@
for (curdev = all_devices; curdev; curdev = curdev->next) {
int i;
printk(BIOS_SPEW,
- "%s: dev %s, have_resources %d #resources %d\n",
- __func__, curdev->dtsname, curdev->have_resources,
- curdev->resources);
- /* Ignore disabled devices. */
- if (!curdev->have_resources)
- continue;
+ "%s: dev %s, #resources %d\n",
+ __func__, curdev->dtsname, curdev->resources);
for (i = 0; i < curdev->resources; i++) {
struct resource *resource = &curdev->resource[i];
printk(BIOS_SPEW,
Modified: coreboot-v3/device/pci_device.c
===================================================================
--- coreboot-v3/device/pci_device.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/pci_device.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -11,6 +11,7 @@
* Copyright (C) 2005-2006 Tyan
* (Written by Yinghai Lu <yhlu(a)tyan.com> for Tyan)
* Copyright (C) 2005-2007 Stefan Reinauer <stepan(a)openbios.org>
+ * Copyright (C) 2008 Myles Watson <mylesgw(a)gmail.com>
*/
/*
@@ -153,7 +154,7 @@
struct resource *pci_get_resource(struct device *dev, unsigned long index)
{
struct resource *resource;
- unsigned long value, attr, base;
+ unsigned long value, attr;
resource_t moving, limit;
/* Initialize the resources to nothing. */
@@ -162,15 +163,9 @@
/* Get the initial value. */
value = pci_read_config32(dev, index);
- /* save the base address */
- if (value & PCI_BASE_ADDRESS_SPACE_IO)
- base = value & ~PCI_BASE_ADDRESS_IO_ATTR_MASK;
- else
- base = value & ~PCI_BASE_ADDRESS_MEM_ATTR_MASK;
-
/* See which bits move. */
moving = pci_moving_config32(dev, index);
- /* Next step: save the base in the dev struct. For later next week */
+
/* Initialize attr to the bits that do not move. */
attr = value & ~moving;
@@ -222,7 +217,7 @@
* Shouldn't zero because we'll get off with 64-bit BARs.
* Are there any others to save?
*/
- resource->flags &= ~IORESOURCE_PCI64;
+ resource->flags &= IORESOURCE_PCI64;
} else if (attr & PCI_BASE_ADDRESS_SPACE_IO) {
/* An I/O mapped base address. */
attr &= PCI_BASE_ADDRESS_IO_ATTR_MASK;
@@ -248,6 +243,8 @@
resource->limit = 0xffffffffffffffffULL;
} else {
/* Invalid value. */
+ printk(BIOS_ERR,"Broken BAR with value %lx\n",attr);
+ printk(BIOS_ERR," on dev %s at index %02lx\n",dev->dtsname,index);
resource->flags = 0;
}
}
@@ -347,15 +344,12 @@
compact_resources(dev);
}
-static void pci_set_resource(struct device *dev, struct resource *resource);
-
static void pci_record_bridge_resource(struct device *dev, resource_t moving,
- unsigned int index, unsigned long mask,
- unsigned long type)
+ unsigned int index, unsigned long type)
{
/* Initialize the constraints on the current bus. */
struct resource *resource;
- resource = 0;
+ resource = NULL;
if (moving) {
unsigned long gran;
resource_t step;
@@ -370,18 +364,7 @@
resource->gran = gran;
resource->align = gran;
resource->limit = moving | (step - 1);
- resource->flags = type | IORESOURCE_PCI_BRIDGE;
- compute_allocate_resource(&dev->link[0], resource, mask, type);
- /* If there is nothing behind the resource,
- * clear it and forget it.
- */
- if (resource->size == 0) {
- resource->base = moving;
- resource->flags |= IORESOURCE_ASSIGNED;
- resource->flags &= ~IORESOURCE_STORED;
- pci_set_resource(dev, resource);
- resource->flags = 0;
- }
+ resource->flags = type | IORESOURCE_PCI_BRIDGE | IORESOURCE_BRIDGE;
}
return;
}
@@ -402,8 +385,7 @@
moving = moving_base & moving_limit;
/* Initialize the I/O space constraints on the current bus. */
- pci_record_bridge_resource(dev, moving, PCI_IO_BASE,
- IORESOURCE_IO, IORESOURCE_IO);
+ pci_record_bridge_resource(dev, moving, PCI_IO_BASE, IORESOURCE_IO);
/* See if the bridge prefmem resources are implemented. */
moving_base =
@@ -416,7 +398,6 @@
moving = moving_base & moving_limit;
/* Initialize the prefetchable memory constraints on the current bus. */
pci_record_bridge_resource(dev, moving, PCI_PREF_MEMORY_BASE,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
IORESOURCE_MEM | IORESOURCE_PREFETCH);
/* See if the bridge mem resources are implemented. */
@@ -427,7 +408,6 @@
/* Initialize the memory resources on the current bus. */
pci_record_bridge_resource(dev, moving, PCI_MEMORY_BASE,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
IORESOURCE_MEM);
compact_resources(dev);
@@ -441,9 +421,24 @@
void pci_bus_read_resources(struct device *dev)
{
+ struct device *child;
+
+ printk(BIOS_DEBUG, "%s: %s bus %s\n",
+ __func__, dev_path(dev), dev->bus? dev_path(dev->bus->dev):"NULL");
pci_bridge_read_bases(dev);
pci_read_bases(dev, 2);
pci_get_rom_resource(dev, PCI_ROM_ADDRESS1);
+ if (!dev->bus){
+ printk(BIOS_ERR, "%s: %s bus %s\n",
+ __func__, dev_path(dev), dev->bus? dev_path(dev->bus->dev):"NULL");
+ }
+
+ for (child = dev->link[0].children; child; child = child->sibling)
+ if (child->ops && child->ops->phase4_read_resources)
+ child->ops->phase4_read_resources(child);
+ else
+ printk(BIOS_ERR, "%s: %s missing Phase4\n",
+ __func__, dev_path(child));
}
/**
@@ -462,22 +457,22 @@
/* Initialize the system-wide I/O space constraints. */
res = new_resource(dev, IOINDEX_SUBTRACTIVE(0, 0));
res->limit = 0xffffUL;
- res->flags =
- IORESOURCE_IO | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ res->flags = IORESOURCE_IO | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_BRIDGE;
/* Initialize the system-wide memory resources constraints. */
res = new_resource(dev, IOINDEX_SUBTRACTIVE(1, 0));
res->limit = 0xffffffffULL;
- res->flags =
- IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
+ res->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE |
+ IORESOURCE_ASSIGNED | IORESOURCE_BRIDGE;
}
static void pci_set_resource(struct device *dev, struct resource *resource)
{
resource_t base, end;
- /* Make certain the resource has actually been set. */
- if (!(resource->flags & IORESOURCE_ASSIGNED)) {
+ /* Make certain the resource has actually been assigned a value. */
+ if (!(resource->flags & IORESOURCE_ASSIGNED) && resource->size!=0) {
printk(BIOS_ERR,
"ERROR: %s %02lx %s size: 0x%010llx not assigned\n",
dev_path(dev), resource->index, resource_type(resource),
@@ -519,6 +514,16 @@
/* Now store the resource. */
resource->flags |= IORESOURCE_STORED;
+ /* PCI Bridges have no enable bit. They are disabled if the base of
+ * the range is greater than the limit. If the size is zero, disable
+ * by setting the base = limit and end = limit - 2^gran.
+ */
+ if (resource->size == 0 && (resource->flags & IORESOURCE_PCI_BRIDGE)) {
+ base = resource->limit;
+ end = resource->limit - (1<<resource->gran);
+ resource->base = base;
+ }
+
if (!(resource->flags & IORESOURCE_PCI_BRIDGE)) {
unsigned long base_lo, base_hi;
/* Some chipsets allow us to set/clear the I/O bit
@@ -535,24 +540,16 @@
}
} else if (resource->index == PCI_IO_BASE) {
/* Set the I/O ranges. */
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_IO, IORESOURCE_IO);
pci_write_config8(dev, PCI_IO_BASE, base >> 8);
pci_write_config16(dev, PCI_IO_BASE_UPPER16, base >> 16);
pci_write_config8(dev, PCI_IO_LIMIT, end >> 8);
pci_write_config16(dev, PCI_IO_LIMIT_UPPER16, end >> 16);
} else if (resource->index == PCI_MEMORY_BASE) {
/* Set the memory range. */
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM);
pci_write_config16(dev, PCI_MEMORY_BASE, base >> 16);
pci_write_config16(dev, PCI_MEMORY_LIMIT, end >> 16);
} else if (resource->index == PCI_PREF_MEMORY_BASE) {
/* Set the prefetchable memory range. */
- compute_allocate_resource(&dev->link[0], resource,
- IORESOURCE_MEM | IORESOURCE_PREFETCH,
- IORESOURCE_MEM | IORESOURCE_PREFETCH);
pci_write_config16(dev, PCI_PREF_MEMORY_BASE, base >> 16);
pci_write_config32(dev, PCI_PREF_BASE_UPPER32, base >> 32);
pci_write_config16(dev, PCI_PREF_MEMORY_LIMIT, end >> 16);
@@ -563,7 +560,7 @@
printk(BIOS_ERR, "ERROR: invalid resource->index %lx\n",
resource->index);
}
- report_resource_stored(dev, resource, "");
+ report_resource_stored(dev, resource, __func__);
return;
}
@@ -582,7 +579,7 @@
struct bus *bus;
bus = &dev->link[link];
if (bus->children) {
- phase4_assign_resources(bus);
+ phase4_set_resources(bus);
}
}
Modified: coreboot-v3/device/pci_ops.c
===================================================================
--- coreboot-v3/device/pci_ops.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/pci_ops.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -36,7 +36,7 @@
struct bus *pbus = dev->bus;
while (pbus && pbus->dev && !ops_pci_bus(pbus)) {
if (pbus->dev == dev) {
- printk(BIOS_EMERG, "Loop: dev->dtsname dev->bus->dev\n");
+ printk(BIOS_EMERG, "Loop: %s->bus->dev\n", dev->dtsname);
printk(BIOS_EMERG, "To fix this, set ops_pci_bus in dts\n");
die("loop due to insufficient dts");
}
Modified: coreboot-v3/device/root_device.c
===================================================================
--- coreboot-v3/device/root_device.c 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/device/root_device.c 2008-12-31 19:43:34 UTC (rev 1089)
@@ -35,13 +35,7 @@
*/
void root_dev_read_resources(struct device *root)
{
- void read_resources(struct bus *bus);
- void show_all_devs_resources(void);
-
- read_resources(&root->link[0]);
-
- printk(BIOS_DEBUG, "%s: Done allocating\n", __FUNCTION__);
- show_all_devs_resources();
+ printk(BIOS_DEBUG, "This shouldn't be called!\n");
}
/**
@@ -52,7 +46,7 @@
*/
void root_dev_set_resources(struct device *root)
{
- phase4_assign_resources(&root->link[0]);
+ printk(BIOS_DEBUG, "This shouldn't be called!\n");
}
/**
@@ -193,6 +187,7 @@
* mainboard directory.
*/
struct device_operations default_dev_ops_root = {
+ .id = {.type = DEVICE_ID_ROOT},
.phase3_scan = root_dev_scan_bus,
.phase4_read_resources = root_dev_read_resources,
.phase4_set_resources = root_dev_set_resources,
Modified: coreboot-v3/include/device/device.h
===================================================================
--- coreboot-v3/include/device/device.h 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/include/device/device.h 2008-12-31 19:43:34 UTC (rev 1089)
@@ -199,12 +199,11 @@
u16 subsystem_vendor;
u16 subsystem_device;
- unsigned int class; /* 3 bytes: (base,sub,prog-if) */
- unsigned int hdr_type; /* PCI header type */
- unsigned int enabled:1; /* set if we should enable the device */
- unsigned int have_resources:1; /* Set if we have read the devices resources */
- unsigned int on_mainboard:1;
- unsigned long rom_address;
+ unsigned int class; /* 3 bytes: (base,sub,prog-if) */
+ unsigned int hdr_type; /* PCI header type */
+ unsigned int enabled : 1; /* set if we should enable the device */
+ unsigned int on_mainboard : 1;
+ unsigned long rom_address;
u8 command;
@@ -239,9 +238,7 @@
/* Generic device helper functions */
int reset_bus(struct bus *bus);
unsigned int scan_bus(struct device *bus, unsigned int max);
-void compute_allocate_resource(struct bus *bus, struct resource *bridge,
- unsigned long type_mask, unsigned long type);
-void assign_resources(struct bus *bus);
+//void assign_resources(struct bus *bus);
void enable_resources(struct device *dev);
void enumerate_static_device(void);
void enumerate_static_devices(void);
@@ -267,13 +264,10 @@
const struct device_operations *constructor);
void show_all_devs(int debug_level, const char *msg);
void show_all_devs_tree(int debug_level, const char *msg);
+void show_all_devs(int debug_level, const char *msg);
+void show_all_devs_tree(int debug_level, const char *msg);
+void print_resource_tree(const struct device * const dev, int debug_level, const char* msg);
-/* Rounding for boundaries.
- * Due to some chip bugs, go ahead and round IO to 16
- */
-#define DEVICE_IO_ALIGN 16
-#define DEVICE_MEM_ALIGN 4096
-
resource_t align_up(resource_t val, unsigned long gran);
resource_t align_down(resource_t val, unsigned long gran);
@@ -296,7 +290,7 @@
void dev_root_phase5(void);
void dev_phase6(void);
-void phase4_assign_resources(struct bus *bus);
+void phase4_set_resources(struct bus *bus);
unsigned int dev_phase3(struct device *bus, unsigned int max);
void dev_phase5(struct device *dev);
Modified: coreboot-v3/include/device/resource.h
===================================================================
--- coreboot-v3/include/device/resource.h 2008-12-30 07:02:52 UTC (rev 1088)
+++ coreboot-v3/include/device/resource.h 2008-12-31 19:43:34 UTC (rev 1089)
@@ -36,6 +36,7 @@
#define IORESOURCE_SUBTRACTIVE 0x00040000 /* This resource filters all of the unclaimed transactions
* to the bus below.
*/
+#define IORESOURCE_BRIDGE 0x00080000 /* The IO resource has a bus below it. */
#define IORESOURCE_STORED 0x20000000 /* The IO resource assignment has been stored in the device */
#define IORESOURCE_ASSIGNED 0x40000000 /* An IO resource that has been assigned a value */
#define IORESOURCE_FIXED 0x80000000 /* An IO resource the allocator must not change */
1
0
Hi,
I'm just starting to find the time to get involved in coreboot.
My board is an Advantec SOM-5781. It seems pretty close to the reference design so I thought I would give loading the vanilla dbm690t bios a shot.
I have a Sempron 2100+ in a AM2 socket. ITE IT8712F SuperIO @ 0x2E.
Has anyone seen this before? It keeps happening over and over. I'll be looking in to it tonight. My understanding so far is that it is only supposed to happen once.
Thanks
Dan Lykowski
coreboot-2.0.0 Tue Dec 30 10:32:31 PST 2008 starting...
bsp_apicid=0x0
core0 started:
SBLink=00
NC node|link=00
rs690_early_setup()
get_cpu_rev EAX=0x40fc2.
CPU Rev is K8_Fx.
NB Revision is A12.
k8_optimization()
rs690_por_init
sb600_early_setup()
sb600_devices_por_init()
sb600_devices_por_init(): SMBus Device, BDF:0-20-0
SMBus controller enabled, sb revision is 0x13
sb600_devices_por_init(): IDE Device, BDF:0-20-1
sb600_devices_por_init(): LPC Device, BDF:0-20-3
sb600_devices_por_init(): P2P Bridge, BDF:0-20-4
sb600_devices_por_init(): SATA Device, BDF:0-18-0
sb600_pmio_por_init()
INIT detected from --- { APICID = 00 NODEID = 00 COREID = 00} ---
Issuing SOFT_RESET...
coreboot-2.0.0 Tue Dec 30 10:32:31 PST 2008 starting...
bsp_apicid=0x0
core0 started:
SBLink=00
NC node|link=00
rs690_early_setup()
get_cpu_rev EAX=0x40fc2.
CPU Rev is K8_Fx.
NB Revision is A12.
k8_optimization()
rs690_por_init
sb600_early_setup()
sb600_devices_por_init()
sb600_devices_por_init(): SMBus Device, BDF:0-20-0
SMBus controller enabled, sb revision is 0x13
sb600_devices_por_init(): IDE Device, BDF:0-20-1
sb600_devices_por_init(): LPC Device, BDF:0-20-3
sb600_devices_por_init(): P2P Bridge, BDF:0-20-4
sb600_devices_por_init(): SATA Device, BDF:0-18-0
sb600_pmio_por_init()
INIT detected from --- { APICID = 00 NODEID = 00 COREID = 00} ---
Issuing SOFT_RESET...
4
5

Dec. 31, 2008
#2: Complete tables of supported motherboards
----------------------------------+-----------------------------------------
Reporter: uwe | Owner: somebody
Type: task | Status: new
Priority: major | Milestone:
Component: wiki/website/tracker | Version:
Keywords: | Dependencies:
----------------------------------+-----------------------------------------
Comment(by pallaximmal):
Bite my shiny metal ass, assholes, <a href=http://justnkldkhsjvd.com/>you
were joked!</a>
--
Ticket URL: <http://tracker.coreboot.org/trac/coreboot/ticket/2#comment:7>
coreboot <http://www.coreboot.org/>
1
0