[U-Boot] [PATCH 2/8] sf: Use mtd_info ops instead of spi_flash ops

Heiko Schocher
2015-10-29T06:29:23Z

Hello Jagan,

Am 12.10.2015 um 21:54 schrieb Jagan Teki:
> Since MTD support is added in spi_flash layer, this patch uses
> mtd_info operations instead of legacy spi_flash operations.
>
> Signed-off-by: Jagan Teki <jteki@openedev.com>
> ---
> drivers/mtd/spi/sf_ops.c | 66 ++++++++++++++++++++++++++++--------------------
> include/spi_flash.h | 24 ++++++++----------
> 2 files changed, 49 insertions(+), 41 deletions(-)

Reviewed-by: Heiko Schocher <hs@denx.de>

bye,
Heiko
>
> diff --git a/drivers/mtd/spi/sf_ops.c b/drivers/mtd/spi/sf_ops.c
> index f5ee376..d10ca45 100644
> --- a/drivers/mtd/spi/sf_ops.c
> +++ b/drivers/mtd/spi/sf_ops.c
> @@ -296,18 +296,16 @@ int spi_flash_write_common(struct spi_flash *flash, const u8 *cmd,
> return ret;
> }
>
> -static int spi_flash_cmd_erase_ops(struct spi_flash *flash, u32 offset,
> - size_t len)
> +static int spi_flash_cmd_erase_ops(struct mtd_info *mtd,
> + struct erase_info *instr)
> {
> - u32 erase_size, erase_addr;
> + struct spi_flash *flash = mtd->priv;
> + u32 offset, len, erase_addr;
> u8 cmd[SPI_FLASH_CMD_LEN];
> int ret = -1;
>
> - erase_size = mtd->erasesize;
> - if (offset % erase_size || len % erase_size) {
> - debug("SF: Erase offset/length not multiple of erase size\n");
> - return -1;
> - }
> + offset = instr->addr;
> + len = instr->len;
>
> cmd[0] = flash->erase_cmd;
> while (len) {
> @@ -330,19 +328,24 @@ static int spi_flash_cmd_erase_ops(struct spi_flash *flash, u32 offset,
> ret = spi_flash_write_common(flash, cmd, sizeof(cmd), NULL, 0);
> if (ret < 0) {
> debug("SF: erase failed\n");
> - break;
> + goto erase_err;
> }
>
> - offset += erase_size;
> - len -= erase_size;
> + offset += mtd->erasesize;
> + len -= mtd->erasesize;
> }
>
> return ret;
> +
> +erase_err:
> + instr->state = MTD_ERASE_FAILED;
> + return ret;
> }
>
> -static int spi_flash_cmd_write_ops(struct spi_flash *flash, u32 offset,
> - size_t len, const void *buf)
> +static int spi_flash_cmd_write_ops(struct mtd_info *mtd, loff_t offset,
> + size_t len, size_t *retlen, const u_char *buf)
> {
> + struct spi_flash *flash = mtd->priv;
> unsigned long byte_addr, page_size;
> u32 write_addr;
> size_t chunk_len, actual;
> @@ -384,6 +387,7 @@ static int spi_flash_cmd_write_ops(struct spi_flash *flash, u32 offset,
> }
>
> offset += chunk_len;
> + *retlen += chunk_len;
> }
>
> return ret;
> @@ -417,11 +421,12 @@ void __weak spi_flash_copy_mmap(void *data, void *offset, size_t len)
> memcpy(data, offset, len);
> }
>
> -static int spi_flash_cmd_read_ops(struct spi_flash *flash, u32 offset,
> - size_t len, void *data)
> +static int spi_flash_cmd_read_ops(struct mtd_info *mtd, loff_t offset,
> + size_t len, size_t *retlen, u_char *data)
> {
> - u8 *cmd, cmdsz;
> + struct spi_flash *flash = mtd->priv;
> u32 remain_len, read_len, read_addr;
> + u8 *cmd, cmdsz;
> int bank_sel = 0;
> int ret = -1;
>
> @@ -478,6 +483,7 @@ static int spi_flash_cmd_read_ops(struct spi_flash *flash, u32 offset,
> offset += read_len;
> len -= read_len;
> data += read_len;
> + *retlen += read_len;
> }
>
> free(cmd);
> @@ -485,7 +491,8 @@ static int spi_flash_cmd_read_ops(struct spi_flash *flash, u32 offset,
> }
>
> #ifdef CONFIG_SPI_FLASH_SST
> -static int sst_byte_write(struct spi_flash *flash, u32 offset, const void *buf)
> +static int sst_byte_write(struct spi_flash *flash, u32 offset,
> + const void *buf, size_t *retlen)
> {
> int ret;
> u8 cmd[4] = {
> @@ -506,12 +513,15 @@ static int sst_byte_write(struct spi_flash *flash, u32 offset, const void *buf)
> if (ret)
> return ret;
>
> + *retlen += 1;
> +
> return spi_flash_cmd_wait_ready(flash, SPI_FLASH_PROG_TIMEOUT);
> }
>
> -static int sst_write_wp(struct spi_flash *flash, u32 offset, size_t len,
> - const void *buf)
> +static int sst_write_wp(struct mtd_info *mtd, loff_t offset, size_t len,
> + size_t *retlen, const u_char *buf)
> {
> + struct spi_flash *flash = mtd->priv;
> size_t actual, cmd_len;
> int ret;
> u8 cmd[4];
> @@ -525,7 +535,7 @@ static int sst_write_wp(struct spi_flash *flash, u32 offset, size_t len,
> /* If the data is not word aligned, write out leading single byte */
> actual = offset % 2;
> if (actual) {
> - ret = sst_byte_write(flash, offset, buf);
> + ret = sst_byte_write(flash, offset, buf, retlen);
> if (ret)
> goto done;
> }
> @@ -542,7 +552,7 @@ static int sst_write_wp(struct spi_flash *flash, u32 offset, size_t len,
> cmd[3] = offset;
>
> for (; actual < len - 1; actual += 2) {
> - debug("WP[%02x]: 0x%p => cmd = { 0x%02x 0x%06x }\n",
> + debug("WP[%02x]: 0x%p => cmd = { 0x%02x 0x%06llx }\n",
> spi_w8r8(flash->spi, CMD_READ_STATUS), buf + actual,
> cmd[0], offset);
>
> @@ -559,6 +569,7 @@ static int sst_write_wp(struct spi_flash *flash, u32 offset, size_t len,
>
> cmd_len = 1;
> offset += 2;
> + *retlen += 2;
> }
>
> if (!ret)
> @@ -566,19 +577,20 @@ static int sst_write_wp(struct spi_flash *flash, u32 offset, size_t len,
>
> /* If there is a single trailing byte, write it out */
> if (!ret && actual != len)
> - ret = sst_byte_write(flash, offset, buf + actual);
> + ret = sst_byte_write(flash, offset, buf + actual, retlen);
>
> done:
> - debug("SF: sst: program %s %zu bytes @ 0x%zx\n",
> + debug("SF: sst: program %s %zu bytes @ 0x%llx\n",
> ret ? "failure" : "success", len, offset - actual);
>
> spi_release_bus(flash->spi);
> return ret;
> }
>
> -static int sst_write_bp(struct spi_flash *flash, u32 offset, size_t len,
> - const void *buf)
> +static int sst_write_bp(struct mtd_info *mtd, loff_t offset, size_t len,
> + size_t *retlen, const u_char *buf)
> {
> + struct spi_flash *flash = mtd->priv;
> size_t actual;
> int ret;
>
> @@ -589,7 +601,7 @@ static int sst_write_bp(struct spi_flash *flash, u32 offset, size_t len,
> }
>
> for (actual = 0; actual < len; actual++) {
> - ret = sst_byte_write(flash, offset, buf + actual);
> + ret = sst_byte_write(flash, offset, buf + actual, retlen);
> if (ret) {
> debug("SF: sst byte program failed\n");
> break;
> @@ -600,7 +612,7 @@ static int sst_write_bp(struct spi_flash *flash, u32 offset, size_t len,
> if (!ret)
> ret = spi_flash_cmd_write_disable(flash);
>
> - debug("SF: sst: program %s %zu bytes @ 0x%zx\n",
> + debug("SF: sst: program %s %zu bytes @ 0x%llx\n",
> ret ? "failure" : "success", len, offset - actual);
>
> spi_release_bus(flash->spi);
> diff --git a/include/spi_flash.h b/include/spi_flash.h
> index d0af8d3..fe03b8d 100644
> --- a/include/spi_flash.h
> +++ b/include/spi_flash.h
> @@ -55,13 +55,6 @@ struct spi_slave;
> * @dummy_byte: Dummy cycles for read operation.
> * @memory_map: Address of read-only SPI flash access
> * @priv: the private data
> - * @read: Flash read ops: Read len bytes at offset into buf
> - * Supported cmds: Fast Array Read
> - * @write: Flash write ops: Write len bytes from buf into offset
> - * Supported cmds: Page Program
> - * @erase: Flash erase ops: Erase len bytes from offset
> - * Supported cmds: Sector erase 4K, 32K, 64K
> - * return 0 - Success, 1 - Failure
> */
> struct spi_flash {
> struct mtd_info *mtd;
> @@ -88,10 +81,6 @@ struct spi_flash {
>
> void *memory_map;
> void *priv;
> - int (*read)(struct spi_flash *flash, u32 offset, size_t len, void *buf);
> - int (*write)(struct spi_flash *flash, u32 offset, size_t len,
> - const void *buf);
> - int (*erase)(struct spi_flash *flash, u32 offset, size_t len);
> };
>
> struct dm_spi_flash_ops {
> @@ -156,19 +145,26 @@ int spi_flash_remove(struct udevice *flash);
> static inline int spi_flash_read(struct spi_flash *flash, u32 offset,
> size_t len, void *buf)
> {
> - return spi_flash_read_dm(flash->dev, offset, len, buf);
> + return mtd_read(flash->mtd, offset, len, &len, (u_char *)buf);
> }
>
> static inline int spi_flash_write(struct spi_flash *flash, u32 offset,
> size_t len, const void *buf)
> {
> - return spi_flash_write_dm(flash->dev, offset, len, buf);
> + return mtd_write(flash->mtd, offset, len, &len, (u_char *)buf);
> }
>
> static inline int spi_flash_erase(struct spi_flash *flash, u32 offset,
> size_t len)
> {
> - return spi_flash_erase_dm(flash->dev, offset, len);
> + struct erase_info instr;
> +
> + instr.mtd = flash->mtd;
> + instr.addr = offset;
> + instr.len = len;
> + instr.callback = 0;
> +
> + return mtd_erase(flash->mtd, &instr);
> }
>
> struct sandbox_state;
>

--
DENX Software Engineering GmbH, Managing Director: Wolfgang Denk
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany