1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * Rockchip OTP Driver 4 * 5 * Copyright (c) 2018 Rockchip Electronics Co. Ltd. 6 * Author: Finley Xiao <finley.xiao@rock-chips.com> 7 */ 8 9 #include <linux/clk.h> 10 #include <linux/delay.h> 11 #include <linux/device.h> 12 #include <linux/io.h> 13 #include <linux/iopoll.h> 14 #include <linux/module.h> 15 #include <linux/nvmem-provider.h> 16 #include <linux/reset.h> 17 #include <linux/slab.h> 18 #include <linux/of.h> 19 #include <linux/of_platform.h> 20 #include <linux/platform_device.h> 21 22 /* OTP Register Offsets */ 23 #define OTPC_SBPI_CTRL 0x0020 24 #define OTPC_SBPI_CMD_VALID_PRE 0x0024 25 #define OTPC_SBPI_CS_VALID_PRE 0x0028 26 #define OTPC_SBPI_STATUS 0x002C 27 #define OTPC_USER_CTRL 0x0100 28 #define OTPC_USER_ADDR 0x0104 29 #define OTPC_USER_ENABLE 0x0108 30 #define OTPC_USER_Q 0x0124 31 #define OTPC_INT_STATUS 0x0304 32 #define OTPC_SBPI_CMD0_OFFSET 0x1000 33 #define OTPC_SBPI_CMD1_OFFSET 0x1004 34 35 /* OTP Register bits and masks */ 36 #define OTPC_USER_ADDR_MASK GENMASK(31, 16) 37 #define OTPC_USE_USER BIT(0) 38 #define OTPC_USE_USER_MASK GENMASK(16, 16) 39 #define OTPC_USER_FSM_ENABLE BIT(0) 40 #define OTPC_USER_FSM_ENABLE_MASK GENMASK(16, 16) 41 #define OTPC_SBPI_DONE BIT(1) 42 #define OTPC_USER_DONE BIT(2) 43 44 #define SBPI_DAP_ADDR 0x02 45 #define SBPI_DAP_ADDR_SHIFT 8 46 #define SBPI_DAP_ADDR_MASK GENMASK(31, 24) 47 #define SBPI_CMD_VALID_MASK GENMASK(31, 16) 48 #define SBPI_DAP_CMD_WRF 0xC0 49 #define SBPI_DAP_REG_ECC 0x3A 50 #define SBPI_ECC_ENABLE 0x00 51 #define SBPI_ECC_DISABLE 0x09 52 #define SBPI_ENABLE BIT(0) 53 #define SBPI_ENABLE_MASK GENMASK(16, 16) 54 55 #define OTPC_TIMEOUT 10000 56 57 /* RK3588 Register */ 58 #define RK3588_OTPC_AUTO_CTRL 0x04 59 #define RK3588_OTPC_AUTO_EN 0x08 60 #define RK3588_OTPC_INT_ST 0x84 61 #define RK3588_OTPC_DOUT0 0x20 62 #define RK3588_NO_SECURE_OFFSET 0x300 63 #define RK3588_NBYTES 4 64 #define RK3588_BURST_NUM 1 65 #define RK3588_BURST_SHIFT 8 66 #define RK3588_ADDR_SHIFT 16 67 #define RK3588_AUTO_EN BIT(0) 68 #define RK3588_RD_DONE BIT(1) 69 70 struct rockchip_data { 71 int size; 72 const char * const *clks; 73 int num_clks; 74 nvmem_reg_read_t reg_read; 75 }; 76 77 struct rockchip_otp { 78 struct device *dev; 79 void __iomem *base; 80 struct clk_bulk_data *clks; 81 struct reset_control *rst; 82 const struct rockchip_data *data; 83 }; 84 85 static int rockchip_otp_reset(struct rockchip_otp *otp) 86 { 87 int ret; 88 89 ret = reset_control_assert(otp->rst); 90 if (ret) { 91 dev_err(otp->dev, "failed to assert otp phy %d\n", ret); 92 return ret; 93 } 94 95 udelay(2); 96 97 ret = reset_control_deassert(otp->rst); 98 if (ret) { 99 dev_err(otp->dev, "failed to deassert otp phy %d\n", ret); 100 return ret; 101 } 102 103 return 0; 104 } 105 106 static int rockchip_otp_wait_status(struct rockchip_otp *otp, 107 unsigned int reg, u32 flag) 108 { 109 u32 status = 0; 110 int ret; 111 112 ret = readl_poll_timeout_atomic(otp->base + reg, status, 113 (status & flag), 1, OTPC_TIMEOUT); 114 if (ret) 115 return ret; 116 117 /* clean int status */ 118 writel(flag, otp->base + reg); 119 120 return 0; 121 } 122 123 static int rockchip_otp_ecc_enable(struct rockchip_otp *otp, bool enable) 124 { 125 int ret = 0; 126 127 writel(SBPI_DAP_ADDR_MASK | (SBPI_DAP_ADDR << SBPI_DAP_ADDR_SHIFT), 128 otp->base + OTPC_SBPI_CTRL); 129 130 writel(SBPI_CMD_VALID_MASK | 0x1, otp->base + OTPC_SBPI_CMD_VALID_PRE); 131 writel(SBPI_DAP_CMD_WRF | SBPI_DAP_REG_ECC, 132 otp->base + OTPC_SBPI_CMD0_OFFSET); 133 if (enable) 134 writel(SBPI_ECC_ENABLE, otp->base + OTPC_SBPI_CMD1_OFFSET); 135 else 136 writel(SBPI_ECC_DISABLE, otp->base + OTPC_SBPI_CMD1_OFFSET); 137 138 writel(SBPI_ENABLE_MASK | SBPI_ENABLE, otp->base + OTPC_SBPI_CTRL); 139 140 ret = rockchip_otp_wait_status(otp, OTPC_INT_STATUS, OTPC_SBPI_DONE); 141 if (ret < 0) 142 dev_err(otp->dev, "timeout during ecc_enable\n"); 143 144 return ret; 145 } 146 147 static int px30_otp_read(void *context, unsigned int offset, 148 void *val, size_t bytes) 149 { 150 struct rockchip_otp *otp = context; 151 u8 *buf = val; 152 int ret; 153 154 ret = rockchip_otp_reset(otp); 155 if (ret) { 156 dev_err(otp->dev, "failed to reset otp phy\n"); 157 return ret; 158 } 159 160 ret = rockchip_otp_ecc_enable(otp, false); 161 if (ret < 0) { 162 dev_err(otp->dev, "rockchip_otp_ecc_enable err\n"); 163 return ret; 164 } 165 166 writel(OTPC_USE_USER | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL); 167 udelay(5); 168 while (bytes--) { 169 writel(offset++ | OTPC_USER_ADDR_MASK, 170 otp->base + OTPC_USER_ADDR); 171 writel(OTPC_USER_FSM_ENABLE | OTPC_USER_FSM_ENABLE_MASK, 172 otp->base + OTPC_USER_ENABLE); 173 ret = rockchip_otp_wait_status(otp, OTPC_INT_STATUS, OTPC_USER_DONE); 174 if (ret < 0) { 175 dev_err(otp->dev, "timeout during read setup\n"); 176 goto read_end; 177 } 178 *buf++ = readb(otp->base + OTPC_USER_Q); 179 } 180 181 read_end: 182 writel(0x0 | OTPC_USE_USER_MASK, otp->base + OTPC_USER_CTRL); 183 184 return ret; 185 } 186 187 static int rk3588_otp_read(void *context, unsigned int offset, 188 void *val, size_t bytes) 189 { 190 struct rockchip_otp *otp = context; 191 unsigned int addr_start, addr_end, addr_len; 192 int ret, i = 0; 193 u32 data; 194 u8 *buf; 195 196 addr_start = round_down(offset, RK3588_NBYTES) / RK3588_NBYTES; 197 addr_end = round_up(offset + bytes, RK3588_NBYTES) / RK3588_NBYTES; 198 addr_len = addr_end - addr_start; 199 addr_start += RK3588_NO_SECURE_OFFSET; 200 201 buf = kzalloc(array_size(addr_len, RK3588_NBYTES), GFP_KERNEL); 202 if (!buf) 203 return -ENOMEM; 204 205 while (addr_len--) { 206 writel((addr_start << RK3588_ADDR_SHIFT) | 207 (RK3588_BURST_NUM << RK3588_BURST_SHIFT), 208 otp->base + RK3588_OTPC_AUTO_CTRL); 209 writel(RK3588_AUTO_EN, otp->base + RK3588_OTPC_AUTO_EN); 210 211 ret = rockchip_otp_wait_status(otp, RK3588_OTPC_INT_ST, 212 RK3588_RD_DONE); 213 if (ret < 0) { 214 dev_err(otp->dev, "timeout during read setup\n"); 215 goto read_end; 216 } 217 218 data = readl(otp->base + RK3588_OTPC_DOUT0); 219 memcpy(&buf[i], &data, RK3588_NBYTES); 220 221 i += RK3588_NBYTES; 222 addr_start++; 223 } 224 225 memcpy(val, buf + offset % RK3588_NBYTES, bytes); 226 227 read_end: 228 kfree(buf); 229 230 return ret; 231 } 232 233 static int rockchip_otp_read(void *context, unsigned int offset, 234 void *val, size_t bytes) 235 { 236 struct rockchip_otp *otp = context; 237 int ret; 238 239 if (!otp->data || !otp->data->reg_read) 240 return -EINVAL; 241 242 ret = clk_bulk_prepare_enable(otp->data->num_clks, otp->clks); 243 if (ret < 0) { 244 dev_err(otp->dev, "failed to prepare/enable clks\n"); 245 return ret; 246 } 247 248 ret = otp->data->reg_read(context, offset, val, bytes); 249 250 clk_bulk_disable_unprepare(otp->data->num_clks, otp->clks); 251 252 return ret; 253 } 254 255 static struct nvmem_config otp_config = { 256 .name = "rockchip-otp", 257 .owner = THIS_MODULE, 258 .read_only = true, 259 .stride = 1, 260 .word_size = 1, 261 .reg_read = rockchip_otp_read, 262 }; 263 264 static const char * const px30_otp_clocks[] = { 265 "otp", "apb_pclk", "phy", 266 }; 267 268 static const struct rockchip_data px30_data = { 269 .size = 0x40, 270 .clks = px30_otp_clocks, 271 .num_clks = ARRAY_SIZE(px30_otp_clocks), 272 .reg_read = px30_otp_read, 273 }; 274 275 static const char * const rk3588_otp_clocks[] = { 276 "otp", "apb_pclk", "phy", "arb", 277 }; 278 279 static const struct rockchip_data rk3588_data = { 280 .size = 0x400, 281 .clks = rk3588_otp_clocks, 282 .num_clks = ARRAY_SIZE(rk3588_otp_clocks), 283 .reg_read = rk3588_otp_read, 284 }; 285 286 static const struct of_device_id rockchip_otp_match[] = { 287 { 288 .compatible = "rockchip,px30-otp", 289 .data = &px30_data, 290 }, 291 { 292 .compatible = "rockchip,rk3308-otp", 293 .data = &px30_data, 294 }, 295 { 296 .compatible = "rockchip,rk3588-otp", 297 .data = &rk3588_data, 298 }, 299 { /* sentinel */ }, 300 }; 301 MODULE_DEVICE_TABLE(of, rockchip_otp_match); 302 303 static int rockchip_otp_probe(struct platform_device *pdev) 304 { 305 struct device *dev = &pdev->dev; 306 struct rockchip_otp *otp; 307 const struct rockchip_data *data; 308 struct nvmem_device *nvmem; 309 int ret, i; 310 311 data = of_device_get_match_data(dev); 312 if (!data) 313 return dev_err_probe(dev, -EINVAL, "failed to get match data\n"); 314 315 otp = devm_kzalloc(&pdev->dev, sizeof(struct rockchip_otp), 316 GFP_KERNEL); 317 if (!otp) 318 return -ENOMEM; 319 320 otp->data = data; 321 otp->dev = dev; 322 otp->base = devm_platform_ioremap_resource(pdev, 0); 323 if (IS_ERR(otp->base)) 324 return dev_err_probe(dev, PTR_ERR(otp->base), 325 "failed to ioremap resource\n"); 326 327 otp->clks = devm_kcalloc(dev, data->num_clks, sizeof(*otp->clks), 328 GFP_KERNEL); 329 if (!otp->clks) 330 return -ENOMEM; 331 332 for (i = 0; i < data->num_clks; ++i) 333 otp->clks[i].id = data->clks[i]; 334 335 ret = devm_clk_bulk_get(dev, data->num_clks, otp->clks); 336 if (ret) 337 return dev_err_probe(dev, ret, "failed to get clocks\n"); 338 339 otp->rst = devm_reset_control_array_get_exclusive(dev); 340 if (IS_ERR(otp->rst)) 341 return dev_err_probe(dev, PTR_ERR(otp->rst), 342 "failed to get resets\n"); 343 344 otp_config.size = data->size; 345 otp_config.priv = otp; 346 otp_config.dev = dev; 347 348 nvmem = devm_nvmem_register(dev, &otp_config); 349 if (IS_ERR(nvmem)) 350 return dev_err_probe(dev, PTR_ERR(nvmem), 351 "failed to register nvmem device\n"); 352 return 0; 353 } 354 355 static struct platform_driver rockchip_otp_driver = { 356 .probe = rockchip_otp_probe, 357 .driver = { 358 .name = "rockchip-otp", 359 .of_match_table = rockchip_otp_match, 360 }, 361 }; 362 363 module_platform_driver(rockchip_otp_driver); 364 MODULE_DESCRIPTION("Rockchip OTP driver"); 365 MODULE_LICENSE("GPL v2"); 366