[PATCH 01/11] mtd: bind the block device without leaking on failure

Simon Glass sjg at chromium.org
Thu Oct 1 08:59:39 PDT 2026


Hi Daniel,

On 2026-09-29T00:04:16, Daniel Golle <daniel at makrotopia.org> wrote:
> mtd: bind the block device without leaking on failure
>
> add_mtd_device() allocates a slot to hold the mtd_info pointer that
> mtd_bind() keeps, but drops the return value. mtd_bind() only logs and
> returns on failure, so the slot leaks. A failed kmalloc() is ignored
> too, leaving the master without a block device and no hint why its
> partitions are unreachable.
>
> Move the bind into a helper that frees the slot when mtd_bind() fails
> and warns with the errno in both cases.
>
> Fixes: e8a7453824b7 ("mtd: bind an mtd_blk device for non-NAND MTD masters")
> Signed-off-by: Daniel Golle <daniel at makrotopia.org>
>
> drivers/mtd/mtdcore.c | 37 ++++++++++++++++++++++++++-----------
>  1 file changed, 26 insertions(+), 11 deletions(-)

> diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c
> @@ -396,6 +396,31 @@ static struct device_type mtd_devtype = {
> +     /*
> +      * mtd_bind() keeps the passed pointer, so it needs storage that lives
> +      * as long as the block device; an MTD master is never removed.
> +      */

I don't think this holds for SPI flash. With DM_SPI_FLASH, 'sf probe'
calls device_remove() on the existing flash device before probing it
again (cmd/sf.c:135). spi_flash_std_remove() then calls
spi_flash_mtd_unregister() -> del_mtd_device(), and the new probe
calls add_mtd_device() again. Neither del_mtd_device() nor
device_remove() unbinds the mtd_blk child, so each 'sf probe'
allocates another slot and binds a second mtd_blk device under the
same flash device, while the old one still points at the old slot.
That leak is more frequent than the mtd_bind() failure fixed here.
Please can you either skip the bind when mtd->dev already has a
UCLASS_BLK child (device_find_first_child_by_uclass()), or unbind the
block device and free the slot in del_mtd_device(), as patch 3 does
for UBI? Either way, please update the comment.

> diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c
> @@ -396,6 +396,31 @@ static struct device_type mtd_devtype = {
> +     kfree(mtdp);
> +warn:
> +     pr_warn("mtd: %s: cannot bind a block device: %d\n", mtd->name, ret);

mtd_bind() already does pr_err("Cannot create block device\n") on
failure, so this prints two lines for one failure. Not a big deal, but
you could drop the message from mtd_bind() (the SPI NAND caller in
nand/spi/core.c already checks the return value) and keep this one,
since it has the name and errno.

Regards,
Simon



More information about the openwrt-devel mailing list