int spi_xfer(struct spi_slave *slave, unsigned int bitlen, const void *dout, void *din, unsigned long flags) { struct fsl_qspi *qspi = to_qspi_spi(slave); u32 bytes = DIV_ROUND_UP(bitlen, 8); static u32 pp_sfaddr; u32 txbuf; if (dout) { memcpy(&txbuf, dout, 4); qspi->cur_seqid = *(u8 *)dout; if (flags == SPI_XFER_END) { qspi->sf_addr = pp_sfaddr; qspi_op_pp(qspi, (u32 *)dout, bytes); return 0; } if (qspi->cur_seqid == OPCODE_FAST_READ) { qspi->sf_addr = swab32(txbuf) & OFFSET_BITS_MASK; } else if (qspi->cur_seqid == OPCODE_SE) { qspi->sf_addr = swab32(txbuf) & OFFSET_BITS_MASK; qspi_op_se(qspi); } else if (qspi->cur_seqid == OPCODE_PP) { pp_sfaddr = swab32(txbuf) & OFFSET_BITS_MASK; } } if (din) { if (qspi->cur_seqid == OPCODE_FAST_READ) qspi_op_read(qspi, din, bytes); else if (qspi->cur_seqid == OPCODE_RDID) qspi_op_rdid(qspi, din, bytes); else if (qspi->cur_seqid == OPCODE_RDSR) qspi_op_rdsr(qspi, din); } return 0; }
int qspi_xfer(struct fsl_qspi_priv *priv, unsigned int bitlen, const void *dout, void *din, unsigned long flags) { u32 bytes = DIV_ROUND_UP(bitlen, 8); static u32 wr_sfaddr; u32 txbuf; if (dout) { if (flags & SPI_XFER_BEGIN) { priv->cur_seqid = *(u8 *)dout; memcpy(&txbuf, dout, 4); } if (flags == SPI_XFER_END) { priv->sf_addr = wr_sfaddr; qspi_op_write(priv, (u8 *)dout, bytes); return 0; } if (priv->cur_seqid == QSPI_CMD_FAST_READ) { priv->sf_addr = swab32(txbuf) & OFFSET_BITS_MASK; } else if ((priv->cur_seqid == QSPI_CMD_SE) || (priv->cur_seqid == QSPI_CMD_BE_4K)) { priv->sf_addr = swab32(txbuf) & OFFSET_BITS_MASK; qspi_op_erase(priv); } else if (priv->cur_seqid == QSPI_CMD_PP) { wr_sfaddr = swab32(txbuf) & OFFSET_BITS_MASK; } else if ((priv->cur_seqid == QSPI_CMD_BRWR) || (priv->cur_seqid == QSPI_CMD_WREAR)) { #ifdef CONFIG_SPI_FLASH_BAR wr_sfaddr = 0; #endif } } if (din) { if (priv->cur_seqid == QSPI_CMD_FAST_READ) { #ifdef CONFIG_SYS_FSL_QSPI_AHB qspi_ahb_read(priv, din, bytes); #else qspi_op_read(priv, din, bytes); #endif } else if (priv->cur_seqid == QSPI_CMD_RDID) qspi_op_rdid(priv, din, bytes); else if (priv->cur_seqid == QSPI_CMD_RDSR) qspi_op_rdsr(priv, din, bytes); #ifdef CONFIG_SPI_FLASH_BAR else if ((priv->cur_seqid == QSPI_CMD_BRRD) || (priv->cur_seqid == QSPI_CMD_RDEAR)) { priv->sf_addr = 0; qspi_op_rdbank(priv, din, bytes); } #endif } #ifdef CONFIG_SYS_FSL_QSPI_AHB if ((priv->cur_seqid == QSPI_CMD_SE) || (priv->cur_seqid == QSPI_CMD_PP) || (priv->cur_seqid == QSPI_CMD_BE_4K) || (priv->cur_seqid == QSPI_CMD_WREAR) || (priv->cur_seqid == QSPI_CMD_BRWR)) qspi_ahb_invalid(priv); #endif return 0; }