From 487d9fc5016529d7d77dfe35b666fd3a090e2953 Mon Sep 17 00:00:00 2001 From: Magnus Damm Date: Tue, 18 May 2010 14:42:51 +0000 Subject: sh: prepare MMCIF driver header file Update the MMCIF driver to include register information and register access functions in the header file. The MMCIF boot code builds on top of this. Signed-off-by: Magnus Damm Signed-off-by: Paul Mundt --- drivers/mmc/host/sh_mmcif.c | 125 ++++++++++++++++++-------------------------- 1 file changed, 50 insertions(+), 75 deletions(-) (limited to 'drivers/mmc') diff --git a/drivers/mmc/host/sh_mmcif.c b/drivers/mmc/host/sh_mmcif.c index eb97830c0344..5d3f824bb5a3 100644 --- a/drivers/mmc/host/sh_mmcif.c +++ b/drivers/mmc/host/sh_mmcif.c @@ -30,25 +30,6 @@ #define DRIVER_NAME "sh_mmcif" #define DRIVER_VERSION "2010-04-28" -#define MMCIF_CE_CMD_SET 0x00000000 -#define MMCIF_CE_ARG 0x00000008 -#define MMCIF_CE_ARG_CMD12 0x0000000C -#define MMCIF_CE_CMD_CTRL 0x00000010 -#define MMCIF_CE_BLOCK_SET 0x00000014 -#define MMCIF_CE_CLK_CTRL 0x00000018 -#define MMCIF_CE_BUF_ACC 0x0000001C -#define MMCIF_CE_RESP3 0x00000020 -#define MMCIF_CE_RESP2 0x00000024 -#define MMCIF_CE_RESP1 0x00000028 -#define MMCIF_CE_RESP0 0x0000002C -#define MMCIF_CE_RESP_CMD12 0x00000030 -#define MMCIF_CE_DATA 0x00000034 -#define MMCIF_CE_INT 0x00000040 -#define MMCIF_CE_INT_MASK 0x00000044 -#define MMCIF_CE_HOST_STS1 0x00000048 -#define MMCIF_CE_HOST_STS2 0x0000004C -#define MMCIF_CE_VERSION 0x0000007C - /* CE_CMD_SET */ #define CMD_MASK 0x3f000000 #define CMD_SET_RTYP_NO ((0 << 23) | (0 << 22)) @@ -207,27 +188,17 @@ struct sh_mmcif_host { wait_queue_head_t intr_wait; }; -static inline u32 sh_mmcif_readl(struct sh_mmcif_host *host, unsigned int reg) -{ - return readl(host->addr + reg); -} - -static inline void sh_mmcif_writel(struct sh_mmcif_host *host, - unsigned int reg, u32 val) -{ - writel(val, host->addr + reg); -} static inline void sh_mmcif_bitset(struct sh_mmcif_host *host, unsigned int reg, u32 val) { - writel(val | sh_mmcif_readl(host, reg), host->addr + reg); + writel(val | readl(host->addr + reg), host->addr + reg); } static inline void sh_mmcif_bitclr(struct sh_mmcif_host *host, unsigned int reg, u32 val) { - writel(~val & sh_mmcif_readl(host, reg), host->addr + reg); + writel(~val & readl(host->addr + reg), host->addr + reg); } @@ -253,10 +224,10 @@ static void sh_mmcif_sync_reset(struct sh_mmcif_host *host) { u32 tmp; - tmp = 0x010f0000 & sh_mmcif_readl(host, MMCIF_CE_CLK_CTRL); + tmp = 0x010f0000 & sh_mmcif_readl(host->addr, MMCIF_CE_CLK_CTRL); - sh_mmcif_writel(host, MMCIF_CE_VERSION, SOFT_RST_ON); - sh_mmcif_writel(host, MMCIF_CE_VERSION, SOFT_RST_OFF); + sh_mmcif_writel(host->addr, MMCIF_CE_VERSION, SOFT_RST_ON); + sh_mmcif_writel(host->addr, MMCIF_CE_VERSION, SOFT_RST_OFF); sh_mmcif_bitset(host, MMCIF_CE_CLK_CTRL, tmp | SRSPTO_256 | SRBSYTO_29 | SRWDTO_29 | SCCSTO_29); /* byte swap on */ @@ -271,12 +242,10 @@ static int sh_mmcif_error_manage(struct sh_mmcif_host *host) host->sd_error = 0; host->wait_int = 0; - state1 = sh_mmcif_readl(host, MMCIF_CE_HOST_STS1); - state2 = sh_mmcif_readl(host, MMCIF_CE_HOST_STS2); - pr_debug("%s: ERR HOST_STS1 = %08x\n", \ - DRIVER_NAME, sh_mmcif_readl(host, MMCIF_CE_HOST_STS1)); - pr_debug("%s: ERR HOST_STS2 = %08x\n", \ - DRIVER_NAME, sh_mmcif_readl(host, MMCIF_CE_HOST_STS2)); + state1 = sh_mmcif_readl(host->addr, MMCIF_CE_HOST_STS1); + state2 = sh_mmcif_readl(host->addr, MMCIF_CE_HOST_STS2); + pr_debug("%s: ERR HOST_STS1 = %08x\n", DRIVER_NAME, state1); + pr_debug("%s: ERR HOST_STS2 = %08x\n", DRIVER_NAME, state2); if (state1 & STS1_CMDSEQ) { sh_mmcif_bitset(host, MMCIF_CE_CMD_CTRL, CMD_CTRL_BREAK); @@ -288,7 +257,7 @@ static int sh_mmcif_error_manage(struct sh_mmcif_host *host) "command sequence timeout err\n"); return -EIO; } - if (!(sh_mmcif_readl(host, MMCIF_CE_HOST_STS1) + if (!(sh_mmcif_readl(host->addr, MMCIF_CE_HOST_STS1) & STS1_CMDSEQ)) break; mdelay(1); @@ -330,9 +299,9 @@ static int sh_mmcif_single_read(struct sh_mmcif_host *host, host->wait_int = 0; blocksize = (BLOCK_SIZE_MASK & - sh_mmcif_readl(host, MMCIF_CE_BLOCK_SET)) + 3; + sh_mmcif_readl(host->addr, MMCIF_CE_BLOCK_SET)) + 3; for (i = 0; i < blocksize / 4; i++) - *p++ = sh_mmcif_readl(host, MMCIF_CE_DATA); + *p++ = sh_mmcif_readl(host->addr, MMCIF_CE_DATA); /* buffer read end */ sh_mmcif_bitset(host, MMCIF_CE_INT_MASK, MASK_MBUFRE); @@ -353,7 +322,8 @@ static int sh_mmcif_multi_read(struct sh_mmcif_host *host, long time; u32 blocksize, i, j, sec, *p; - blocksize = BLOCK_SIZE_MASK & sh_mmcif_readl(host, MMCIF_CE_BLOCK_SET); + blocksize = BLOCK_SIZE_MASK & sh_mmcif_readl(host->addr, + MMCIF_CE_BLOCK_SET); for (j = 0; j < data->sg_len; j++) { p = sg_virt(data->sg); host->wait_int = 0; @@ -370,7 +340,8 @@ static int sh_mmcif_multi_read(struct sh_mmcif_host *host, host->wait_int = 0; for (i = 0; i < blocksize / 4; i++) - *p++ = sh_mmcif_readl(host, MMCIF_CE_DATA); + *p++ = sh_mmcif_readl(host->addr, + MMCIF_CE_DATA); } if (j < data->sg_len - 1) data->sg++; @@ -397,9 +368,9 @@ static int sh_mmcif_single_write(struct sh_mmcif_host *host, host->wait_int = 0; blocksize = (BLOCK_SIZE_MASK & - sh_mmcif_readl(host, MMCIF_CE_BLOCK_SET)) + 3; + sh_mmcif_readl(host->addr, MMCIF_CE_BLOCK_SET)) + 3; for (i = 0; i < blocksize / 4; i++) - sh_mmcif_writel(host, MMCIF_CE_DATA, *p++); + sh_mmcif_writel(host->addr, MMCIF_CE_DATA, *p++); /* buffer write end */ sh_mmcif_bitset(host, MMCIF_CE_INT_MASK, MASK_MDTRANE); @@ -421,7 +392,8 @@ static int sh_mmcif_multi_write(struct sh_mmcif_host *host, long time; u32 i, sec, j, blocksize, *p; - blocksize = BLOCK_SIZE_MASK & sh_mmcif_readl(host, MMCIF_CE_BLOCK_SET); + blocksize = BLOCK_SIZE_MASK & sh_mmcif_readl(host->addr, + MMCIF_CE_BLOCK_SET); for (j = 0; j < data->sg_len; j++) { p = sg_virt(data->sg); @@ -439,7 +411,8 @@ static int sh_mmcif_multi_write(struct sh_mmcif_host *host, host->wait_int = 0; for (i = 0; i < blocksize / 4; i++) - sh_mmcif_writel(host, MMCIF_CE_DATA, *p++); + sh_mmcif_writel(host->addr, + MMCIF_CE_DATA, *p++); } if (j < data->sg_len - 1) data->sg++; @@ -451,18 +424,18 @@ static void sh_mmcif_get_response(struct sh_mmcif_host *host, struct mmc_command *cmd) { if (cmd->flags & MMC_RSP_136) { - cmd->resp[0] = sh_mmcif_readl(host, MMCIF_CE_RESP3); - cmd->resp[1] = sh_mmcif_readl(host, MMCIF_CE_RESP2); - cmd->resp[2] = sh_mmcif_readl(host, MMCIF_CE_RESP1); - cmd->resp[3] = sh_mmcif_readl(host, MMCIF_CE_RESP0); + cmd->resp[0] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP3); + cmd->resp[1] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP2); + cmd->resp[2] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP1); + cmd->resp[3] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP0); } else - cmd->resp[0] = sh_mmcif_readl(host, MMCIF_CE_RESP0); + cmd->resp[0] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP0); } static void sh_mmcif_get_cmd12response(struct sh_mmcif_host *host, struct mmc_command *cmd) { - cmd->resp[0] = sh_mmcif_readl(host, MMCIF_CE_RESP_CMD12); + cmd->resp[0] = sh_mmcif_readl(host->addr, MMCIF_CE_RESP_CMD12); } static u32 sh_mmcif_set_cmd(struct sh_mmcif_host *host, @@ -596,18 +569,19 @@ static void sh_mmcif_start_cmd(struct sh_mmcif_host *host, MASK_MRDATTO | MASK_MRBSYTO | MASK_MRSPTO; if (host->data) { - sh_mmcif_writel(host, MMCIF_CE_BLOCK_SET, 0); - sh_mmcif_writel(host, MMCIF_CE_BLOCK_SET, mrq->data->blksz); + sh_mmcif_writel(host->addr, MMCIF_CE_BLOCK_SET, 0); + sh_mmcif_writel(host->addr, MMCIF_CE_BLOCK_SET, + mrq->data->blksz); } opc = sh_mmcif_set_cmd(host, mrq, cmd, opc); - sh_mmcif_writel(host, MMCIF_CE_INT, 0xD80430C0); - sh_mmcif_writel(host, MMCIF_CE_INT_MASK, mask); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, 0xD80430C0); + sh_mmcif_writel(host->addr, MMCIF_CE_INT_MASK, mask); /* set arg */ - sh_mmcif_writel(host, MMCIF_CE_ARG, cmd->arg); + sh_mmcif_writel(host->addr, MMCIF_CE_ARG, cmd->arg); host->wait_int = 0; /* set cmd */ - sh_mmcif_writel(host, MMCIF_CE_CMD_SET, opc); + sh_mmcif_writel(host->addr, MMCIF_CE_CMD_SET, opc); time = wait_event_interruptible_timeout(host->intr_wait, host->wait_int == 1 || host->sd_error == 1, host->timeout); @@ -752,43 +726,44 @@ static irqreturn_t sh_mmcif_intr(int irq, void *dev_id) u32 state = 0; int err = 0; - state = sh_mmcif_readl(host, MMCIF_CE_INT); + state = sh_mmcif_readl(host->addr, MMCIF_CE_INT); if (state & INT_RBSYE) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~(INT_RBSYE | INT_CRSPE)); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, + ~(INT_RBSYE | INT_CRSPE)); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MRBSYE); } else if (state & INT_CRSPE) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~INT_CRSPE); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~INT_CRSPE); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MCRSPE); } else if (state & INT_BUFREN) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~INT_BUFREN); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~INT_BUFREN); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MBUFREN); } else if (state & INT_BUFWEN) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~INT_BUFWEN); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~INT_BUFWEN); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MBUFWEN); } else if (state & INT_CMD12DRE) { - sh_mmcif_writel(host, MMCIF_CE_INT, + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~(INT_CMD12DRE | INT_CMD12RBE | INT_CMD12CRE | INT_BUFRE)); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MCMD12DRE); } else if (state & INT_BUFRE) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~INT_BUFRE); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~INT_BUFRE); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MBUFRE); } else if (state & INT_DTRANE) { - sh_mmcif_writel(host, MMCIF_CE_INT, ~INT_DTRANE); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~INT_DTRANE); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MDTRANE); } else if (state & INT_CMD12RBE) { - sh_mmcif_writel(host, MMCIF_CE_INT, + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~(INT_CMD12RBE | INT_CMD12CRE)); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, MASK_MCMD12RBE); } else if (state & INT_ERR_STS) { /* err interrupts */ - sh_mmcif_writel(host, MMCIF_CE_INT, ~state); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~state); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, state); err = 1; } else { pr_debug("%s: Not support int\n", DRIVER_NAME); - sh_mmcif_writel(host, MMCIF_CE_INT, ~state); + sh_mmcif_writel(host->addr, MMCIF_CE_INT, ~state); sh_mmcif_bitclr(host, MMCIF_CE_INT_MASK, state); err = 1; } @@ -894,12 +869,12 @@ static int __devinit sh_mmcif_probe(struct platform_device *pdev) goto clean_up2; } - sh_mmcif_writel(host, MMCIF_CE_INT_MASK, MASK_ALL); + sh_mmcif_writel(host->addr, MMCIF_CE_INT_MASK, MASK_ALL); sh_mmcif_detect(host->mmc); pr_info("%s: driver version %s\n", DRIVER_NAME, DRIVER_VERSION); pr_debug("%s: chip ver H'%04x\n", DRIVER_NAME, - sh_mmcif_readl(host, MMCIF_CE_VERSION) & 0x0000ffff); + sh_mmcif_readl(host->addr, MMCIF_CE_VERSION) & 0x0000ffff); return ret; clean_up2: @@ -917,7 +892,7 @@ static int __devexit sh_mmcif_remove(struct platform_device *pdev) struct sh_mmcif_host *host = platform_get_drvdata(pdev); int irq[2]; - sh_mmcif_writel(host, MMCIF_CE_INT_MASK, MASK_ALL); + sh_mmcif_writel(host->addr, MMCIF_CE_INT_MASK, MASK_ALL); irq[0] = platform_get_irq(pdev, 0); irq[1] = platform_get_irq(pdev, 1); -- cgit v1.2.3 From 683eb94777c3c67b9b258765b9cb03641344c418 Mon Sep 17 00:00:00 2001 From: Cory Maccarrone Date: Fri, 4 Jun 2010 14:15:07 -0700 Subject: omap: remove BUG_ON for disabled interrupts Remove a BUG_ON for when interrupts are disabled during an MMC request. During boot, interrupts can be disabled when a request is made, causing this bug to be triggered. In reality, there's no reason this should halt the kernel, as the driver has proved reliable in spite of disabled interrupts, and additionally, there's nothing in this code that would require interrupts to be enabled. The only setup I've managed to make it trigger on is on the HTC Herald during bootup when the driver is built into the kernel (mostly because that's all I have). I believe it's related to the fact that on bootup I get many timeout errors on "CMD5" while initializing the card. Each CMD5 timeout triggers that bug (I changed it to a WARN_ON to get it to boot in) due to the fact that part of the timeout code involves sending the request again. With interrupts turned off, that BUG would be triggered. Signed-off-by: Cory Maccarrone Acked-by: Tony Lindgren Cc: Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/mmc/host/omap.c | 1 - 1 file changed, 1 deletion(-) (limited to 'drivers/mmc') diff --git a/drivers/mmc/host/omap.c b/drivers/mmc/host/omap.c index 2b281680e320..d98ddcfac5e5 100644 --- a/drivers/mmc/host/omap.c +++ b/drivers/mmc/host/omap.c @@ -1157,7 +1157,6 @@ static void mmc_omap_start_request(struct mmc_omap_host *host, mmc_omap_start_command(host, req->cmd); if (host->dma_in_use) omap_start_dma(host->dma_ch); - BUG_ON(irqs_disabled()); } static void mmc_omap_request(struct mmc_host *mmc, struct mmc_request *req) -- cgit v1.2.3 From f3d56144c86beb25c7d206efa66d6efba908371c Mon Sep 17 00:00:00 2001 From: Daniel Walker Date: Mon, 24 May 2010 10:15:00 -0700 Subject: mmc: msm: fix compile error on MSM7x30 MSM7x30 isn't supported in this driver yet. If ones tried to compile it in with MSM7x30 configure you get, linux-2.6/drivers/mmc/host/msm_sdcc.c: In function 'msmsdcc_fifo_addr': linux-2.6/drivers/mmc/host/msm_sdcc.c:165: error: 'MSM_SDC1_PHYS' undeclared (first use in this function) linux-2.6/drivers/mmc/host/msm_sdcc.c:165: error: (Each undeclared identifier is reported only once linux-2.6/drivers/mmc/host/msm_sdcc.c:165: error: for each function it appears in.) linux-2.6/drivers/mmc/host/msm_sdcc.c:167: error: 'MSM_SDC2_PHYS' undeclared (first use in this function) linux-2.6/drivers/mmc/host/msm_sdcc.c:169: error: 'MSM_SDC3_PHYS' undeclared (first use in this function) linux-2.6/drivers/mmc/host/msm_sdcc.c:171: error: 'MSM_SDC4_PHYS' undeclared (first use in this function) So we add a Kconfig check to prevent this. Signed-off-by: Daniel Walker --- drivers/mmc/host/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/mmc') diff --git a/drivers/mmc/host/Kconfig b/drivers/mmc/host/Kconfig index e171e77f6129..f06d06e7fdfa 100644 --- a/drivers/mmc/host/Kconfig +++ b/drivers/mmc/host/Kconfig @@ -249,7 +249,7 @@ config MMC_IMX config MMC_MSM7X00A tristate "Qualcomm MSM 7X00A SDCC Controller Support" - depends on MMC && ARCH_MSM + depends on MMC && ARCH_MSM && !ARCH_MSM7X30 help This provides support for the SD/MMC cell found in the MSM 7X00A controllers from Qualcomm. -- cgit v1.2.3