perf/imx_ddr: Fix cpu hotplug state cleanup
[ Upstream commit9ee68b314e
] This driver allocates a dynamic cpu hotplug state but never releases it. If reloaded in a loop it will quickly trigger a WARN message: "No more dynamic states available for CPU hotplug" Fix by calling cpuhp_remove_multi_state on remove like several other perf pmu drivers. Also fix the cleanup logic on probe error paths: add the missing cpuhp_remove_multi_state call and properly check the return value from cpuhp_state_add_instant_nocalls. Fixes:9a66d36cc7
("drivers/perf: imx_ddr: Add DDR performance counter support to perf") Acked-by: Joakim Zhang <qiangqing.zhang@nxp.com> Signed-off-by: Leonard Crestez <leonard.crestez@nxp.com> Signed-off-by: Will Deacon <will@kernel.org> Signed-off-by: Sasha Levin <sashal@kernel.org>
This commit is contained in:
parent
994b203b61
commit
9112d1ef5a
|
@ -572,13 +572,17 @@ static int ddr_perf_probe(struct platform_device *pdev)
|
|||
|
||||
if (ret < 0) {
|
||||
dev_err(&pdev->dev, "cpuhp_setup_state_multi failed\n");
|
||||
goto ddr_perf_err;
|
||||
goto cpuhp_state_err;
|
||||
}
|
||||
|
||||
pmu->cpuhp_state = ret;
|
||||
|
||||
/* Register the pmu instance for cpu hotplug */
|
||||
cpuhp_state_add_instance_nocalls(pmu->cpuhp_state, &pmu->node);
|
||||
ret = cpuhp_state_add_instance_nocalls(pmu->cpuhp_state, &pmu->node);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "Error %d registering hotplug\n", ret);
|
||||
goto cpuhp_instance_err;
|
||||
}
|
||||
|
||||
/* Request irq */
|
||||
irq = of_irq_get(np, 0);
|
||||
|
@ -612,9 +616,10 @@ static int ddr_perf_probe(struct platform_device *pdev)
|
|||
return 0;
|
||||
|
||||
ddr_perf_err:
|
||||
if (pmu->cpuhp_state)
|
||||
cpuhp_state_remove_instance_nocalls(pmu->cpuhp_state, &pmu->node);
|
||||
|
||||
cpuhp_state_remove_instance_nocalls(pmu->cpuhp_state, &pmu->node);
|
||||
cpuhp_instance_err:
|
||||
cpuhp_remove_multi_state(pmu->cpuhp_state);
|
||||
cpuhp_state_err:
|
||||
ida_simple_remove(&ddr_ida, pmu->id);
|
||||
dev_warn(&pdev->dev, "i.MX8 DDR Perf PMU failed (%d), disabled\n", ret);
|
||||
return ret;
|
||||
|
@ -625,6 +630,7 @@ static int ddr_perf_remove(struct platform_device *pdev)
|
|||
struct ddr_pmu *pmu = platform_get_drvdata(pdev);
|
||||
|
||||
cpuhp_state_remove_instance_nocalls(pmu->cpuhp_state, &pmu->node);
|
||||
cpuhp_remove_multi_state(pmu->cpuhp_state);
|
||||
irq_set_affinity_hint(pmu->irq, NULL);
|
||||
|
||||
perf_pmu_unregister(&pmu->pmu);
|
||||
|
|
Loading…
Reference in New Issue