>
> > static inline iowrite8_32_align_rep(void __iomem *fifo, u8 *p, int n)
> > {
> > if (((int)p) & 3) {
> > int align_cnt = 4 -(((int)p) & 3);
> > if (align_cnt > n) align_cnt = n;
> > iowrite8_rep(fifo, p, align_cnt);
> > p += align_cnt;
> > n -= align_cnt;
> > }
> > if (n>>2) {
> > iowrite32_rep(fifo, p, n>>2);
> > p += n & ~3;
> > n &= 3;
> > }
> > if (n)
> > iowrite8_rep(fifo, p, n);
> > }
I tried with both iowrite8_32_align_rep and directly calling iowrite32_rep but
none of these work properly when I tested with SD card in PIO mode after
removing asm code. It has failed to mount. In stead of using either
iowrite8_32_align_rep or iowrite32_rep, I wrote directly to MMCDRR and MMCDXR
in the PIO mode and it has worked properly. I will submit this as patch in next
1-2 days. This also assumes that it will work if access width is 4 bytes. I
feel there is no point in spending time for making generic enough so that it
will support all access width in the PIO mode. Code is available below:
-Purushotam
diff --git a/drivers/mmc/host/davinci_mmc.c b/drivers/mmc/host/davinci_mmc.c
index c631c91..535d55e 100644
--- a/drivers/mmc/host/davinci_mmc.c
+++ b/drivers/mmc/host/davinci_mmc.c
@@ -201,60 +201,6 @@ struct mmc_davinci_host {
};
-#define DAVINCI_MMCSD_READ_FIFO(pDst, pRegs, cnt) asm( \
- " cmp %3,#16\n" \
- "1: ldrhs r0,[%1,%2]\n" \
- " ldrhs r1,[%1,%2]\n" \
- " ldrhs r2,[%1,%2]\n" \
- " ldrhs r3,[%1,%2]\n" \
- " stmhsia %0!,{r0,r1,r2,r3}\n" \
- " beq 3f\n" \
- " subhs %3,%3,#16\n" \
- " cmp %3,#16\n" \
- " bhs 1b\n" \
- " tst %3,#0x0c\n" \
- "2: ldrne r0,[%1,%2]\n" \
- " strne r0,[%0],#4\n" \
- " subne %3,%3,#4\n" \
- " tst %3,#0x0c\n" \
- " bne 2b\n" \
- " tst %3,#2\n" \
- " ldrneh r0,[%1,%2]\n" \
- " strneh r0,[%0],#2\n" \
- " tst %3,#1\n" \
- " ldrneb r0,[%1,%2]\n" \
- " strneb r0,[%0],#1\n" \
- "3:\n" \
- : "+r"(pDst) : "r"(pRegs), "i"(DAVINCI_MMCDRR), \
- "r"(cnt) : "r0", "r1", "r2", "r3");
-
-#define DAVINCI_MMCSD_WRITE_FIFO(pDst, pRegs, cnt) asm( \
- " cmp %3,#16\n" \
- "1: ldmhsia %0!,{r0,r1,r2,r3}\n" \
- " strhs r0,[%1,%2]\n" \
- " strhs r1,[%1,%2]\n" \
- " strhs r2,[%1,%2]\n" \
- " strhs r3,[%1,%2]\n" \
- " beq 3f\n" \
- " subhs %3,%3,#16\n" \
- " cmp %3,#16\n" \
- " bhs 1b\n" \
- " tst %3,#0x0c\n" \
- "2: ldrne r0,[%0],#4\n" \
- " strne r0,[%1,%2]\n" \
- " subne %3,%3,#4\n" \
- " tst %3,#0x0c\n" \
- " bne 2b\n" \
- " tst %3,#2\n" \
- " ldrneh r0,[%0],#2\n" \
- " strneh r0,[%1,%2]\n" \
- " tst %3,#1\n" \
- " ldrneb r0,[%0],#1\n" \
- " strneb r0,[%1,%2]\n" \
- "3:\n" \
- : "+r"(pDst) : "r"(pRegs), "i"(DAVINCI_MMCDXR), \
- "r"(cnt) : "r0", "r1", "r2", "r3");
-
/* PIO only */
static void mmc_davinci_sg_to_buf(struct mmc_davinci_host *host)
{
@@ -270,6 +216,7 @@ static void mmc_davinci_sg_to_buf(struct mmc_davinci_host
*host)
static void davinci_fifo_data_trans(struct mmc_davinci_host *host, int n)
{
u8 *p;
+ int i;
if (host->buffer_bytes_left == 0) {
host->sg_idx++;
@@ -285,11 +232,18 @@ static void davinci_fifo_data_trans(struct
mmc_davinci_host *host, int n)
/* NOTE: we never transfer more than rw_threshold bytes
* to/from the fifo here; there's no I/O overlap.
+ * This also assumes that access width( i.e. ACCWD) is 4 bytes
*/
if (host->data_dir == DAVINCI_MMC_DATADIR_WRITE) {
- DAVINCI_MMCSD_WRITE_FIFO(p, host->base, n);
+ for (i = 0; i < (n / 4); i++) {
+ writel(*((u32 *)p), host->base + DAVINCI_MMCDXR);
+ p = p + 4;
+ }
} else {
- DAVINCI_MMCSD_READ_FIFO(p, host->base, n);
+ for (i = 0; i < (n / 4); i++) {
+ *((u32 *)p) = readl(host->base + DAVINCI_MMCDRR);
+ p = p + 4;
+ }
}
host->buffer = p;
}
_______________________________________________
Davinci-linux-open-source mailing list
[email protected]
http://linux.davincidsp.com/mailman/listinfo/davinci-linux-open-source