1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * RNG driver for Freescale RNGC 4 * 5 * Copyright (C) 2008-2012 Freescale Semiconductor, Inc. 6 * Copyright (C) 2017 Martin Kaiser <martin@kaiser.cx> 7 */ 8 9 #include <linux/module.h> 10 #include <linux/mod_devicetable.h> 11 #include <linux/init.h> 12 #include <linux/kernel.h> 13 #include <linux/clk.h> 14 #include <linux/err.h> 15 #include <linux/platform_device.h> 16 #include <linux/interrupt.h> 17 #include <linux/hw_random.h> 18 #include <linux/completion.h> 19 #include <linux/io.h> 20 21 #define RNGC_COMMAND 0x0004 22 #define RNGC_CONTROL 0x0008 23 #define RNGC_STATUS 0x000C 24 #define RNGC_ERROR 0x0010 25 #define RNGC_FIFO 0x0014 26 27 #define RNGC_CMD_CLR_ERR 0x00000020 28 #define RNGC_CMD_CLR_INT 0x00000010 29 #define RNGC_CMD_SEED 0x00000002 30 #define RNGC_CMD_SELF_TEST 0x00000001 31 32 #define RNGC_CTRL_MASK_ERROR 0x00000040 33 #define RNGC_CTRL_MASK_DONE 0x00000020 34 35 #define RNGC_STATUS_ERROR 0x00010000 36 #define RNGC_STATUS_FIFO_LEVEL_MASK 0x00000f00 37 #define RNGC_STATUS_FIFO_LEVEL_SHIFT 8 38 #define RNGC_STATUS_SEED_DONE 0x00000020 39 #define RNGC_STATUS_ST_DONE 0x00000010 40 41 #define RNGC_ERROR_STATUS_STAT_ERR 0x00000008 42 43 #define RNGC_TIMEOUT 3000 /* 3 sec */ 44 45 46 static bool self_test = true; 47 module_param(self_test, bool, 0); 48 49 struct imx_rngc { 50 struct device *dev; 51 struct clk *clk; 52 void __iomem *base; 53 struct hwrng rng; 54 struct completion rng_op_done; 55 /* 56 * err_reg is written only by the irq handler and read only 57 * when interrupts are masked, we need no spinlock 58 */ 59 u32 err_reg; 60 }; 61 62 63 static inline void imx_rngc_irq_mask_clear(struct imx_rngc *rngc) 64 { 65 u32 ctrl, cmd; 66 67 /* mask interrupts */ 68 ctrl = readl(rngc->base + RNGC_CONTROL); 69 ctrl |= RNGC_CTRL_MASK_DONE | RNGC_CTRL_MASK_ERROR; 70 writel(ctrl, rngc->base + RNGC_CONTROL); 71 72 /* 73 * CLR_INT clears the interrupt only if there's no error 74 * CLR_ERR clear the interrupt and the error register if there 75 * is an error 76 */ 77 cmd = readl(rngc->base + RNGC_COMMAND); 78 cmd |= RNGC_CMD_CLR_INT | RNGC_CMD_CLR_ERR; 79 writel(cmd, rngc->base + RNGC_COMMAND); 80 } 81 82 static inline void imx_rngc_irq_unmask(struct imx_rngc *rngc) 83 { 84 u32 ctrl; 85 86 ctrl = readl(rngc->base + RNGC_CONTROL); 87 ctrl &= ~(RNGC_CTRL_MASK_DONE | RNGC_CTRL_MASK_ERROR); 88 writel(ctrl, rngc->base + RNGC_CONTROL); 89 } 90 91 static int imx_rngc_self_test(struct imx_rngc *rngc) 92 { 93 u32 cmd; 94 int ret; 95 96 imx_rngc_irq_unmask(rngc); 97 98 /* run self test */ 99 cmd = readl(rngc->base + RNGC_COMMAND); 100 writel(cmd | RNGC_CMD_SELF_TEST, rngc->base + RNGC_COMMAND); 101 102 ret = wait_for_completion_timeout(&rngc->rng_op_done, RNGC_TIMEOUT); 103 if (!ret) { 104 imx_rngc_irq_mask_clear(rngc); 105 return -ETIMEDOUT; 106 } 107 108 if (rngc->err_reg != 0) 109 return -EIO; 110 111 return 0; 112 } 113 114 static int imx_rngc_read(struct hwrng *rng, void *data, size_t max, bool wait) 115 { 116 struct imx_rngc *rngc = container_of(rng, struct imx_rngc, rng); 117 unsigned int status; 118 unsigned int level; 119 int retval = 0; 120 121 while (max >= sizeof(u32)) { 122 status = readl(rngc->base + RNGC_STATUS); 123 124 /* is there some error while reading this random number? */ 125 if (status & RNGC_STATUS_ERROR) 126 break; 127 128 /* how many random numbers are in FIFO? [0-16] */ 129 level = (status & RNGC_STATUS_FIFO_LEVEL_MASK) >> 130 RNGC_STATUS_FIFO_LEVEL_SHIFT; 131 132 if (level) { 133 /* retrieve a random number from FIFO */ 134 *(u32 *)data = readl(rngc->base + RNGC_FIFO); 135 136 retval += sizeof(u32); 137 data += sizeof(u32); 138 max -= sizeof(u32); 139 } 140 } 141 142 return retval ? retval : -EIO; 143 } 144 145 static irqreturn_t imx_rngc_irq(int irq, void *priv) 146 { 147 struct imx_rngc *rngc = (struct imx_rngc *)priv; 148 u32 status; 149 150 /* 151 * clearing the interrupt will also clear the error register 152 * read error and status before clearing 153 */ 154 status = readl(rngc->base + RNGC_STATUS); 155 rngc->err_reg = readl(rngc->base + RNGC_ERROR); 156 157 imx_rngc_irq_mask_clear(rngc); 158 159 if (status & (RNGC_STATUS_SEED_DONE | RNGC_STATUS_ST_DONE)) 160 complete(&rngc->rng_op_done); 161 162 return IRQ_HANDLED; 163 } 164 165 static int imx_rngc_init(struct hwrng *rng) 166 { 167 struct imx_rngc *rngc = container_of(rng, struct imx_rngc, rng); 168 u32 cmd; 169 int ret; 170 171 /* clear error */ 172 cmd = readl(rngc->base + RNGC_COMMAND); 173 writel(cmd | RNGC_CMD_CLR_ERR, rngc->base + RNGC_COMMAND); 174 175 /* create seed, repeat while there is some statistical error */ 176 do { 177 imx_rngc_irq_unmask(rngc); 178 179 /* seed creation */ 180 cmd = readl(rngc->base + RNGC_COMMAND); 181 writel(cmd | RNGC_CMD_SEED, rngc->base + RNGC_COMMAND); 182 183 ret = wait_for_completion_timeout(&rngc->rng_op_done, 184 RNGC_TIMEOUT); 185 186 if (!ret) { 187 imx_rngc_irq_mask_clear(rngc); 188 return -ETIMEDOUT; 189 } 190 191 } while (rngc->err_reg == RNGC_ERROR_STATUS_STAT_ERR); 192 193 return rngc->err_reg ? -EIO : 0; 194 } 195 196 static int imx_rngc_probe(struct platform_device *pdev) 197 { 198 struct imx_rngc *rngc; 199 int ret; 200 int irq; 201 202 rngc = devm_kzalloc(&pdev->dev, sizeof(*rngc), GFP_KERNEL); 203 if (!rngc) 204 return -ENOMEM; 205 206 rngc->base = devm_platform_ioremap_resource(pdev, 0); 207 if (IS_ERR(rngc->base)) 208 return PTR_ERR(rngc->base); 209 210 rngc->clk = devm_clk_get(&pdev->dev, NULL); 211 if (IS_ERR(rngc->clk)) { 212 dev_err(&pdev->dev, "Can not get rng_clk\n"); 213 return PTR_ERR(rngc->clk); 214 } 215 216 irq = platform_get_irq(pdev, 0); 217 if (irq <= 0) { 218 dev_err(&pdev->dev, "Couldn't get irq %d\n", irq); 219 return irq; 220 } 221 222 ret = clk_prepare_enable(rngc->clk); 223 if (ret) 224 return ret; 225 226 ret = devm_request_irq(&pdev->dev, 227 irq, imx_rngc_irq, 0, pdev->name, (void *)rngc); 228 if (ret) { 229 dev_err(rngc->dev, "Can't get interrupt working.\n"); 230 goto err; 231 } 232 233 init_completion(&rngc->rng_op_done); 234 235 rngc->rng.name = pdev->name; 236 rngc->rng.init = imx_rngc_init; 237 rngc->rng.read = imx_rngc_read; 238 239 rngc->dev = &pdev->dev; 240 platform_set_drvdata(pdev, rngc); 241 242 imx_rngc_irq_mask_clear(rngc); 243 244 if (self_test) { 245 ret = imx_rngc_self_test(rngc); 246 if (ret) { 247 dev_err(rngc->dev, "FSL RNGC self test failed.\n"); 248 goto err; 249 } 250 } 251 252 ret = hwrng_register(&rngc->rng); 253 if (ret) { 254 dev_err(&pdev->dev, "FSL RNGC registering failed (%d)\n", ret); 255 goto err; 256 } 257 258 dev_info(&pdev->dev, "Freescale RNGC registered.\n"); 259 return 0; 260 261 err: 262 clk_disable_unprepare(rngc->clk); 263 264 return ret; 265 } 266 267 static int __exit imx_rngc_remove(struct platform_device *pdev) 268 { 269 struct imx_rngc *rngc = platform_get_drvdata(pdev); 270 271 hwrng_unregister(&rngc->rng); 272 273 clk_disable_unprepare(rngc->clk); 274 275 return 0; 276 } 277 278 static int __maybe_unused imx_rngc_suspend(struct device *dev) 279 { 280 struct imx_rngc *rngc = dev_get_drvdata(dev); 281 282 clk_disable_unprepare(rngc->clk); 283 284 return 0; 285 } 286 287 static int __maybe_unused imx_rngc_resume(struct device *dev) 288 { 289 struct imx_rngc *rngc = dev_get_drvdata(dev); 290 291 clk_prepare_enable(rngc->clk); 292 293 return 0; 294 } 295 296 static SIMPLE_DEV_PM_OPS(imx_rngc_pm_ops, imx_rngc_suspend, imx_rngc_resume); 297 298 static const struct of_device_id imx_rngc_dt_ids[] = { 299 { .compatible = "fsl,imx25-rngb", .data = NULL, }, 300 { /* sentinel */ } 301 }; 302 MODULE_DEVICE_TABLE(of, imx_rngc_dt_ids); 303 304 static struct platform_driver imx_rngc_driver = { 305 .driver = { 306 .name = "imx_rngc", 307 .pm = &imx_rngc_pm_ops, 308 .of_match_table = imx_rngc_dt_ids, 309 }, 310 .remove = __exit_p(imx_rngc_remove), 311 }; 312 313 module_platform_driver_probe(imx_rngc_driver, imx_rngc_probe); 314 315 MODULE_AUTHOR("Freescale Semiconductor, Inc."); 316 MODULE_DESCRIPTION("H/W RNGC driver for i.MX"); 317 MODULE_LICENSE("GPL"); 318