[PATCH 5/7] spi: realtek-rtl: set transfer mode in, transfer_one_message()

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Refactor the SPI transfer function to allow support for parallel IO.
Use transfer_one_message() instead of the generic transfer_one()
for the necessary HW control for the transfer.

Signed-off-by: Birger Koblitz <mail@xxxxxxxxxxxxxxxxx>
---
 drivers/spi/spi-realtek-rtl.c | 84 ++++++++++++++++++++++-------------
 1 file changed, 54 insertions(+), 30 deletions(-)

diff --git a/drivers/spi/spi-realtek-rtl.c b/drivers/spi/spi-realtek-rtl.c
index 25a90493bf6e..21c0dc16c8cc 100644
--- a/drivers/spi/spi-realtek-rtl.c
+++ b/drivers/spi/spi-realtek-rtl.c
@@ -140,42 +140,66 @@ static void set_mode(struct rtspi *rtspi, unsigned int mode)
 	writel(value, REG(RTL_SPI_SFCSR));
 }

-static int transfer_one(struct spi_controller *ctrl, struct spi_device *spi,
-			struct spi_transfer *xfer)
+static void raw_write(struct rtspi *rtspi, const void *tx_buf, int cnt)
+{
+	while (cnt >= 4) {
+		send4(rtspi, tx_buf);
+		tx_buf += 4;
+		cnt -= 4;
+	}
+	while (cnt) {
+		send1(rtspi, tx_buf);
+		tx_buf++;
+		cnt--;
+	}
+}
+
+static void raw_read(struct rtspi *rtspi, void *rx_buf, int cnt)
+{
+	while (cnt >= 4) {
+		rcv4(rtspi, rx_buf);
+		rx_buf += 4;
+		cnt -= 4;
+	}
+	while (cnt) {
+		rcv1(rtspi, rx_buf);
+		rx_buf++;
+		cnt--;
+	}
+}
+
+static int transfer_one_message(struct spi_controller *ctrl, struct spi_message *m)
 {
 	struct rtspi *rtspi = spi_controller_get_devdata(ctrl);
-	void *rx_buf;
-	const void *tx_buf;
+	struct spi_device *spi = m->spi;
+	struct spi_transfer *xfer = NULL;
+	int status = 0;
 	int cnt;

-	tx_buf = xfer->tx_buf;
-	rx_buf = xfer->rx_buf;
-	cnt = xfer->len;
-	if (tx_buf) {
-		while (cnt >= 4) {
-			send4(rtspi, tx_buf);
-			tx_buf += 4;
-			cnt -= 4;
-		}
-		while (cnt) {
-			send1(rtspi, tx_buf);
-			tx_buf++;
-			cnt--;
-		}
-	} else if (rx_buf) {
-		while (cnt >= 4) {
-			rcv4(rtspi, rx_buf);
-			rx_buf += 4;
-			cnt -= 4;
-		}
-		while (cnt) {
-			rcv1(rtspi, rx_buf);
-			rx_buf++;
-			cnt--;
+	wait_ready(rtspi);
+
+	/* Assert CS */
+	rt_set_cs(spi, false);
+
+	m->actual_length = 0;
+	list_for_each_entry(xfer, &m->transfers, transfer_list) {
+		cnt = xfer->len;
+		if (xfer->rx_buf) {
+			set_mode(rtspi, xfer->rx_nbits);
+			raw_read(rtspi, xfer->rx_buf, cnt);
+		} else if (xfer->tx_buf) {
+			set_mode(rtspi, xfer->tx_nbits);
+			raw_write(rtspi, xfer->tx_buf, cnt);
 		}
+		m->actual_length += xfer->len;
 	}

-	spi_finalize_current_transfer(ctrl);
+	/* Wait until transfer finished and de-assert CS */
+	wait_ready(rtspi);
+	rt_set_cs(spi, true);
+
+	m->status = status;
+	spi_finalize_current_message(ctrl);

 	return 0;
 }
@@ -223,7 +247,7 @@ static int realtek_rtl_spi_probe(struct platform_device *pdev)
 	if (rtspi->dev_flags & SPI_QUAD_SUPPORTED)
 		ctrl->flags |= SPI_TX_QUAD | SPI_RX_QUAD;
 	ctrl->set_cs = rt_set_cs;
-	ctrl->transfer_one = transfer_one;
+	ctrl->transfer_one_message = transfer_one_message;
 	ctrl->num_chipselect = rtspi->dev_flags & SPI_CSMAX_3?4:2;
 	rtspi->cs_all = RTL_SPI_SFCSR_CSB0 | RTL_SPI_SFCSR_CSB1;
 	if (rtspi->dev_flags & SPI_CSMAX_3)
--
2.25.1




[Index of Archives]     [Linux Kernel]     [Linux ARM (vger)]     [Linux ARM MSM]     [Linux Omap]     [Linux Arm]     [Linux Tegra]     [Fedora ARM]     [Linux for Samsung SOC]     [eCos]     [Linux Fastboot]     [Gcc Help]     [Git]     [DCCP]     [IETF Announce]     [Security]     [Linux MIPS]     [Yosemite Campsites]

  Powered by Linux