aboutsummaryrefslogtreecommitdiffstats
path: root/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch
diff options
context:
space:
mode:
Diffstat (limited to 'target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch')
-rw-r--r--target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch166
1 files changed, 166 insertions, 0 deletions
diff --git a/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch b/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch
new file mode 100644
index 0000000000..3b6e6e57f5
--- /dev/null
+++ b/target/linux/generic/backport-5.15/813-v6.5-0004-nvmem-rockchip-otp-Add-clks-and-reg_read-to-rockchip.patch
@@ -0,0 +1,166 @@
+From 8dc61364164e79e44c07fa2ac0a7b6939f00d5db Mon Sep 17 00:00:00 2001
+From: Cristian Ciocaltea <cristian.ciocaltea@collabora.com>
+Date: Sun, 11 Jun 2023 15:03:13 +0100
+Subject: [PATCH] nvmem: rockchip-otp: Add clks and reg_read to rockchip_data
+
+In preparation to support new Rockchip OTP memory devices with different
+clock configurations and register layout, extend rockchip_data struct
+with the related members: clks, num_clks, reg_read.
+
+Additionally, to avoid managing redundant driver data, drop num_clks
+member from rockchip_otp struct and update all references to point to
+the equivalent member in rockchip_data.
+
+Signed-off-by: Cristian Ciocaltea <cristian.ciocaltea@collabora.com>
+Tested-by: Vincent Legoll <vincent.legoll@gmail.com>
+Reviewed-by: Heiko Stuebner <heiko@sntech.de>
+Signed-off-by: Srinivas Kandagatla <srinivas.kandagatla@linaro.org>
+Message-ID: <20230611140330.154222-10-srinivas.kandagatla@linaro.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/nvmem/rockchip-otp.c | 79 ++++++++++++++++++++++--------------
+ 1 file changed, 49 insertions(+), 30 deletions(-)
+
+--- a/drivers/nvmem/rockchip-otp.c
++++ b/drivers/nvmem/rockchip-otp.c
+@@ -54,21 +54,19 @@
+
+ #define OTPC_TIMEOUT 10000
+
++struct rockchip_data {
++ int size;
++ const char * const *clks;
++ int num_clks;
++ nvmem_reg_read_t reg_read;
++};
++
+ struct rockchip_otp {
+ struct device *dev;
+ void __iomem *base;
+- struct clk_bulk_data *clks;
+- int num_clks;
++ struct clk_bulk_data *clks;
+ struct reset_control *rst;
+-};
+-
+-/* list of required clocks */
+-static const char * const rockchip_otp_clocks[] = {
+- "otp", "apb_pclk", "phy",
+-};
+-
+-struct rockchip_data {
+- int size;
++ const struct rockchip_data *data;
+ };
+
+ static int rockchip_otp_reset(struct rockchip_otp *otp)
+@@ -132,29 +130,23 @@ static int rockchip_otp_ecc_enable(struc
+ return ret;
+ }
+
+-static int rockchip_otp_read(void *context, unsigned int offset,
+- void *val, size_t bytes)
++static int px30_otp_read(void *context, unsigned int offset,
++ void *val, size_t bytes)
+ {
+ struct rockchip_otp *otp = context;
+ u8 *buf = val;
+- int ret = 0;
+-
+- ret = clk_bulk_prepare_enable(otp->num_clks, otp->clks);
+- if (ret < 0) {
+- dev_err(otp->dev, "failed to prepare/enable clks\n");
+- return ret;
+- }
++ int ret;
+
+ ret = rockchip_otp_reset(otp);
+ if (ret) {
+ dev_err(otp->dev, "failed to reset otp phy\n");
+- goto disable_clks;
++ return ret;
+ }
+
+ ret = rockchip_otp_ecc_enable(otp, false);
+ if (ret < 0) {
+ dev_err(otp->dev, "rockchip_otp_ecc_enable err\n");
+- goto disable_clks;
++ return ret;
+ }
+
+ writel(OTPC_USE_USER | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL);
+@@ -174,8 +166,28 @@ static int rockchip_otp_read(void *conte
+
+ read_end:
+ writel(0x0 | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL);
+-disable_clks:
+- clk_bulk_disable_unprepare(otp->num_clks, otp->clks);
++
++ return ret;
++}
++
++static int rockchip_otp_read(void *context, unsigned int offset,
++ void *val, size_t bytes)
++{
++ struct rockchip_otp *otp = context;
++ int ret;
++
++ if (!otp->data || !otp->data->reg_read)
++ return -EINVAL;
++
++ ret = clk_bulk_prepare_enable(otp->data->num_clks, otp->clks);
++ if (ret < 0) {
++ dev_err(otp->dev, "failed to prepare/enable clks\n");
++ return ret;
++ }
++
++ ret = otp->data->reg_read(context, offset, val, bytes);
++
++ clk_bulk_disable_unprepare(otp->data->num_clks, otp->clks);
+
+ return ret;
+ }
+@@ -189,8 +201,15 @@ static struct nvmem_config otp_config =
+ .reg_read = rockchip_otp_read,
+ };
+
++static const char * const px30_otp_clocks[] = {
++ "otp", "apb_pclk", "phy",
++};
++
+ static const struct rockchip_data px30_data = {
+ .size = 0x40,
++ .clks = px30_otp_clocks,
++ .num_clks = ARRAY_SIZE(px30_otp_clocks),
++ .reg_read = px30_otp_read,
+ };
+
+ static const struct of_device_id rockchip_otp_match[] = {
+@@ -225,21 +244,21 @@ static int rockchip_otp_probe(struct pla
+ if (!otp)
+ return -ENOMEM;
+
++ otp->data = data;
+ otp->dev = dev;
+ otp->base = devm_platform_ioremap_resource(pdev, 0);
+ if (IS_ERR(otp->base))
+ return PTR_ERR(otp->base);
+
+- otp->num_clks = ARRAY_SIZE(rockchip_otp_clocks);
+- otp->clks = devm_kcalloc(dev, otp->num_clks,
+- sizeof(*otp->clks), GFP_KERNEL);
++ otp->clks = devm_kcalloc(dev, data->num_clks, sizeof(*otp->clks),
++ GFP_KERNEL);
+ if (!otp->clks)
+ return -ENOMEM;
+
+- for (i = 0; i < otp->num_clks; ++i)
+- otp->clks[i].id = rockchip_otp_clocks[i];
++ for (i = 0; i < data->num_clks; ++i)
++ otp->clks[i].id = data->clks[i];
+
+- ret = devm_clk_bulk_get(dev, otp->num_clks, otp->clks);
++ ret = devm_clk_bulk_get(dev, data->num_clks, otp->clks);
+ if (ret)
+ return ret;
+