[ARM] 3457/1: i.MX: SD/MMC support for i.MX/MX1

Patch from Pavel Pisa

This patch adds support of i.MX/MX1 SD/MMC controller.
It has been significantly redesigned from the original Sascha Hauer's
version to support scatter-gather DMA, to conform to latest Pierre Ossman's
and Russell King's MMC-SD Linux 2.6.x infrastructure.
The handling of all events has been moved to the softirq context
and is designed with no busy-looping in mind. Unfortunately
some controller bugs has to be overcome by limited looping
about 2-20 usec but these are observed only for initial card
recognition phase.

There are still some missing/missed IRQs problems under heavy load.
Help of somebody with access to the full SDHC design information
is probably necessary.

Regenerated against 2.6.16-git-060402 to solve clash with other patches.

Signed-off-by: Pavel Pisa <pisa@cmp.felk.cvut.cz>
Acked-by: Sascha Hauer <s.hauer@pengutronix.de>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>

authored by Pavel Pisa and committed by Russell King 56ca9040 65dbf343

+1199
+13
arch/arm/mach-imx/generic.c
··· 33 33 #include <asm/arch/imx-regs.h> 34 34 35 35 #include <asm/mach/map.h> 36 + #include <asm/arch/mmc.h> 36 37 37 38 void imx_gpio_mode(int gpio_mode) 38 39 { ··· 176 175 }, 177 176 }; 178 177 178 + static u64 imxmmmc_dmamask = 0xffffffffUL; 179 + 179 180 static struct platform_device imx_mmc_device = { 180 181 .name = "imx-mmc", 181 182 .id = 0, 183 + .dev = { 184 + .dma_mask = &imxmmmc_dmamask, 185 + .coherent_dma_mask = 0xffffffff, 186 + }, 182 187 .num_resources = ARRAY_SIZE(imx_mmc_resources), 183 188 .resource = imx_mmc_resources, 184 189 }; 190 + 191 + void __init imx_set_mmc_info(struct imxmmc_platform_data *info) 192 + { 193 + imx_mmc_device.dev.platform_data = info; 194 + } 195 + EXPORT_SYMBOL(imx_set_mmc_info); 185 196 186 197 static struct resource imx_uart1_resources[] = { 187 198 [0] = {
+10
drivers/mmc/Kconfig
··· 99 99 100 100 If unsure, say N. 101 101 102 + config MMC_IMX 103 + tristate "Motorola i.MX Multimedia Card Interface support" 104 + depends on ARCH_IMX && MMC 105 + help 106 + This selects the Motorola i.MX Multimedia card Interface. 107 + If you have a i.MX platform with a Multimedia Card slot, 108 + say Y or M here. 109 + 110 + If unsure, say N. 111 + 102 112 endmenu
+1
drivers/mmc/Makefile
··· 17 17 # 18 18 obj-$(CONFIG_MMC_ARMMMCI) += mmci.o 19 19 obj-$(CONFIG_MMC_PXA) += pxamci.o 20 + obj-$(CONFIG_MMC_IMX) += imxmmc.o 20 21 obj-$(CONFIG_MMC_SDHCI) += sdhci.o 21 22 obj-$(CONFIG_MMC_WBSD) += wbsd.o 22 23 obj-$(CONFIG_MMC_AU1X) += au1xmmc.o
+1096
drivers/mmc/imxmmc.c
··· 1 + /* 2 + * linux/drivers/mmc/imxmmc.c - Motorola i.MX MMCI driver 3 + * 4 + * Copyright (C) 2004 Sascha Hauer, Pengutronix <sascha@saschahauer.de> 5 + * Copyright (C) 2006 Pavel Pisa, PiKRON <ppisa@pikron.com> 6 + * 7 + * derived from pxamci.c by Russell King 8 + * 9 + * This program is free software; you can redistribute it and/or modify 10 + * it under the terms of the GNU General Public License version 2 as 11 + * published by the Free Software Foundation. 12 + * 13 + * 2005-04-17 Pavel Pisa <pisa@cmp.felk.cvut.cz> 14 + * Changed to conform redesigned i.MX scatter gather DMA interface 15 + * 16 + * 2005-11-04 Pavel Pisa <pisa@cmp.felk.cvut.cz> 17 + * Updated for 2.6.14 kernel 18 + * 19 + * 2005-12-13 Jay Monkman <jtm@smoothsmoothie.com> 20 + * Found and corrected problems in the write path 21 + * 22 + * 2005-12-30 Pavel Pisa <pisa@cmp.felk.cvut.cz> 23 + * The event handling rewritten right way in softirq. 24 + * Added many ugly hacks and delays to overcome SDHC 25 + * deficiencies 26 + * 27 + */ 28 + #include <linux/config.h> 29 + 30 + #ifdef CONFIG_MMC_DEBUG 31 + #define DEBUG 32 + #else 33 + #undef DEBUG 34 + #endif 35 + 36 + #include <linux/module.h> 37 + #include <linux/init.h> 38 + #include <linux/ioport.h> 39 + #include <linux/platform_device.h> 40 + #include <linux/interrupt.h> 41 + #include <linux/blkdev.h> 42 + #include <linux/dma-mapping.h> 43 + #include <linux/mmc/host.h> 44 + #include <linux/mmc/card.h> 45 + #include <linux/mmc/protocol.h> 46 + #include <linux/delay.h> 47 + 48 + #include <asm/dma.h> 49 + #include <asm/io.h> 50 + #include <asm/irq.h> 51 + #include <asm/sizes.h> 52 + #include <asm/arch/mmc.h> 53 + #include <asm/arch/imx-dma.h> 54 + 55 + #include "imxmmc.h" 56 + 57 + #define DRIVER_NAME "imx-mmc" 58 + 59 + #define IMXMCI_INT_MASK_DEFAULT (INT_MASK_BUF_READY | INT_MASK_DATA_TRAN | \ 60 + INT_MASK_WRITE_OP_DONE | INT_MASK_END_CMD_RES | \ 61 + INT_MASK_AUTO_CARD_DETECT | INT_MASK_DAT0_EN | INT_MASK_SDIO) 62 + 63 + struct imxmci_host { 64 + struct mmc_host *mmc; 65 + spinlock_t lock; 66 + struct resource *res; 67 + int irq; 68 + imx_dmach_t dma; 69 + unsigned int clkrt; 70 + unsigned int cmdat; 71 + volatile unsigned int imask; 72 + unsigned int power_mode; 73 + unsigned int present; 74 + struct imxmmc_platform_data *pdata; 75 + 76 + struct mmc_request *req; 77 + struct mmc_command *cmd; 78 + struct mmc_data *data; 79 + 80 + struct timer_list timer; 81 + struct tasklet_struct tasklet; 82 + unsigned int status_reg; 83 + unsigned long pending_events; 84 + /* Next to fields are there for CPU driven transfers to overcome SDHC deficiencies */ 85 + u16 *data_ptr; 86 + unsigned int data_cnt; 87 + atomic_t stuck_timeout; 88 + 89 + unsigned int dma_nents; 90 + unsigned int dma_size; 91 + unsigned int dma_dir; 92 + int dma_allocated; 93 + 94 + unsigned char actual_bus_width; 95 + }; 96 + 97 + #define IMXMCI_PEND_IRQ_b 0 98 + #define IMXMCI_PEND_DMA_END_b 1 99 + #define IMXMCI_PEND_DMA_ERR_b 2 100 + #define IMXMCI_PEND_WAIT_RESP_b 3 101 + #define IMXMCI_PEND_DMA_DATA_b 4 102 + #define IMXMCI_PEND_CPU_DATA_b 5 103 + #define IMXMCI_PEND_CARD_XCHG_b 6 104 + #define IMXMCI_PEND_SET_INIT_b 7 105 + 106 + #define IMXMCI_PEND_IRQ_m (1 << IMXMCI_PEND_IRQ_b) 107 + #define IMXMCI_PEND_DMA_END_m (1 << IMXMCI_PEND_DMA_END_b) 108 + #define IMXMCI_PEND_DMA_ERR_m (1 << IMXMCI_PEND_DMA_ERR_b) 109 + #define IMXMCI_PEND_WAIT_RESP_m (1 << IMXMCI_PEND_WAIT_RESP_b) 110 + #define IMXMCI_PEND_DMA_DATA_m (1 << IMXMCI_PEND_DMA_DATA_b) 111 + #define IMXMCI_PEND_CPU_DATA_m (1 << IMXMCI_PEND_CPU_DATA_b) 112 + #define IMXMCI_PEND_CARD_XCHG_m (1 << IMXMCI_PEND_CARD_XCHG_b) 113 + #define IMXMCI_PEND_SET_INIT_m (1 << IMXMCI_PEND_SET_INIT_b) 114 + 115 + static void imxmci_stop_clock(struct imxmci_host *host) 116 + { 117 + int i = 0; 118 + MMC_STR_STP_CLK &= ~STR_STP_CLK_START_CLK; 119 + while(i < 0x1000) { 120 + if(!(i & 0x7f)) 121 + MMC_STR_STP_CLK |= STR_STP_CLK_STOP_CLK; 122 + 123 + if(!(MMC_STATUS & STATUS_CARD_BUS_CLK_RUN)) { 124 + /* Check twice before cut */ 125 + if(!(MMC_STATUS & STATUS_CARD_BUS_CLK_RUN)) 126 + return; 127 + } 128 + 129 + i++; 130 + } 131 + dev_dbg(mmc_dev(host->mmc), "imxmci_stop_clock blocked, no luck\n"); 132 + } 133 + 134 + static void imxmci_start_clock(struct imxmci_host *host) 135 + { 136 + int i = 0; 137 + MMC_STR_STP_CLK &= ~STR_STP_CLK_STOP_CLK; 138 + while(i < 0x1000) { 139 + if(!(i & 0x7f)) 140 + MMC_STR_STP_CLK |= STR_STP_CLK_START_CLK; 141 + 142 + if(MMC_STATUS & STATUS_CARD_BUS_CLK_RUN) { 143 + /* Check twice before cut */ 144 + if(MMC_STATUS & STATUS_CARD_BUS_CLK_RUN) 145 + return; 146 + } 147 + 148 + i++; 149 + } 150 + dev_dbg(mmc_dev(host->mmc), "imxmci_start_clock blocked, no luck\n"); 151 + } 152 + 153 + static void imxmci_softreset(void) 154 + { 155 + /* reset sequence */ 156 + MMC_STR_STP_CLK = 0x8; 157 + MMC_STR_STP_CLK = 0xD; 158 + MMC_STR_STP_CLK = 0x5; 159 + MMC_STR_STP_CLK = 0x5; 160 + MMC_STR_STP_CLK = 0x5; 161 + MMC_STR_STP_CLK = 0x5; 162 + MMC_STR_STP_CLK = 0x5; 163 + MMC_STR_STP_CLK = 0x5; 164 + MMC_STR_STP_CLK = 0x5; 165 + MMC_STR_STP_CLK = 0x5; 166 + 167 + MMC_RES_TO = 0xff; 168 + MMC_BLK_LEN = 512; 169 + MMC_NOB = 1; 170 + } 171 + 172 + static int imxmci_busy_wait_for_status(struct imxmci_host *host, 173 + unsigned int *pstat, unsigned int stat_mask, 174 + int timeout, const char *where) 175 + { 176 + int loops=0; 177 + while(!(*pstat & stat_mask)) { 178 + loops+=2; 179 + if(loops >= timeout) { 180 + dev_dbg(mmc_dev(host->mmc), "busy wait timeout in %s, STATUS = 0x%x (0x%x)\n", 181 + where, *pstat, stat_mask); 182 + return -1; 183 + } 184 + udelay(2); 185 + *pstat |= MMC_STATUS; 186 + } 187 + if(!loops) 188 + return 0; 189 + 190 + dev_info(mmc_dev(host->mmc), "busy wait for %d usec in %s, STATUS = 0x%x (0x%x)\n", 191 + loops, where, *pstat, stat_mask); 192 + return loops; 193 + } 194 + 195 + static void imxmci_setup_data(struct imxmci_host *host, struct mmc_data *data) 196 + { 197 + unsigned int nob = data->blocks; 198 + unsigned int blksz = 1 << data->blksz_bits; 199 + unsigned int datasz = nob * blksz; 200 + int i; 201 + 202 + if (data->flags & MMC_DATA_STREAM) 203 + nob = 0xffff; 204 + 205 + host->data = data; 206 + data->bytes_xfered = 0; 207 + 208 + MMC_NOB = nob; 209 + MMC_BLK_LEN = blksz; 210 + 211 + /* 212 + * DMA cannot be used for small block sizes, we have to use CPU driven transfers otherwise. 213 + * We are in big troubles for non-512 byte transfers according to note in the paragraph 214 + * 20.6.7 of User Manual anyway, but we need to be able to transfer SCR at least. 215 + * The situation is even more complex in reality. The SDHC in not able to handle wll 216 + * partial FIFO fills and reads. The length has to be rounded up to burst size multiple. 217 + * This is required for SCR read at least. 218 + */ 219 + if (datasz < 64) { 220 + host->dma_size = datasz; 221 + if (data->flags & MMC_DATA_READ) { 222 + host->dma_dir = DMA_FROM_DEVICE; 223 + 224 + /* Hack to enable read SCR */ 225 + if(datasz < 16) { 226 + MMC_NOB = 1; 227 + MMC_BLK_LEN = 16; 228 + } 229 + } else { 230 + host->dma_dir = DMA_TO_DEVICE; 231 + } 232 + 233 + /* Convert back to virtual address */ 234 + host->data_ptr = (u16*)(page_address(data->sg->page) + data->sg->offset); 235 + host->data_cnt = 0; 236 + 237 + clear_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events); 238 + set_bit(IMXMCI_PEND_CPU_DATA_b, &host->pending_events); 239 + 240 + return; 241 + } 242 + 243 + if (data->flags & MMC_DATA_READ) { 244 + host->dma_dir = DMA_FROM_DEVICE; 245 + host->dma_nents = dma_map_sg(mmc_dev(host->mmc), data->sg, 246 + data->sg_len, host->dma_dir); 247 + 248 + imx_dma_setup_sg(host->dma, data->sg, data->sg_len, datasz, 249 + host->res->start + MMC_BUFFER_ACCESS_OFS, DMA_MODE_READ); 250 + 251 + /*imx_dma_setup_mem2dev_ccr(host->dma, DMA_MODE_READ, IMX_DMA_WIDTH_16, CCR_REN);*/ 252 + CCR(host->dma) = CCR_DMOD_LINEAR | CCR_DSIZ_32 | CCR_SMOD_FIFO | CCR_SSIZ_16 | CCR_REN; 253 + } else { 254 + host->dma_dir = DMA_TO_DEVICE; 255 + 256 + host->dma_nents = dma_map_sg(mmc_dev(host->mmc), data->sg, 257 + data->sg_len, host->dma_dir); 258 + 259 + imx_dma_setup_sg(host->dma, data->sg, data->sg_len, datasz, 260 + host->res->start + MMC_BUFFER_ACCESS_OFS, DMA_MODE_WRITE); 261 + 262 + /*imx_dma_setup_mem2dev_ccr(host->dma, DMA_MODE_WRITE, IMX_DMA_WIDTH_16, CCR_REN);*/ 263 + CCR(host->dma) = CCR_SMOD_LINEAR | CCR_SSIZ_32 | CCR_DMOD_FIFO | CCR_DSIZ_16 | CCR_REN; 264 + } 265 + 266 + #if 1 /* This code is there only for consistency checking and can be disabled in future */ 267 + host->dma_size = 0; 268 + for(i=0; i<host->dma_nents; i++) 269 + host->dma_size+=data->sg[i].length; 270 + 271 + if (datasz > host->dma_size) { 272 + dev_err(mmc_dev(host->mmc), "imxmci_setup_data datasz 0x%x > 0x%x dm_size\n", 273 + datasz, host->dma_size); 274 + } 275 + #endif 276 + 277 + host->dma_size = datasz; 278 + 279 + wmb(); 280 + 281 + if(host->actual_bus_width == MMC_BUS_WIDTH_4) 282 + BLR(host->dma) = 0; /* burst 64 byte read / 64 bytes write */ 283 + else 284 + BLR(host->dma) = 16; /* burst 16 byte read / 16 bytes write */ 285 + 286 + RSSR(host->dma) = DMA_REQ_SDHC; 287 + 288 + set_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events); 289 + clear_bit(IMXMCI_PEND_CPU_DATA_b, &host->pending_events); 290 + 291 + /* start DMA engine for read, write is delayed after initial response */ 292 + if (host->dma_dir == DMA_FROM_DEVICE) { 293 + imx_dma_enable(host->dma); 294 + } 295 + } 296 + 297 + static void imxmci_start_cmd(struct imxmci_host *host, struct mmc_command *cmd, unsigned int cmdat) 298 + { 299 + unsigned long flags; 300 + u32 imask; 301 + 302 + WARN_ON(host->cmd != NULL); 303 + host->cmd = cmd; 304 + 305 + if (cmd->flags & MMC_RSP_BUSY) 306 + cmdat |= CMD_DAT_CONT_BUSY; 307 + 308 + switch (mmc_resp_type(cmd)) { 309 + case MMC_RSP_R1: /* short CRC, OPCODE */ 310 + case MMC_RSP_R1B:/* short CRC, OPCODE, BUSY */ 311 + cmdat |= CMD_DAT_CONT_RESPONSE_FORMAT_R1; 312 + break; 313 + case MMC_RSP_R2: /* long 136 bit + CRC */ 314 + cmdat |= CMD_DAT_CONT_RESPONSE_FORMAT_R2; 315 + break; 316 + case MMC_RSP_R3: /* short */ 317 + cmdat |= CMD_DAT_CONT_RESPONSE_FORMAT_R3; 318 + break; 319 + case MMC_RSP_R6: /* short CRC */ 320 + cmdat |= CMD_DAT_CONT_RESPONSE_FORMAT_R6; 321 + break; 322 + default: 323 + break; 324 + } 325 + 326 + if ( test_and_clear_bit(IMXMCI_PEND_SET_INIT_b, &host->pending_events) ) 327 + cmdat |= CMD_DAT_CONT_INIT; /* This command needs init */ 328 + 329 + if ( host->actual_bus_width == MMC_BUS_WIDTH_4 ) 330 + cmdat |= CMD_DAT_CONT_BUS_WIDTH_4; 331 + 332 + MMC_CMD = cmd->opcode; 333 + MMC_ARGH = cmd->arg >> 16; 334 + MMC_ARGL = cmd->arg & 0xffff; 335 + MMC_CMD_DAT_CONT = cmdat; 336 + 337 + atomic_set(&host->stuck_timeout, 0); 338 + set_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events); 339 + 340 + 341 + imask = IMXMCI_INT_MASK_DEFAULT; 342 + imask &= ~INT_MASK_END_CMD_RES; 343 + if ( cmdat & CMD_DAT_CONT_DATA_ENABLE ) { 344 + /*imask &= ~INT_MASK_BUF_READY;*/ 345 + imask &= ~INT_MASK_DATA_TRAN; 346 + if ( cmdat & CMD_DAT_CONT_WRITE ) 347 + imask &= ~INT_MASK_WRITE_OP_DONE; 348 + if(test_bit(IMXMCI_PEND_CPU_DATA_b, &host->pending_events)) 349 + imask &= ~INT_MASK_BUF_READY; 350 + } 351 + 352 + spin_lock_irqsave(&host->lock, flags); 353 + host->imask = imask; 354 + MMC_INT_MASK = host->imask; 355 + spin_unlock_irqrestore(&host->lock, flags); 356 + 357 + dev_dbg(mmc_dev(host->mmc), "CMD%02d (0x%02x) mask set to 0x%04x\n", 358 + cmd->opcode, cmd->opcode, imask); 359 + 360 + imxmci_start_clock(host); 361 + } 362 + 363 + static void imxmci_finish_request(struct imxmci_host *host, struct mmc_request *req) 364 + { 365 + unsigned long flags; 366 + 367 + spin_lock_irqsave(&host->lock, flags); 368 + 369 + host->pending_events &= ~(IMXMCI_PEND_WAIT_RESP_m | IMXMCI_PEND_DMA_END_m | 370 + IMXMCI_PEND_DMA_DATA_m | IMXMCI_PEND_CPU_DATA_m); 371 + 372 + host->imask = IMXMCI_INT_MASK_DEFAULT; 373 + MMC_INT_MASK = host->imask; 374 + 375 + spin_unlock_irqrestore(&host->lock, flags); 376 + 377 + host->req = NULL; 378 + host->cmd = NULL; 379 + host->data = NULL; 380 + mmc_request_done(host->mmc, req); 381 + } 382 + 383 + static int imxmci_finish_data(struct imxmci_host *host, unsigned int stat) 384 + { 385 + struct mmc_data *data = host->data; 386 + int data_error; 387 + 388 + if(test_and_clear_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events)){ 389 + imx_dma_disable(host->dma); 390 + dma_unmap_sg(mmc_dev(host->mmc), data->sg, host->dma_nents, 391 + host->dma_dir); 392 + } 393 + 394 + if ( stat & STATUS_ERR_MASK ) { 395 + dev_dbg(mmc_dev(host->mmc), "request failed. status: 0x%08x\n",stat); 396 + if(stat & (STATUS_CRC_READ_ERR | STATUS_CRC_WRITE_ERR)) 397 + data->error = MMC_ERR_BADCRC; 398 + else if(stat & STATUS_TIME_OUT_READ) 399 + data->error = MMC_ERR_TIMEOUT; 400 + else 401 + data->error = MMC_ERR_FAILED; 402 + } else { 403 + data->bytes_xfered = host->dma_size; 404 + } 405 + 406 + data_error = data->error; 407 + 408 + host->data = NULL; 409 + 410 + return data_error; 411 + } 412 + 413 + static int imxmci_cmd_done(struct imxmci_host *host, unsigned int stat) 414 + { 415 + struct mmc_command *cmd = host->cmd; 416 + int i; 417 + u32 a,b,c; 418 + struct mmc_data *data = host->data; 419 + 420 + if (!cmd) 421 + return 0; 422 + 423 + host->cmd = NULL; 424 + 425 + if (stat & STATUS_TIME_OUT_RESP) { 426 + dev_dbg(mmc_dev(host->mmc), "CMD TIMEOUT\n"); 427 + cmd->error = MMC_ERR_TIMEOUT; 428 + } else if (stat & STATUS_RESP_CRC_ERR && cmd->flags & MMC_RSP_CRC) { 429 + dev_dbg(mmc_dev(host->mmc), "cmd crc error\n"); 430 + cmd->error = MMC_ERR_BADCRC; 431 + } 432 + 433 + if(cmd->flags & MMC_RSP_PRESENT) { 434 + if(cmd->flags & MMC_RSP_136) { 435 + for (i = 0; i < 4; i++) { 436 + u32 a = MMC_RES_FIFO & 0xffff; 437 + u32 b = MMC_RES_FIFO & 0xffff; 438 + cmd->resp[i] = a<<16 | b; 439 + } 440 + } else { 441 + a = MMC_RES_FIFO & 0xffff; 442 + b = MMC_RES_FIFO & 0xffff; 443 + c = MMC_RES_FIFO & 0xffff; 444 + cmd->resp[0] = a<<24 | b<<8 | c>>8; 445 + } 446 + } 447 + 448 + dev_dbg(mmc_dev(host->mmc), "RESP 0x%08x, 0x%08x, 0x%08x, 0x%08x, error %d\n", 449 + cmd->resp[0], cmd->resp[1], cmd->resp[2], cmd->resp[3], cmd->error); 450 + 451 + if (data && (cmd->error == MMC_ERR_NONE) && !(stat & STATUS_ERR_MASK)) { 452 + if (host->req->data->flags & MMC_DATA_WRITE) { 453 + 454 + /* Wait for FIFO to be empty before starting DMA write */ 455 + 456 + stat = MMC_STATUS; 457 + if(imxmci_busy_wait_for_status(host, &stat, 458 + STATUS_APPL_BUFF_FE, 459 + 40, "imxmci_cmd_done DMA WR") < 0) { 460 + cmd->error = MMC_ERR_FIFO; 461 + imxmci_finish_data(host, stat); 462 + if(host->req) 463 + imxmci_finish_request(host, host->req); 464 + dev_warn(mmc_dev(host->mmc), "STATUS = 0x%04x\n", 465 + stat); 466 + return 0; 467 + } 468 + 469 + if(test_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events)) { 470 + imx_dma_enable(host->dma); 471 + } 472 + } 473 + } else { 474 + struct mmc_request *req; 475 + imxmci_stop_clock(host); 476 + req = host->req; 477 + 478 + if(data) 479 + imxmci_finish_data(host, stat); 480 + 481 + if( req ) { 482 + imxmci_finish_request(host, req); 483 + } else { 484 + dev_warn(mmc_dev(host->mmc), "imxmci_cmd_done: no request to finish\n"); 485 + } 486 + } 487 + 488 + return 1; 489 + } 490 + 491 + static int imxmci_data_done(struct imxmci_host *host, unsigned int stat) 492 + { 493 + struct mmc_data *data = host->data; 494 + int data_error; 495 + 496 + if (!data) 497 + return 0; 498 + 499 + data_error = imxmci_finish_data(host, stat); 500 + 501 + if (host->req->stop && (data_error == MMC_ERR_NONE)) { 502 + imxmci_stop_clock(host); 503 + imxmci_start_cmd(host, host->req->stop, 0); 504 + } else { 505 + struct mmc_request *req; 506 + req = host->req; 507 + if( req ) { 508 + imxmci_finish_request(host, req); 509 + } else { 510 + dev_warn(mmc_dev(host->mmc), "imxmci_data_done: no request to finish\n"); 511 + } 512 + } 513 + 514 + return 1; 515 + } 516 + 517 + static int imxmci_cpu_driven_data(struct imxmci_host *host, unsigned int *pstat) 518 + { 519 + int i; 520 + int burst_len; 521 + int flush_len; 522 + int trans_done = 0; 523 + unsigned int stat = *pstat; 524 + 525 + if(host->actual_bus_width == MMC_BUS_WIDTH_4) 526 + burst_len = 16; 527 + else 528 + burst_len = 64; 529 + 530 + /* This is unfortunately required */ 531 + dev_dbg(mmc_dev(host->mmc), "imxmci_cpu_driven_data running STATUS = 0x%x\n", 532 + stat); 533 + 534 + if(host->dma_dir == DMA_FROM_DEVICE) { 535 + imxmci_busy_wait_for_status(host, &stat, 536 + STATUS_APPL_BUFF_FF | STATUS_DATA_TRANS_DONE, 537 + 20, "imxmci_cpu_driven_data read"); 538 + 539 + while((stat & (STATUS_APPL_BUFF_FF | STATUS_DATA_TRANS_DONE)) && 540 + (host->data_cnt < host->dma_size)) { 541 + if(burst_len >= host->dma_size - host->data_cnt) { 542 + flush_len = burst_len; 543 + burst_len = host->dma_size - host->data_cnt; 544 + flush_len -= burst_len; 545 + host->data_cnt = host->dma_size; 546 + trans_done = 1; 547 + } else { 548 + flush_len = 0; 549 + host->data_cnt += burst_len; 550 + } 551 + 552 + for(i = burst_len; i>=2 ; i-=2) { 553 + *(host->data_ptr++) = MMC_BUFFER_ACCESS; 554 + udelay(20); /* required for clocks < 8MHz*/ 555 + } 556 + 557 + if(i == 1) 558 + *(u8*)(host->data_ptr) = MMC_BUFFER_ACCESS; 559 + 560 + stat = MMC_STATUS; 561 + 562 + /* Flush extra bytes from FIFO */ 563 + while(flush_len >= 2){ 564 + flush_len -= 2; 565 + i = MMC_BUFFER_ACCESS; 566 + stat = MMC_STATUS; 567 + stat &= ~STATUS_CRC_READ_ERR; /* Stupid but required there */ 568 + } 569 + 570 + dev_dbg(mmc_dev(host->mmc), "imxmci_cpu_driven_data read burst %d STATUS = 0x%x\n", 571 + burst_len, stat); 572 + } 573 + } else { 574 + imxmci_busy_wait_for_status(host, &stat, 575 + STATUS_APPL_BUFF_FE, 576 + 20, "imxmci_cpu_driven_data write"); 577 + 578 + while((stat & STATUS_APPL_BUFF_FE) && 579 + (host->data_cnt < host->dma_size)) { 580 + if(burst_len >= host->dma_size - host->data_cnt) { 581 + burst_len = host->dma_size - host->data_cnt; 582 + host->data_cnt = host->dma_size; 583 + trans_done = 1; 584 + } else { 585 + host->data_cnt += burst_len; 586 + } 587 + 588 + for(i = burst_len; i>0 ; i-=2) 589 + MMC_BUFFER_ACCESS = *(host->data_ptr++); 590 + 591 + stat = MMC_STATUS; 592 + 593 + dev_dbg(mmc_dev(host->mmc), "imxmci_cpu_driven_data write burst %d STATUS = 0x%x\n", 594 + burst_len, stat); 595 + } 596 + } 597 + 598 + *pstat = stat; 599 + 600 + return trans_done; 601 + } 602 + 603 + static void imxmci_dma_irq(int dma, void *devid, struct pt_regs *regs) 604 + { 605 + struct imxmci_host *host = devid; 606 + uint32_t stat = MMC_STATUS; 607 + 608 + atomic_set(&host->stuck_timeout, 0); 609 + host->status_reg = stat; 610 + set_bit(IMXMCI_PEND_DMA_END_b, &host->pending_events); 611 + tasklet_schedule(&host->tasklet); 612 + } 613 + 614 + static irqreturn_t imxmci_irq(int irq, void *devid, struct pt_regs *regs) 615 + { 616 + struct imxmci_host *host = devid; 617 + uint32_t stat = MMC_STATUS; 618 + int handled = 1; 619 + 620 + MMC_INT_MASK = host->imask | INT_MASK_SDIO | INT_MASK_AUTO_CARD_DETECT; 621 + 622 + atomic_set(&host->stuck_timeout, 0); 623 + host->status_reg = stat; 624 + set_bit(IMXMCI_PEND_IRQ_b, &host->pending_events); 625 + tasklet_schedule(&host->tasklet); 626 + 627 + return IRQ_RETVAL(handled);; 628 + } 629 + 630 + static void imxmci_tasklet_fnc(unsigned long data) 631 + { 632 + struct imxmci_host *host = (struct imxmci_host *)data; 633 + u32 stat; 634 + unsigned int data_dir_mask = 0; /* STATUS_WR_CRC_ERROR_CODE_MASK */ 635 + int timeout = 0; 636 + 637 + if(atomic_read(&host->stuck_timeout) > 4) { 638 + char *what; 639 + timeout = 1; 640 + stat = MMC_STATUS; 641 + host->status_reg = stat; 642 + if (test_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events)) 643 + if (test_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events)) 644 + what = "RESP+DMA"; 645 + else 646 + what = "RESP"; 647 + else 648 + if (test_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events)) 649 + if(test_bit(IMXMCI_PEND_DMA_END_b, &host->pending_events)) 650 + what = "DATA"; 651 + else 652 + what = "DMA"; 653 + else 654 + what = "???"; 655 + 656 + dev_err(mmc_dev(host->mmc), "%s TIMEOUT, hardware stucked STATUS = 0x%04x IMASK = 0x%04x\n", 657 + what, stat, MMC_INT_MASK); 658 + dev_err(mmc_dev(host->mmc), "CMD_DAT_CONT = 0x%04x, MMC_BLK_LEN = 0x%04x, MMC_NOB = 0x%04x, DMA_CCR = 0x%08x\n", 659 + MMC_CMD_DAT_CONT, MMC_BLK_LEN, MMC_NOB, CCR(host->dma)); 660 + dev_err(mmc_dev(host->mmc), "CMD%d, bus %d-bit, dma_size = 0x%x\n", 661 + host->cmd?host->cmd->opcode:0, 1<<host->actual_bus_width, host->dma_size); 662 + } 663 + 664 + if(!host->present || timeout) 665 + host->status_reg = STATUS_TIME_OUT_RESP | STATUS_TIME_OUT_READ | 666 + STATUS_CRC_READ_ERR | STATUS_CRC_WRITE_ERR; 667 + 668 + if(test_bit(IMXMCI_PEND_IRQ_b, &host->pending_events) || timeout) { 669 + clear_bit(IMXMCI_PEND_IRQ_b, &host->pending_events); 670 + 671 + stat = MMC_STATUS; 672 + /* 673 + * This is not required in theory, but there is chance to miss some flag 674 + * which clears automatically by mask write, FreeScale original code keeps 675 + * stat from IRQ time so do I 676 + */ 677 + stat |= host->status_reg; 678 + 679 + if(test_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events)) { 680 + imxmci_busy_wait_for_status(host, &stat, 681 + STATUS_END_CMD_RESP | STATUS_ERR_MASK, 682 + 20, "imxmci_tasklet_fnc resp (ERRATUM #4)"); 683 + } 684 + 685 + if(stat & (STATUS_END_CMD_RESP | STATUS_ERR_MASK)) { 686 + if(test_and_clear_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events)) 687 + imxmci_cmd_done(host, stat); 688 + if(host->data && (stat & STATUS_ERR_MASK)) 689 + imxmci_data_done(host, stat); 690 + } 691 + 692 + if(test_bit(IMXMCI_PEND_CPU_DATA_b, &host->pending_events)) { 693 + stat |= MMC_STATUS; 694 + if(imxmci_cpu_driven_data(host, &stat)){ 695 + if(test_and_clear_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events)) 696 + imxmci_cmd_done(host, stat); 697 + atomic_clear_mask(IMXMCI_PEND_IRQ_m|IMXMCI_PEND_CPU_DATA_m, 698 + &host->pending_events); 699 + imxmci_data_done(host, stat); 700 + } 701 + } 702 + } 703 + 704 + if(test_bit(IMXMCI_PEND_DMA_END_b, &host->pending_events) && 705 + !test_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events)) { 706 + 707 + stat = MMC_STATUS; 708 + /* Same as above */ 709 + stat |= host->status_reg; 710 + 711 + if(host->dma_dir == DMA_TO_DEVICE) { 712 + data_dir_mask = STATUS_WRITE_OP_DONE; 713 + } else { 714 + data_dir_mask = STATUS_DATA_TRANS_DONE; 715 + } 716 + 717 + imxmci_busy_wait_for_status(host, &stat, 718 + data_dir_mask, 719 + 50, "imxmci_tasklet_fnc data"); 720 + 721 + if(stat & data_dir_mask) { 722 + clear_bit(IMXMCI_PEND_DMA_END_b, &host->pending_events); 723 + imxmci_data_done(host, stat); 724 + } 725 + } 726 + 727 + if(test_and_clear_bit(IMXMCI_PEND_CARD_XCHG_b, &host->pending_events)) { 728 + 729 + if(host->cmd) 730 + imxmci_cmd_done(host, STATUS_TIME_OUT_RESP); 731 + 732 + if(host->data) 733 + imxmci_data_done(host, STATUS_TIME_OUT_READ | 734 + STATUS_CRC_READ_ERR | STATUS_CRC_WRITE_ERR); 735 + 736 + if(host->req) 737 + imxmci_finish_request(host, host->req); 738 + 739 + mmc_detect_change(host->mmc, msecs_to_jiffies(100)); 740 + 741 + } 742 + } 743 + 744 + static void imxmci_request(struct mmc_host *mmc, struct mmc_request *req) 745 + { 746 + struct imxmci_host *host = mmc_priv(mmc); 747 + unsigned int cmdat; 748 + 749 + WARN_ON(host->req != NULL); 750 + 751 + host->req = req; 752 + 753 + cmdat = 0; 754 + 755 + if (req->data) { 756 + imxmci_setup_data(host, req->data); 757 + 758 + cmdat |= CMD_DAT_CONT_DATA_ENABLE; 759 + 760 + if (req->data->flags & MMC_DATA_WRITE) 761 + cmdat |= CMD_DAT_CONT_WRITE; 762 + 763 + if (req->data->flags & MMC_DATA_STREAM) { 764 + cmdat |= CMD_DAT_CONT_STREAM_BLOCK; 765 + } 766 + } 767 + 768 + imxmci_start_cmd(host, req->cmd, cmdat); 769 + } 770 + 771 + #define CLK_RATE 19200000 772 + 773 + static void imxmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) 774 + { 775 + struct imxmci_host *host = mmc_priv(mmc); 776 + int prescaler; 777 + 778 + dev_dbg(mmc_dev(host->mmc), "clock %u power %u vdd %u width %u\n", 779 + ios->clock, ios->power_mode, ios->vdd, 780 + (ios->bus_width==MMC_BUS_WIDTH_4)?4:1); 781 + 782 + if( ios->bus_width==MMC_BUS_WIDTH_4 ) { 783 + host->actual_bus_width = MMC_BUS_WIDTH_4; 784 + imx_gpio_mode(PB11_PF_SD_DAT3); 785 + }else{ 786 + host->actual_bus_width = MMC_BUS_WIDTH_1; 787 + imx_gpio_mode(GPIO_PORTB | GPIO_IN | GPIO_PUEN | 11); 788 + } 789 + 790 + if ( host->power_mode != ios->power_mode ) { 791 + switch (ios->power_mode) { 792 + case MMC_POWER_OFF: 793 + break; 794 + case MMC_POWER_UP: 795 + set_bit(IMXMCI_PEND_SET_INIT_b, &host->pending_events); 796 + break; 797 + case MMC_POWER_ON: 798 + break; 799 + } 800 + host->power_mode = ios->power_mode; 801 + } 802 + 803 + if ( ios->clock ) { 804 + unsigned int clk; 805 + 806 + /* The prescaler is 5 for PERCLK2 equal to 96MHz 807 + * then 96MHz / 5 = 19.2 MHz 808 + */ 809 + clk=imx_get_perclk2(); 810 + prescaler=(clk+(CLK_RATE*7)/8)/CLK_RATE; 811 + switch(prescaler) { 812 + case 0: 813 + case 1: prescaler = 0; 814 + break; 815 + case 2: prescaler = 1; 816 + break; 817 + case 3: prescaler = 2; 818 + break; 819 + case 4: prescaler = 4; 820 + break; 821 + default: 822 + case 5: prescaler = 5; 823 + break; 824 + } 825 + 826 + dev_dbg(mmc_dev(host->mmc), "PERCLK2 %d MHz -> prescaler %d\n", 827 + clk, prescaler); 828 + 829 + for(clk=0; clk<8; clk++) { 830 + int x; 831 + x = CLK_RATE / (1<<clk); 832 + if( x <= ios->clock) 833 + break; 834 + } 835 + 836 + MMC_STR_STP_CLK |= STR_STP_CLK_ENABLE; /* enable controller */ 837 + 838 + imxmci_stop_clock(host); 839 + MMC_CLK_RATE = (prescaler<<3) | clk; 840 + imxmci_start_clock(host); 841 + 842 + dev_dbg(mmc_dev(host->mmc), "MMC_CLK_RATE: 0x%08x\n", MMC_CLK_RATE); 843 + } else { 844 + imxmci_stop_clock(host); 845 + } 846 + } 847 + 848 + static struct mmc_host_ops imxmci_ops = { 849 + .request = imxmci_request, 850 + .set_ios = imxmci_set_ios, 851 + }; 852 + 853 + static struct resource *platform_device_resource(struct platform_device *dev, unsigned int mask, int nr) 854 + { 855 + int i; 856 + 857 + for (i = 0; i < dev->num_resources; i++) 858 + if (dev->resource[i].flags == mask && nr-- == 0) 859 + return &dev->resource[i]; 860 + return NULL; 861 + } 862 + 863 + static int platform_device_irq(struct platform_device *dev, int nr) 864 + { 865 + int i; 866 + 867 + for (i = 0; i < dev->num_resources; i++) 868 + if (dev->resource[i].flags == IORESOURCE_IRQ && nr-- == 0) 869 + return dev->resource[i].start; 870 + return NO_IRQ; 871 + } 872 + 873 + static void imxmci_check_status(unsigned long data) 874 + { 875 + struct imxmci_host *host = (struct imxmci_host *)data; 876 + 877 + if( host->pdata->card_present() != host->present ) { 878 + host->present ^= 1; 879 + dev_info(mmc_dev(host->mmc), "card %s\n", 880 + host->present ? "inserted" : "removed"); 881 + 882 + set_bit(IMXMCI_PEND_CARD_XCHG_b, &host->pending_events); 883 + tasklet_schedule(&host->tasklet); 884 + } 885 + 886 + if(test_bit(IMXMCI_PEND_WAIT_RESP_b, &host->pending_events) || 887 + test_bit(IMXMCI_PEND_DMA_DATA_b, &host->pending_events)) { 888 + atomic_inc(&host->stuck_timeout); 889 + if(atomic_read(&host->stuck_timeout) > 4) 890 + tasklet_schedule(&host->tasklet); 891 + } else { 892 + atomic_set(&host->stuck_timeout, 0); 893 + 894 + } 895 + 896 + mod_timer(&host->timer, jiffies + (HZ>>1)); 897 + } 898 + 899 + static int imxmci_probe(struct platform_device *pdev) 900 + { 901 + struct mmc_host *mmc; 902 + struct imxmci_host *host = NULL; 903 + struct resource *r; 904 + int ret = 0, irq; 905 + 906 + printk(KERN_INFO "i.MX mmc driver\n"); 907 + 908 + r = platform_device_resource(pdev, IORESOURCE_MEM, 0); 909 + irq = platform_device_irq(pdev, 0); 910 + if (!r || irq == NO_IRQ) 911 + return -ENXIO; 912 + 913 + r = request_mem_region(r->start, 0x100, "IMXMCI"); 914 + if (!r) 915 + return -EBUSY; 916 + 917 + mmc = mmc_alloc_host(sizeof(struct imxmci_host), &pdev->dev); 918 + if (!mmc) { 919 + ret = -ENOMEM; 920 + goto out; 921 + } 922 + 923 + mmc->ops = &imxmci_ops; 924 + mmc->f_min = 150000; 925 + mmc->f_max = CLK_RATE/2; 926 + mmc->ocr_avail = MMC_VDD_32_33; 927 + mmc->caps |= MMC_CAP_4_BIT_DATA; 928 + 929 + /* MMC core transfer sizes tunable parameters */ 930 + mmc->max_hw_segs = 64; 931 + mmc->max_phys_segs = 64; 932 + mmc->max_sectors = 64; /* default 1 << (PAGE_CACHE_SHIFT - 9) */ 933 + mmc->max_seg_size = 64*512; /* default PAGE_CACHE_SIZE */ 934 + 935 + host = mmc_priv(mmc); 936 + host->mmc = mmc; 937 + host->dma_allocated = 0; 938 + host->pdata = pdev->dev.platform_data; 939 + 940 + spin_lock_init(&host->lock); 941 + host->res = r; 942 + host->irq = irq; 943 + 944 + imx_gpio_mode(PB8_PF_SD_DAT0); 945 + imx_gpio_mode(PB9_PF_SD_DAT1); 946 + imx_gpio_mode(PB10_PF_SD_DAT2); 947 + /* Configured as GPIO with pull-up to ensure right MCC card mode */ 948 + /* Switched to PB11_PF_SD_DAT3 if 4 bit bus is configured */ 949 + imx_gpio_mode(GPIO_PORTB | GPIO_IN | GPIO_PUEN | 11); 950 + /* imx_gpio_mode(PB11_PF_SD_DAT3); */ 951 + imx_gpio_mode(PB12_PF_SD_CLK); 952 + imx_gpio_mode(PB13_PF_SD_CMD); 953 + 954 + imxmci_softreset(); 955 + 956 + if ( MMC_REV_NO != 0x390 ) { 957 + dev_err(mmc_dev(host->mmc), "wrong rev.no. 0x%08x. aborting.\n", 958 + MMC_REV_NO); 959 + goto out; 960 + } 961 + 962 + MMC_READ_TO = 0x2db4; /* recommended in data sheet */ 963 + 964 + host->imask = IMXMCI_INT_MASK_DEFAULT; 965 + MMC_INT_MASK = host->imask; 966 + 967 + 968 + if(imx_dma_request_by_prio(&host->dma, DRIVER_NAME, DMA_PRIO_LOW)<0){ 969 + dev_err(mmc_dev(host->mmc), "imx_dma_request_by_prio failed\n"); 970 + ret = -EBUSY; 971 + goto out; 972 + } 973 + host->dma_allocated=1; 974 + imx_dma_setup_handlers(host->dma, imxmci_dma_irq, NULL, host); 975 + 976 + tasklet_init(&host->tasklet, imxmci_tasklet_fnc, (unsigned long)host); 977 + host->status_reg=0; 978 + host->pending_events=0; 979 + 980 + ret = request_irq(host->irq, imxmci_irq, 0, DRIVER_NAME, host); 981 + if (ret) 982 + goto out; 983 + 984 + host->present = host->pdata->card_present(); 985 + init_timer(&host->timer); 986 + host->timer.data = (unsigned long)host; 987 + host->timer.function = imxmci_check_status; 988 + add_timer(&host->timer); 989 + mod_timer(&host->timer, jiffies + (HZ>>1)); 990 + 991 + platform_set_drvdata(pdev, mmc); 992 + 993 + mmc_add_host(mmc); 994 + 995 + return 0; 996 + 997 + out: 998 + if (host) { 999 + if(host->dma_allocated){ 1000 + imx_dma_free(host->dma); 1001 + host->dma_allocated=0; 1002 + } 1003 + } 1004 + if (mmc) 1005 + mmc_free_host(mmc); 1006 + release_resource(r); 1007 + return ret; 1008 + } 1009 + 1010 + static int imxmci_remove(struct platform_device *pdev) 1011 + { 1012 + struct mmc_host *mmc = platform_get_drvdata(pdev); 1013 + 1014 + platform_set_drvdata(pdev, NULL); 1015 + 1016 + if (mmc) { 1017 + struct imxmci_host *host = mmc_priv(mmc); 1018 + 1019 + tasklet_disable(&host->tasklet); 1020 + 1021 + del_timer_sync(&host->timer); 1022 + mmc_remove_host(mmc); 1023 + 1024 + free_irq(host->irq, host); 1025 + if(host->dma_allocated){ 1026 + imx_dma_free(host->dma); 1027 + host->dma_allocated=0; 1028 + } 1029 + 1030 + tasklet_kill(&host->tasklet); 1031 + 1032 + release_resource(host->res); 1033 + 1034 + mmc_free_host(mmc); 1035 + } 1036 + return 0; 1037 + } 1038 + 1039 + #ifdef CONFIG_PM 1040 + static int imxmci_suspend(struct platform_device *dev, pm_message_t state) 1041 + { 1042 + struct mmc_host *mmc = platform_get_drvdata(dev); 1043 + int ret = 0; 1044 + 1045 + if (mmc) 1046 + ret = mmc_suspend_host(mmc, state); 1047 + 1048 + return ret; 1049 + } 1050 + 1051 + static int imxmci_resume(struct platform_device *dev) 1052 + { 1053 + struct mmc_host *mmc = platform_get_drvdata(dev); 1054 + struct imxmci_host *host; 1055 + int ret = 0; 1056 + 1057 + if (mmc) { 1058 + host = mmc_priv(mmc); 1059 + if(host) 1060 + set_bit(IMXMCI_PEND_SET_INIT_b, &host->pending_events); 1061 + ret = mmc_resume_host(mmc); 1062 + } 1063 + 1064 + return ret; 1065 + } 1066 + #else 1067 + #define imxmci_suspend NULL 1068 + #define imxmci_resume NULL 1069 + #endif /* CONFIG_PM */ 1070 + 1071 + static struct platform_driver imxmci_driver = { 1072 + .probe = imxmci_probe, 1073 + .remove = imxmci_remove, 1074 + .suspend = imxmci_suspend, 1075 + .resume = imxmci_resume, 1076 + .driver = { 1077 + .name = DRIVER_NAME, 1078 + } 1079 + }; 1080 + 1081 + static int __init imxmci_init(void) 1082 + { 1083 + return platform_driver_register(&imxmci_driver); 1084 + } 1085 + 1086 + static void __exit imxmci_exit(void) 1087 + { 1088 + platform_driver_unregister(&imxmci_driver); 1089 + } 1090 + 1091 + module_init(imxmci_init); 1092 + module_exit(imxmci_exit); 1093 + 1094 + MODULE_DESCRIPTION("i.MX Multimedia Card Interface Driver"); 1095 + MODULE_AUTHOR("Sascha Hauer, Pengutronix"); 1096 + MODULE_LICENSE("GPL");
+67
drivers/mmc/imxmmc.h
··· 1 + 2 + # define __REG16(x) (*((volatile u16 *)IO_ADDRESS(x))) 3 + 4 + #define MMC_STR_STP_CLK __REG16(IMX_MMC_BASE + 0x00) 5 + #define MMC_STATUS __REG16(IMX_MMC_BASE + 0x04) 6 + #define MMC_CLK_RATE __REG16(IMX_MMC_BASE + 0x08) 7 + #define MMC_CMD_DAT_CONT __REG16(IMX_MMC_BASE + 0x0C) 8 + #define MMC_RES_TO __REG16(IMX_MMC_BASE + 0x10) 9 + #define MMC_READ_TO __REG16(IMX_MMC_BASE + 0x14) 10 + #define MMC_BLK_LEN __REG16(IMX_MMC_BASE + 0x18) 11 + #define MMC_NOB __REG16(IMX_MMC_BASE + 0x1C) 12 + #define MMC_REV_NO __REG16(IMX_MMC_BASE + 0x20) 13 + #define MMC_INT_MASK __REG16(IMX_MMC_BASE + 0x24) 14 + #define MMC_CMD __REG16(IMX_MMC_BASE + 0x28) 15 + #define MMC_ARGH __REG16(IMX_MMC_BASE + 0x2C) 16 + #define MMC_ARGL __REG16(IMX_MMC_BASE + 0x30) 17 + #define MMC_RES_FIFO __REG16(IMX_MMC_BASE + 0x34) 18 + #define MMC_BUFFER_ACCESS __REG16(IMX_MMC_BASE + 0x38) 19 + #define MMC_BUFFER_ACCESS_OFS 0x38 20 + 21 + 22 + #define STR_STP_CLK_ENDIAN (1<<5) 23 + #define STR_STP_CLK_RESET (1<<3) 24 + #define STR_STP_CLK_ENABLE (1<<2) 25 + #define STR_STP_CLK_START_CLK (1<<1) 26 + #define STR_STP_CLK_STOP_CLK (1<<0) 27 + #define STATUS_CARD_PRESENCE (1<<15) 28 + #define STATUS_SDIO_INT_ACTIVE (1<<14) 29 + #define STATUS_END_CMD_RESP (1<<13) 30 + #define STATUS_WRITE_OP_DONE (1<<12) 31 + #define STATUS_DATA_TRANS_DONE (1<<11) 32 + #define STATUS_WR_CRC_ERROR_CODE_MASK (3<<10) 33 + #define STATUS_CARD_BUS_CLK_RUN (1<<8) 34 + #define STATUS_APPL_BUFF_FF (1<<7) 35 + #define STATUS_APPL_BUFF_FE (1<<6) 36 + #define STATUS_RESP_CRC_ERR (1<<5) 37 + #define STATUS_CRC_READ_ERR (1<<3) 38 + #define STATUS_CRC_WRITE_ERR (1<<2) 39 + #define STATUS_TIME_OUT_RESP (1<<1) 40 + #define STATUS_TIME_OUT_READ (1<<0) 41 + #define STATUS_ERR_MASK 0x2f 42 + #define CLK_RATE_PRESCALER(x) ((x) & 0x7) 43 + #define CLK_RATE_CLK_RATE(x) (((x) & 0x7) << 3) 44 + #define CMD_DAT_CONT_CMD_RESP_LONG_OFF (1<<12) 45 + #define CMD_DAT_CONT_STOP_READWAIT (1<<11) 46 + #define CMD_DAT_CONT_START_READWAIT (1<<10) 47 + #define CMD_DAT_CONT_BUS_WIDTH_1 (0<<8) 48 + #define CMD_DAT_CONT_BUS_WIDTH_4 (2<<8) 49 + #define CMD_DAT_CONT_INIT (1<<7) 50 + #define CMD_DAT_CONT_BUSY (1<<6) 51 + #define CMD_DAT_CONT_STREAM_BLOCK (1<<5) 52 + #define CMD_DAT_CONT_WRITE (1<<4) 53 + #define CMD_DAT_CONT_DATA_ENABLE (1<<3) 54 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R1 (1) 55 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R2 (2) 56 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R3 (3) 57 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R4 (4) 58 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R5 (5) 59 + #define CMD_DAT_CONT_RESPONSE_FORMAT_R6 (6) 60 + #define INT_MASK_AUTO_CARD_DETECT (1<<6) 61 + #define INT_MASK_DAT0_EN (1<<5) 62 + #define INT_MASK_SDIO (1<<4) 63 + #define INT_MASK_BUF_READY (1<<3) 64 + #define INT_MASK_END_CMD_RES (1<<2) 65 + #define INT_MASK_WRITE_OP_DONE (1<<1) 66 + #define INT_MASK_DATA_TRAN (1<<0) 67 + #define INT_ALL (0x7f)
+12
include/asm-arm/arch-imx/mmc.h
··· 1 + #ifndef ASMARM_ARCH_MMC_H 2 + #define ASMARM_ARCH_MMC_H 3 + 4 + #include <linux/mmc/protocol.h> 5 + 6 + struct imxmmc_platform_data { 7 + int (*card_present)(void); 8 + }; 9 + 10 + extern void imx_set_mmc_info(struct imxmmc_platform_data *info); 11 + 12 + #endif