> Subject: RE: [PATCH v7 01/12] mtd: core: always create master device > > Hi > > > Hello, > > > > > The mtd_master is completely different class to avoid mtd tree > disturbances. > > > It is real kernel device object, I'm not sure how we can do 'link to' > > > magic here. > > > > Maybe we can add that later if someone needs. > > > > > About MTD_PARTITIONED_MASTER - we can treat it as another partition > > and > > > create master device plus whole device partition as it's child with all > > > other > > > partitions as children of master device. > > > For unpartitioned device this mean that we create master device and > > partition > > > regardless of MTD_PARTITIONED_MASTER flag. > > > > I am not sure I follow you. I am proposing to create the mtd_master > > device in all cases. I believe this is the future-proof approach. Can > > you make this change? > > > > Regarding the hierarchy, I indeed agree with what you propose: > > mtd_master parent of whole partition device (if any) parent of > > partitions. > > > > To be sure: > > You want to have this hierarchy without MTD_PARTITIONED_MASTER: > mtd_master > \/ > |->partition1 > |->partition2 > > With MTD_PARTITIONED_MASTER flag: > > mtd_master > \/ > |->master_partition > \/ > |->partition1 > |->partition2 >
Like this? diff --git a/drivers/mtd/mtdchar.c b/drivers/mtd/mtdchar.c index 8dc4f5c493fc..391d81ad960c 100644 --- a/drivers/mtd/mtdchar.c +++ b/drivers/mtd/mtdchar.c @@ -559,7 +559,7 @@ static int mtdchar_blkpg_ioctl(struct mtd_info *mtd, /* Sanitize user input */ p.devname[BLKPG_DEVNAMELTH - 1] = '\0'; - return mtd_add_partition(mtd, p.devname, p.start, p.length); + return mtd_add_partition(mtd, p.devname, p.start, p.length, NULL); case BLKPG_DEL_PARTITION: diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c index ee46766d74f1..a32cea0ba535 100644 --- a/drivers/mtd/mtdcore.c +++ b/drivers/mtd/mtdcore.c @@ -1108,6 +1108,7 @@ int mtd_device_parse_register(struct mtd_info *mtd, const char * const *types, const struct mtd_partition *parts, int nr_parts) { + struct mtd_info *parent; int ret, err; mtd_set_dev_defaults(mtd); @@ -1116,17 +1117,31 @@ int mtd_device_parse_register(struct mtd_info *mtd, const char * const *types, if (ret) goto out; + ret = add_mtd_device(mtd, false); + if (ret) + goto out; + + if (IS_ENABLED(CONFIG_MTD_PARTITIONED_MASTER)) + { + ret = mtd_add_partition(mtd, dev_name(&mtd->dev), 0, MTDPART_SIZ_FULL, &parent); + if (ret) + goto out; + + } else { + parent = mtd; + } + /* Prefer parsed partitions over driver-provided fallback */ - ret = parse_mtd_partitions(mtd, types, parser_data); + ret = parse_mtd_partitions(parent, types, parser_data); if (ret == -EPROBE_DEFER) goto out; if (ret > 0) ret = 0; else if (nr_parts) - ret = add_mtd_partitions(mtd, parts, nr_parts); - else - ret = add_mtd_device(mtd, true); + ret = add_mtd_partitions(parent, parts, nr_parts); + else if (!IS_ENABLED(CONFIG_MTD_PARTITIONED_MASTER)) + ret = mtd_add_partition(parent, dev_name(&mtd->dev), 0, MTDPART_SIZ_FULL, NULL); if (ret) goto out; diff --git a/drivers/mtd/mtdpart.c b/drivers/mtd/mtdpart.c index 8a019cf0360d..cd5ae919b80c 100644 --- a/drivers/mtd/mtdpart.c +++ b/drivers/mtd/mtdpart.c @@ -242,7 +242,7 @@ static int mtd_add_partition_attrs(struct mtd_info *new) } int mtd_add_partition(struct mtd_info *parent, const char *name, - long long offset, long long length) + long long offset, long long length, struct mtd_info **out) { struct mtd_info *master = mtd_get_master(parent); u64 parent_size = mtd_is_partition(parent) ? @@ -281,6 +281,9 @@ int mtd_add_partition(struct mtd_info *parent, const char *name, mtd_add_partition_attrs(child); + if (*out) + *out = child; + return 0; err_remove_part: @@ -401,12 +404,6 @@ int add_mtd_partitions(struct mtd_info *parent, printk(KERN_NOTICE "Creating %d MTD partitions on \"%s\":\n", nbparts, parent->name); - if (!mtd_is_partition(parent)) { - ret = add_mtd_device(parent, IS_ENABLED(CONFIG_MTD_PARTITIONED_MASTER)); - if (ret) - return ret; - } - for (i = 0; i < nbparts; i++) { child = allocate_partition(parent, parts + i, i, cur_offset); if (IS_ERR(child)) { diff --git a/include/linux/mtd/partitions.h b/include/linux/mtd/partitions.h index b74a539ec581..5daf80df9e89 100644 --- a/include/linux/mtd/partitions.h +++ b/include/linux/mtd/partitions.h @@ -108,7 +108,7 @@ extern void deregister_mtd_parser(struct mtd_part_parser *parser); deregister_mtd_parser) int mtd_add_partition(struct mtd_info *master, const char *name, - long long offset, long long length); + long long offset, long long length, struct mtd_info **part); int mtd_del_partition(struct mtd_info *master, int partno); uint64_t mtd_get_device_size(const struct mtd_info *mtd);