71e920cd0fb1526fa9d332360468ff1345a74358
[openwrt/staging/thess.git] /
1 From 7a4b3ebf1d60349587fee21872536e7bd6a4cf39 Mon Sep 17 00:00:00 2001
2 From: Lorenzo Bianconi <lorenzo@kernel.org>
3 Date: Sun, 22 Sep 2024 19:38:30 +0200
4 Subject: [PATCH] spi: airoha: do not keep {tx,rx} dma buffer always mapped
5
6 DMA map txrx_buf on demand in airoha_snand_dirmap_read and
7 airoha_snand_dirmap_write routines and do not keep it always mapped.
8 This patch is not fixing any bug or introducing any functional change
9 to the driver, it just simplifies the code and improve code readability
10 without introducing any performance degradation according to the results
11 obtained from the mtd_speedtest kernel module test.
12
13 root@OpenWrt:# insmod mtd_test.ko
14 root@OpenWrt:# insmod mtd_speedtest.ko dev=5
15 [ 49.849869] =================================================
16 [ 49.855659] mtd_speedtest: MTD device: 5
17 [ 49.859583] mtd_speedtest: MTD device size 8388608, eraseblock size 131072, page size 2048, count of eraseblocks 64, pages per eraseblock 64, OOB size 128
18 [ 49.874622] mtd_test: scanning for bad eraseblocks
19 [ 49.879433] mtd_test: scanned 64 eraseblocks, 0 are bad
20 [ 50.106372] mtd_speedtest: testing eraseblock write speed
21 [ 53.083380] mtd_speedtest: eraseblock write speed is 2756 KiB/s
22 [ 53.089322] mtd_speedtest: testing eraseblock read speed
23 [ 54.143360] mtd_speedtest: eraseblock read speed is 7811 KiB/s
24 [ 54.370365] mtd_speedtest: testing page write speed
25 [ 57.349480] mtd_speedtest: page write speed is 2754 KiB/s
26 [ 57.354895] mtd_speedtest: testing page read speed
27 [ 58.410431] mtd_speedtest: page read speed is 7796 KiB/s
28 [ 58.636805] mtd_speedtest: testing 2 page write speed
29 [ 61.612427] mtd_speedtest: 2 page write speed is 2757 KiB/s
30 [ 61.618021] mtd_speedtest: testing 2 page read speed
31 [ 62.672653] mtd_speedtest: 2 page read speed is 7804 KiB/s
32 [ 62.678159] mtd_speedtest: Testing erase speed
33 [ 62.903617] mtd_speedtest: erase speed is 37063 KiB/s
34 [ 62.908678] mtd_speedtest: Testing 2x multi-block erase speed
35 [ 63.134083] mtd_speedtest: 2x multi-block erase speed is 37292 KiB/s
36 [ 63.140442] mtd_speedtest: Testing 4x multi-block erase speed
37 [ 63.364262] mtd_speedtest: 4x multi-block erase speed is 37566 KiB/s
38 [ 63.370632] mtd_speedtest: Testing 8x multi-block erase speed
39 [ 63.595740] mtd_speedtest: 8x multi-block erase speed is 37344 KiB/s
40 [ 63.602089] mtd_speedtest: Testing 16x multi-block erase speed
41 [ 63.827426] mtd_speedtest: 16x multi-block erase speed is 37320 KiB/s
42 [ 63.833860] mtd_speedtest: Testing 32x multi-block erase speed
43 [ 64.059389] mtd_speedtest: 32x multi-block erase speed is 37288 KiB/s
44 [ 64.065833] mtd_speedtest: Testing 64x multi-block erase speed
45 [ 64.290609] mtd_speedtest: 64x multi-block erase speed is 37415 KiB/s
46 [ 64.297063] mtd_speedtest: finished
47 [ 64.300555] =================================================
48
49 Tested-by: Christian Marangi <ansuelsmth@gmail.com>
50 Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
51 Link: https://patch.msgid.link/20240922-airoha-spi-fixes-v3-1-f958802b3d68@kernel.org
52 Signed-off-by: Mark Brown <broonie@kernel.org>
53 ---
54 drivers/spi/spi-airoha-snfi.c | 154 ++++++++++++++++------------------
55 1 file changed, 71 insertions(+), 83 deletions(-)
56
57 --- a/drivers/spi/spi-airoha-snfi.c
58 +++ b/drivers/spi/spi-airoha-snfi.c
59 @@ -206,13 +206,6 @@ enum airoha_snand_cs {
60 SPI_CHIP_SEL_LOW,
61 };
62
63 -struct airoha_snand_dev {
64 - size_t buf_len;
65 -
66 - u8 *txrx_buf;
67 - dma_addr_t dma_addr;
68 -};
69 -
70 struct airoha_snand_ctrl {
71 struct device *dev;
72 struct regmap *regmap_ctrl;
73 @@ -617,9 +610,9 @@ static bool airoha_snand_supports_op(str
74
75 static int airoha_snand_dirmap_create(struct spi_mem_dirmap_desc *desc)
76 {
77 - struct airoha_snand_dev *as_dev = spi_get_ctldata(desc->mem->spi);
78 + u8 *txrx_buf = spi_get_ctldata(desc->mem->spi);
79
80 - if (!as_dev->txrx_buf)
81 + if (!txrx_buf)
82 return -EINVAL;
83
84 if (desc->info.offset + desc->info.length > U32_MAX)
85 @@ -634,10 +627,11 @@ static int airoha_snand_dirmap_create(st
86 static ssize_t airoha_snand_dirmap_read(struct spi_mem_dirmap_desc *desc,
87 u64 offs, size_t len, void *buf)
88 {
89 - struct spi_device *spi = desc->mem->spi;
90 - struct airoha_snand_dev *as_dev = spi_get_ctldata(spi);
91 struct spi_mem_op *op = &desc->info.op_tmpl;
92 + struct spi_device *spi = desc->mem->spi;
93 struct airoha_snand_ctrl *as_ctrl;
94 + u8 *txrx_buf = spi_get_ctldata(spi);
95 + dma_addr_t dma_addr;
96 u32 val, rd_mode;
97 int err;
98
99 @@ -662,14 +656,17 @@ static ssize_t airoha_snand_dirmap_read(
100 if (err)
101 return err;
102
103 - dma_sync_single_for_device(as_ctrl->dev, as_dev->dma_addr,
104 - as_dev->buf_len, DMA_BIDIRECTIONAL);
105 + dma_addr = dma_map_single(as_ctrl->dev, txrx_buf, SPI_NAND_CACHE_SIZE,
106 + DMA_FROM_DEVICE);
107 + err = dma_mapping_error(as_ctrl->dev, dma_addr);
108 + if (err)
109 + return err;
110
111 /* set dma addr */
112 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_STRADDR,
113 - as_dev->dma_addr);
114 + dma_addr);
115 if (err)
116 - return err;
117 + goto error_dma_unmap;
118
119 /* set cust sec size */
120 val = as_ctrl->nfi_cfg.sec_size * as_ctrl->nfi_cfg.sec_num;
121 @@ -678,58 +675,58 @@ static ssize_t airoha_snand_dirmap_read(
122 REG_SPI_NFI_SNF_MISC_CTL2,
123 SPI_NFI_READ_DATA_BYTE_NUM, val);
124 if (err)
125 - return err;
126 + goto error_dma_unmap;
127
128 /* set read command */
129 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_RD_CTL2,
130 op->cmd.opcode);
131 if (err)
132 - return err;
133 + goto error_dma_unmap;
134
135 /* set read mode */
136 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_SNF_MISC_CTL,
137 FIELD_PREP(SPI_NFI_DATA_READ_WR_MODE, rd_mode));
138 if (err)
139 - return err;
140 + goto error_dma_unmap;
141
142 /* set read addr */
143 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_RD_CTL3, 0x0);
144 if (err)
145 - return err;
146 + goto error_dma_unmap;
147
148 /* set nfi read */
149 err = regmap_update_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CNFG,
150 SPI_NFI_OPMODE,
151 FIELD_PREP(SPI_NFI_OPMODE, 6));
152 if (err)
153 - return err;
154 + goto error_dma_unmap;
155
156 err = regmap_set_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CNFG,
157 SPI_NFI_READ_MODE | SPI_NFI_DMA_MODE);
158 if (err)
159 - return err;
160 + goto error_dma_unmap;
161
162 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_CMD, 0x0);
163 if (err)
164 - return err;
165 + goto error_dma_unmap;
166
167 /* trigger dma start read */
168 err = regmap_clear_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CON,
169 SPI_NFI_RD_TRIG);
170 if (err)
171 - return err;
172 + goto error_dma_unmap;
173
174 err = regmap_set_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CON,
175 SPI_NFI_RD_TRIG);
176 if (err)
177 - return err;
178 + goto error_dma_unmap;
179
180 err = regmap_read_poll_timeout(as_ctrl->regmap_nfi,
181 REG_SPI_NFI_SNF_STA_CTL1, val,
182 (val & SPI_NFI_READ_FROM_CACHE_DONE),
183 0, 1 * USEC_PER_SEC);
184 if (err)
185 - return err;
186 + goto error_dma_unmap;
187
188 /*
189 * SPI_NFI_READ_FROM_CACHE_DONE bit must be written at the end
190 @@ -739,35 +736,41 @@ static ssize_t airoha_snand_dirmap_read(
191 SPI_NFI_READ_FROM_CACHE_DONE,
192 SPI_NFI_READ_FROM_CACHE_DONE);
193 if (err)
194 - return err;
195 + goto error_dma_unmap;
196
197 err = regmap_read_poll_timeout(as_ctrl->regmap_nfi, REG_SPI_NFI_INTR,
198 val, (val & SPI_NFI_AHB_DONE), 0,
199 1 * USEC_PER_SEC);
200 if (err)
201 - return err;
202 + goto error_dma_unmap;
203
204 /* DMA read need delay for data ready from controller to DRAM */
205 udelay(1);
206
207 - dma_sync_single_for_cpu(as_ctrl->dev, as_dev->dma_addr,
208 - as_dev->buf_len, DMA_BIDIRECTIONAL);
209 + dma_unmap_single(as_ctrl->dev, dma_addr, SPI_NAND_CACHE_SIZE,
210 + DMA_FROM_DEVICE);
211 err = airoha_snand_set_mode(as_ctrl, SPI_MODE_MANUAL);
212 if (err < 0)
213 return err;
214
215 - memcpy(buf, as_dev->txrx_buf + offs, len);
216 + memcpy(buf, txrx_buf + offs, len);
217
218 return len;
219 +
220 +error_dma_unmap:
221 + dma_unmap_single(as_ctrl->dev, dma_addr, SPI_NAND_CACHE_SIZE,
222 + DMA_FROM_DEVICE);
223 + return err;
224 }
225
226 static ssize_t airoha_snand_dirmap_write(struct spi_mem_dirmap_desc *desc,
227 u64 offs, size_t len, const void *buf)
228 {
229 - struct spi_device *spi = desc->mem->spi;
230 - struct airoha_snand_dev *as_dev = spi_get_ctldata(spi);
231 struct spi_mem_op *op = &desc->info.op_tmpl;
232 + struct spi_device *spi = desc->mem->spi;
233 + u8 *txrx_buf = spi_get_ctldata(spi);
234 struct airoha_snand_ctrl *as_ctrl;
235 + dma_addr_t dma_addr;
236 u32 wr_mode, val;
237 int err;
238
239 @@ -776,19 +779,20 @@ static ssize_t airoha_snand_dirmap_write
240 if (err < 0)
241 return err;
242
243 - dma_sync_single_for_cpu(as_ctrl->dev, as_dev->dma_addr,
244 - as_dev->buf_len, DMA_BIDIRECTIONAL);
245 - memcpy(as_dev->txrx_buf + offs, buf, len);
246 - dma_sync_single_for_device(as_ctrl->dev, as_dev->dma_addr,
247 - as_dev->buf_len, DMA_BIDIRECTIONAL);
248 + memcpy(txrx_buf + offs, buf, len);
249 + dma_addr = dma_map_single(as_ctrl->dev, txrx_buf, SPI_NAND_CACHE_SIZE,
250 + DMA_TO_DEVICE);
251 + err = dma_mapping_error(as_ctrl->dev, dma_addr);
252 + if (err)
253 + return err;
254
255 err = airoha_snand_set_mode(as_ctrl, SPI_MODE_DMA);
256 if (err < 0)
257 - return err;
258 + goto error_dma_unmap;
259
260 err = airoha_snand_nfi_config(as_ctrl);
261 if (err)
262 - return err;
263 + goto error_dma_unmap;
264
265 if (op->cmd.opcode == SPI_NAND_OP_PROGRAM_LOAD_QUAD ||
266 op->cmd.opcode == SPI_NAND_OP_PROGRAM_LOAD_RAMDON_QUAD)
267 @@ -797,9 +801,9 @@ static ssize_t airoha_snand_dirmap_write
268 wr_mode = 0;
269
270 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_STRADDR,
271 - as_dev->dma_addr);
272 + dma_addr);
273 if (err)
274 - return err;
275 + goto error_dma_unmap;
276
277 val = FIELD_PREP(SPI_NFI_PROG_LOAD_BYTE_NUM,
278 as_ctrl->nfi_cfg.sec_size * as_ctrl->nfi_cfg.sec_num);
279 @@ -807,65 +811,65 @@ static ssize_t airoha_snand_dirmap_write
280 REG_SPI_NFI_SNF_MISC_CTL2,
281 SPI_NFI_PROG_LOAD_BYTE_NUM, val);
282 if (err)
283 - return err;
284 + goto error_dma_unmap;
285
286 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_PG_CTL1,
287 FIELD_PREP(SPI_NFI_PG_LOAD_CMD,
288 op->cmd.opcode));
289 if (err)
290 - return err;
291 + goto error_dma_unmap;
292
293 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_SNF_MISC_CTL,
294 FIELD_PREP(SPI_NFI_DATA_READ_WR_MODE, wr_mode));
295 if (err)
296 - return err;
297 + goto error_dma_unmap;
298
299 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_PG_CTL2, 0x0);
300 if (err)
301 - return err;
302 + goto error_dma_unmap;
303
304 err = regmap_clear_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CNFG,
305 SPI_NFI_READ_MODE);
306 if (err)
307 - return err;
308 + goto error_dma_unmap;
309
310 err = regmap_update_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CNFG,
311 SPI_NFI_OPMODE,
312 FIELD_PREP(SPI_NFI_OPMODE, 3));
313 if (err)
314 - return err;
315 + goto error_dma_unmap;
316
317 err = regmap_set_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CNFG,
318 SPI_NFI_DMA_MODE);
319 if (err)
320 - return err;
321 + goto error_dma_unmap;
322
323 err = regmap_write(as_ctrl->regmap_nfi, REG_SPI_NFI_CMD, 0x80);
324 if (err)
325 - return err;
326 + goto error_dma_unmap;
327
328 err = regmap_clear_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CON,
329 SPI_NFI_WR_TRIG);
330 if (err)
331 - return err;
332 + goto error_dma_unmap;
333
334 err = regmap_set_bits(as_ctrl->regmap_nfi, REG_SPI_NFI_CON,
335 SPI_NFI_WR_TRIG);
336 if (err)
337 - return err;
338 + goto error_dma_unmap;
339
340 err = regmap_read_poll_timeout(as_ctrl->regmap_nfi, REG_SPI_NFI_INTR,
341 val, (val & SPI_NFI_AHB_DONE), 0,
342 1 * USEC_PER_SEC);
343 if (err)
344 - return err;
345 + goto error_dma_unmap;
346
347 err = regmap_read_poll_timeout(as_ctrl->regmap_nfi,
348 REG_SPI_NFI_SNF_STA_CTL1, val,
349 (val & SPI_NFI_LOAD_TO_CACHE_DONE),
350 0, 1 * USEC_PER_SEC);
351 if (err)
352 - return err;
353 + goto error_dma_unmap;
354
355 /*
356 * SPI_NFI_LOAD_TO_CACHE_DONE bit must be written at the end
357 @@ -875,13 +879,20 @@ static ssize_t airoha_snand_dirmap_write
358 SPI_NFI_LOAD_TO_CACHE_DONE,
359 SPI_NFI_LOAD_TO_CACHE_DONE);
360 if (err)
361 - return err;
362 + goto error_dma_unmap;
363
364 + dma_unmap_single(as_ctrl->dev, dma_addr, SPI_NAND_CACHE_SIZE,
365 + DMA_TO_DEVICE);
366 err = airoha_snand_set_mode(as_ctrl, SPI_MODE_MANUAL);
367 if (err < 0)
368 return err;
369
370 return len;
371 +
372 +error_dma_unmap:
373 + dma_unmap_single(as_ctrl->dev, dma_addr, SPI_NAND_CACHE_SIZE,
374 + DMA_TO_DEVICE);
375 + return err;
376 }
377
378 static int airoha_snand_exec_op(struct spi_mem *mem,
379 @@ -956,42 +967,20 @@ static const struct spi_controller_mem_o
380 static int airoha_snand_setup(struct spi_device *spi)
381 {
382 struct airoha_snand_ctrl *as_ctrl;
383 - struct airoha_snand_dev *as_dev;
384 -
385 - as_ctrl = spi_controller_get_devdata(spi->controller);
386 -
387 - as_dev = devm_kzalloc(as_ctrl->dev, sizeof(*as_dev), GFP_KERNEL);
388 - if (!as_dev)
389 - return -ENOMEM;
390 + u8 *txrx_buf;
391
392 /* prepare device buffer */
393 - as_dev->buf_len = SPI_NAND_CACHE_SIZE;
394 - as_dev->txrx_buf = devm_kzalloc(as_ctrl->dev, as_dev->buf_len,
395 - GFP_KERNEL);
396 - if (!as_dev->txrx_buf)
397 - return -ENOMEM;
398 -
399 - as_dev->dma_addr = dma_map_single(as_ctrl->dev, as_dev->txrx_buf,
400 - as_dev->buf_len, DMA_BIDIRECTIONAL);
401 - if (dma_mapping_error(as_ctrl->dev, as_dev->dma_addr))
402 + as_ctrl = spi_controller_get_devdata(spi->controller);
403 + txrx_buf = devm_kzalloc(as_ctrl->dev, SPI_NAND_CACHE_SIZE,
404 + GFP_KERNEL);
405 + if (!txrx_buf)
406 return -ENOMEM;
407
408 - spi_set_ctldata(spi, as_dev);
409 + spi_set_ctldata(spi, txrx_buf);
410
411 return 0;
412 }
413
414 -static void airoha_snand_cleanup(struct spi_device *spi)
415 -{
416 - struct airoha_snand_dev *as_dev = spi_get_ctldata(spi);
417 - struct airoha_snand_ctrl *as_ctrl;
418 -
419 - as_ctrl = spi_controller_get_devdata(spi->controller);
420 - dma_unmap_single(as_ctrl->dev, as_dev->dma_addr,
421 - as_dev->buf_len, DMA_BIDIRECTIONAL);
422 - spi_set_ctldata(spi, NULL);
423 -}
424 -
425 static int airoha_snand_nfi_setup(struct airoha_snand_ctrl *as_ctrl)
426 {
427 u32 val, sec_size, sec_num;
428 @@ -1093,7 +1082,6 @@ static int airoha_snand_probe(struct pla
429 ctrl->bits_per_word_mask = SPI_BPW_MASK(8);
430 ctrl->mode_bits = SPI_RX_DUAL;
431 ctrl->setup = airoha_snand_setup;
432 - ctrl->cleanup = airoha_snand_cleanup;
433 device_set_node(&ctrl->dev, dev_fwnode(dev));
434
435 err = airoha_snand_nfi_setup(as_ctrl);