aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/crypto/caam
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/crypto/caam')
-rw-r--r--drivers/crypto/caam/ctrl.c63
-rw-r--r--drivers/crypto/caam/regs.h7
2 files changed, 52 insertions, 18 deletions
diff --git a/drivers/crypto/caam/ctrl.c b/drivers/crypto/caam/ctrl.c
index 11c7f295857b..d5fe5f57108c 100644
--- a/drivers/crypto/caam/ctrl.c
+++ b/drivers/crypto/caam/ctrl.c
@@ -82,7 +82,7 @@ static int instantiate_rng(struct device *ctrldev)
82 struct caam_drv_private *ctrlpriv = dev_get_drvdata(ctrldev); 82 struct caam_drv_private *ctrlpriv = dev_get_drvdata(ctrldev);
83 struct caam_full __iomem *topregs; 83 struct caam_full __iomem *topregs;
84 unsigned int timeout = 100000; 84 unsigned int timeout = 100000;
85 u32 *desc; 85 u32 *desc, deco_dbg_reg;
86 int i, ret = 0; 86 int i, ret = 0;
87 87
88 desc = kmalloc(CAAM_CMD_SZ * 7, GFP_KERNEL | GFP_DMA); 88 desc = kmalloc(CAAM_CMD_SZ * 7, GFP_KERNEL | GFP_DMA);
@@ -112,9 +112,17 @@ static int instantiate_rng(struct device *ctrldev)
112 wr_reg32(&topregs->deco.jr_ctl_hi, DECO_JQCR_WHL | DECO_JQCR_FOUR); 112 wr_reg32(&topregs->deco.jr_ctl_hi, DECO_JQCR_WHL | DECO_JQCR_FOUR);
113 113
114 timeout = 10000000; 114 timeout = 10000000;
115 while ((rd_reg32(&topregs->deco.desc_dbg) & DECO_DBG_VALID) && 115 do {
116 --timeout) 116 deco_dbg_reg = rd_reg32(&topregs->deco.desc_dbg);
117 /*
118 * If an error occured in the descriptor, then
119 * the DECO status field will be set to 0x0D
120 */
121 if ((deco_dbg_reg & DESC_DBG_DECO_STAT_MASK) ==
122 DESC_DBG_DECO_STAT_HOST_ERR)
123 break;
117 cpu_relax(); 124 cpu_relax();
125 } while ((deco_dbg_reg & DESC_DBG_DECO_STAT_VALID) && --timeout);
118 126
119 if (!timeout) { 127 if (!timeout) {
120 dev_err(ctrldev, "failed to instantiate RNG\n"); 128 dev_err(ctrldev, "failed to instantiate RNG\n");
@@ -128,10 +136,12 @@ out:
128} 136}
129 137
130/* 138/*
131 * By default, the TRNG runs for 200 clocks per sample; 139 * kick_trng - sets the various parameters for enabling the initialization
132 * 1600 clocks per sample generates better entropy. 140 * of the RNG4 block in CAAM
141 * @pdev - pointer to the platform device
142 * @ent_delay - Defines the length (in system clocks) of each entropy sample.
133 */ 143 */
134static void kick_trng(struct platform_device *pdev) 144static void kick_trng(struct platform_device *pdev, int ent_delay)
135{ 145{
136 struct device *ctrldev = &pdev->dev; 146 struct device *ctrldev = &pdev->dev;
137 struct caam_drv_private *ctrlpriv = dev_get_drvdata(ctrldev); 147 struct caam_drv_private *ctrlpriv = dev_get_drvdata(ctrldev);
@@ -144,14 +154,31 @@ static void kick_trng(struct platform_device *pdev)
144 154
145 /* put RNG4 into program mode */ 155 /* put RNG4 into program mode */
146 setbits32(&r4tst->rtmctl, RTMCTL_PRGM); 156 setbits32(&r4tst->rtmctl, RTMCTL_PRGM);
147 /* 1600 clocks per sample */ 157
158 /*
159 * Performance-wise, it does not make sense to
160 * set the delay to a value that is lower
161 * than the last one that worked (i.e. the state handles
162 * were instantiated properly. Thus, instead of wasting
163 * time trying to set the values controlling the sample
164 * frequency, the function simply returns.
165 */
166 val = (rd_reg32(&r4tst->rtsdctl) & RTSDCTL_ENT_DLY_MASK)
167 >> RTSDCTL_ENT_DLY_SHIFT;
168 if (ent_delay <= val) {
169 /* put RNG4 into run mode */
170 clrbits32(&r4tst->rtmctl, RTMCTL_PRGM);
171 return;
172 }
173
148 val = rd_reg32(&r4tst->rtsdctl); 174 val = rd_reg32(&r4tst->rtsdctl);
149 val = (val & ~RTSDCTL_ENT_DLY_MASK) | (1600 << RTSDCTL_ENT_DLY_SHIFT); 175 val = (val & ~RTSDCTL_ENT_DLY_MASK) |
176 (ent_delay << RTSDCTL_ENT_DLY_SHIFT);
150 wr_reg32(&r4tst->rtsdctl, val); 177 wr_reg32(&r4tst->rtsdctl, val);
151 /* min. freq. count */ 178 /* min. freq. count, equal to 1/4 of the entropy sample length */
152 wr_reg32(&r4tst->rtfrqmin, 400); 179 wr_reg32(&r4tst->rtfrqmin, ent_delay >> 2);
153 /* max. freq. count */ 180 /* max. freq. count, equal to 8 times the entropy sample length */
154 wr_reg32(&r4tst->rtfrqmax, 6400); 181 wr_reg32(&r4tst->rtfrqmax, ent_delay << 3);
155 /* put RNG4 into run mode */ 182 /* put RNG4 into run mode */
156 clrbits32(&r4tst->rtmctl, RTMCTL_PRGM); 183 clrbits32(&r4tst->rtmctl, RTMCTL_PRGM);
157} 184}
@@ -192,7 +219,7 @@ EXPORT_SYMBOL(caam_get_era);
192/* Probe routine for CAAM top (controller) level */ 219/* Probe routine for CAAM top (controller) level */
193static int caam_probe(struct platform_device *pdev) 220static int caam_probe(struct platform_device *pdev)
194{ 221{
195 int ret, ring, rspec; 222 int ret, ring, rspec, ent_delay = RTSDCTL_ENT_DLY_MIN;
196 u64 caam_id; 223 u64 caam_id;
197 struct device *dev; 224 struct device *dev;
198 struct device_node *nprop, *np; 225 struct device_node *nprop, *np;
@@ -298,13 +325,17 @@ static int caam_probe(struct platform_device *pdev)
298 325
299 /* 326 /*
300 * If SEC has RNG version >= 4 and RNG state handle has not been 327 * If SEC has RNG version >= 4 and RNG state handle has not been
301 * already instantiated ,do RNG instantiation 328 * already instantiated, do RNG instantiation
302 */ 329 */
303 if ((cha_vid & CHA_ID_RNG_MASK) >> CHA_ID_RNG_SHIFT >= 4 && 330 if ((cha_vid & CHA_ID_RNG_MASK) >> CHA_ID_RNG_SHIFT >= 4 &&
304 !(rd_reg32(&topregs->ctrl.r4tst[0].rdsta) & RDSTA_IF0)) { 331 !(rd_reg32(&topregs->ctrl.r4tst[0].rdsta) & RDSTA_IF0)) {
305 kick_trng(pdev); 332 do {
306 ret = instantiate_rng(dev); 333 kick_trng(pdev, ent_delay);
334 ret = instantiate_rng(dev);
335 ent_delay += 400;
336 } while ((ret == -EIO) && (ent_delay < RTSDCTL_ENT_DLY_MAX));
307 if (ret) { 337 if (ret) {
338 dev_err(dev, "failed to instantiate RNG");
308 caam_remove(pdev); 339 caam_remove(pdev);
309 return ret; 340 return ret;
310 } 341 }
diff --git a/drivers/crypto/caam/regs.h b/drivers/crypto/caam/regs.h
index 4455396918de..9aa9f718a6fc 100644
--- a/drivers/crypto/caam/regs.h
+++ b/drivers/crypto/caam/regs.h
@@ -255,6 +255,8 @@ struct rng4tst {
255 }; 255 };
256#define RTSDCTL_ENT_DLY_SHIFT 16 256#define RTSDCTL_ENT_DLY_SHIFT 16
257#define RTSDCTL_ENT_DLY_MASK (0xffff << RTSDCTL_ENT_DLY_SHIFT) 257#define RTSDCTL_ENT_DLY_MASK (0xffff << RTSDCTL_ENT_DLY_SHIFT)
258#define RTSDCTL_ENT_DLY_MIN 1200
259#define RTSDCTL_ENT_DLY_MAX 12800
258 u32 rtsdctl; /* seed control register */ 260 u32 rtsdctl; /* seed control register */
259 union { 261 union {
260 u32 rtsblim; /* PRGM=1: sparse bit limit register */ 262 u32 rtsblim; /* PRGM=1: sparse bit limit register */
@@ -706,12 +708,13 @@ struct caam_deco {
706 u32 rsvd29[48]; 708 u32 rsvd29[48];
707 u32 descbuf[64]; /* DxDESB - Descriptor buffer */ 709 u32 descbuf[64]; /* DxDESB - Descriptor buffer */
708 u32 rscvd30[193]; 710 u32 rscvd30[193];
711#define DESC_DBG_DECO_STAT_HOST_ERR 0x00D00000
712#define DESC_DBG_DECO_STAT_VALID 0x80000000
713#define DESC_DBG_DECO_STAT_MASK 0x00F00000
709 u32 desc_dbg; /* DxDDR - DECO Debug Register */ 714 u32 desc_dbg; /* DxDDR - DECO Debug Register */
710 u32 rsvd31[126]; 715 u32 rsvd31[126];
711}; 716};
712 717
713/* DECO DBG Register Valid Bit*/
714#define DECO_DBG_VALID 0x80000000
715#define DECO_JQCR_WHL 0x20000000 718#define DECO_JQCR_WHL 0x20000000
716#define DECO_JQCR_FOUR 0x10000000 719#define DECO_JQCR_FOUR 0x10000000
717 720