Lines Matching +full:tx +full:- +full:fifo +full:- +full:max +full:- +full:num
1 // SPDX-License-Identifier: GPL-2.0-only
8 // This code is based on spi-dw-core.c.
26 #define HISI_SPI_FIFOC 0x0c /* fifo level control register */
57 #define SR_TXE BIT(0) /* Transmit FIFO empty */
58 #define SR_TXNF BIT(1) /* Transmit FIFO not full */
59 #define SR_RXNE BIT(2) /* Receive FIFO not empty */
60 #define SR_RXF BIT(3) /* Receive FIFO full */
129 u32 fifo_len; /* depth of the FIFO buffer */
132 const void *tx; member
169 master = container_of(hs->dev, struct spi_controller, dev); in hisi_spi_debugfs_init()
170 snprintf(name, 32, "hisi_spi%d", master->bus_num); in hisi_spi_debugfs_init()
171 hs->debugfs = debugfs_create_dir(name, NULL); in hisi_spi_debugfs_init()
172 if (!hs->debugfs) in hisi_spi_debugfs_init()
173 return -ENOMEM; in hisi_spi_debugfs_init()
175 hs->regset.regs = hisi_spi_regs; in hisi_spi_debugfs_init()
176 hs->regset.nregs = ARRAY_SIZE(hisi_spi_regs); in hisi_spi_debugfs_init()
177 hs->regset.base = hs->regs; in hisi_spi_debugfs_init()
178 debugfs_create_regset32("registers", 0400, hs->debugfs, &hs->regset); in hisi_spi_debugfs_init()
185 return readl(hs->regs + HISI_SPI_SR) & SR_BUSY; in hisi_spi_busy()
190 return readl(hs->regs + HISI_SPI_SR) & SR_RXNE; in hisi_spi_rx_not_empty()
195 return readl(hs->regs + HISI_SPI_SR) & SR_TXNF; in hisi_spi_tx_not_full()
204 readl(hs->regs + HISI_SPI_DOUT); in hisi_spi_flush_fifo()
205 } while (hisi_spi_busy(hs) && limit--); in hisi_spi_flush_fifo()
211 writel(0, hs->regs + HISI_SPI_ENR); in hisi_spi_disable()
212 writel(IMR_MASK, hs->regs + HISI_SPI_IMR); in hisi_spi_disable()
213 writel(ICR_MASK, hs->regs + HISI_SPI_ICR); in hisi_spi_disable()
218 if (transfer->bits_per_word <= 8) in hisi_spi_n_bytes()
220 else if (transfer->bits_per_word <= 16) in hisi_spi_n_bytes()
228 u32 max = min_t(u32, hs->rx_len, hs->fifo_len); in hisi_spi_reader() local
231 while (hisi_spi_rx_not_empty(hs) && max--) { in hisi_spi_reader()
232 rxw = readl(hs->regs + HISI_SPI_DOUT); in hisi_spi_reader()
234 if (hs->rx) { in hisi_spi_reader()
235 switch (hs->n_bytes) { in hisi_spi_reader()
237 *(u8 *)(hs->rx) = rxw; in hisi_spi_reader()
240 *(u16 *)(hs->rx) = rxw; in hisi_spi_reader()
243 *(u32 *)(hs->rx) = rxw; in hisi_spi_reader()
246 hs->rx += hs->n_bytes; in hisi_spi_reader()
248 --hs->rx_len; in hisi_spi_reader()
254 u32 max = min_t(u32, hs->tx_len, hs->fifo_len); in hisi_spi_writer() local
257 while (hisi_spi_tx_not_full(hs) && max--) { in hisi_spi_writer()
258 /* Check the transfer's original "tx" is not null */ in hisi_spi_writer()
259 if (hs->tx) { in hisi_spi_writer()
260 switch (hs->n_bytes) { in hisi_spi_writer()
262 txw = *(u8 *)(hs->tx); in hisi_spi_writer()
265 txw = *(u16 *)(hs->tx); in hisi_spi_writer()
268 txw = *(u32 *)(hs->tx); in hisi_spi_writer()
271 hs->tx += hs->n_bytes; in hisi_spi_writer()
273 writel(txw, hs->regs + HISI_SPI_DIN); in hisi_spi_writer()
274 --hs->tx_len; in hisi_spi_writer()
280 chip->div_pre = DIV_PRE_MAX; in __hisi_calc_div_reg()
281 while (chip->div_pre >= DIV_PRE_MIN) { in __hisi_calc_div_reg()
282 if (chip->clk_div % chip->div_pre == 0) in __hisi_calc_div_reg()
285 chip->div_pre -= 2; in __hisi_calc_div_reg()
288 if (chip->div_pre > chip->clk_div) in __hisi_calc_div_reg()
289 chip->div_pre = chip->clk_div; in __hisi_calc_div_reg()
291 chip->div_post = (chip->clk_div / chip->div_pre) - 1; in __hisi_calc_div_reg()
300 chip->clk_div = DIV_ROUND_UP(master->max_speed_hz, speed_hz) + 1; in hisi_calc_effective_speed()
301 chip->clk_div &= 0xfffe; in hisi_calc_effective_speed()
302 if (chip->clk_div > CLK_DIV_MAX) in hisi_calc_effective_speed()
303 chip->clk_div = CLK_DIV_MAX; in hisi_calc_effective_speed()
305 effective_speed = master->max_speed_hz / chip->clk_div; in hisi_calc_effective_speed()
306 if (chip->speed_hz != effective_speed) { in hisi_calc_effective_speed()
308 chip->speed_hz = effective_speed; in hisi_calc_effective_speed()
318 cr |= FIELD_PREP(CR_CPHA_MASK, (spi->mode & SPI_CPHA) ? 1 : 0); in hisi_spi_prepare_cr()
319 cr |= FIELD_PREP(CR_CPOL_MASK, (spi->mode & SPI_CPOL) ? 1 : 0); in hisi_spi_prepare_cr()
320 cr |= FIELD_PREP(CR_LOOP_MASK, (spi->mode & SPI_LOOP) ? 1 : 0); in hisi_spi_prepare_cr()
329 /* FIFO default config */ in hisi_spi_hw_init()
332 hs->regs + HISI_SPI_FIFOC); in hisi_spi_hw_init()
334 hs->fifo_len = 256; in hisi_spi_hw_init()
341 u32 irq_status = readl(hs->regs + HISI_SPI_ISR) & ISR_MASK; in hisi_spi_irq()
346 if (!master->cur_msg) in hisi_spi_irq()
351 dev_err(hs->dev, "interrupt_transfer: fifo overflow\n"); in hisi_spi_irq()
352 master->cur_msg->status = -EIO; in hisi_spi_irq()
357 * Read data from the Rx FIFO every time. If there is in hisi_spi_irq()
361 if (!hs->rx_len) in hisi_spi_irq()
364 /* Send data out when Tx FIFO IRQ triggered */ in hisi_spi_irq()
381 u32 cr = chip->cr; in hisi_spi_transfer_one()
384 transfer->effective_speed_hz = in hisi_spi_transfer_one()
385 hisi_calc_effective_speed(master, chip, transfer->speed_hz); in hisi_spi_transfer_one()
386 cr |= FIELD_PREP(CR_DIV_PRE_MASK, chip->div_pre); in hisi_spi_transfer_one()
387 cr |= FIELD_PREP(CR_DIV_POST_MASK, chip->div_post); in hisi_spi_transfer_one()
388 cr |= FIELD_PREP(CR_BPW_MASK, transfer->bits_per_word - 1); in hisi_spi_transfer_one()
389 writel(cr, hs->regs + HISI_SPI_CR); in hisi_spi_transfer_one()
393 hs->n_bytes = hisi_spi_n_bytes(transfer); in hisi_spi_transfer_one()
394 hs->tx = transfer->tx_buf; in hisi_spi_transfer_one()
395 hs->tx_len = transfer->len / hs->n_bytes; in hisi_spi_transfer_one()
396 hs->rx = transfer->rx_buf; in hisi_spi_transfer_one()
397 hs->rx_len = hs->tx_len; in hisi_spi_transfer_one()
406 writel(~(u32)IMR_MASK, hs->regs + HISI_SPI_IMR); in hisi_spi_transfer_one()
407 writel(1, hs->regs + HISI_SPI_ENR); in hisi_spi_transfer_one()
435 return -ENOMEM; in hisi_spi_setup()
439 chip->cr = hisi_spi_prepare_cr(spi); in hisi_spi_setup()
454 struct device *dev = &pdev->dev; in hisi_spi_probe()
465 return -ENOMEM; in hisi_spi_probe()
470 hs->dev = dev; in hisi_spi_probe()
471 hs->irq = irq; in hisi_spi_probe()
473 hs->regs = devm_platform_ioremap_resource(pdev, 0); in hisi_spi_probe()
474 if (IS_ERR(hs->regs)) in hisi_spi_probe()
475 return PTR_ERR(hs->regs); in hisi_spi_probe()
478 ret = device_property_read_u32(dev, "spi-max-frequency", in hisi_spi_probe()
479 &master->max_speed_hz); in hisi_spi_probe()
481 dev_err(dev, "failed to get max SPI clocking speed, ret=%d\n", in hisi_spi_probe()
483 return -EINVAL; in hisi_spi_probe()
486 ret = device_property_read_u16(dev, "num-cs", in hisi_spi_probe()
487 &master->num_chipselect); in hisi_spi_probe()
489 master->num_chipselect = DEFAULT_NUM_CS; in hisi_spi_probe()
491 master->use_gpio_descriptors = true; in hisi_spi_probe()
492 master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH | SPI_LOOP; in hisi_spi_probe()
493 master->bits_per_word_mask = SPI_BPW_RANGE_MASK(4, 32); in hisi_spi_probe()
494 master->bus_num = pdev->id; in hisi_spi_probe()
495 master->setup = hisi_spi_setup; in hisi_spi_probe()
496 master->cleanup = hisi_spi_cleanup; in hisi_spi_probe()
497 master->transfer_one = hisi_spi_transfer_one; in hisi_spi_probe()
498 master->handle_err = hisi_spi_handle_err; in hisi_spi_probe()
499 master->dev.fwnode = dev->fwnode; in hisi_spi_probe()
503 ret = devm_request_irq(dev, hs->irq, hisi_spi_irq, 0, dev_name(dev), in hisi_spi_probe()
506 dev_err(dev, "failed to get IRQ=%d, ret=%d\n", hs->irq, ret); in hisi_spi_probe()
519 dev_info(dev, "hw version:0x%x max-freq:%u kHz\n", in hisi_spi_probe()
520 readl(hs->regs + HISI_SPI_VERSION), in hisi_spi_probe()
521 master->max_speed_hz / 1000); in hisi_spi_probe()
531 debugfs_remove_recursive(hs->debugfs); in hisi_spi_remove()
547 .name = "hisi-kunpeng-spi",