1 // SPDX-License-Identifier: GPL-2.0-only
3 * SPI-Engine SPI controller driver
4 * Copyright 2015 Analog Devices Inc.
5 * Author: Lars-Peter Clausen <lars@metafoo.de>
9 #include <linux/interrupt.h>
12 #include <linux/module.h>
13 #include <linux/platform_device.h>
14 #include <linux/spi/spi.h>
16 #define SPI_ENGINE_VERSION_MAJOR(x) ((x >> 16) & 0xff)
17 #define SPI_ENGINE_VERSION_MINOR(x) ((x >> 8) & 0xff)
18 #define SPI_ENGINE_VERSION_PATCH(x) (x & 0xff)
20 #define SPI_ENGINE_REG_VERSION 0x00
22 #define SPI_ENGINE_REG_RESET 0x40
24 #define SPI_ENGINE_REG_INT_ENABLE 0x80
25 #define SPI_ENGINE_REG_INT_PENDING 0x84
26 #define SPI_ENGINE_REG_INT_SOURCE 0x88
28 #define SPI_ENGINE_REG_SYNC_ID 0xc0
30 #define SPI_ENGINE_REG_CMD_FIFO_ROOM 0xd0
31 #define SPI_ENGINE_REG_SDO_FIFO_ROOM 0xd4
32 #define SPI_ENGINE_REG_SDI_FIFO_LEVEL 0xd8
34 #define SPI_ENGINE_REG_CMD_FIFO 0xe0
35 #define SPI_ENGINE_REG_SDO_DATA_FIFO 0xe4
36 #define SPI_ENGINE_REG_SDI_DATA_FIFO 0xe8
37 #define SPI_ENGINE_REG_SDI_DATA_FIFO_PEEK 0xec
39 #define SPI_ENGINE_INT_CMD_ALMOST_EMPTY BIT(0)
40 #define SPI_ENGINE_INT_SDO_ALMOST_EMPTY BIT(1)
41 #define SPI_ENGINE_INT_SDI_ALMOST_FULL BIT(2)
42 #define SPI_ENGINE_INT_SYNC BIT(3)
44 #define SPI_ENGINE_CONFIG_CPHA BIT(0)
45 #define SPI_ENGINE_CONFIG_CPOL BIT(1)
46 #define SPI_ENGINE_CONFIG_3WIRE BIT(2)
48 #define SPI_ENGINE_INST_TRANSFER 0x0
49 #define SPI_ENGINE_INST_ASSERT 0x1
50 #define SPI_ENGINE_INST_WRITE 0x2
51 #define SPI_ENGINE_INST_MISC 0x3
53 #define SPI_ENGINE_CMD_REG_CLK_DIV 0x0
54 #define SPI_ENGINE_CMD_REG_CONFIG 0x1
56 #define SPI_ENGINE_MISC_SYNC 0x0
57 #define SPI_ENGINE_MISC_SLEEP 0x1
59 #define SPI_ENGINE_TRANSFER_WRITE 0x1
60 #define SPI_ENGINE_TRANSFER_READ 0x2
62 #define SPI_ENGINE_CMD(inst, arg1, arg2) \
63 (((inst) << 12) | ((arg1) << 8) | (arg2))
65 #define SPI_ENGINE_CMD_TRANSFER(flags, n) \
66 SPI_ENGINE_CMD(SPI_ENGINE_INST_TRANSFER, (flags), (n))
67 #define SPI_ENGINE_CMD_ASSERT(delay, cs) \
68 SPI_ENGINE_CMD(SPI_ENGINE_INST_ASSERT, (delay), (cs))
69 #define SPI_ENGINE_CMD_WRITE(reg, val) \
70 SPI_ENGINE_CMD(SPI_ENGINE_INST_WRITE, (reg), (val))
71 #define SPI_ENGINE_CMD_SLEEP(delay) \
72 SPI_ENGINE_CMD(SPI_ENGINE_INST_MISC, SPI_ENGINE_MISC_SLEEP, (delay))
73 #define SPI_ENGINE_CMD_SYNC(id) \
74 SPI_ENGINE_CMD(SPI_ENGINE_INST_MISC, SPI_ENGINE_MISC_SYNC, (id))
76 struct spi_engine_program
{
78 uint16_t instructions
[];
89 struct spi_message
*msg
;
90 struct spi_engine_program
*p
;
92 const uint16_t *cmd_buf
;
94 struct spi_transfer
*tx_xfer
;
95 unsigned int tx_length
;
96 const uint8_t *tx_buf
;
98 struct spi_transfer
*rx_xfer
;
99 unsigned int rx_length
;
102 unsigned int sync_id
;
103 unsigned int completed_id
;
105 unsigned int int_enable
;
108 static void spi_engine_program_add_cmd(struct spi_engine_program
*p
,
109 bool dry
, uint16_t cmd
)
112 p
->instructions
[p
->length
] = cmd
;
116 static unsigned int spi_engine_get_config(struct spi_device
*spi
)
118 unsigned int config
= 0;
120 if (spi
->mode
& SPI_CPOL
)
121 config
|= SPI_ENGINE_CONFIG_CPOL
;
122 if (spi
->mode
& SPI_CPHA
)
123 config
|= SPI_ENGINE_CONFIG_CPHA
;
124 if (spi
->mode
& SPI_3WIRE
)
125 config
|= SPI_ENGINE_CONFIG_3WIRE
;
130 static unsigned int spi_engine_get_clk_div(struct spi_engine
*spi_engine
,
131 struct spi_device
*spi
, struct spi_transfer
*xfer
)
133 unsigned int clk_div
;
135 clk_div
= DIV_ROUND_UP(clk_get_rate(spi_engine
->ref_clk
),
139 else if (clk_div
> 0)
145 static void spi_engine_gen_xfer(struct spi_engine_program
*p
, bool dry
,
146 struct spi_transfer
*xfer
)
148 unsigned int len
= xfer
->len
;
151 unsigned int n
= min(len
, 256U);
152 unsigned int flags
= 0;
155 flags
|= SPI_ENGINE_TRANSFER_WRITE
;
157 flags
|= SPI_ENGINE_TRANSFER_READ
;
159 spi_engine_program_add_cmd(p
, dry
,
160 SPI_ENGINE_CMD_TRANSFER(flags
, n
- 1));
165 static void spi_engine_gen_sleep(struct spi_engine_program
*p
, bool dry
,
166 struct spi_engine
*spi_engine
, unsigned int clk_div
,
167 struct spi_transfer
*xfer
)
169 unsigned int spi_clk
= clk_get_rate(spi_engine
->ref_clk
);
173 if (xfer
->delay_usecs
) {
174 delay
= xfer
->delay_usecs
;
176 delay
= spi_delay_to_ns(&xfer
->delay
, xfer
);
185 t
= DIV_ROUND_UP(delay
* spi_clk
, (clk_div
+ 1) * 2);
187 unsigned int n
= min(t
, 256U);
189 spi_engine_program_add_cmd(p
, dry
, SPI_ENGINE_CMD_SLEEP(n
- 1));
194 static void spi_engine_gen_cs(struct spi_engine_program
*p
, bool dry
,
195 struct spi_device
*spi
, bool assert)
197 unsigned int mask
= 0xff;
200 mask
^= BIT(spi
->chip_select
);
202 spi_engine_program_add_cmd(p
, dry
, SPI_ENGINE_CMD_ASSERT(1, mask
));
205 static int spi_engine_compile_message(struct spi_engine
*spi_engine
,
206 struct spi_message
*msg
, bool dry
, struct spi_engine_program
*p
)
208 struct spi_device
*spi
= msg
->spi
;
209 struct spi_transfer
*xfer
;
210 int clk_div
, new_clk_div
;
211 bool cs_change
= true;
215 spi_engine_program_add_cmd(p
, dry
,
216 SPI_ENGINE_CMD_WRITE(SPI_ENGINE_CMD_REG_CONFIG
,
217 spi_engine_get_config(spi
)));
219 list_for_each_entry(xfer
, &msg
->transfers
, transfer_list
) {
220 new_clk_div
= spi_engine_get_clk_div(spi_engine
, spi
, xfer
);
221 if (new_clk_div
!= clk_div
) {
222 clk_div
= new_clk_div
;
223 spi_engine_program_add_cmd(p
, dry
,
224 SPI_ENGINE_CMD_WRITE(SPI_ENGINE_CMD_REG_CLK_DIV
,
229 spi_engine_gen_cs(p
, dry
, spi
, true);
231 spi_engine_gen_xfer(p
, dry
, xfer
);
232 spi_engine_gen_sleep(p
, dry
, spi_engine
, clk_div
, xfer
);
234 cs_change
= xfer
->cs_change
;
235 if (list_is_last(&xfer
->transfer_list
, &msg
->transfers
))
236 cs_change
= !cs_change
;
239 spi_engine_gen_cs(p
, dry
, spi
, false);
245 static void spi_engine_xfer_next(struct spi_engine
*spi_engine
,
246 struct spi_transfer
**_xfer
)
248 struct spi_message
*msg
= spi_engine
->msg
;
249 struct spi_transfer
*xfer
= *_xfer
;
252 xfer
= list_first_entry(&msg
->transfers
,
253 struct spi_transfer
, transfer_list
);
254 } else if (list_is_last(&xfer
->transfer_list
, &msg
->transfers
)) {
257 xfer
= list_next_entry(xfer
, transfer_list
);
263 static void spi_engine_tx_next(struct spi_engine
*spi_engine
)
265 struct spi_transfer
*xfer
= spi_engine
->tx_xfer
;
268 spi_engine_xfer_next(spi_engine
, &xfer
);
269 } while (xfer
&& !xfer
->tx_buf
);
271 spi_engine
->tx_xfer
= xfer
;
273 spi_engine
->tx_length
= xfer
->len
;
274 spi_engine
->tx_buf
= xfer
->tx_buf
;
276 spi_engine
->tx_buf
= NULL
;
280 static void spi_engine_rx_next(struct spi_engine
*spi_engine
)
282 struct spi_transfer
*xfer
= spi_engine
->rx_xfer
;
285 spi_engine_xfer_next(spi_engine
, &xfer
);
286 } while (xfer
&& !xfer
->rx_buf
);
288 spi_engine
->rx_xfer
= xfer
;
290 spi_engine
->rx_length
= xfer
->len
;
291 spi_engine
->rx_buf
= xfer
->rx_buf
;
293 spi_engine
->rx_buf
= NULL
;
297 static bool spi_engine_write_cmd_fifo(struct spi_engine
*spi_engine
)
299 void __iomem
*addr
= spi_engine
->base
+ SPI_ENGINE_REG_CMD_FIFO
;
300 unsigned int n
, m
, i
;
303 n
= readl_relaxed(spi_engine
->base
+ SPI_ENGINE_REG_CMD_FIFO_ROOM
);
304 while (n
&& spi_engine
->cmd_length
) {
305 m
= min(n
, spi_engine
->cmd_length
);
306 buf
= spi_engine
->cmd_buf
;
307 for (i
= 0; i
< m
; i
++)
308 writel_relaxed(buf
[i
], addr
);
309 spi_engine
->cmd_buf
+= m
;
310 spi_engine
->cmd_length
-= m
;
314 return spi_engine
->cmd_length
!= 0;
317 static bool spi_engine_write_tx_fifo(struct spi_engine
*spi_engine
)
319 void __iomem
*addr
= spi_engine
->base
+ SPI_ENGINE_REG_SDO_DATA_FIFO
;
320 unsigned int n
, m
, i
;
323 n
= readl_relaxed(spi_engine
->base
+ SPI_ENGINE_REG_SDO_FIFO_ROOM
);
324 while (n
&& spi_engine
->tx_length
) {
325 m
= min(n
, spi_engine
->tx_length
);
326 buf
= spi_engine
->tx_buf
;
327 for (i
= 0; i
< m
; i
++)
328 writel_relaxed(buf
[i
], addr
);
329 spi_engine
->tx_buf
+= m
;
330 spi_engine
->tx_length
-= m
;
332 if (spi_engine
->tx_length
== 0)
333 spi_engine_tx_next(spi_engine
);
336 return spi_engine
->tx_length
!= 0;
339 static bool spi_engine_read_rx_fifo(struct spi_engine
*spi_engine
)
341 void __iomem
*addr
= spi_engine
->base
+ SPI_ENGINE_REG_SDI_DATA_FIFO
;
342 unsigned int n
, m
, i
;
345 n
= readl_relaxed(spi_engine
->base
+ SPI_ENGINE_REG_SDI_FIFO_LEVEL
);
346 while (n
&& spi_engine
->rx_length
) {
347 m
= min(n
, spi_engine
->rx_length
);
348 buf
= spi_engine
->rx_buf
;
349 for (i
= 0; i
< m
; i
++)
350 buf
[i
] = readl_relaxed(addr
);
351 spi_engine
->rx_buf
+= m
;
352 spi_engine
->rx_length
-= m
;
354 if (spi_engine
->rx_length
== 0)
355 spi_engine_rx_next(spi_engine
);
358 return spi_engine
->rx_length
!= 0;
361 static irqreturn_t
spi_engine_irq(int irq
, void *devid
)
363 struct spi_master
*master
= devid
;
364 struct spi_engine
*spi_engine
= spi_master_get_devdata(master
);
365 unsigned int disable_int
= 0;
366 unsigned int pending
;
368 pending
= readl_relaxed(spi_engine
->base
+ SPI_ENGINE_REG_INT_PENDING
);
370 if (pending
& SPI_ENGINE_INT_SYNC
) {
371 writel_relaxed(SPI_ENGINE_INT_SYNC
,
372 spi_engine
->base
+ SPI_ENGINE_REG_INT_PENDING
);
373 spi_engine
->completed_id
= readl_relaxed(
374 spi_engine
->base
+ SPI_ENGINE_REG_SYNC_ID
);
377 spin_lock(&spi_engine
->lock
);
379 if (pending
& SPI_ENGINE_INT_CMD_ALMOST_EMPTY
) {
380 if (!spi_engine_write_cmd_fifo(spi_engine
))
381 disable_int
|= SPI_ENGINE_INT_CMD_ALMOST_EMPTY
;
384 if (pending
& SPI_ENGINE_INT_SDO_ALMOST_EMPTY
) {
385 if (!spi_engine_write_tx_fifo(spi_engine
))
386 disable_int
|= SPI_ENGINE_INT_SDO_ALMOST_EMPTY
;
389 if (pending
& (SPI_ENGINE_INT_SDI_ALMOST_FULL
| SPI_ENGINE_INT_SYNC
)) {
390 if (!spi_engine_read_rx_fifo(spi_engine
))
391 disable_int
|= SPI_ENGINE_INT_SDI_ALMOST_FULL
;
394 if (pending
& SPI_ENGINE_INT_SYNC
) {
395 if (spi_engine
->msg
&&
396 spi_engine
->completed_id
== spi_engine
->sync_id
) {
397 struct spi_message
*msg
= spi_engine
->msg
;
399 kfree(spi_engine
->p
);
401 msg
->actual_length
= msg
->frame_length
;
402 spi_engine
->msg
= NULL
;
403 spi_finalize_current_message(master
);
404 disable_int
|= SPI_ENGINE_INT_SYNC
;
409 spi_engine
->int_enable
&= ~disable_int
;
410 writel_relaxed(spi_engine
->int_enable
,
411 spi_engine
->base
+ SPI_ENGINE_REG_INT_ENABLE
);
414 spin_unlock(&spi_engine
->lock
);
419 static int spi_engine_transfer_one_message(struct spi_master
*master
,
420 struct spi_message
*msg
)
422 struct spi_engine_program p_dry
, *p
;
423 struct spi_engine
*spi_engine
= spi_master_get_devdata(master
);
424 unsigned int int_enable
= 0;
429 spi_engine_compile_message(spi_engine
, msg
, true, &p_dry
);
431 size
= sizeof(*p
->instructions
) * (p_dry
.length
+ 1);
432 p
= kzalloc(sizeof(*p
) + size
, GFP_KERNEL
);
435 spi_engine_compile_message(spi_engine
, msg
, false, p
);
437 spin_lock_irqsave(&spi_engine
->lock
, flags
);
438 spi_engine
->sync_id
= (spi_engine
->sync_id
+ 1) & 0xff;
439 spi_engine_program_add_cmd(p
, false,
440 SPI_ENGINE_CMD_SYNC(spi_engine
->sync_id
));
442 spi_engine
->msg
= msg
;
445 spi_engine
->cmd_buf
= p
->instructions
;
446 spi_engine
->cmd_length
= p
->length
;
447 if (spi_engine_write_cmd_fifo(spi_engine
))
448 int_enable
|= SPI_ENGINE_INT_CMD_ALMOST_EMPTY
;
450 spi_engine_tx_next(spi_engine
);
451 if (spi_engine_write_tx_fifo(spi_engine
))
452 int_enable
|= SPI_ENGINE_INT_SDO_ALMOST_EMPTY
;
454 spi_engine_rx_next(spi_engine
);
455 if (spi_engine
->rx_length
!= 0)
456 int_enable
|= SPI_ENGINE_INT_SDI_ALMOST_FULL
;
458 int_enable
|= SPI_ENGINE_INT_SYNC
;
460 writel_relaxed(int_enable
,
461 spi_engine
->base
+ SPI_ENGINE_REG_INT_ENABLE
);
462 spi_engine
->int_enable
= int_enable
;
463 spin_unlock_irqrestore(&spi_engine
->lock
, flags
);
468 static int spi_engine_probe(struct platform_device
*pdev
)
470 struct spi_engine
*spi_engine
;
471 struct spi_master
*master
;
472 unsigned int version
;
476 irq
= platform_get_irq(pdev
, 0);
480 spi_engine
= devm_kzalloc(&pdev
->dev
, sizeof(*spi_engine
), GFP_KERNEL
);
484 master
= spi_alloc_master(&pdev
->dev
, 0);
488 spi_master_set_devdata(master
, spi_engine
);
490 spin_lock_init(&spi_engine
->lock
);
492 spi_engine
->base
= devm_platform_ioremap_resource(pdev
, 0);
493 if (IS_ERR(spi_engine
->base
)) {
494 ret
= PTR_ERR(spi_engine
->base
);
498 version
= readl(spi_engine
->base
+ SPI_ENGINE_REG_VERSION
);
499 if (SPI_ENGINE_VERSION_MAJOR(version
) != 1) {
500 dev_err(&pdev
->dev
, "Unsupported peripheral version %u.%u.%c\n",
501 SPI_ENGINE_VERSION_MAJOR(version
),
502 SPI_ENGINE_VERSION_MINOR(version
),
503 SPI_ENGINE_VERSION_PATCH(version
));
508 spi_engine
->clk
= devm_clk_get(&pdev
->dev
, "s_axi_aclk");
509 if (IS_ERR(spi_engine
->clk
)) {
510 ret
= PTR_ERR(spi_engine
->clk
);
514 spi_engine
->ref_clk
= devm_clk_get(&pdev
->dev
, "spi_clk");
515 if (IS_ERR(spi_engine
->ref_clk
)) {
516 ret
= PTR_ERR(spi_engine
->ref_clk
);
520 ret
= clk_prepare_enable(spi_engine
->clk
);
524 ret
= clk_prepare_enable(spi_engine
->ref_clk
);
526 goto err_clk_disable
;
528 writel_relaxed(0x00, spi_engine
->base
+ SPI_ENGINE_REG_RESET
);
529 writel_relaxed(0xff, spi_engine
->base
+ SPI_ENGINE_REG_INT_PENDING
);
530 writel_relaxed(0x00, spi_engine
->base
+ SPI_ENGINE_REG_INT_ENABLE
);
532 ret
= request_irq(irq
, spi_engine_irq
, 0, pdev
->name
, master
);
534 goto err_ref_clk_disable
;
536 master
->dev
.of_node
= pdev
->dev
.of_node
;
537 master
->mode_bits
= SPI_CPOL
| SPI_CPHA
| SPI_3WIRE
;
538 master
->bits_per_word_mask
= SPI_BPW_MASK(8);
539 master
->max_speed_hz
= clk_get_rate(spi_engine
->ref_clk
) / 2;
540 master
->transfer_one_message
= spi_engine_transfer_one_message
;
541 master
->num_chipselect
= 8;
543 ret
= spi_register_master(master
);
547 platform_set_drvdata(pdev
, master
);
551 free_irq(irq
, master
);
553 clk_disable_unprepare(spi_engine
->ref_clk
);
555 clk_disable_unprepare(spi_engine
->clk
);
557 spi_master_put(master
);
561 static int spi_engine_remove(struct platform_device
*pdev
)
563 struct spi_master
*master
= spi_master_get(platform_get_drvdata(pdev
));
564 struct spi_engine
*spi_engine
= spi_master_get_devdata(master
);
565 int irq
= platform_get_irq(pdev
, 0);
567 spi_unregister_master(master
);
569 free_irq(irq
, master
);
571 spi_master_put(master
);
573 writel_relaxed(0xff, spi_engine
->base
+ SPI_ENGINE_REG_INT_PENDING
);
574 writel_relaxed(0x00, spi_engine
->base
+ SPI_ENGINE_REG_INT_ENABLE
);
575 writel_relaxed(0x01, spi_engine
->base
+ SPI_ENGINE_REG_RESET
);
577 clk_disable_unprepare(spi_engine
->ref_clk
);
578 clk_disable_unprepare(spi_engine
->clk
);
583 static const struct of_device_id spi_engine_match_table
[] = {
584 { .compatible
= "adi,axi-spi-engine-1.00.a" },
587 MODULE_DEVICE_TABLE(of
, spi_engine_match_table
);
589 static struct platform_driver spi_engine_driver
= {
590 .probe
= spi_engine_probe
,
591 .remove
= spi_engine_remove
,
593 .name
= "spi-engine",
594 .of_match_table
= spi_engine_match_table
,
597 module_platform_driver(spi_engine_driver
);
599 MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
600 MODULE_DESCRIPTION("Analog Devices SPI engine peripheral driver");
601 MODULE_LICENSE("GPL");