mtd: implement proper partition handling
Instead of collecting partitions in a flat list, create a hierarchy within the mtd_info structure: use a partitions list to keep track of the partitions of an MTD device (which might be itself a partition of another MTD device), a pointer to the parent device (NULL when the MTD device is the root one, not a partition). By also saving directly in mtd_info the offset of the partition, we can get rid of the mtd_part structure. While at it, be consistent in the naming of the mtd_info structures to ease the understanding of the new hierarchy: these structures are usually called 'mtd', unless there are multiple instances of the same structure. In this case, there is usually a parent/child bound so we will call them 'parent' and 'child'. Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com> Link: https://lore.kernel.org/linux-mtd/20200114090952.11232-1-miquel.raynal@bootlin.com
This commit is contained in:
@@ -349,6 +349,7 @@ static int mtdchar_writeoob(struct file *file, struct mtd_info *mtd,
|
||||
uint64_t start, uint32_t length, void __user *ptr,
|
||||
uint32_t __user *retp)
|
||||
{
|
||||
struct mtd_info *master = mtd_get_master(mtd);
|
||||
struct mtd_file_info *mfi = file->private_data;
|
||||
struct mtd_oob_ops ops = {};
|
||||
uint32_t retlen;
|
||||
@@ -360,7 +361,7 @@ static int mtdchar_writeoob(struct file *file, struct mtd_info *mtd,
|
||||
if (length > 4096)
|
||||
return -EINVAL;
|
||||
|
||||
if (!mtd->_write_oob)
|
||||
if (!master->_write_oob)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
ops.ooblen = length;
|
||||
@@ -586,6 +587,7 @@ static int mtdchar_blkpg_ioctl(struct mtd_info *mtd,
|
||||
static int mtdchar_write_ioctl(struct mtd_info *mtd,
|
||||
struct mtd_write_req __user *argp)
|
||||
{
|
||||
struct mtd_info *master = mtd_get_master(mtd);
|
||||
struct mtd_write_req req;
|
||||
struct mtd_oob_ops ops = {};
|
||||
const void __user *usr_data, *usr_oob;
|
||||
@@ -597,9 +599,8 @@ static int mtdchar_write_ioctl(struct mtd_info *mtd,
|
||||
usr_data = (const void __user *)(uintptr_t)req.usr_data;
|
||||
usr_oob = (const void __user *)(uintptr_t)req.usr_oob;
|
||||
|
||||
if (!mtd->_write_oob)
|
||||
if (!master->_write_oob)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
ops.mode = req.mode;
|
||||
ops.len = (size_t)req.len;
|
||||
ops.ooblen = (size_t)req.ooblen;
|
||||
@@ -635,6 +636,7 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
||||
{
|
||||
struct mtd_file_info *mfi = file->private_data;
|
||||
struct mtd_info *mtd = mfi->mtd;
|
||||
struct mtd_info *master = mtd_get_master(mtd);
|
||||
void __user *argp = (void __user *)arg;
|
||||
int ret = 0;
|
||||
struct mtd_info_user info;
|
||||
@@ -824,7 +826,7 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
||||
{
|
||||
struct nand_oobinfo oi;
|
||||
|
||||
if (!mtd->ooblayout)
|
||||
if (!master->ooblayout)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
ret = get_oobinfo(mtd, &oi);
|
||||
@@ -918,7 +920,7 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
||||
{
|
||||
struct nand_ecclayout_user *usrlay;
|
||||
|
||||
if (!mtd->ooblayout)
|
||||
if (!master->ooblayout)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
usrlay = kmalloc(sizeof(*usrlay), GFP_KERNEL);
|
||||
|
Reference in New Issue
Block a user