Home | History | Annotate | Download | only in linux
      1 /*
      2  * SdioDrv.c
      3  *
      4  * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved.
      5  * All rights reserved.
      6  *
      7  * Redistribution and use in source and binary forms, with or without
      8  * modification, are permitted provided that the following conditions
      9  * are met:
     10  *
     11  *  * Redistributions of source code must retain the above copyright
     12  *    notice, this list of conditions and the following disclaimer.
     13  *  * Redistributions in binary form must reproduce the above copyright
     14  *    notice, this list of conditions and the following disclaimer in
     15  *    the documentation and/or other materials provided with the
     16  *    distribution.
     17  *  * Neither the name Texas Instruments nor the names of its
     18  *    contributors may be used to endorse or promote products derived
     19  *    from this software without specific prior written permission.
     20  *
     21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     24  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     25  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     26  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     27  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     32  */
     33 
     34 #include <linux/kernel.h>
     35 #include <linux/module.h>
     36 #include <linux/version.h>
     37 #include <linux/moduleparam.h>
     38 #include <linux/delay.h>
     39 #include <linux/interrupt.h>
     40 #include <linux/slab.h>
     41 #include <linux/types.h>
     42 #include <linux/dma-mapping.h>
     43 #include <linux/platform_device.h>
     44 #include <linux/i2c/twl4030.h>
     45 #include <linux/errno.h>
     46 #include <linux/clk.h>
     47 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 31))
     48 #include <plat/hardware.h>
     49 #include <plat/board.h>
     50 #include <plat/clock.h>
     51 #include <plat/dma.h>
     52 #include <plat/io.h>
     53 #include <plat/resource.h>
     54 #define IO_ADDRESS(pa)	OMAP2_L4_IO_ADDRESS(pa)
     55 #else
     56 #include <mach/hardware.h>
     57 #include <mach/board.h>
     58 #include <mach/clock.h>
     59 #include <mach/dma.h>
     60 #include <mach/io.h>
     61 #include <mach/resource.h>
     62 #endif
     63 typedef void *TI_HANDLE;
     64 #include "host_platform.h"
     65 #include "SdioDrvDbg.h"
     66 #include "SdioDrv.h"
     67 
     68 /* #define TI_SDIO_DEBUG */
     69 
     70 #ifndef CONFIG_MMC_EMBEDDED_SDIO
     71 
     72 #define SDIOWQ_NAME			"sdio_wq"
     73 
     74 /*
     75  * HSMMC Address and DMA Settings
     76  */
     77 static unsigned long TIWLAN_MMC_CONTROLLER = 2; /* MMC3 */
     78 static unsigned long TIWLAN_MMC_CONTROLLER_BASE_ADDR = OMAP_HSMMC3_BASE;
     79 #define TIWLAN_MMC_CONTROLLER_BASE_SIZE	512
     80 #define TIWLAN_MMC_MAX_DMA		8192
     81 static unsigned long TIWLAN_MMC_DMA_TX = OMAP34XX_DMA_MMC3_TX;
     82 static unsigned long TIWLAN_MMC_DMA_RX = OMAP34XX_DMA_MMC3_RX;
     83 static unsigned long OMAP_MMC_IRQ = INT_MMC3_IRQ;
     84 
     85 #define OMAP_MMC_MASTER_CLOCK          96000000
     86 /*
     87  *  HSMMC Host Controller Registers
     88  */
     89 #define OMAP_HSMMC_SYSCONFIG           0x0010
     90 #define OMAP_HSMMC_SYSSTATUS           0x0014
     91 #define OMAP_HSMMC_CSRE                0x0024
     92 #define OMAP_HSMMC_SYSTEST             0x0028
     93 #define OMAP_HSMMC_CON                 0x002C
     94 #define OMAP_HSMMC_BLK                 0x0104
     95 #define OMAP_HSMMC_ARG                 0x0108
     96 #define OMAP_HSMMC_CMD                 0x010C
     97 #define OMAP_HSMMC_RSP10               0x0110
     98 #define OMAP_HSMMC_RSP32               0x0114
     99 #define OMAP_HSMMC_RSP54               0x0118
    100 #define OMAP_HSMMC_RSP76               0x011C
    101 #define OMAP_HSMMC_DATA                0x0120
    102 #define OMAP_HSMMC_PSTATE              0x0124
    103 #define OMAP_HSMMC_HCTL                0x0128
    104 #define OMAP_HSMMC_SYSCTL              0x012C
    105 #define OMAP_HSMMC_STAT                0x0130
    106 #define OMAP_HSMMC_IE                  0x0134
    107 #define OMAP_HSMMC_ISE                 0x0138
    108 #define OMAP_HSMMC_AC12                0x013C
    109 #define OMAP_HSMMC_CAPA                0x0140
    110 #define OMAP_HSMMC_CUR_CAPA            0x0148
    111 #define OMAP_HSMMC_REV                 0x01FC
    112 
    113 #define VS18                           (1 << 26)
    114 #define VS30                           (1 << 25)
    115 #define SRA                            (1 << 24)
    116 #define SDVS18                         (0x5 << 9)
    117 #define SDVS30                         (0x6 << 9)
    118 #define SDVSCLR                        0xFFFFF1FF
    119 #define SDVSDET                        0x00000400
    120 #define SIDLE_MODE                     (0x2 << 3)
    121 #define AUTOIDLE                       0x1
    122 #define SDBP                           (1 << 8)
    123 #define DTO                            0xE
    124 #define ICE                            0x1
    125 #define ICS                            0x2
    126 #define CEN                            (1 << 2)
    127 #define CLKD_MASK                      0x0000FFC0
    128 #define IE_EN_MASK                     0x317F0137
    129 #define INIT_STREAM                    (1 << 1)
    130 #define DP_SELECT                      (1 << 21)
    131 #define DDIR                           (1 << 4)
    132 #define DMA_EN                         0x1
    133 #define MSBS                           (1 << 5)
    134 #define BCE                            (1 << 1)
    135 #define ONE_BIT                        (~(0x2))
    136 #define EIGHT_BIT                      (~(0x20))
    137 #define CC                             0x1
    138 #define TC                             0x02
    139 #define OD                             0x1
    140 #define BRW                            0x400
    141 #define BRR                            0x800
    142 #define BRE                            (1 << 11)
    143 #define BWE                            (1 << 10)
    144 #define SBGR                           (1 << 16)
    145 #define CT                             (1 << 17)
    146 #define SDIO_READ                      (1 << 31)
    147 #define SDIO_BLKMODE                   (1 << 27)
    148 #define OMAP_HSMMC_ERR                 (1 << 15)  /* Any error */
    149 #define OMAP_HSMMC_CMD_TIMEOUT         (1 << 16)  /* Com mand response time-out */
    150 #define OMAP_HSMMC_DATA_TIMEOUT        (1 << 20)  /* Data response time-out */
    151 #define OMAP_HSMMC_CMD_CRC             (1 << 17)  /* Command CRC error */
    152 #define OMAP_HSMMC_DATA_CRC            (1 << 21)  /* Date CRC error */
    153 #define OMAP_HSMMC_CARD_ERR            (1 << 28)  /* Card ERR */
    154 #define OMAP_HSMMC_STAT_CLEAR          0xFFFFFFFF
    155 #define INIT_STREAM_CMD                0x00000000
    156 #define INT_CLEAR                      0x00000000
    157 #define BLK_CLEAR                      0x00000000
    158 
    159 /* SCM CONTROL_DEVCONF1 MMC1 overwrite but */
    160 
    161 #define MMC1_ACTIVE_OVERWRITE          (1 << 31)
    162 
    163 #define sdio_blkmode_regaddr           0x2000
    164 #define sdio_blkmode_mask              0xFF00
    165 
    166 #define IO_RW_DIRECT_MASK              0xF000FF00
    167 #define IO_RW_DIRECT_ARG_MASK          0x80001A00
    168 
    169 #define RMASK                          (MMC_RSP_MASK | MMC_RSP_CRC)
    170 #define MMC_TIMEOUT_MS                 100 /*on the new 2430 it was 20, i changed back to 100*//* obc */
    171 #define MMCA_VSN_4                     4
    172 
    173 #define VMMC1_DEV_GRP                  0x27
    174 #define P1_DEV_GRP                     0x20
    175 #define VMMC1_DEDICATED                0x2A
    176 #define VSEL_3V                        0x02
    177 #define VSEL_18V                       0x00
    178 #define PBIAS_3V                       0x03
    179 #define PBIAS_18V                      0x02
    180 #define PBIAS_LITE                     0x04A0
    181 #define PBIAS_CLR                      0x00
    182 
    183 #define OMAP_MMC_REGS_BASE             IO_ADDRESS(TIWLAN_MMC_CONTROLLER_BASE_ADDR)
    184 
    185 /*
    186  * MMC Host controller read/write API's.
    187  */
    188 #define OMAP_HSMMC_READ_OFFSET(offset) (__raw_readl((OMAP_MMC_REGS_BASE) + (offset)))
    189 #define OMAP_HSMMC_READ(reg)           (__raw_readl((OMAP_MMC_REGS_BASE) + OMAP_HSMMC_##reg))
    190 #define OMAP_HSMMC_WRITE(reg, val)     (__raw_writel((val), (OMAP_MMC_REGS_BASE) + OMAP_HSMMC_##reg))
    191 
    192 #define OMAP_HSMMC_SEND_COMMAND(cmd, arg) do \
    193 { \
    194 	OMAP_HSMMC_WRITE(ARG, arg); \
    195 	OMAP_HSMMC_WRITE(CMD, cmd); \
    196 } while (0)
    197 
    198 #define OMAP_HSMMC_CMD52_WRITE     ((SD_IO_RW_DIRECT    << 24) | (OMAP_HSMMC_CMD_SHORT_RESPONSE << 16))
    199 #define OMAP_HSMMC_CMD52_READ      (((SD_IO_RW_DIRECT   << 24) | (OMAP_HSMMC_CMD_SHORT_RESPONSE << 16)) | DDIR)
    200 #define OMAP_HSMMC_CMD53_WRITE     (((SD_IO_RW_EXTENDED << 24) | (OMAP_HSMMC_CMD_SHORT_RESPONSE << 16)) | DP_SELECT)
    201 #define OMAP_HSMMC_CMD53_READ      (((SD_IO_RW_EXTENDED << 24) | (OMAP_HSMMC_CMD_SHORT_RESPONSE << 16)) | DP_SELECT | DDIR)
    202 #define OMAP_HSMMC_CMD53_READ_DMA  (OMAP_HSMMC_CMD53_READ  | DMA_EN)
    203 #define OMAP_HSMMC_CMD53_WRITE_DMA (OMAP_HSMMC_CMD53_WRITE | DMA_EN)
    204 
    205 /* Macros to build commands 52 and 53 in format according to SDIO spec */
    206 #define SDIO_CMD52_READ(v1,v2,v3,v4)        (SDIO_RWFLAG(v1)|SDIO_FUNCN(v2)|SDIO_RAWFLAG(v3)| SDIO_ADDRREG(v4))
    207 #define SDIO_CMD52_WRITE(v1,v2,v3,v4,v5)    (SDIO_RWFLAG(v1)|SDIO_FUNCN(v2)|SDIO_RAWFLAG(v3)| SDIO_ADDRREG(v4)|(v5))
    208 #define SDIO_CMD53_READ(v1,v2,v3,v4,v5,v6)  (SDIO_RWFLAG(v1)|SDIO_FUNCN(v2)|SDIO_BLKM(v3)| SDIO_OPCODE(v4)|SDIO_ADDRREG(v5)|(v6&0x1ff))
    209 #define SDIO_CMD53_WRITE(v1,v2,v3,v4,v5,v6) (SDIO_RWFLAG(v1)|SDIO_FUNCN(v2)|SDIO_BLKM(v3)| SDIO_OPCODE(v4)|SDIO_ADDRREG(v5)|(v6&0x1ff))
    210 
    211 #define SDIODRV_MAX_LOOPS	50000
    212 
    213 #define VMMC2_DEV_GRP		0x2B
    214 #define VMMC2_DEDICATED		0x2E
    215 #define VSEL_S2_18V		0x05
    216 #define LDO_CLR			0x00
    217 #define VSEL_S2_CLR		0x40
    218 #define GPIO_0_BIT_POS		1 << 0
    219 #define GPIO_1_BIT_POS		1 << 1
    220 #define VSIM_DEV_GRP		0x37
    221 #define VSIM_DEDICATED		0x3A
    222 #define TWL4030_MODULE_PM_RECIEVER	0x13
    223 
    224 typedef struct OMAP3430_sdiodrv
    225 {
    226 	struct clk    *fclk, *iclk, *dbclk;
    227 	int           ifclks_enabled;
    228 	spinlock_t    clk_lock;
    229 	int           dma_tx_channel;
    230 	int           dma_rx_channel;
    231 	int           irq;
    232 	void          (*BusTxnCB)(void* BusTxnHandle, int status);
    233 	void*         BusTxnHandle;
    234 	unsigned int  uBlkSize;
    235 	unsigned int  uBlkSizeShift;
    236 	int           async_status;
    237 	int (*wlanDrvIf_pm_resume)(void);
    238 	int (*wlanDrvIf_pm_suspend)(void);
    239 	struct device *dev;
    240 	dma_addr_t dma_read_addr;
    241 	size_t dma_read_size;
    242 	dma_addr_t dma_write_addr;
    243 	size_t dma_write_size;
    244 	struct workqueue_struct *sdio_wq; /* Work Queue */
    245 	struct work_struct sdiodrv_work;
    246 } OMAP3430_sdiodrv_t;
    247 
    248 struct omap_hsmmc_regs {
    249         u32 hctl;
    250         u32 capa;
    251         u32 sysconfig;
    252         u32 ise;
    253         u32 ie;
    254         u32 con;
    255         u32 sysctl;
    256 };
    257 static struct omap_hsmmc_regs hsmmc_ctx;
    258 
    259 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 31))
    260 static struct platform_device dummy_pdev = {
    261 	.dev = {
    262 		.bus = &platform_bus_type,
    263 	},
    264 };
    265 #endif
    266 
    267 #define SDIO_DRIVER_NAME 			"TIWLAN_SDIO"
    268 
    269 module_param(g_sdio_debug_level, int, 0644);
    270 MODULE_PARM_DESC(g_sdio_debug_level, "debug level");
    271 int g_sdio_debug_level = SDIO_DEBUGLEVEL_ERR;
    272 EXPORT_SYMBOL(g_sdio_debug_level);
    273 
    274 OMAP3430_sdiodrv_t g_drv;
    275 
    276 static int sdiodrv_irq_requested = 0;
    277 static int sdiodrv_iclk_got = 0;
    278 static int sdiodrv_fclk_got = 0;
    279 
    280 static void sdioDrv_hsmmc_save_ctx(void);
    281 static void sdioDrv_hsmmc_restore_ctx(void);
    282 static void sdiodrv_dma_shutdown(void);
    283 
    284 #ifndef TI_SDIO_STANDALONE
    285 void sdio_init( int sdcnum )
    286 {
    287 	if( sdcnum <= 0 )
    288 		return;
    289 	TIWLAN_MMC_CONTROLLER = sdcnum - 1;
    290 	if( sdcnum == 2 ) {
    291 		TIWLAN_MMC_CONTROLLER_BASE_ADDR = OMAP_HSMMC2_BASE;
    292 		TIWLAN_MMC_DMA_TX = OMAP24XX_DMA_MMC2_TX;
    293 		TIWLAN_MMC_DMA_RX = OMAP24XX_DMA_MMC2_RX;
    294 		OMAP_MMC_IRQ = INT_MMC2_IRQ;
    295 	}
    296 	else if( sdcnum == 3 ) {
    297 		TIWLAN_MMC_CONTROLLER_BASE_ADDR	= OMAP_HSMMC3_BASE;
    298 		TIWLAN_MMC_DMA_TX = OMAP34XX_DMA_MMC3_TX;
    299 		TIWLAN_MMC_DMA_RX = OMAP34XX_DMA_MMC3_RX;
    300 		OMAP_MMC_IRQ = INT_MMC3_IRQ;
    301 	}
    302 }
    303 #endif
    304 
    305 static void sdioDrv_hsmmc_save_ctx(void)
    306 {
    307 	/* MMC : context save */
    308 	hsmmc_ctx.hctl = OMAP_HSMMC_READ(HCTL);
    309 	hsmmc_ctx.capa = OMAP_HSMMC_READ(CAPA);
    310 	hsmmc_ctx.sysconfig = OMAP_HSMMC_READ(SYSCONFIG);
    311 	hsmmc_ctx.ise = OMAP_HSMMC_READ(ISE);
    312 	hsmmc_ctx.ie = OMAP_HSMMC_READ(IE);
    313 	hsmmc_ctx.con = OMAP_HSMMC_READ(CON);
    314 	hsmmc_ctx.sysctl = OMAP_HSMMC_READ(SYSCTL);
    315 	OMAP_HSMMC_WRITE(ISE, 0);
    316 	OMAP_HSMMC_WRITE(IE, 0);
    317 }
    318 
    319 static void sdioDrv_hsmmc_restore_ctx(void)
    320 {
    321         /* MMC : context restore */
    322         OMAP_HSMMC_WRITE(HCTL, hsmmc_ctx.hctl);
    323         OMAP_HSMMC_WRITE(CAPA, hsmmc_ctx.capa);
    324         OMAP_HSMMC_WRITE(SYSCONFIG, hsmmc_ctx.sysconfig);
    325         OMAP_HSMMC_WRITE(CON, hsmmc_ctx.con);
    326         OMAP_HSMMC_WRITE(ISE, hsmmc_ctx.ise);
    327         OMAP_HSMMC_WRITE(IE, hsmmc_ctx.ie);
    328         OMAP_HSMMC_WRITE(SYSCTL, hsmmc_ctx.sysctl);
    329         OMAP_HSMMC_WRITE(HCTL, OMAP_HSMMC_READ(HCTL) | SDBP);
    330 }
    331 
    332 void sdiodrv_task(struct work_struct *unused)
    333 {
    334 	PDEBUG("sdiodrv_tasklet()\n");
    335 
    336 	if (g_drv.dma_read_addr != 0) {
    337 		dma_unmap_single(g_drv.dev, g_drv.dma_read_addr, g_drv.dma_read_size, DMA_FROM_DEVICE);
    338 		g_drv.dma_read_addr = 0;
    339 		g_drv.dma_read_size = 0;
    340 	}
    341 
    342 	if (g_drv.dma_write_addr != 0) {
    343 		dma_unmap_single(g_drv.dev, g_drv.dma_write_addr, g_drv.dma_write_size, DMA_TO_DEVICE);
    344 		g_drv.dma_write_addr = 0;
    345 		g_drv.dma_write_size = 0;
    346 	}
    347 
    348 	if (g_drv.BusTxnCB != NULL) {
    349 		g_drv.BusTxnCB(g_drv.BusTxnHandle, g_drv.async_status);
    350 	}
    351 }
    352 
    353 irqreturn_t sdiodrv_irq(int irq, void *drv)
    354 {
    355 	int status;
    356 
    357 	PDEBUG("sdiodrv_irq()\n");
    358 
    359 	status = OMAP_HSMMC_READ(STAT);
    360 	OMAP_HSMMC_WRITE(ISE, 0);
    361 	g_drv.async_status = status & (OMAP_HSMMC_ERR);
    362 	if (g_drv.async_status) {
    363 		PERR("sdiodrv_irq: ERROR in STAT = 0x%x\n", status);
    364 	}
    365 	queue_work(g_drv.sdio_wq, &g_drv.sdiodrv_work);
    366 	return IRQ_HANDLED;
    367 }
    368 
    369 void sdiodrv_dma_read_cb(int lch, u16 ch_status, void *data)
    370 {
    371 	PDEBUG("sdiodrv_dma_read_cb() channel=%d status=0x%x\n", lch, (int)ch_status);
    372 
    373 	g_drv.async_status = ch_status & (1 << 7);
    374 
    375 	queue_work(g_drv.sdio_wq, &g_drv.sdiodrv_work);
    376 	sdiodrv_dma_shutdown();
    377 }
    378 
    379 void sdiodrv_dma_write_cb(int lch, u16 ch_status, void *data)
    380 {
    381 	sdiodrv_dma_shutdown();
    382 }
    383 
    384 int sdiodrv_dma_init(void)
    385 {
    386 	int rc;
    387 
    388 	rc = omap_request_dma(TIWLAN_MMC_DMA_TX, "SDIO WRITE", sdiodrv_dma_write_cb, &g_drv, &g_drv.dma_tx_channel);
    389 	if (rc != 0) {
    390 		PERR("sdiodrv_dma_init() omap_request_dma(TIWLAN_MMC_DMA_TX) FAILED\n");
    391 		goto out;
    392 	}
    393 
    394 	rc = omap_request_dma(TIWLAN_MMC_DMA_RX, "SDIO READ", sdiodrv_dma_read_cb, &g_drv, &g_drv.dma_rx_channel);
    395 	if (rc != 0) {
    396 		PERR("sdiodrv_dma_init() omap_request_dma(TIWLAN_MMC_DMA_RX) FAILED\n");
    397 		goto freetx;
    398 	}
    399 
    400 	omap_set_dma_src_params(g_drv.dma_rx_channel,
    401   							0,			// src_port is only for OMAP1
    402   							OMAP_DMA_AMODE_CONSTANT,
    403   							(TIWLAN_MMC_CONTROLLER_BASE_ADDR) + OMAP_HSMMC_DATA, 0, 0);
    404 
    405 	omap_set_dma_dest_params(g_drv.dma_tx_channel,
    406 							0,			// dest_port is only for OMAP1
    407   	  						OMAP_DMA_AMODE_CONSTANT,
    408   	  						(TIWLAN_MMC_CONTROLLER_BASE_ADDR) + OMAP_HSMMC_DATA, 0, 0);
    409 
    410 	return 0;
    411 
    412 freetx:
    413 	omap_free_dma(g_drv.dma_tx_channel);
    414 out:
    415 	return rc;
    416 }
    417 
    418 static void sdiodrv_dma_shutdown(void)
    419 {
    420 	omap_free_dma(g_drv.dma_tx_channel);
    421 	omap_free_dma(g_drv.dma_rx_channel);
    422 } /* sdiodrv_dma_shutdown() */
    423 
    424 static u32 sdiodrv_poll_status(u32 reg_offset, u32 stat, unsigned int msecs)
    425 {
    426 	u32 status=0, loops=0;
    427 
    428 	do
    429 	{
    430 		status = OMAP_HSMMC_READ_OFFSET(reg_offset);
    431 		if(( status & stat))
    432 		{
    433 			break;
    434 		}
    435 	} while (loops++ < SDIODRV_MAX_LOOPS);
    436 
    437 	return status;
    438 } /* sdiodrv_poll_status */
    439 
    440 void dumpreg(void)
    441 {
    442 	printk(KERN_ERR "\n MMCHS_SYSCONFIG   for mmc3 = %x  ", omap_readl( 0x480AD010 ));
    443 	printk(KERN_ERR "\n MMCHS_SYSSTATUS   for mmc3 = %x  ", omap_readl( 0x480AD014 ));
    444 	printk(KERN_ERR "\n MMCHS_CSRE	      for mmc3 = %x  ", omap_readl( 0x480AD024 ));
    445 	printk(KERN_ERR "\n MMCHS_SYSTEST     for mmc3 = %x  ", omap_readl( 0x480AD028 ));
    446 	printk(KERN_ERR "\n MMCHS_CON         for mmc3 = %x  ", omap_readl( 0x480AD02C ));
    447 	printk(KERN_ERR "\n MMCHS_PWCNT       for mmc3 = %x  ", omap_readl( 0x480AD030 ));
    448 	printk(KERN_ERR "\n MMCHS_BLK         for mmc3 = %x  ", omap_readl( 0x480AD104 ));
    449 	printk(KERN_ERR "\n MMCHS_ARG         for mmc3 = %x  ", omap_readl( 0x480AD108 ));
    450 	printk(KERN_ERR "\n MMCHS_CMD         for mmc3 = %x  ", omap_readl( 0x480AD10C ));
    451 	printk(KERN_ERR "\n MMCHS_RSP10       for mmc3 = %x  ", omap_readl( 0x480AD110 ));
    452 	printk(KERN_ERR "\n MMCHS_RSP32       for mmc3 = %x  ", omap_readl( 0x480AD114 ));
    453 	printk(KERN_ERR "\n MMCHS_RSP54       for mmc3 = %x  ", omap_readl( 0x480AD118 ));
    454 	printk(KERN_ERR "\n MMCHS_RSP76       for mmc3 = %x  ", omap_readl( 0x480AD11C ));
    455 	printk(KERN_ERR "\n MMCHS_DATA        for mmc3 = %x  ", omap_readl( 0x480AD120 ));
    456 	printk(KERN_ERR "\n MMCHS_PSTATE      for mmc3 = %x  ", omap_readl( 0x480AD124 ));
    457 	printk(KERN_ERR "\n MMCHS_HCTL        for mmc3 = %x  ", omap_readl( 0x480AD128 ));
    458 	printk(KERN_ERR "\n MMCHS_SYSCTL      for mmc3 = %x  ", omap_readl( 0x480AD12C ));
    459 	printk(KERN_ERR "\n MMCHS_STAT        for mmc3 = %x  ", omap_readl( 0x480AD130 ));
    460 	printk(KERN_ERR "\n MMCHS_IE          for mmc3 = %x  ", omap_readl( 0x480AD134 ));
    461 	printk(KERN_ERR "\n MMCHS_ISE         for mmc3 = %x  ", omap_readl( 0x480AD138 ));
    462 	printk(KERN_ERR "\n MMCHS_AC12        for mmc3 = %x  ", omap_readl( 0x480AD13C ));
    463 	printk(KERN_ERR "\n MMCHS_CAPA        for mmc3 = %x  ", omap_readl( 0x480AD140 ));
    464 	printk(KERN_ERR "\n MMCHS_CUR_CAPA    for mmc3 = %x  ", omap_readl( 0x480AD148 ));
    465 }
    466 
    467 //cmd flow p. 3609 obc
    468 static int sdiodrv_send_command(u32 cmdreg, u32 cmdarg)
    469 {
    470 	OMAP_HSMMC_WRITE(STAT, OMAP_HSMMC_STAT_CLEAR);
    471 	OMAP_HSMMC_SEND_COMMAND(cmdreg, cmdarg);
    472 
    473 	return sdiodrv_poll_status(OMAP_HSMMC_STAT, CC, MMC_TIMEOUT_MS);
    474 } /* sdiodrv_send_command() */
    475 
    476 /*
    477  *  Disable clock to the card
    478  */
    479 static void OMAP3430_mmc_stop_clock(void)
    480 {
    481 	OMAP_HSMMC_WRITE(SYSCTL, OMAP_HSMMC_READ(SYSCTL) & ~CEN);
    482 	if ((OMAP_HSMMC_READ(SYSCTL) & CEN) != 0x0)
    483     {
    484 		PERR("MMC clock not stoped, clock freq can not be altered\n");
    485     }
    486 } /* OMAP3430_mmc_stop_clock */
    487 
    488 /*
    489  *  Reset the SD system
    490  */
    491 int OMAP3430_mmc_reset(void)
    492 {
    493 	int status, loops=0;
    494 	//p. 3598 - need to set SOFTRESET to 0x1 0bc
    495 	OMAP_HSMMC_WRITE(SYSCTL, OMAP_HSMMC_READ(SYSCTL) | SRA);
    496 	while ((status = OMAP_HSMMC_READ(SYSCTL) &  SRA) && loops++ < SDIODRV_MAX_LOOPS);
    497 	if (status & SRA)
    498 	{
    499 	    PERR("OMAP3430_mmc_reset() MMC reset FAILED!! status=0x%x\n",status);
    500 	}
    501 
    502 	return status;
    503 
    504 } /* OMAP3430_mmc_reset */
    505 
    506 //p. 3611
    507 static void OMAP3430_mmc_set_clock(unsigned int clock, OMAP3430_sdiodrv_t *host)
    508 {
    509 	u16           dsor = 0;
    510 	unsigned long regVal;
    511 	int           status;
    512 
    513 	PDEBUG("OMAP3430_mmc_set_clock(%d)\n",clock);
    514 	if (clock) {
    515 		/* Enable MMC_SD_CLK */
    516 		dsor = OMAP_MMC_MASTER_CLOCK / clock;
    517 		if (dsor < 1) {
    518 			dsor = 1;
    519 		}
    520 		if (OMAP_MMC_MASTER_CLOCK / dsor > clock) {
    521 			dsor++;
    522 		}
    523 		if (dsor > 250) {
    524 			dsor = 250;
    525 		}
    526 	}
    527 	OMAP3430_mmc_stop_clock();
    528 	regVal = OMAP_HSMMC_READ(SYSCTL);
    529 	regVal = regVal & ~(CLKD_MASK);//p. 3652
    530 	regVal = regVal | (dsor << 6);
    531 	regVal = regVal | (DTO << 16);//data timeout
    532 	OMAP_HSMMC_WRITE(SYSCTL, regVal);
    533 	OMAP_HSMMC_WRITE(SYSCTL, OMAP_HSMMC_READ(SYSCTL) | ICE);//internal clock enable. obc not mentioned in the spec
    534 	/*
    535      * wait till the the clock is stable (ICS) bit is set
    536 	 */
    537 	status  = sdiodrv_poll_status(OMAP_HSMMC_SYSCTL, ICS, MMC_TIMEOUT_MS);
    538 	if(!(status & ICS)) {
    539 	    PERR("OMAP3430_mmc_set_clock() clock not stable!! status=0x%x\n",status);
    540 	}
    541 	/*
    542 	 * Enable clock to the card
    543 	 */
    544 	OMAP_HSMMC_WRITE(SYSCTL, OMAP_HSMMC_READ(SYSCTL) | CEN);
    545 
    546 } /* OMAP3430_mmc_set_clock() */
    547 
    548 static void sdiodrv_free_resources(void)
    549 {
    550 	if(g_drv.ifclks_enabled) {
    551 		sdioDrv_clk_disable();
    552 	}
    553 
    554 	if (sdiodrv_fclk_got) {
    555 		clk_put(g_drv.fclk);
    556 		sdiodrv_fclk_got = 0;
    557 	}
    558 
    559 	if (sdiodrv_iclk_got) {
    560 		clk_put(g_drv.iclk);
    561 		sdiodrv_iclk_got = 0;
    562 	}
    563 
    564         if (sdiodrv_irq_requested) {
    565                 free_irq(OMAP_MMC_IRQ, &g_drv);
    566                 sdiodrv_irq_requested = 0;
    567         }
    568 }
    569 
    570 int sdioDrv_InitHw(void)
    571 {
    572 	return 0;
    573 } /* sdioDrv_InitHw */
    574 
    575 void sdiodrv_shutdown(void)
    576 {
    577 	PDEBUG("entering %s()\n" , __FUNCTION__ );
    578 
    579 	sdiodrv_free_resources();
    580 
    581 	PDEBUG("exiting %s\n", __FUNCTION__);
    582 } /* sdiodrv_shutdown() */
    583 
    584 static int sdiodrv_send_data_xfer_commad(u32 cmd, u32 cmdarg, int length, u32 buffer_enable_status, unsigned int bBlkMode)
    585 {
    586     int status;
    587 
    588 	PDEBUG("%s() writing CMD 0x%x ARG 0x%x\n",__FUNCTION__, cmd, cmdarg);
    589 
    590     /* block mode */
    591 	if(bBlkMode) {
    592         /*
    593          * Bits 31:16 of BLK reg: NBLK Blocks count for current transfer.
    594          *                        in case of Block MOde the lenght is treated here as number of blocks
    595          *                        (and not as a length).
    596          * Bits 11:0 of BLK reg: BLEN Transfer Block Size. in case of block mode set that field to block size.
    597          */
    598         OMAP_HSMMC_WRITE(BLK, (length << 16) | (g_drv.uBlkSize << 0));
    599 
    600         /*
    601          * In CMD reg:
    602          * BCE: Block Count Enable
    603          * MSBS: Multi/Single block select
    604          */
    605         cmd |= MSBS | BCE ;
    606 	} else {
    607         OMAP_HSMMC_WRITE(BLK, length);
    608     }
    609 
    610     status = sdiodrv_send_command(cmd, cmdarg);
    611 	if(!(status & CC)) {
    612 	    PERR("sdiodrv_send_data_xfer_commad() SDIO Command error! STAT = 0x%x\n", status);
    613 	    return 0;
    614 	}
    615 	PDEBUG("%s() length = %d(%dw) BLK = 0x%x\n",
    616 		   __FUNCTION__, length,((length + 3) >> 2), OMAP_HSMMC_READ(BLK));
    617 
    618     return sdiodrv_poll_status(OMAP_HSMMC_PSTATE, buffer_enable_status, MMC_TIMEOUT_MS);
    619 
    620 } /* sdiodrv_send_data_xfer_commad() */
    621 
    622 int sdiodrv_data_xfer_sync(u32 cmd, u32 cmdarg, void *data, int length, u32 buffer_enable_status)
    623 {
    624     u32 buf_start, buf_end, data32;
    625 	int status;
    626 
    627     status = sdiodrv_send_data_xfer_commad(cmd, cmdarg, length, buffer_enable_status, 0);
    628 	if(!(status & buffer_enable_status))
    629     {
    630 	    PERR("sdiodrv_data_xfer_sync() buffer disabled! length = %d BLK = 0x%x PSTATE = 0x%x\n",
    631 			   length, OMAP_HSMMC_READ(BLK), status);
    632 	    return -1;
    633 	}
    634 	buf_end = (u32)data+(u32)length;
    635 
    636 	//obc need to check BRE/BWE every time, see p. 3605
    637 	/*
    638 	 * Read loop
    639 	 */
    640 	if (buffer_enable_status == BRE)
    641 	{
    642 	  if (((u32)data & 3) == 0) /* 4 bytes aligned */
    643 	  {
    644 		for (buf_start = (u32)data; (u32)data < buf_end; data += sizeof(unsigned long))
    645 		{
    646 		  *((unsigned long*)(data)) = OMAP_HSMMC_READ(DATA);
    647 		}
    648 	  }
    649 	  else                      /* 2 bytes aligned */
    650 	  {
    651 		for (buf_start = (u32)data; (u32)data < buf_end; data += sizeof(unsigned long))
    652 		{
    653 		  data32 = OMAP_HSMMC_READ(DATA);
    654 		  *((unsigned short *)data)     = (unsigned short)data32;
    655 		  *((unsigned short *)data + 1) = (unsigned short)(data32 >> 16);
    656 		}
    657 	  }
    658 	}
    659 	/*
    660 	 * Write loop
    661 	 */
    662 	else
    663 	{
    664 	  if (((u32)data & 3) == 0) /* 4 bytes aligned */
    665 	  {
    666 		for (buf_start = (u32)data; (u32)data < buf_end; data += sizeof(unsigned long))
    667 		{
    668 		  OMAP_HSMMC_WRITE(DATA,*((unsigned long*)(data)));
    669 		}
    670 	  }
    671 	  else                      /* 2 bytes aligned */
    672 	  {
    673 		for (buf_start = (u32)data; (u32)data < buf_end; data += sizeof(unsigned long))
    674 		{
    675 		  OMAP_HSMMC_WRITE(DATA,*((unsigned short*)data) | *((unsigned short*)data+1) << 16 );
    676 		}
    677 
    678 	  }
    679 	}
    680 	status  = sdiodrv_poll_status(OMAP_HSMMC_STAT, TC, MMC_TIMEOUT_MS);
    681 	if(!(status & TC))
    682 	{
    683 	    PERR("sdiodrv_data_xfer_sync() transfer error! STAT = 0x%x\n", status);
    684 	    return -1;
    685 	}
    686 
    687 	return 0;
    688 
    689 } /* sdiodrv_data_xfer_sync() */
    690 
    691 int sdioDrv_ConnectBus (void *       fCbFunc,
    692                         void *       hCbArg,
    693                         unsigned int uBlkSizeShift,
    694                         unsigned int  uSdioThreadPriority)
    695 {
    696 	g_drv.BusTxnCB      = fCbFunc;
    697 	g_drv.BusTxnHandle  = hCbArg;
    698 	g_drv.uBlkSizeShift = uBlkSizeShift;
    699 	g_drv.uBlkSize      = 1 << uBlkSizeShift;
    700 
    701 	INIT_WORK(&g_drv.sdiodrv_work, sdiodrv_task);
    702 
    703 	return sdioDrv_InitHw ();
    704 }
    705 
    706 /*--------------------------------------------------------------------------------------*/
    707 
    708 int sdioDrv_DisconnectBus (void)
    709 {
    710 	/* Disable clocks to handle driver stop command */
    711 	sdioDrv_clk_disable();
    712 	return 0;
    713 }
    714 
    715 //p.3609 cmd flow
    716 int sdioDrv_ExecuteCmd (unsigned int uCmd,
    717                         unsigned int uArg,
    718                         unsigned int uRespType,
    719                         void *       pResponse,
    720                         unsigned int uLen)
    721 {
    722 	unsigned int uCmdReg   = 0;
    723 	unsigned int uStatus   = 0;
    724 	unsigned int uResponse = 0;
    725 
    726 	PDEBUG("sdioDrv_ExecuteCmd() starting cmd %02x arg %08x\n", (int)uCmd, (int)uArg);
    727 
    728 	sdioDrv_clk_enable(); /* To make sure we have clocks enable */
    729 
    730 	uCmdReg = (uCmd << 24) | (uRespType << 16) ;
    731 
    732 	uStatus = sdiodrv_send_command(uCmdReg, uArg);
    733 
    734 	if (!(uStatus & CC))
    735 	{
    736 	    PERR("sdioDrv_ExecuteCmd() SDIO Command error status = 0x%x\n", uStatus);
    737 	    return -1;
    738 	}
    739 	if ((uLen > 0) && (uLen <= 4))/*obc - Len > 4 ? shouldn't read anything ? */
    740 	{
    741 	    uResponse = OMAP_HSMMC_READ(RSP10);
    742 		memcpy (pResponse, (char *)&uResponse, uLen);
    743 		PDEBUG("sdioDrv_ExecuteCmd() response = 0x%x\n", uResponse);
    744 	}
    745 	return 0;
    746 }
    747 
    748 /*--------------------------------------------------------------------------------------*/
    749 
    750 int sdioDrv_ReadSync (unsigned int uFunc,
    751                       unsigned int uHwAddr,
    752                       void *       pData,
    753                       unsigned int uLen,
    754                       unsigned int bIncAddr,
    755                       unsigned int bMore)
    756 {
    757 	unsigned int uCmdArg;
    758 	int          iStatus;
    759 
    760 //	printk(KERN_INFO "in sdioDrv_ReadSync\n");
    761 	uCmdArg = SDIO_CMD53_READ(0, uFunc, 0, bIncAddr, uHwAddr, uLen);
    762 
    763 	iStatus = sdiodrv_data_xfer_sync(OMAP_HSMMC_CMD53_READ, uCmdArg, pData, uLen, BRE);
    764 	if (iStatus != 0) {
    765 		PERR("sdioDrv_ReadSync() FAILED!!\n");
    766 	}
    767 #ifdef TI_SDIO_DEBUG
    768 	if (uLen == 1)
    769 		printk(KERN_INFO "R53: [0x%x](%u) = 0x%x\n", uHwAddr, uLen, (unsigned)(*(char *)pData));
    770 	else if (uLen == 2)
    771 		printk(KERN_INFO "R53: [0x%x](%u) = 0x%x\n", uHwAddr, uLen, (unsigned)(*(short *)pData));
    772 	else if (uLen == 4)
    773 		printk(KERN_INFO "R53: [0x%x](%u) = 0x%x\n", uHwAddr, uLen, (unsigned)(*(long *)pData));
    774 	else
    775 		printk(KERN_INFO "R53: [0x%x](%u)\n", uHwAddr, uLen);
    776 #endif
    777 	return iStatus;
    778 }
    779 
    780 /*--------------------------------------------------------------------------------------*/
    781 int sdioDrv_ReadAsync (unsigned int uFunc,
    782                        unsigned int uHwAddr,
    783                        void *       pData,
    784                        unsigned int uLen,
    785                        unsigned int bBlkMode,
    786                        unsigned int bIncAddr,
    787                        unsigned int bMore)
    788 {
    789 	int          iStatus;
    790 	unsigned int uCmdArg;
    791 	unsigned int uNumBlks;
    792 	unsigned int uDmaBlockCount;
    793 	unsigned int uNumOfElem;
    794 	dma_addr_t dma_bus_address;
    795 
    796 #ifdef TI_SDIO_DEBUG
    797 	printk(KERN_INFO "R53: [0x%x](%u) F[%d]\n", uHwAddr, uLen, uFunc);
    798 #endif
    799 
    800 	//printk(KERN_INFO "in sdioDrv_ReadAsync\n");
    801 
    802     if (bBlkMode)
    803     {
    804         /* For block mode use number of blocks instead of length in bytes */
    805         uNumBlks = uLen >> g_drv.uBlkSizeShift;
    806         uDmaBlockCount = uNumBlks;
    807         /* due to the DMA config to 32Bit per element (OMAP_DMA_DATA_TYPE_S32) the division is by 4 */
    808         uNumOfElem = g_drv.uBlkSize >> 2;
    809     }
    810     else
    811     {
    812         uNumBlks = uLen;
    813         uDmaBlockCount = 1;
    814         uNumOfElem = (uLen + 3) >> 2;
    815     }
    816 
    817     uCmdArg = SDIO_CMD53_READ(0, uFunc, bBlkMode, bIncAddr, uHwAddr, uNumBlks);
    818 
    819     iStatus = sdiodrv_send_data_xfer_commad(OMAP_HSMMC_CMD53_READ_DMA, uCmdArg, uNumBlks, BRE, bBlkMode);
    820 
    821     if (!(iStatus & BRE))
    822     {
    823         PERR("sdioDrv_ReadAsync() buffer disabled! length = %d BLK = 0x%x PSTATE = 0x%x, BlkMode = %d\n",
    824               uLen, OMAP_HSMMC_READ(BLK), iStatus, bBlkMode);
    825 	goto err;
    826     }
    827 
    828 	sdiodrv_dma_init();
    829 
    830 	PDEBUG("sdiodrv_read_async() dma_ch=%d \n",g_drv.dma_rx_channel);
    831 
    832 	dma_bus_address = dma_map_single(g_drv.dev, pData, uLen, DMA_FROM_DEVICE);
    833 	if (!dma_bus_address) {
    834 		PERR("sdioDrv_ReadAsync: dma_map_single failed\n");
    835 		goto err;
    836 	}
    837 
    838 	if (g_drv.dma_read_addr != 0) {
    839 		printk(KERN_ERR "sdioDrv_ReadAsync: previous DMA op is not finished!\n");
    840 		BUG();
    841 	}
    842 
    843 	g_drv.dma_read_addr = dma_bus_address;
    844 	g_drv.dma_read_size = uLen;
    845 
    846 	omap_set_dma_dest_params    (g_drv.dma_rx_channel,
    847 									0,			// dest_port is only for OMAP1
    848 									OMAP_DMA_AMODE_POST_INC,
    849 									dma_bus_address,
    850 									0, 0);
    851 
    852 	omap_set_dma_transfer_params(g_drv.dma_rx_channel, OMAP_DMA_DATA_TYPE_S32, uNumOfElem , uDmaBlockCount , OMAP_DMA_SYNC_FRAME, TIWLAN_MMC_DMA_RX, OMAP_DMA_SRC_SYNC);
    853 
    854 	omap_start_dma(g_drv.dma_rx_channel);
    855 
    856 	/* Continued at sdiodrv_irq() after DMA transfer is finished */
    857 #ifdef TI_SDIO_DEBUG
    858 	printk(KERN_INFO "R53: [0x%x](%u) (A)\n", uHwAddr, uLen);
    859 #endif
    860 	return 0;
    861 err:
    862 	return -1;
    863 
    864 }
    865 
    866 
    867 /*--------------------------------------------------------------------------------------*/
    868 
    869 int sdioDrv_WriteSync (unsigned int uFunc,
    870                        unsigned int uHwAddr,
    871                        void *       pData,
    872                        unsigned int uLen,
    873                        unsigned int bIncAddr,
    874                        unsigned int bMore)
    875 {
    876 	unsigned int uCmdArg;
    877 	int          iStatus;
    878 
    879 //	printk(KERN_INFO "in sdioDrv_WriteSync\n");
    880 
    881 	uCmdArg = SDIO_CMD53_WRITE(1, uFunc, 0, bIncAddr, uHwAddr, uLen);
    882 
    883 	iStatus = sdiodrv_data_xfer_sync(OMAP_HSMMC_CMD53_WRITE, uCmdArg, pData, uLen, BWE);
    884 	if (iStatus != 0)
    885 	{
    886 		PERR("sdioDrv_WriteSync() FAILED!!\n");
    887 	}
    888 #ifdef TI_SDIO_DEBUG
    889 	if (uLen == 1)
    890 		printk(KERN_INFO "W53: [0x%x](%u) < 0x%x\n", uHwAddr, uLen, (unsigned)(*(char *)pData));
    891 	else if (uLen == 2)
    892 		printk(KERN_INFO "W53: [0x%x](%u) < 0x%x\n", uHwAddr, uLen, (unsigned)(*(short *)pData));
    893 	else if (uLen == 4)
    894 		printk(KERN_INFO "W53: [0x%x](%u) < 0x%x\n", uHwAddr, uLen, (unsigned)(*(long *)pData));
    895 	else
    896 		printk(KERN_INFO "W53: [0x%x](%u)\n", uHwAddr, uLen);
    897 #endif
    898 	return iStatus;
    899 }
    900 
    901 /*--------------------------------------------------------------------------------------*/
    902 int sdioDrv_WriteAsync (unsigned int uFunc,
    903                         unsigned int uHwAddr,
    904                         void *       pData,
    905                         unsigned int uLen,
    906                         unsigned int bBlkMode,
    907                         unsigned int bIncAddr,
    908                         unsigned int bMore)
    909 {
    910 	int          iStatus;
    911 	unsigned int uCmdArg;
    912 	unsigned int uNumBlks;
    913 	unsigned int uDmaBlockCount;
    914 	unsigned int uNumOfElem;
    915 	dma_addr_t dma_bus_address;
    916 
    917 #ifdef TI_SDIO_DEBUG
    918 	printk(KERN_INFO "W53: [0x%x](%u) F[%d] B[%d] I[%d]\n", uHwAddr, uLen, uFunc, bBlkMode, bIncAddr);
    919 #endif
    920 
    921 //	printk(KERN_INFO "in sdioDrv_WriteAsync\n");
    922     if (bBlkMode)
    923     {
    924         /* For block mode use number of blocks instead of length in bytes */
    925         uNumBlks = uLen >> g_drv.uBlkSizeShift;
    926         uDmaBlockCount = uNumBlks;
    927         /* due to the DMA config to 32Bit per element (OMAP_DMA_DATA_TYPE_S32) the division is by 4 */
    928         uNumOfElem = g_drv.uBlkSize >> 2;
    929     }
    930     else
    931     {
    932         uNumBlks = uLen;
    933         uDmaBlockCount = 1;
    934         uNumOfElem = (uLen + 3) >> 2;
    935     }
    936 
    937     uCmdArg = SDIO_CMD53_WRITE(1, uFunc, bBlkMode, bIncAddr, uHwAddr, uNumBlks);
    938 
    939     iStatus = sdiodrv_send_data_xfer_commad(OMAP_HSMMC_CMD53_WRITE_DMA, uCmdArg, uNumBlks, BWE, bBlkMode);
    940     if (!(iStatus & BWE))
    941     {
    942         PERR("sdioDrv_WriteAsync() buffer disabled! length = %d, BLK = 0x%x, Status = 0x%x\n",
    943              uLen, OMAP_HSMMC_READ(BLK), iStatus);
    944 	goto err;
    945     }
    946 
    947 	OMAP_HSMMC_WRITE(ISE, TC);
    948 
    949 	sdiodrv_dma_init();
    950 
    951 	dma_bus_address = dma_map_single(g_drv.dev, pData, uLen, DMA_TO_DEVICE);
    952 	if (!dma_bus_address) {
    953 		PERR("sdioDrv_WriteAsync: dma_map_single failed\n");
    954 		goto err;
    955 	}
    956 
    957 	if (g_drv.dma_write_addr != 0) {
    958 		PERR("sdioDrv_WriteAsync: previous DMA op is not finished!\n");
    959 		BUG();
    960 	}
    961 
    962 	g_drv.dma_write_addr = dma_bus_address;
    963 	g_drv.dma_write_size = uLen;
    964 
    965 	omap_set_dma_src_params     (g_drv.dma_tx_channel,
    966 									0,			// src_port is only for OMAP1
    967 									OMAP_DMA_AMODE_POST_INC,
    968 									dma_bus_address,
    969 									0, 0);
    970 
    971 	omap_set_dma_transfer_params(g_drv.dma_tx_channel, OMAP_DMA_DATA_TYPE_S32, uNumOfElem, uDmaBlockCount, OMAP_DMA_SYNC_FRAME, TIWLAN_MMC_DMA_TX, OMAP_DMA_DST_SYNC);
    972 
    973 	omap_start_dma(g_drv.dma_tx_channel);
    974 
    975 	/* Continued at sdiodrv_irq() after DMA transfer is finished */
    976 	return 0;
    977 err:
    978 	return -1;
    979 }
    980 
    981 /*--------------------------------------------------------------------------------------*/
    982 
    983 int sdioDrv_ReadSyncBytes (unsigned int  uFunc,
    984                            unsigned int  uHwAddr,
    985                            unsigned char *pData,
    986                            unsigned int  uLen,
    987                            unsigned int  bMore)
    988 {
    989 	unsigned int uCmdArg;
    990 	unsigned int i;
    991 	int          iStatus;
    992 
    993 	for (i = 0; i < uLen; i++) {
    994 		uCmdArg = SDIO_CMD52_READ(0, uFunc, 0, uHwAddr);
    995 
    996 		iStatus = sdiodrv_send_command(OMAP_HSMMC_CMD52_READ, uCmdArg);
    997 
    998 		if (!(iStatus & CC)) {
    999 			PERR("sdioDrv_ReadSyncBytes() SDIO Command error status = 0x%x\n", iStatus);
   1000 			return -1;
   1001 		}
   1002 		else {
   1003 			*pData = (unsigned char)(OMAP_HSMMC_READ(RSP10));
   1004 		}
   1005 #ifdef TI_SDIO_DEBUG
   1006 		printk(KERN_INFO "R52: [0x%x](%u) = 0x%x\n", uHwAddr, uLen, (unsigned)*pData);
   1007 #endif
   1008 		uHwAddr++;
   1009 		pData++;
   1010 	}
   1011 
   1012 	return 0;
   1013 }
   1014 
   1015 /*--------------------------------------------------------------------------------------*/
   1016 
   1017 int sdioDrv_WriteSyncBytes (unsigned int  uFunc,
   1018                             unsigned int  uHwAddr,
   1019                             unsigned char *pData,
   1020                             unsigned int  uLen,
   1021                             unsigned int  bMore)
   1022 {
   1023 	unsigned int uCmdArg;
   1024 	unsigned int i;
   1025 	int          iStatus;
   1026 
   1027 	for (i = 0; i < uLen; i++) {
   1028 #ifdef TI_SDIO_DEBUG
   1029 		printk(KERN_INFO "W52: [0x%x](%u) < 0x%x\n", uHwAddr, uLen, (unsigned)*pData);
   1030 #endif
   1031 		uCmdArg = SDIO_CMD52_WRITE(1, uFunc, 0, uHwAddr, *pData);
   1032 
   1033 		iStatus = sdiodrv_send_command(OMAP_HSMMC_CMD52_WRITE, uCmdArg);
   1034 		if (!(iStatus & CC)) {
   1035 			PERR("sdioDrv_WriteSyncBytes() SDIO Command error status = 0x%x\n", iStatus);
   1036 			return -1;
   1037 		}
   1038 		uHwAddr++;
   1039 		pData++;
   1040 	}
   1041 
   1042 	return 0;
   1043 }
   1044 
   1045 static int sdioDrv_probe(struct platform_device *pdev)
   1046 {
   1047 	int rc;
   1048 	u32 status;
   1049 #ifdef SDIO_1_BIT /* see also in SdioAdapter.c */
   1050 	unsigned long clock_rate = 6000000;
   1051 #else
   1052 	unsigned long clock_rate = 24000000;
   1053 #endif
   1054 
   1055 	printk(KERN_INFO "TIWLAN SDIO probe: initializing mmc%d device\n", pdev->id + 1);
   1056 
   1057 	/* remember device struct for future DMA operations */
   1058 	g_drv.dev = &pdev->dev;
   1059 	g_drv.irq = platform_get_irq(pdev, 0);
   1060 	if (g_drv.irq < 0)
   1061 		return -ENXIO;
   1062 
   1063         rc= request_irq(OMAP_MMC_IRQ, sdiodrv_irq, 0, SDIO_DRIVER_NAME, &g_drv);
   1064         if (rc != 0) {
   1065                 PERR("sdioDrv_InitHw() - request_irq FAILED!!\n");
   1066                 return rc;
   1067         }
   1068         sdiodrv_irq_requested = 1;
   1069 
   1070 	spin_lock_init(&g_drv.clk_lock);
   1071 
   1072 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 31))
   1073 	dummy_pdev.id = TIWLAN_MMC_CONTROLLER;
   1074 	dev_set_name(&dummy_pdev.dev, "mmci-omap-hs.%lu", TIWLAN_MMC_CONTROLLER);
   1075 	g_drv.fclk = clk_get(&dummy_pdev.dev, "fck");
   1076 #else
   1077 	g_drv.fclk = clk_get(&pdev->dev, "mmchs_fck");
   1078 #endif
   1079 	if (IS_ERR(g_drv.fclk)) {
   1080 		rc = PTR_ERR(g_drv.fclk);
   1081 		PERR("clk_get(fclk) FAILED !!!\n");
   1082 		goto err;
   1083 	}
   1084 	sdiodrv_fclk_got = 1;
   1085 
   1086 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 31))
   1087 	g_drv.iclk = clk_get(&dummy_pdev.dev, "ick");
   1088 #else
   1089 	g_drv.iclk = clk_get(&pdev->dev, "mmchs_ick");
   1090 #endif
   1091 	if (IS_ERR(g_drv.iclk)) {
   1092 		rc = PTR_ERR(g_drv.iclk);
   1093 		PERR("clk_get(iclk) FAILED !!!\n");
   1094 		goto err;
   1095 	}
   1096 	sdiodrv_iclk_got = 1;
   1097 
   1098         rc = sdioDrv_clk_enable();
   1099         if (rc) {
   1100                 PERR("sdioDrv_probe : clk_enable FAILED !!!\n");
   1101                 goto err;
   1102         }
   1103 
   1104 	OMAP3430_mmc_reset();
   1105 
   1106 	//obc - init sequence p. 3600,3617
   1107 	/* 1.8V */
   1108 	OMAP_HSMMC_WRITE(CAPA,		OMAP_HSMMC_READ(CAPA) | VS18);
   1109 	OMAP_HSMMC_WRITE(HCTL,		OMAP_HSMMC_READ(HCTL) | SDVS18);//SDVS fits p. 3650
   1110 	/* clock gating */
   1111 	OMAP_HSMMC_WRITE(SYSCONFIG, OMAP_HSMMC_READ(SYSCONFIG) | AUTOIDLE);
   1112 
   1113 	/* bus power */
   1114 	OMAP_HSMMC_WRITE(HCTL,		OMAP_HSMMC_READ(HCTL) | SDBP);//SDBP fits p. 3650
   1115 	/* interrupts */
   1116 	OMAP_HSMMC_WRITE(ISE,		0);
   1117 	OMAP_HSMMC_WRITE(IE,		IE_EN_MASK);
   1118 
   1119 	//p. 3601 suggests moving to the end
   1120 	OMAP3430_mmc_set_clock(clock_rate, &g_drv);
   1121 	printk(KERN_INFO "SDIO clock Configuration is now set to %dMhz\n",(int)clock_rate/1000000);
   1122 
   1123 	/* Bus width */
   1124 #ifdef SDIO_1_BIT /* see also in SdioAdapter.c */
   1125 	PDEBUG("%s() setting %d data lines\n",__FUNCTION__, 1);
   1126 	OMAP_HSMMC_WRITE(HCTL, OMAP_HSMMC_READ(HCTL) & (ONE_BIT));
   1127 #else
   1128 	PDEBUG("%s() setting %d data lines\n",__FUNCTION__, 4);
   1129 	OMAP_HSMMC_WRITE(HCTL, OMAP_HSMMC_READ(HCTL) | (1 << 1));//DTW 4 bits - p. 3650
   1130 #endif
   1131 
   1132 	/* send the init sequence. 80 clocks of synchronization in the SDIO */
   1133 	//doesn't match p. 3601,3617 - obc
   1134 	OMAP_HSMMC_WRITE( CON, OMAP_HSMMC_READ(CON) | INIT_STREAM);
   1135 	OMAP_HSMMC_SEND_COMMAND( 0, 0);
   1136 	status = sdiodrv_poll_status(OMAP_HSMMC_STAT, CC, MMC_TIMEOUT_MS);
   1137 	if (!(status & CC)) {
   1138 		PERR("sdioDrv_InitHw() SDIO Command error status = 0x%x\n", status);
   1139 		rc = -1;
   1140 		goto err;
   1141 	}
   1142 	OMAP_HSMMC_WRITE(CON, OMAP_HSMMC_READ(CON) & ~INIT_STREAM);
   1143 
   1144 	/* Disabling clocks for now */
   1145 	sdioDrv_clk_disable();
   1146 
   1147 	return 0;
   1148 err:
   1149 	sdiodrv_free_resources();
   1150 	return rc;
   1151 }
   1152 
   1153 static int sdioDrv_remove(struct platform_device *pdev)
   1154 {
   1155 	printk(KERN_INFO "sdioDrv_remove: calling sdiodrv_shutdown\n");
   1156 
   1157 	sdiodrv_shutdown();
   1158 
   1159 	return 0;
   1160 }
   1161 
   1162 #ifdef CONFIG_PM
   1163 static int sdioDrv_suspend(struct platform_device *pdev, pm_message_t state)
   1164 {
   1165 	printk(KERN_INFO "TISDIO: sdioDrv is suspending\n");
   1166 	return 0;
   1167 }
   1168 
   1169 /* Routine to resume the MMC device */
   1170 static int sdioDrv_resume(struct platform_device *pdev)
   1171 {
   1172 	printk(KERN_INFO "TISDIO: sdioDrv is resuming\n");
   1173 	return 0;
   1174 }
   1175 #else
   1176 #define sdioDrv_suspend		NULL
   1177 #define sdioDrv_resume		NULL
   1178 #endif
   1179 
   1180 static struct platform_driver sdioDrv_struct = {
   1181 	.probe		= sdioDrv_probe,
   1182 	.remove		= sdioDrv_remove,
   1183 	.suspend	= sdioDrv_suspend,
   1184 	.resume		= sdioDrv_resume,
   1185 	.driver		= {
   1186 		.name = SDIO_DRIVER_NAME,
   1187 	},
   1188 };
   1189 
   1190 void sdioDrv_register_pm(int (*wlanDrvIf_Start)(void),
   1191 						int (*wlanDrvIf_Stop)(void))
   1192 {
   1193 	g_drv.wlanDrvIf_pm_resume = wlanDrvIf_Start;
   1194 	g_drv.wlanDrvIf_pm_suspend = wlanDrvIf_Stop;
   1195 }
   1196 
   1197 int sdioDrv_clk_enable(void)
   1198 {
   1199        unsigned long flags;
   1200        int ret = 0;
   1201 
   1202        spin_lock_irqsave(&g_drv.clk_lock, flags);
   1203        if (g_drv.ifclks_enabled)
   1204                goto done;
   1205 
   1206        ret = clk_enable(g_drv.iclk);
   1207        if (ret)
   1208               goto clk_en_err1;
   1209 
   1210        ret = clk_enable(g_drv.fclk);
   1211        if (ret)
   1212                goto clk_en_err2;
   1213        g_drv.ifclks_enabled = 1;
   1214 
   1215        sdioDrv_hsmmc_restore_ctx();
   1216 
   1217 done:
   1218        spin_unlock_irqrestore(&g_drv.clk_lock, flags);
   1219        return ret;
   1220 
   1221 clk_en_err2:
   1222        clk_disable(g_drv.iclk);
   1223 clk_en_err1 :
   1224        spin_unlock_irqrestore(&g_drv.clk_lock, flags);
   1225        return ret;
   1226 }
   1227 
   1228 void sdioDrv_clk_disable(void)
   1229 {
   1230        unsigned long flags;
   1231 
   1232        spin_lock_irqsave(&g_drv.clk_lock, flags);
   1233        if (!g_drv.ifclks_enabled)
   1234                goto done;
   1235 
   1236        sdioDrv_hsmmc_save_ctx();
   1237 
   1238        clk_disable(g_drv.fclk);
   1239        clk_disable(g_drv.iclk);
   1240        g_drv.ifclks_enabled = 0;
   1241 done:
   1242        spin_unlock_irqrestore(&g_drv.clk_lock, flags);
   1243 }
   1244 
   1245 #ifdef TI_SDIO_STANDALONE
   1246 static int __init sdioDrv_init(void)
   1247 #else
   1248 int __init sdioDrv_init(int sdcnum)
   1249 #endif
   1250 {
   1251 	memset(&g_drv, 0, sizeof(g_drv));
   1252 	memset(&hsmmc_ctx, 0, sizeof(hsmmc_ctx));
   1253 
   1254 	printk(KERN_INFO "TIWLAN SDIO init\n");
   1255 #ifndef TI_SDIO_STANDALONE
   1256 	sdio_init( sdcnum );
   1257 #endif
   1258 	g_drv.sdio_wq = create_freezeable_workqueue(SDIOWQ_NAME);
   1259 	if (!g_drv.sdio_wq) {
   1260 		printk("TISDIO: Fail to create SDIO WQ\n");
   1261 		return -EINVAL;
   1262 	}
   1263 	/* Register the sdio driver */
   1264 	return platform_driver_register(&sdioDrv_struct);
   1265 }
   1266 
   1267 #ifdef TI_SDIO_STANDALONE
   1268 static
   1269 #endif
   1270 void __exit sdioDrv_exit(void)
   1271 {
   1272 	/* Unregister sdio driver */
   1273 	platform_driver_unregister(&sdioDrv_struct);
   1274 	if (g_drv.sdio_wq)
   1275 		destroy_workqueue(g_drv.sdio_wq);
   1276 }
   1277 
   1278 #ifdef TI_SDIO_STANDALONE
   1279 module_init(sdioDrv_init);
   1280 module_exit(sdioDrv_exit);
   1281 #endif
   1282 
   1283 EXPORT_SYMBOL(sdioDrv_ConnectBus);
   1284 EXPORT_SYMBOL(sdioDrv_DisconnectBus);
   1285 EXPORT_SYMBOL(sdioDrv_ExecuteCmd);
   1286 EXPORT_SYMBOL(sdioDrv_ReadSync);
   1287 EXPORT_SYMBOL(sdioDrv_WriteSync);
   1288 EXPORT_SYMBOL(sdioDrv_ReadAsync);
   1289 EXPORT_SYMBOL(sdioDrv_WriteAsync);
   1290 EXPORT_SYMBOL(sdioDrv_ReadSyncBytes);
   1291 EXPORT_SYMBOL(sdioDrv_WriteSyncBytes);
   1292 EXPORT_SYMBOL(sdioDrv_register_pm);
   1293 MODULE_DESCRIPTION("TI WLAN SDIO driver");
   1294 MODULE_LICENSE("GPL");
   1295 MODULE_ALIAS(SDIO_DRIVER_NAME);
   1296 MODULE_AUTHOR("Texas Instruments Inc");
   1297 #endif
   1298