]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
spi: fsl-espi: eliminate spi nor flash read loop
authorHeiner Kallweit <hkallweit1@gmail.com>
Wed, 17 Aug 2016 19:11:01 +0000 (21:11 +0200)
committerMark Brown <broonie@kernel.org>
Thu, 18 Aug 2016 10:15:16 +0000 (11:15 +0100)
The fsl-espi driver contains a read loop that implicitely assumes that
the device to read from is a m25p80 SPI NOR flash (bytes 2 - 4 of the
first write transfer are interpreted as 3 byte flash address).

Now that we have such a read loop in the spi-nor driver and are able
to correctly indicate the message size limit of the controller,
the read loop can be removed from the fsl-espi driver.

Signed-off-by: Heiner Kallweit <hkallweit1@gmail.com>
Signed-off-by: Mark Brown <broonie@kernel.org>
drivers/spi/spi-fsl-espi.c

index 8d85a3c343dab635811cf4b6a871a841977fa09f..96a2442c1623b0711fab3b060fe41c9932cb0788 100644 (file)
@@ -258,23 +258,6 @@ static int fsl_espi_bufs(struct spi_device *spi, struct spi_transfer *t)
        return mpc8xxx_spi->count;
 }
 
-static inline void fsl_espi_addr2cmd(unsigned int addr, u8 *cmd)
-{
-       if (cmd) {
-               cmd[1] = (u8)(addr >> 16);
-               cmd[2] = (u8)(addr >> 8);
-               cmd[3] = (u8)(addr >> 0);
-       }
-}
-
-static inline unsigned int fsl_espi_cmd2addr(u8 *cmd)
-{
-       if (cmd)
-               return cmd[1] << 16 | cmd[2] << 8 | cmd[3] << 0;
-
-       return 0;
-}
-
 static void fsl_espi_do_trans(struct spi_message *m,
                                struct fsl_espi_transfer *tr)
 {
@@ -366,68 +349,36 @@ static void fsl_espi_cmd_trans(struct spi_message *m,
 static void fsl_espi_rw_trans(struct spi_message *m,
                                struct fsl_espi_transfer *trans, u8 *rx_buff)
 {
-       struct fsl_espi_transfer *espi_trans = trans;
-       unsigned int total_len = espi_trans->len;
        struct spi_transfer *t;
        u8 *local_buf;
-       u8 *rx_buf = rx_buff;
-       unsigned int trans_len;
-       unsigned int addr;
-       unsigned int tx_only;
-       unsigned int rx_pos = 0;
-       unsigned int pos;
-       int i, loop;
+       unsigned int tx_only = 0;
+       int i = 0;
 
        local_buf = kzalloc(SPCOM_TRANLEN_MAX, GFP_KERNEL);
        if (!local_buf) {
-               espi_trans->status = -ENOMEM;
+               trans->status = -ENOMEM;
                return;
        }
 
-       for (pos = 0, loop = 0; pos < total_len; pos += trans_len, loop++) {
-               trans_len = total_len - pos;
-
-               i = 0;
-               tx_only = 0;
-               list_for_each_entry(t, &m->transfers, transfer_list) {
-                       if (t->tx_buf) {
-                               memcpy(local_buf + i, t->tx_buf, t->len);
-                               i += t->len;
-                               if (!t->rx_buf)
-                                       tx_only += t->len;
-                       }
-               }
-
-               /* Add additional TX bytes to compensate SPCOM_TRANLEN_MAX */
-               if (loop > 0)
-                       trans_len += tx_only;
-
-               if (trans_len > SPCOM_TRANLEN_MAX)
-                       trans_len = SPCOM_TRANLEN_MAX;
-
-               /* Update device offset */
-               if (pos > 0) {
-                       addr = fsl_espi_cmd2addr(local_buf);
-                       addr += rx_pos;
-                       fsl_espi_addr2cmd(addr, local_buf);
+       list_for_each_entry(t, &m->transfers, transfer_list) {
+               if (t->tx_buf) {
+                       memcpy(local_buf + i, t->tx_buf, t->len);
+                       i += t->len;
+                       if (!t->rx_buf)
+                               tx_only += t->len;
                }
+       }
 
-               espi_trans->len = trans_len;
-               espi_trans->tx_buf = local_buf;
-               espi_trans->rx_buf = local_buf;
-               fsl_espi_do_trans(m, espi_trans);
-
-               /* If there is at least one RX byte then copy it to rx_buf */
-               if (tx_only < SPCOM_TRANLEN_MAX)
-                       memcpy(rx_buf + rx_pos, espi_trans->rx_buf + tx_only,
-                                       trans_len - tx_only);
-
-               rx_pos += trans_len - tx_only;
+       trans->tx_buf = local_buf;
+       trans->rx_buf = local_buf;
+       fsl_espi_do_trans(m, trans);
 
-               if (loop > 0)
-                       espi_trans->actual_length += espi_trans->len - tx_only;
-               else
-                       espi_trans->actual_length += espi_trans->len;
+       if (!trans->status) {
+               /* If there is at least one RX byte then copy it to rx_buff */
+               if (trans->len > tx_only)
+                       memcpy(rx_buff, trans->rx_buf + tx_only,
+                              trans->len - tx_only);
+               trans->actual_length += trans->len;
        }
 
        kfree(local_buf);
@@ -663,7 +614,7 @@ static int fsl_espi_runtime_resume(struct device *dev)
 }
 #endif
 
-static size_t fsl_espi_max_transfer_size(struct spi_device *spi)
+static size_t fsl_espi_max_message_size(struct spi_device *spi)
 {
        return SPCOM_TRANLEN_MAX;
 }
@@ -695,7 +646,7 @@ static struct spi_master * fsl_espi_probe(struct device *dev,
        master->cleanup = fsl_espi_cleanup;
        master->transfer_one_message = fsl_espi_do_one_msg;
        master->auto_runtime_pm = true;
-       master->max_transfer_size = fsl_espi_max_transfer_size;
+       master->max_message_size = fsl_espi_max_message_size;
 
        mpc8xxx_spi = spi_master_get_devdata(master);