[PATCH 2/4] soc: qcom: stats: don't crash if DDR offset contains invalid data

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The stats ram on sm8150 platform contains invalid data at the
DDR_DYNAMIC_OFFSET. Most likely this is because the platform didn't
support DDR sleep stats. However this platform uses generic
"qcom,rpmh-stats" compatible, which implies presense of the DDR data.
Add safety net to prevent old DTB files from crashing the
qcom,rpmh-stats driver.

Fixes: e84e61bdb97c ("soc: qcom: stats: Add DDR sleep stats")
Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@xxxxxxxxxx>
---
 drivers/soc/qcom/qcom_stats.c | 10 ++++++++--
 1 file changed, 8 insertions(+), 2 deletions(-)

diff --git a/drivers/soc/qcom/qcom_stats.c b/drivers/soc/qcom/qcom_stats.c
index 4763d62a8cb0..813c9f3c6bec 100644
--- a/drivers/soc/qcom/qcom_stats.c
+++ b/drivers/soc/qcom/qcom_stats.c
@@ -319,6 +319,7 @@ static void qcom_create_subsystem_stat_files(struct dentry *root,
 static int qcom_create_ddr_stats_files(struct device *dev,
 				       struct dentry *root,
 				       void __iomem *reg,
+				       resource_size_t reg_size,
 				       const struct stats_config *config)
 {
 	struct ddr_stats_data *ddrd;
@@ -337,6 +338,8 @@ static int qcom_create_ddr_stats_files(struct device *dev,
 
 	/* Get the offset of DDR stats */
 	stats_offset = readl(reg + DDR_DYNAMIC_OFFSET) & DDR_OFFSET_MASK;
+	if (stats_offset >= reg_size || stats_offset % 4)
+		return -EINVAL;
 	ddrd->base = reg + stats_offset;
 
 	/* Check if DDR stats are present */
@@ -364,6 +367,7 @@ static int qcom_stats_probe(struct platform_device *pdev)
 	void __iomem *reg;
 	struct dentry *root;
 	const struct stats_config *config;
+	struct resource *res;
 	struct stats_data *d;
 	int i, ret;
 
@@ -371,7 +375,7 @@ static int qcom_stats_probe(struct platform_device *pdev)
 	if (!config)
 		return -ENODEV;
 
-	reg = devm_platform_get_and_ioremap_resource(pdev, 0, NULL);
+	reg = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
 	if (IS_ERR(reg))
 		return -ENOMEM;
 
@@ -387,7 +391,9 @@ static int qcom_stats_probe(struct platform_device *pdev)
 
 	qcom_create_subsystem_stat_files(root, config);
 	qcom_create_soc_sleep_stat_files(root, reg, d, config);
-	ret = qcom_create_ddr_stats_files(&pdev->dev, root, reg, config);
+	ret = qcom_create_ddr_stats_files(&pdev->dev, root, reg,
+					  resource_size(res),
+					  config);
 	if (ret) {
 		debugfs_remove_recursive(root);
 		return ret;
-- 
2.39.2





[Index of Archives]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [Linux for Sparc]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux MIPS]     [ECOS]     [Asterisk Internet PBX]     [Linux API]

  Powered by Linux