X-Git-Url: http://git.onelab.eu/?a=blobdiff_plain;f=arch%2Fsparc64%2Fkernel%2Fchmc.c;fp=arch%2Fsparc64%2Fkernel%2Fchmc.c;h=97cf912f0853e7aa45676063648b557b878959eb;hb=64ba3f394c830ec48a1c31b53dcae312c56f1604;hp=259f37e516f54f1e82d5c91169ede37faf3382d6;hpb=be1e6109ac94a859551f8e1774eb9a8469fe055c;p=linux-2.6.git diff --git a/arch/sparc64/kernel/chmc.c b/arch/sparc64/kernel/chmc.c index 259f37e51..97cf912f0 100644 --- a/arch/sparc64/kernel/chmc.c +++ b/arch/sparc64/kernel/chmc.c @@ -17,7 +17,6 @@ #include #include #include -#include #include #define CHMCTRL_NDGRPS 2 @@ -68,6 +67,7 @@ struct bank_info { struct mctrl_info { struct list_head list; int portid; + int index; struct obp_mem_layout layout_prop; int layout_size; @@ -339,13 +339,12 @@ static void fetch_decode_regs(struct mctrl_info *mp) read_mcreg(mp, CHMCTRL_DECODE4)); } -static int init_one_mctrl(struct device_node *dp) +static int init_one_mctrl(int node, int index) { struct mctrl_info *mp = kmalloc(sizeof(*mp), GFP_KERNEL); - int portid = of_getintprop_default(dp, "portid", -1); - struct linux_prom64_registers *regs; - void *pval; - int len; + int portid = prom_getintdefault(node, "portid", -1); + struct linux_prom64_registers p_reg_prop; + int t; if (!mp) return -1; @@ -354,21 +353,24 @@ static int init_one_mctrl(struct device_node *dp) goto fail; mp->portid = portid; - pval = of_get_property(dp, "memory-layout", &len); - mp->layout_size = len; - if (!pval) + mp->layout_size = prom_getproplen(node, "memory-layout"); + if (mp->layout_size < 0) mp->layout_size = 0; - else { - if (mp->layout_size > sizeof(mp->layout_prop)) - goto fail; - memcpy(&mp->layout_prop, pval, len); - } + if (mp->layout_size > sizeof(mp->layout_prop)) + goto fail; - regs = of_get_property(dp, "reg", NULL); - if (!regs || regs->reg_size != 0x48) + if (mp->layout_size > 0) + prom_getproperty(node, "memory-layout", + (char *) &mp->layout_prop, + mp->layout_size); + + t = prom_getproperty(node, "reg", + (char *) &p_reg_prop, + sizeof(p_reg_prop)); + if (t < 0 || p_reg_prop.reg_size != 0x48) goto fail; - mp->regs = ioremap(regs->phys_addr, regs->reg_size); + mp->regs = ioremap(p_reg_prop.phys_addr, p_reg_prop.reg_size); if (mp->regs == NULL) goto fail; @@ -382,11 +384,13 @@ static int init_one_mctrl(struct device_node *dp) fetch_decode_regs(mp); + mp->index = index; + list_add(&mp->list, &mctrl_list); /* Report the device. */ - printk(KERN_INFO "%s: US3 memory controller at %p [%s]\n", - dp->full_name, + printk(KERN_INFO "chmc%d: US3 memory controller at %p [%s]\n", + mp->index, mp->regs, (mp->layout_size ? "ACTIVE" : "INACTIVE")); return 0; @@ -400,19 +404,34 @@ fail: return -1; } +static int __init probe_for_string(char *name, int index) +{ + int node = prom_getchild(prom_root_node); + + while ((node = prom_searchsiblings(node, name)) != 0) { + int ret = init_one_mctrl(node, index); + + if (!ret) + index++; + + node = prom_getsibling(node); + if (!node) + break; + } + + return index; +} + static int __init chmc_init(void) { - struct device_node *dp; + int index; /* This driver is only for cheetah platforms. */ if (tlb_type != cheetah && tlb_type != cheetah_plus) return -ENODEV; - for_each_node_by_name(dp, "memory-controller") - init_one_mctrl(dp); - - for_each_node_by_name(dp, "mc-us3") - init_one_mctrl(dp); + index = probe_for_string("memory-controller", 0); + index = probe_for_string("mc-us3", index); return 0; }