From: Kuninori Morimoto <kuninori.morimoto.gx@xxxxxxxxxxx> Current tmio is using sd_ctrl_read16/write16_rep() for data transfer. It works if transfer size was even number, but, last 1 byte will be ignored if transfer size was odd number. This patch adds new tmio_mmc_transfer_data() and solve this issue. Tested-by: Shinobu Uehara <shinobu.uehara.xc@xxxxxxxxxxx> Signed-off-by: Kuninori Morimoto <kuninori.morimoto.gx@xxxxxxxxxxx> --- drivers/mmc/host/tmio_mmc_pio.c | 42 +++++++++++++++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 4 deletions(-) diff --git a/drivers/mmc/host/tmio_mmc_pio.c b/drivers/mmc/host/tmio_mmc_pio.c index ba45413..817ec7d 100644 --- a/drivers/mmc/host/tmio_mmc_pio.c +++ b/drivers/mmc/host/tmio_mmc_pio.c @@ -376,6 +376,43 @@ static int tmio_mmc_start_command(struct tmio_mmc_host *host, struct mmc_command return 0; } +static void tmio_mmc_transfer_data(struct tmio_mmc_host *host, + unsigned short *buf, + unsigned int count) +{ + int is_read = host->data->flags & MMC_DATA_READ; + u16 extra; + u8 *extra8; + u8 *buf8; + + /* + * Transfer the data + */ + if (is_read) + sd_ctrl_read16_rep(host, CTL_SD_DATA_PORT, buf, count >> 1); + else + sd_ctrl_write16_rep(host, CTL_SD_DATA_PORT, buf, count >> 1); + + /* count was even number */ + if (!(count & 0x1)) + return; + + /* count was odd number */ + + extra8 = (u8 *)&extra; + buf8 = (u8 *)(buf + ((count - 1) >> 1)); + + if (is_read) { + extra = sd_ctrl_read16(host, CTL_SD_DATA_PORT); + + buf8[1] = extra8[1]; + } else { + extra = buf8[1] << 8; + + sd_ctrl_write16(host, CTL_SD_DATA_PORT, extra); + } +} + /* * This chip always returns (at least?) as much data as you ask for. * I'm unsure what happens if you ask for less than a block. This should be @@ -408,10 +445,7 @@ static void tmio_mmc_pio_irq(struct tmio_mmc_host *host) count, host->sg_off, data->flags); /* Transfer the data */ - if (data->flags & MMC_DATA_READ) - sd_ctrl_read16_rep(host, CTL_SD_DATA_PORT, buf, count >> 1); - else - sd_ctrl_write16_rep(host, CTL_SD_DATA_PORT, buf, count >> 1); + tmio_mmc_transfer_data(host, buf, count); host->sg_off += count; -- 1.7.9.5 -- To unsubscribe from this list: send the line "unsubscribe linux-mmc" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html