--- linux/drivers/pcmcia/yenta.c.bridge Sat Aug 10 20:30:35 2002 +++ linux/drivers/pcmcia/yenta.c Mon Aug 12 10:41:56 2002 @@ -712,6 +712,7 @@ static void yenta_allocate_res(pci_socke u32 align, size, min, max; unsigned offset; unsigned mask; + int failed; /* The granularity of the memory limit is 4kB, on IO it's 4 bytes */ mask = ~0xfff; @@ -739,17 +740,39 @@ static void yenta_allocate_res(pci_socke return; } - align = size = 4*1024*1024; - min = PCIBIOS_MIN_MEM; max = ~0U; if (type & IORESOURCE_IO) { align = 1024; size = 256; min = 0x4000; max = 0xffff; } + else { + align = size = 4*1024*1024; + min = PCIBIOS_MIN_MEM; + max = ~0U; + } - if (allocate_resource(root, res, size, min, max, align, NULL, NULL) < 0) - return; + + do { + failed = allocate_resource(root, res, size, min, max, + align, NULL, NULL); + if (failed) { + /* If we failed to allocate the resources here, we + try its parent if we are on a bridge with + positive decode. */ + struct pci_dev *bridge; + bus = bus->parent; + if (bus == NULL) + return; + bridge = bus->self; + if (bridge == NULL + || (bridge->class >> 16) != PCI_BASE_CLASS_BRIDGE + || (bridge->class & 0xff) != 0) + return; + res->name = bridge->subordinate->name; + root = pci_find_parent_resource(bridge, res); + } + } while (failed); config_writel(socket, offset, res->start); config_writel(socket, offset+4, res->end);