Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux-2.6
[pandora-kernel.git] / arch / powerpc / boot / cuboot-pq2.c
index 8021fd4..9c7d134 100644 (file)
@@ -15,6 +15,7 @@
 #include "stdio.h"
 #include "cuboot.h"
 #include "io.h"
+#include "fsl-soc.h"
 
 #define TARGET_CPM2
 #define TARGET_HAS_ETH1
@@ -43,22 +44,21 @@ struct pci_range pci_ranges_buf[MAX_PROP_LEN / sizeof(struct pci_range)];
  * some don't set up the PCI PIC at all, so we assume the device tree is
  * sane and update the BRx registers appropriately.
  *
- * For any node defined as compatible with fsl,pq2-chipselect,
- * #address/#size must be 2/1 for chipselect bus, 1/1 for parent bus,
- * and ranges must be for whole chip selects.
+ * For any node defined as compatible with fsl,pq2-localbus,
+ * #address/#size must be 2/1 for the localbus, and 1/1 for the parent bus.
+ * Ranges must be for whole chip selects.
  */
 static void update_cs_ranges(void)
 {
-       u32 ctrl_ph;
-       void *ctrl_node, *bus_node, *parent_node;
+       void *bus_node, *parent_node;
        u32 *ctrl_addr;
        unsigned long ctrl_size;
        u32 naddr, nsize;
        int len;
        int i;
 
-       bus_node = finddevice("/chipselect");
-       if (!bus_node || !dt_is_compatible(bus_node, "fsl,pq2-chipselect"))
+       bus_node = finddevice("/localbus");
+       if (!bus_node || !dt_is_compatible(bus_node, "fsl,pq2-localbus"))
                return;
 
        dt_get_reg_format(bus_node, &naddr, &nsize);
@@ -73,19 +73,7 @@ static void update_cs_ranges(void)
        if (naddr != 1 || nsize != 1)
                goto err;
 
-       len = getprop(bus_node, "fsl,ctrl", &ctrl_ph, 4);
-       if (len != 4)
-               goto err;
-
-       ctrl_node = find_node_by_prop_value(NULL, "linux,phandle",
-                                           (char *)&ctrl_ph, 4);
-       if (!ctrl_node)
-               goto err;
-
-       if (!dt_is_compatible(ctrl_node, "fsl,pq2-chipselect-ctrl"))
-               goto err;
-
-       if (!dt_xlate_reg(ctrl_node, 0, (unsigned long *)&ctrl_addr,
+       if (!dt_xlate_reg(bus_node, 0, (unsigned long *)&ctrl_addr,
                          &ctrl_size))
                goto err;
 
@@ -122,7 +110,7 @@ static void update_cs_ranges(void)
        return;
 
 err:
-       printf("Bad /chipselect or fsl,pq2-chipselect-ctrl node\r\n");
+       printf("Bad /localbus node\r\n");
 }
 
 /* Older u-boots don't set PCI up properly.  Update the hardware to match
@@ -139,47 +127,35 @@ static void fixup_pci(void)
        u32 *pci_regs[3];
        u8 *soc_regs;
        int i, len;
-       void *ctrl_node, *bus_node, *parent_node, *soc_node;
-       u32 naddr, nsize, bus_ph, mem_log2;
+       void *node, *parent_node;
+       u32 naddr, nsize, mem_pow2, mem_mask;
 
-       ctrl_node = finddevice("/soc/pci");
-       if (!ctrl_node || !dt_is_compatible(ctrl_node, "fsl,pq2-pci"))
+       node = finddevice("/pci");
+       if (!node || !dt_is_compatible(node, "fsl,pq2-pci"))
                return;
 
-       soc_node = finddevice("/soc");
-       if (!soc_node || !dt_is_compatible(soc_node, "fsl,pq2-soc"))
-               goto err;
-
        for (i = 0; i < 3; i++)
-               if (!dt_xlate_reg(ctrl_node, i,
+               if (!dt_xlate_reg(node, i,
                                  (unsigned long *)&pci_regs[i], NULL))
                        goto err;
 
-       if (!dt_xlate_reg(soc_node, 0, (unsigned long *)&soc_regs, NULL))
-               goto err;
-
-       len = getprop(ctrl_node, "fsl,bus", &bus_ph, 4);
-       if (len != 4)
-               goto err;
-
-       bus_node = find_node_by_prop_value(NULL, "linux,phandle",
-                                          (char *)&bus_ph, 4);
-       if (!bus_node)
-               goto err;
+       soc_regs = (u8 *)fsl_get_immr();
+       if (!soc_regs)
+               goto unhandled;
 
-       dt_get_reg_format(bus_node, &naddr, &nsize);
+       dt_get_reg_format(node, &naddr, &nsize);
        if (naddr != 3 || nsize != 2)
                goto err;
 
-       parent_node = get_parent(bus_node);
+       parent_node = get_parent(node);
        if (!parent_node)
                goto err;
 
        dt_get_reg_format(parent_node, &naddr, &nsize);
        if (naddr != 1 || nsize != 1)
-               goto err;
+               goto unhandled;
 
-       len = getprop(bus_node, "ranges", pci_ranges_buf,
+       len = getprop(node, "ranges", pci_ranges_buf,
                      sizeof(pci_ranges_buf));
 
        for (i = 0; i < len / sizeof(struct pci_range); i++) {
@@ -194,14 +170,20 @@ static void fixup_pci(void)
        }
 
        if (!mem || !mmio || !io)
-               goto err;
+               goto unhandled;
+       if (mem->size[1] != mmio->size[1])
+               goto unhandled;
+       if (mem->size[1] & (mem->size[1] - 1))
+               goto unhandled;
+       if (io->size[1] & (io->size[1] - 1))
+               goto unhandled;
 
        if (mem->phys_addr + mem->size[1] == mmio->phys_addr)
                mem_base = mem;
        else if (mmio->phys_addr + mmio->size[1] == mem->phys_addr)
                mem_base = mmio;
        else
-               goto err;
+               goto unhandled;
 
        out_be32(&pci_regs[1][0], mem_base->phys_addr | 1);
        out_be32(&pci_regs[2][0], ~(mem->size[1] + mmio->size[1] - 1));
@@ -225,8 +207,9 @@ static void fixup_pci(void)
        out_le32(&pci_regs[0][58], 0);
        out_le32(&pci_regs[0][60], 0);
 
-       mem_log2 = 1 << (__ilog2_u32(bd.bi_memsize - 1) + 1);
-       out_le32(&pci_regs[0][62], 0xa0000000 | ~((1 << (mem_log2 - 12)) - 1));
+       mem_pow2 = 1 << (__ilog2_u32(bd.bi_memsize - 1) + 1);
+       mem_mask = ~(mem_pow2 - 1) >> 12;
+       out_le32(&pci_regs[0][62], 0xa0000000 | mem_mask);
 
        /* If PCI is disabled, drive RST high to enable. */
        if (!(in_le32(&pci_regs[0][32]) & 1)) {
@@ -252,7 +235,11 @@ static void fixup_pci(void)
        return;
 
 err:
-       printf("Bad PCI node\r\n");
+       printf("Bad PCI node -- using existing firmware setup.\r\n");
+       return;
+
+unhandled:
+       printf("Unsupported PCI node -- using existing firmware setup.\r\n");
 }
 
 static void pq2_platform_fixups(void)
@@ -264,10 +251,12 @@ static void pq2_platform_fixups(void)
        dt_fixup_cpu_clocks(bd.bi_intfreq, bd.bi_busfreq / 4, bd.bi_busfreq);
 
        node = finddevice("/soc/cpm");
-       if (node) {
+       if (node)
                setprop(node, "clock-frequency", &bd.bi_cpmfreq, 4);
-               setprop(node, "fsl,brg-frequency", &bd.bi_brgfreq, 4);
-       }
+
+       node = finddevice("/soc/cpm/brg");
+       if (node)
+               setprop(node, "clock-frequency",  &bd.bi_brgfreq, 4);
 
        update_cs_ranges();
        fixup_pci();
@@ -277,7 +266,7 @@ void platform_init(unsigned long r3, unsigned long r4, unsigned long r5,
                    unsigned long r6, unsigned long r7)
 {
        CUBOOT_INIT();
-       ft_init(_dtb_start, _dtb_end - _dtb_start, 32);
+       fdt_init(_dtb_start);
        serial_console_init();
        platform_ops.fixups = pq2_platform_fixups;
 }