0017-clk-starfive-Avoid-casting-iomem-pointers.patch 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128
  1. From d9d4e0fb44a50cace195e1639cfb23e518e17e88 Mon Sep 17 00:00:00 2001
  2. From: Stephen Boyd <[email protected]>
  3. Date: Thu, 13 Apr 2023 13:55:28 -0700
  4. Subject: [PATCH 017/122] clk: starfive: Avoid casting iomem pointers
  5. Let's use a wrapper struct for the auxiliary_device made in
  6. jh7110_reset_controller_register() so that we can stop casting iomem
  7. pointers. The casts trip up tools like sparse, and make for some awkward
  8. casts that are largely unnecessary. While we're here, change the
  9. allocation from devm and actually free the auxiliary_device memory in
  10. the release function. This avoids any use after free problems where the
  11. parent device driver is unbound from the device but the
  12. auxiliuary_device is still in use accessing devm freed memory.
  13. Cc: Tommaso Merciai <[email protected]>
  14. Cc: Emil Renner Berthing <[email protected]>
  15. Cc: Hal Feng <[email protected]>
  16. Cc: Conor Dooley <[email protected]>
  17. Cc: Xingyu Wu <[email protected]>
  18. Reviewed-by: Conor Dooley <[email protected]>
  19. Fixes: edab7204afe5 ("clk: starfive: Add StarFive JH7110 system clock driver")
  20. Signed-off-by: Stephen Boyd <[email protected]>
  21. Link: https://lore.kernel.org/r/[email protected]
  22. ---
  23. drivers/clk/starfive/clk-starfive-jh7110-sys.c | 15 ++++++++++++---
  24. drivers/reset/starfive/reset-starfive-jh7110.c | 9 ++++++---
  25. include/soc/starfive/reset-starfive-jh71x0.h | 17 +++++++++++++++++
  26. 3 files changed, 35 insertions(+), 6 deletions(-)
  27. create mode 100644 include/soc/starfive/reset-starfive-jh71x0.h
  28. --- a/drivers/clk/starfive/clk-starfive-jh7110-sys.c
  29. +++ b/drivers/clk/starfive/clk-starfive-jh7110-sys.c
  30. @@ -11,6 +11,9 @@
  31. #include <linux/init.h>
  32. #include <linux/io.h>
  33. #include <linux/platform_device.h>
  34. +#include <linux/slab.h>
  35. +
  36. +#include <soc/starfive/reset-starfive-jh71x0.h>
  37. #include <dt-bindings/clock/starfive,jh7110-crg.h>
  38. @@ -335,26 +338,32 @@ static void jh7110_reset_unregister_adev
  39. struct auxiliary_device *adev = _adev;
  40. auxiliary_device_delete(adev);
  41. + auxiliary_device_uninit(adev);
  42. }
  43. static void jh7110_reset_adev_release(struct device *dev)
  44. {
  45. struct auxiliary_device *adev = to_auxiliary_dev(dev);
  46. + struct jh71x0_reset_adev *rdev = to_jh71x0_reset_adev(adev);
  47. - auxiliary_device_uninit(adev);
  48. + kfree(rdev);
  49. }
  50. int jh7110_reset_controller_register(struct jh71x0_clk_priv *priv,
  51. const char *adev_name,
  52. u32 adev_id)
  53. {
  54. + struct jh71x0_reset_adev *rdev;
  55. struct auxiliary_device *adev;
  56. int ret;
  57. - adev = devm_kzalloc(priv->dev, sizeof(*adev), GFP_KERNEL);
  58. - if (!adev)
  59. + rdev = kzalloc(sizeof(*rdev), GFP_KERNEL);
  60. + if (!rdev)
  61. return -ENOMEM;
  62. + rdev->base = priv->base;
  63. +
  64. + adev = &rdev->adev;
  65. adev->name = adev_name;
  66. adev->dev.parent = priv->dev;
  67. adev->dev.release = jh7110_reset_adev_release;
  68. --- a/drivers/reset/starfive/reset-starfive-jh7110.c
  69. +++ b/drivers/reset/starfive/reset-starfive-jh7110.c
  70. @@ -7,6 +7,8 @@
  71. #include <linux/auxiliary_bus.h>
  72. +#include <soc/starfive/reset-starfive-jh71x0.h>
  73. +
  74. #include "reset-starfive-jh71x0.h"
  75. #include <dt-bindings/reset/starfive,jh7110-crg.h>
  76. @@ -33,14 +35,15 @@ static int jh7110_reset_probe(struct aux
  77. const struct auxiliary_device_id *id)
  78. {
  79. struct jh7110_reset_info *info = (struct jh7110_reset_info *)(id->driver_data);
  80. - void __iomem **base = (void __iomem **)dev_get_drvdata(adev->dev.parent);
  81. + struct jh71x0_reset_adev *rdev = to_jh71x0_reset_adev(adev);
  82. + void __iomem *base = rdev->base;
  83. if (!info || !base)
  84. return -ENODEV;
  85. return reset_starfive_jh71x0_register(&adev->dev, adev->dev.parent->of_node,
  86. - *base + info->assert_offset,
  87. - *base + info->status_offset,
  88. + base + info->assert_offset,
  89. + base + info->status_offset,
  90. NULL,
  91. info->nr_resets,
  92. NULL);
  93. --- /dev/null
  94. +++ b/include/soc/starfive/reset-starfive-jh71x0.h
  95. @@ -0,0 +1,17 @@
  96. +/* SPDX-License-Identifier: GPL-2.0 */
  97. +#ifndef __SOC_STARFIVE_RESET_JH71X0_H
  98. +#define __SOC_STARFIVE_RESET_JH71X0_H
  99. +
  100. +#include <linux/auxiliary_bus.h>
  101. +#include <linux/compiler_types.h>
  102. +#include <linux/container_of.h>
  103. +
  104. +struct jh71x0_reset_adev {
  105. + void __iomem *base;
  106. + struct auxiliary_device adev;
  107. +};
  108. +
  109. +#define to_jh71x0_reset_adev(_adev) \
  110. + container_of((_adev), struct jh71x0_reset_adev, adev)
  111. +
  112. +#endif