aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mtd/maps/physmap_of.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/mtd/maps/physmap_of.c')
-rw-r--r--drivers/mtd/maps/physmap_of.c88
1 files changed, 27 insertions, 61 deletions
diff --git a/drivers/mtd/maps/physmap_of.c b/drivers/mtd/maps/physmap_of.c
index aeed9ea79714..49acd4171893 100644
--- a/drivers/mtd/maps/physmap_of.c
+++ b/drivers/mtd/maps/physmap_of.c
@@ -80,64 +80,6 @@ static int parse_obsolete_partitions(struct of_device *dev,
80 80
81 return nr_parts; 81 return nr_parts;
82} 82}
83
84static int __devinit parse_partitions(struct of_flash *info,
85 struct of_device *dev)
86{
87 const char *partname;
88 static const char *part_probe_types[]
89 = { "cmdlinepart", "RedBoot", NULL };
90 struct device_node *dp = dev->node, *pp;
91 int nr_parts, i;
92
93 /* First look for RedBoot table or partitions on the command
94 * line, these take precedence over device tree information */
95 nr_parts = parse_mtd_partitions(info->mtd, part_probe_types,
96 &info->parts, 0);
97 if (nr_parts > 0) {
98 add_mtd_partitions(info->mtd, info->parts, nr_parts);
99 return 0;
100 }
101
102 /* First count the subnodes */
103 nr_parts = 0;
104 for (pp = dp->child; pp; pp = pp->sibling)
105 nr_parts++;
106
107 if (nr_parts == 0)
108 return parse_obsolete_partitions(dev, info, dp);
109
110 info->parts = kzalloc(nr_parts * sizeof(*info->parts),
111 GFP_KERNEL);
112 if (!info->parts)
113 return -ENOMEM;
114
115 for (pp = dp->child, i = 0; pp; pp = pp->sibling, i++) {
116 const u32 *reg;
117 int len;
118
119 reg = of_get_property(pp, "reg", &len);
120 if (!reg || (len != 2*sizeof(u32))) {
121 dev_err(&dev->dev, "Invalid 'reg' on %s\n",
122 dp->full_name);
123 kfree(info->parts);
124 info->parts = NULL;
125 return -EINVAL;
126 }
127 info->parts[i].offset = reg[0];
128 info->parts[i].size = reg[1];
129
130 partname = of_get_property(pp, "label", &len);
131 if (!partname)
132 partname = of_get_property(pp, "name", &len);
133 info->parts[i].name = (char *)partname;
134
135 if (of_get_property(pp, "read-only", &len))
136 info->parts[i].mask_flags = MTD_WRITEABLE;
137 }
138
139 return nr_parts;
140}
141#else /* MTD_PARTITIONS */ 83#else /* MTD_PARTITIONS */
142#define OF_FLASH_PARTS(info) (0) 84#define OF_FLASH_PARTS(info) (0)
143#define parse_partitions(info, dev) (0) 85#define parse_partitions(info, dev) (0)
@@ -212,6 +154,10 @@ static struct mtd_info * __devinit obsolete_probe(struct of_device *dev,
212static int __devinit of_flash_probe(struct of_device *dev, 154static int __devinit of_flash_probe(struct of_device *dev,
213 const struct of_device_id *match) 155 const struct of_device_id *match)
214{ 156{
157#ifdef CONFIG_MTD_PARTITIONS
158 static const char *part_probe_types[]
159 = { "cmdlinepart", "RedBoot", NULL };
160#endif
215 struct device_node *dp = dev->node; 161 struct device_node *dp = dev->node;
216 struct resource res; 162 struct resource res;
217 struct of_flash *info; 163 struct of_flash *info;
@@ -274,13 +220,33 @@ static int __devinit of_flash_probe(struct of_device *dev,
274 } 220 }
275 info->mtd->owner = THIS_MODULE; 221 info->mtd->owner = THIS_MODULE;
276 222
277 err = parse_partitions(info, dev); 223#ifdef CONFIG_MTD_PARTITIONS
224 /* First look for RedBoot table or partitions on the command
225 * line, these take precedence over device tree information */
226 err = parse_mtd_partitions(info->mtd, part_probe_types,
227 &info->parts, 0);
278 if (err < 0) 228 if (err < 0)
279 goto err_out; 229 return err;
230
231#ifdef CONFIG_MTD_OF_PARTS
232 if (err == 0) {
233 err = of_mtd_parse_partitions(&dev->dev, info->mtd,
234 dp, &info->parts);
235 if (err < 0)
236 return err;
237 }
238#endif
239
240 if (err == 0) {
241 err = parse_obsolete_partitions(dev, info, dp);
242 if (err < 0)
243 return err;
244 }
280 245
281 if (err > 0) 246 if (err > 0)
282 add_mtd_partitions(info->mtd, OF_FLASH_PARTS(info), err); 247 add_mtd_partitions(info->mtd, info->parts, err);
283 else 248 else
249#endif
284 add_mtd_device(info->mtd); 250 add_mtd_device(info->mtd);
285 251
286 return 0; 252 return 0;