From 2c067d906ceece9d1ec1551b3ac1d9f7bcd1c83d Mon Sep 17 00:00:00 2001 From: Thierry Reding Date: Wed, 21 Jan 2015 11:50:52 +0100 Subject: [PATCH] ata: libahci: Fix devres cleanup on failure Commit dcbe62ddaf79 ("ata: libahci: Allow using multiple regulators") releases regulators during ahci_platform_put_resources(). That doesn't work because the function is run as part of the devres machinery. Such resources are torn down in reverse order. Since the array that holds pointers to the regulators is allocated using devres after the device context to which ahci_platform_put_resources() is attached, the memory will be freed before calling ahci_platform_put_resources() and thereby causing a use-after-free error. This commit fixes this by using regular allocations for the array. The memory can then be freed after the regulators have been released. This conserves the advantages of using the managed API. Reported-by: Paul Walmsley Signed-off-by: Thierry Reding Signed-off-by: Tejun Heo --- drivers/ata/libahci_platform.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/ata/libahci_platform.c b/drivers/ata/libahci_platform.c index 73a086664ee7d..504d534ccbfe9 100644 --- a/drivers/ata/libahci_platform.c +++ b/drivers/ata/libahci_platform.c @@ -276,6 +276,7 @@ static void ahci_platform_put_resources(struct device *dev, void *res) if (hpriv->target_pwrs && hpriv->target_pwrs[c]) regulator_put(hpriv->target_pwrs[c]); + kfree(hpriv->target_pwrs); } static int ahci_platform_get_phy(struct ahci_host_priv *hpriv, u32 port, @@ -412,7 +413,7 @@ struct ahci_host_priv *ahci_platform_get_resources(struct platform_device *pdev) goto err_out; } sz = hpriv->nports * sizeof(*hpriv->target_pwrs); - hpriv->target_pwrs = devm_kzalloc(dev, sz, GFP_KERNEL); + hpriv->target_pwrs = kzalloc(sz, GFP_KERNEL); if (!hpriv->target_pwrs) { rc = -ENOMEM; goto err_out; -- 2.39.5