mmc_host_classdev_release() reads host->parent->of_node to decide whether to free the IDA slot, but mmc_alloc_host() does not guarantee that the parent outlives the host (only devm_mmc_alloc_host() does). So the vub300 driver can release its parent usb_device before the host, resulting in a use-after-free. Put the alias decision in host->index_is_alias at allocation time, while the parent is still valid, and use it at release time. Fixes: 10252bae863d ("mmc: core: Don't allocate IDA for OF aliases") Reported-by: syzbot+f312381a95cc080992fd@syzkaller.appspotmail.com Link: https://syzkaller.appspot.com/bug?extid=f312381a95cc080992fd Assisted-by: opencode: deepseek v4 flash Cc: stable@vger.kernel.org Signed-off-by: Adriano Cordova --- Changes since v1: - Added Assisted-by tag - put alias decision in host->index_is_alias Changes since v2: - Split patch into two logical patches - Corrected the Fixes: tag drivers/mmc/core/host.c | 3 ++- include/linux/mmc/host.h | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/mmc/core/host.c b/drivers/mmc/core/host.c index b7ce3137d452..542bb033c6da 100644 --- a/drivers/mmc/core/host.c +++ b/drivers/mmc/core/host.c @@ -67,7 +67,7 @@ static void mmc_host_classdev_release(struct device *dev) { struct mmc_host *host = cls_dev_to_mmc_host(dev); wakeup_source_unregister(host->ws); - if (of_alias_get_id(host->parent->of_node, "mmc") < 0) + if (!host->index_is_alias) ida_free(&mmc_host_ida, host->index); kfree(host); } @@ -538,6 +538,7 @@ struct mmc_host *mmc_alloc_host(int extra, struct device *dev) } host->index = index; + host->index_is_alias = (alias_id >= 0); dev_set_name(&host->class_dev, "mmc%d", host->index); host->ws = wakeup_source_register(NULL, dev_name(&host->class_dev)); diff --git a/include/linux/mmc/host.h b/include/linux/mmc/host.h index ba84f02c2a10..165d24104d3c 100644 --- a/include/linux/mmc/host.h +++ b/include/linux/mmc/host.h @@ -356,6 +356,7 @@ struct mmc_host { struct device *parent; struct device class_dev; int index; + bool index_is_alias; const struct mmc_host_ops *ops; struct mmc_pwrseq *pwrseq; unsigned int f_min; -- 2.51.0