Lines Matching +full:mt2712 +full:- +full:spi +full:- +full:slave
1 // SPDX-License-Identifier: GPL-2.0+
6 #include <linux/dma-mapping.h>
12 #include <linux/spi/spi.h>
90 { .compatible = "mediatek,mt2712-spi-slave",
92 { .compatible = "mediatek,mt8195-spi-slave",
102 reg_val = readl(mdata->base + SPIS_DMA_CFG_REG); in mtk_spi_slave_disable_dma()
105 writel(reg_val, mdata->base + SPIS_DMA_CFG_REG); in mtk_spi_slave_disable_dma()
112 reg_val = readl(mdata->base + SPIS_CFG_REG); in mtk_spi_slave_disable_xfer()
115 writel(reg_val, mdata->base + SPIS_CFG_REG); in mtk_spi_slave_disable_xfer()
120 if (wait_for_completion_interruptible(&mdata->xfer_done) || in mtk_spi_slave_wait_for_completion()
121 mdata->target_aborted) { in mtk_spi_slave_wait_for_completion()
122 dev_err(mdata->dev, "interrupted\n"); in mtk_spi_slave_wait_for_completion()
123 return -EINTR; in mtk_spi_slave_wait_for_completion()
133 struct spi_device *spi = msg->spi; in mtk_spi_slave_prepare_message() local
137 cpha = spi->mode & SPI_CPHA ? 1 : 0; in mtk_spi_slave_prepare_message()
138 cpol = spi->mode & SPI_CPOL ? 1 : 0; in mtk_spi_slave_prepare_message()
140 reg_val = readl(mdata->base + SPIS_CFG_REG); in mtk_spi_slave_prepare_message()
150 if (spi->mode & SPI_LSB_FIRST) in mtk_spi_slave_prepare_message()
157 writel(reg_val, mdata->base + SPIS_CFG_REG); in mtk_spi_slave_prepare_message()
163 struct spi_device *spi, in mtk_spi_slave_fifo_transfer() argument
169 writel(SPIS_SOFT_RST, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_fifo_transfer()
171 reg_val = readl(mdata->base + SPIS_CFG_REG); in mtk_spi_slave_fifo_transfer()
172 if (xfer->rx_buf) in mtk_spi_slave_fifo_transfer()
174 if (xfer->tx_buf) in mtk_spi_slave_fifo_transfer()
176 writel(reg_val, mdata->base + SPIS_CFG_REG); in mtk_spi_slave_fifo_transfer()
178 cnt = xfer->len / 4; in mtk_spi_slave_fifo_transfer()
179 if (xfer->tx_buf) in mtk_spi_slave_fifo_transfer()
180 iowrite32_rep(mdata->base + SPIS_TX_DATA_REG, in mtk_spi_slave_fifo_transfer()
181 xfer->tx_buf, cnt); in mtk_spi_slave_fifo_transfer()
183 remainder = xfer->len % 4; in mtk_spi_slave_fifo_transfer()
184 if (xfer->tx_buf && remainder > 0) { in mtk_spi_slave_fifo_transfer()
186 memcpy(®_val, xfer->tx_buf + cnt * 4, remainder); in mtk_spi_slave_fifo_transfer()
187 writel(reg_val, mdata->base + SPIS_TX_DATA_REG); in mtk_spi_slave_fifo_transfer()
193 writel(SPIS_SOFT_RST, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_fifo_transfer()
200 struct spi_device *spi, in mtk_spi_slave_dma_transfer() argument
204 struct device *dev = mdata->dev; in mtk_spi_slave_dma_transfer()
207 writel(SPIS_SOFT_RST, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_dma_transfer()
209 if (xfer->tx_buf) { in mtk_spi_slave_dma_transfer()
213 void *nonconst_tx = (void *)xfer->tx_buf; in mtk_spi_slave_dma_transfer()
215 xfer->tx_dma = dma_map_single(dev, nonconst_tx, in mtk_spi_slave_dma_transfer()
216 xfer->len, DMA_TO_DEVICE); in mtk_spi_slave_dma_transfer()
217 if (dma_mapping_error(dev, xfer->tx_dma)) { in mtk_spi_slave_dma_transfer()
218 ret = -ENOMEM; in mtk_spi_slave_dma_transfer()
223 if (xfer->rx_buf) { in mtk_spi_slave_dma_transfer()
224 xfer->rx_dma = dma_map_single(dev, xfer->rx_buf, in mtk_spi_slave_dma_transfer()
225 xfer->len, DMA_FROM_DEVICE); in mtk_spi_slave_dma_transfer()
226 if (dma_mapping_error(dev, xfer->rx_dma)) { in mtk_spi_slave_dma_transfer()
227 ret = -ENOMEM; in mtk_spi_slave_dma_transfer()
232 writel(xfer->tx_dma, mdata->base + SPIS_TX_SRC_REG); in mtk_spi_slave_dma_transfer()
233 writel(xfer->rx_dma, mdata->base + SPIS_RX_DST_REG); in mtk_spi_slave_dma_transfer()
235 writel(SPIS_DMA_ADDR_EN, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_dma_transfer()
238 reg_val = readl(mdata->base + SPIS_CFG_REG); in mtk_spi_slave_dma_transfer()
239 if (xfer->tx_buf) in mtk_spi_slave_dma_transfer()
241 if (xfer->rx_buf) in mtk_spi_slave_dma_transfer()
243 writel(reg_val, mdata->base + SPIS_CFG_REG); in mtk_spi_slave_dma_transfer()
247 reg_val |= (xfer->len - 1) & TX_DMA_LEN; in mtk_spi_slave_dma_transfer()
248 writel(reg_val, mdata->base + SPIS_DMA_CFG_REG); in mtk_spi_slave_dma_transfer()
250 reg_val = readl(mdata->base + SPIS_DMA_CFG_REG); in mtk_spi_slave_dma_transfer()
251 if (xfer->tx_buf) in mtk_spi_slave_dma_transfer()
253 if (xfer->rx_buf) in mtk_spi_slave_dma_transfer()
256 writel(reg_val, mdata->base + SPIS_DMA_CFG_REG); in mtk_spi_slave_dma_transfer()
265 if (xfer->rx_buf) in mtk_spi_slave_dma_transfer()
266 dma_unmap_single(dev, xfer->rx_dma, in mtk_spi_slave_dma_transfer()
267 xfer->len, DMA_FROM_DEVICE); in mtk_spi_slave_dma_transfer()
270 if (xfer->tx_buf) in mtk_spi_slave_dma_transfer()
271 dma_unmap_single(dev, xfer->tx_dma, in mtk_spi_slave_dma_transfer()
272 xfer->len, DMA_TO_DEVICE); in mtk_spi_slave_dma_transfer()
277 writel(SPIS_SOFT_RST, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_dma_transfer()
283 struct spi_device *spi, in mtk_spi_slave_transfer_one() argument
288 reinit_completion(&mdata->xfer_done); in mtk_spi_slave_transfer_one()
289 mdata->target_aborted = false; in mtk_spi_slave_transfer_one()
290 mdata->cur_transfer = xfer; in mtk_spi_slave_transfer_one()
292 if (xfer->len > mdata->dev_comp->max_fifo_size) in mtk_spi_slave_transfer_one()
293 return mtk_spi_slave_dma_transfer(ctlr, spi, xfer); in mtk_spi_slave_transfer_one()
295 return mtk_spi_slave_fifo_transfer(ctlr, spi, xfer); in mtk_spi_slave_transfer_one()
298 static int mtk_spi_slave_setup(struct spi_device *spi) in mtk_spi_slave_setup() argument
300 struct mtk_spi_slave *mdata = spi_controller_get_devdata(spi->controller); in mtk_spi_slave_setup()
305 writel(reg_val, mdata->base + SPIS_IRQ_EN_REG); in mtk_spi_slave_setup()
309 writel(reg_val, mdata->base + SPIS_IRQ_MASK_REG); in mtk_spi_slave_setup()
321 mdata->target_aborted = true; in mtk_target_abort()
322 complete(&mdata->xfer_done); in mtk_target_abort()
331 struct spi_transfer *trans = mdata->cur_transfer; in mtk_spi_slave_interrupt()
334 int_status = readl(mdata->base + SPIS_IRQ_ST_REG); in mtk_spi_slave_interrupt()
335 writel(int_status, mdata->base + SPIS_IRQ_CLR_REG); in mtk_spi_slave_interrupt()
343 writel(SPIS_SOFT_RST, mdata->base + SPIS_SOFT_RST_REG); in mtk_spi_slave_interrupt()
345 if (trans->tx_buf) in mtk_spi_slave_interrupt()
346 dma_unmap_single(mdata->dev, trans->tx_dma, in mtk_spi_slave_interrupt()
347 trans->len, DMA_TO_DEVICE); in mtk_spi_slave_interrupt()
348 if (trans->rx_buf) in mtk_spi_slave_interrupt()
349 dma_unmap_single(mdata->dev, trans->rx_dma, in mtk_spi_slave_interrupt()
350 trans->len, DMA_FROM_DEVICE); in mtk_spi_slave_interrupt()
359 cnt = trans->len / 4; in mtk_spi_slave_interrupt()
360 if (trans->rx_buf) in mtk_spi_slave_interrupt()
361 ioread32_rep(mdata->base + SPIS_RX_DATA_REG, in mtk_spi_slave_interrupt()
362 trans->rx_buf, cnt); in mtk_spi_slave_interrupt()
363 remainder = trans->len % 4; in mtk_spi_slave_interrupt()
364 if (trans->rx_buf && remainder > 0) { in mtk_spi_slave_interrupt()
365 reg_val = readl(mdata->base + SPIS_RX_DATA_REG); in mtk_spi_slave_interrupt()
366 memcpy(trans->rx_buf + (cnt * 4), in mtk_spi_slave_interrupt()
374 dev_warn(&ctlr->dev, "cmd invalid\n"); in mtk_spi_slave_interrupt()
378 mdata->cur_transfer = NULL; in mtk_spi_slave_interrupt()
379 complete(&mdata->xfer_done); in mtk_spi_slave_interrupt()
391 ctlr = spi_alloc_slave(&pdev->dev, sizeof(*mdata)); in mtk_spi_slave_probe()
393 dev_err(&pdev->dev, "failed to alloc spi slave\n"); in mtk_spi_slave_probe()
394 return -ENOMEM; in mtk_spi_slave_probe()
397 ctlr->auto_runtime_pm = true; in mtk_spi_slave_probe()
398 ctlr->dev.of_node = pdev->dev.of_node; in mtk_spi_slave_probe()
399 ctlr->mode_bits = SPI_CPOL | SPI_CPHA; in mtk_spi_slave_probe()
400 ctlr->mode_bits |= SPI_LSB_FIRST; in mtk_spi_slave_probe()
402 ctlr->prepare_message = mtk_spi_slave_prepare_message; in mtk_spi_slave_probe()
403 ctlr->transfer_one = mtk_spi_slave_transfer_one; in mtk_spi_slave_probe()
404 ctlr->setup = mtk_spi_slave_setup; in mtk_spi_slave_probe()
405 ctlr->target_abort = mtk_target_abort; in mtk_spi_slave_probe()
407 of_id = of_match_node(mtk_spi_slave_of_match, pdev->dev.of_node); in mtk_spi_slave_probe()
409 dev_err(&pdev->dev, "failed to probe of_node\n"); in mtk_spi_slave_probe()
410 ret = -EINVAL; in mtk_spi_slave_probe()
414 mdata->dev_comp = of_id->data; in mtk_spi_slave_probe()
416 if (mdata->dev_comp->must_rx) in mtk_spi_slave_probe()
417 ctlr->flags = SPI_CONTROLLER_MUST_RX; in mtk_spi_slave_probe()
421 init_completion(&mdata->xfer_done); in mtk_spi_slave_probe()
422 mdata->dev = &pdev->dev; in mtk_spi_slave_probe()
423 mdata->base = devm_platform_ioremap_resource(pdev, 0); in mtk_spi_slave_probe()
424 if (IS_ERR(mdata->base)) { in mtk_spi_slave_probe()
425 ret = PTR_ERR(mdata->base); in mtk_spi_slave_probe()
435 ret = devm_request_irq(&pdev->dev, irq, mtk_spi_slave_interrupt, in mtk_spi_slave_probe()
436 IRQF_TRIGGER_NONE, dev_name(&pdev->dev), ctlr); in mtk_spi_slave_probe()
438 dev_err(&pdev->dev, "failed to register irq (%d)\n", ret); in mtk_spi_slave_probe()
442 mdata->spi_clk = devm_clk_get(&pdev->dev, "spi"); in mtk_spi_slave_probe()
443 if (IS_ERR(mdata->spi_clk)) { in mtk_spi_slave_probe()
444 ret = PTR_ERR(mdata->spi_clk); in mtk_spi_slave_probe()
445 dev_err(&pdev->dev, "failed to get spi-clk: %d\n", ret); in mtk_spi_slave_probe()
449 ret = clk_prepare_enable(mdata->spi_clk); in mtk_spi_slave_probe()
451 dev_err(&pdev->dev, "failed to enable spi_clk (%d)\n", ret); in mtk_spi_slave_probe()
455 pm_runtime_enable(&pdev->dev); in mtk_spi_slave_probe()
457 ret = devm_spi_register_controller(&pdev->dev, ctlr); in mtk_spi_slave_probe()
459 dev_err(&pdev->dev, in mtk_spi_slave_probe()
460 "failed to register slave controller(%d)\n", ret); in mtk_spi_slave_probe()
461 clk_disable_unprepare(mdata->spi_clk); in mtk_spi_slave_probe()
465 clk_disable_unprepare(mdata->spi_clk); in mtk_spi_slave_probe()
470 pm_runtime_disable(&pdev->dev); in mtk_spi_slave_probe()
479 pm_runtime_disable(&pdev->dev); in mtk_spi_slave_remove()
494 clk_disable_unprepare(mdata->spi_clk); in mtk_spi_slave_suspend()
506 ret = clk_prepare_enable(mdata->spi_clk); in mtk_spi_slave_resume()
515 clk_disable_unprepare(mdata->spi_clk); in mtk_spi_slave_resume()
527 clk_disable_unprepare(mdata->spi_clk); in mtk_spi_slave_runtime_suspend()
538 ret = clk_prepare_enable(mdata->spi_clk); in mtk_spi_slave_runtime_resume()
556 .name = "mtk-spi-slave",
566 MODULE_DESCRIPTION("MTK SPI Slave Controller driver");
569 MODULE_ALIAS("platform:mtk-spi-slave");