xref: /openbmc/linux/drivers/mmc/host/sdhci.c (revision 49c468fc)
11c6a0718SPierre Ossman /*
270f10482SPierre Ossman  *  linux/drivers/mmc/host/sdhci.c - Secure Digital Host Controller Interface driver
31c6a0718SPierre Ossman  *
4b69c9058SPierre Ossman  *  Copyright (C) 2005-2008 Pierre Ossman, All Rights Reserved.
51c6a0718SPierre Ossman  *
61c6a0718SPierre Ossman  * This program is free software; you can redistribute it and/or modify
71c6a0718SPierre Ossman  * it under the terms of the GNU General Public License as published by
81c6a0718SPierre Ossman  * the Free Software Foundation; either version 2 of the License, or (at
91c6a0718SPierre Ossman  * your option) any later version.
1084c46a53SPierre Ossman  *
1184c46a53SPierre Ossman  * Thanks to the following companies for their support:
1284c46a53SPierre Ossman  *
1384c46a53SPierre Ossman  *     - JMicron (hardware and technical support)
141c6a0718SPierre Ossman  */
151c6a0718SPierre Ossman 
161c6a0718SPierre Ossman #include <linux/delay.h>
171c6a0718SPierre Ossman #include <linux/highmem.h>
18b8c86fc5SPierre Ossman #include <linux/io.h>
191c6a0718SPierre Ossman #include <linux/dma-mapping.h>
205a0e3ad6STejun Heo #include <linux/slab.h>
2111763609SRalf Baechle #include <linux/scatterlist.h>
229bea3c85SMarek Szyprowski #include <linux/regulator/consumer.h>
231c6a0718SPierre Ossman 
242f730fecSPierre Ossman #include <linux/leds.h>
252f730fecSPierre Ossman 
2622113efdSAries Lee #include <linux/mmc/mmc.h>
271c6a0718SPierre Ossman #include <linux/mmc/host.h>
281c6a0718SPierre Ossman 
291c6a0718SPierre Ossman #include "sdhci.h"
301c6a0718SPierre Ossman 
311c6a0718SPierre Ossman #define DRIVER_NAME "sdhci"
321c6a0718SPierre Ossman 
331c6a0718SPierre Ossman #define DBG(f, x...) \
341c6a0718SPierre Ossman 	pr_debug(DRIVER_NAME " [%s()]: " f, __func__,## x)
351c6a0718SPierre Ossman 
36f9134319SPierre Ossman #if defined(CONFIG_LEDS_CLASS) || (defined(CONFIG_LEDS_CLASS_MODULE) && \
37f9134319SPierre Ossman 	defined(CONFIG_MMC_SDHCI_MODULE))
38f9134319SPierre Ossman #define SDHCI_USE_LEDS_CLASS
39f9134319SPierre Ossman #endif
40f9134319SPierre Ossman 
411c6a0718SPierre Ossman static unsigned int debug_quirks = 0;
421c6a0718SPierre Ossman 
431c6a0718SPierre Ossman static void sdhci_finish_data(struct sdhci_host *);
441c6a0718SPierre Ossman 
451c6a0718SPierre Ossman static void sdhci_send_command(struct sdhci_host *, struct mmc_command *);
461c6a0718SPierre Ossman static void sdhci_finish_command(struct sdhci_host *);
471c6a0718SPierre Ossman 
481c6a0718SPierre Ossman static void sdhci_dumpregs(struct sdhci_host *host)
491c6a0718SPierre Ossman {
50412ab659SPhilip Rakity 	printk(KERN_DEBUG DRIVER_NAME ": =========== REGISTER DUMP (%s)===========\n",
51412ab659SPhilip Rakity 		mmc_hostname(host->mmc));
521c6a0718SPierre Ossman 
531c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Sys addr: 0x%08x | Version:  0x%08x\n",
544e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_DMA_ADDRESS),
554e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_HOST_VERSION));
561c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Blk size: 0x%08x | Blk cnt:  0x%08x\n",
574e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_BLOCK_SIZE),
584e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_BLOCK_COUNT));
591c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Argument: 0x%08x | Trn mode: 0x%08x\n",
604e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_ARGUMENT),
614e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_TRANSFER_MODE));
621c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Present:  0x%08x | Host ctl: 0x%08x\n",
634e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_PRESENT_STATE),
644e4141a5SAnton Vorontsov 		sdhci_readb(host, SDHCI_HOST_CONTROL));
651c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Power:    0x%08x | Blk gap:  0x%08x\n",
664e4141a5SAnton Vorontsov 		sdhci_readb(host, SDHCI_POWER_CONTROL),
674e4141a5SAnton Vorontsov 		sdhci_readb(host, SDHCI_BLOCK_GAP_CONTROL));
681c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Wake-up:  0x%08x | Clock:    0x%08x\n",
694e4141a5SAnton Vorontsov 		sdhci_readb(host, SDHCI_WAKE_UP_CONTROL),
704e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_CLOCK_CONTROL));
711c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Timeout:  0x%08x | Int stat: 0x%08x\n",
724e4141a5SAnton Vorontsov 		sdhci_readb(host, SDHCI_TIMEOUT_CONTROL),
734e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_INT_STATUS));
741c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": Int enab: 0x%08x | Sig enab: 0x%08x\n",
754e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_INT_ENABLE),
764e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_SIGNAL_ENABLE));
771c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": AC12 err: 0x%08x | Slot int: 0x%08x\n",
784e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_ACMD12_ERR),
794e4141a5SAnton Vorontsov 		sdhci_readw(host, SDHCI_SLOT_INT_STATUS));
80e8120ad1SPhilip Rakity 	printk(KERN_DEBUG DRIVER_NAME ": Caps:     0x%08x | Caps_1:   0x%08x\n",
814e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_CAPABILITIES),
82e8120ad1SPhilip Rakity 		sdhci_readl(host, SDHCI_CAPABILITIES_1));
83e8120ad1SPhilip Rakity 	printk(KERN_DEBUG DRIVER_NAME ": Cmd:      0x%08x | Max curr: 0x%08x\n",
84e8120ad1SPhilip Rakity 		sdhci_readw(host, SDHCI_COMMAND),
854e4141a5SAnton Vorontsov 		sdhci_readl(host, SDHCI_MAX_CURRENT));
86f2119df6SArindam Nath 	printk(KERN_DEBUG DRIVER_NAME ": Host ctl2: 0x%08x\n",
87f2119df6SArindam Nath 		sdhci_readw(host, SDHCI_HOST_CONTROL2));
881c6a0718SPierre Ossman 
89be3f4ae0SBen Dooks 	if (host->flags & SDHCI_USE_ADMA)
90be3f4ae0SBen Dooks 		printk(KERN_DEBUG DRIVER_NAME ": ADMA Err: 0x%08x | ADMA Ptr: 0x%08x\n",
91be3f4ae0SBen Dooks 		       readl(host->ioaddr + SDHCI_ADMA_ERROR),
92be3f4ae0SBen Dooks 		       readl(host->ioaddr + SDHCI_ADMA_ADDRESS));
93be3f4ae0SBen Dooks 
941c6a0718SPierre Ossman 	printk(KERN_DEBUG DRIVER_NAME ": ===========================================\n");
951c6a0718SPierre Ossman }
961c6a0718SPierre Ossman 
971c6a0718SPierre Ossman /*****************************************************************************\
981c6a0718SPierre Ossman  *                                                                           *
991c6a0718SPierre Ossman  * Low level functions                                                       *
1001c6a0718SPierre Ossman  *                                                                           *
1011c6a0718SPierre Ossman \*****************************************************************************/
1021c6a0718SPierre Ossman 
1037260cf5eSAnton Vorontsov static void sdhci_clear_set_irqs(struct sdhci_host *host, u32 clear, u32 set)
1047260cf5eSAnton Vorontsov {
1057260cf5eSAnton Vorontsov 	u32 ier;
1067260cf5eSAnton Vorontsov 
1077260cf5eSAnton Vorontsov 	ier = sdhci_readl(host, SDHCI_INT_ENABLE);
1087260cf5eSAnton Vorontsov 	ier &= ~clear;
1097260cf5eSAnton Vorontsov 	ier |= set;
1107260cf5eSAnton Vorontsov 	sdhci_writel(host, ier, SDHCI_INT_ENABLE);
1117260cf5eSAnton Vorontsov 	sdhci_writel(host, ier, SDHCI_SIGNAL_ENABLE);
1127260cf5eSAnton Vorontsov }
1137260cf5eSAnton Vorontsov 
1147260cf5eSAnton Vorontsov static void sdhci_unmask_irqs(struct sdhci_host *host, u32 irqs)
1157260cf5eSAnton Vorontsov {
1167260cf5eSAnton Vorontsov 	sdhci_clear_set_irqs(host, 0, irqs);
1177260cf5eSAnton Vorontsov }
1187260cf5eSAnton Vorontsov 
1197260cf5eSAnton Vorontsov static void sdhci_mask_irqs(struct sdhci_host *host, u32 irqs)
1207260cf5eSAnton Vorontsov {
1217260cf5eSAnton Vorontsov 	sdhci_clear_set_irqs(host, irqs, 0);
1227260cf5eSAnton Vorontsov }
1237260cf5eSAnton Vorontsov 
1247260cf5eSAnton Vorontsov static void sdhci_set_card_detection(struct sdhci_host *host, bool enable)
1257260cf5eSAnton Vorontsov {
1267260cf5eSAnton Vorontsov 	u32 irqs = SDHCI_INT_CARD_REMOVE | SDHCI_INT_CARD_INSERT;
1277260cf5eSAnton Vorontsov 
12868d1fb7eSAnton Vorontsov 	if (host->quirks & SDHCI_QUIRK_BROKEN_CARD_DETECTION)
12968d1fb7eSAnton Vorontsov 		return;
13068d1fb7eSAnton Vorontsov 
1317260cf5eSAnton Vorontsov 	if (enable)
1327260cf5eSAnton Vorontsov 		sdhci_unmask_irqs(host, irqs);
1337260cf5eSAnton Vorontsov 	else
1347260cf5eSAnton Vorontsov 		sdhci_mask_irqs(host, irqs);
1357260cf5eSAnton Vorontsov }
1367260cf5eSAnton Vorontsov 
1377260cf5eSAnton Vorontsov static void sdhci_enable_card_detection(struct sdhci_host *host)
1387260cf5eSAnton Vorontsov {
1397260cf5eSAnton Vorontsov 	sdhci_set_card_detection(host, true);
1407260cf5eSAnton Vorontsov }
1417260cf5eSAnton Vorontsov 
1427260cf5eSAnton Vorontsov static void sdhci_disable_card_detection(struct sdhci_host *host)
1437260cf5eSAnton Vorontsov {
1447260cf5eSAnton Vorontsov 	sdhci_set_card_detection(host, false);
1457260cf5eSAnton Vorontsov }
1467260cf5eSAnton Vorontsov 
1471c6a0718SPierre Ossman static void sdhci_reset(struct sdhci_host *host, u8 mask)
1481c6a0718SPierre Ossman {
1491c6a0718SPierre Ossman 	unsigned long timeout;
150063a9dbbSAnton Vorontsov 	u32 uninitialized_var(ier);
1511c6a0718SPierre Ossman 
152b8c86fc5SPierre Ossman 	if (host->quirks & SDHCI_QUIRK_NO_CARD_NO_RESET) {
1534e4141a5SAnton Vorontsov 		if (!(sdhci_readl(host, SDHCI_PRESENT_STATE) &
1541c6a0718SPierre Ossman 			SDHCI_CARD_PRESENT))
1551c6a0718SPierre Ossman 			return;
1561c6a0718SPierre Ossman 	}
1571c6a0718SPierre Ossman 
158063a9dbbSAnton Vorontsov 	if (host->quirks & SDHCI_QUIRK_RESTORE_IRQS_AFTER_RESET)
159063a9dbbSAnton Vorontsov 		ier = sdhci_readl(host, SDHCI_INT_ENABLE);
160063a9dbbSAnton Vorontsov 
161393c1a34SPhilip Rakity 	if (host->ops->platform_reset_enter)
162393c1a34SPhilip Rakity 		host->ops->platform_reset_enter(host, mask);
163393c1a34SPhilip Rakity 
1644e4141a5SAnton Vorontsov 	sdhci_writeb(host, mask, SDHCI_SOFTWARE_RESET);
1651c6a0718SPierre Ossman 
1661c6a0718SPierre Ossman 	if (mask & SDHCI_RESET_ALL)
1671c6a0718SPierre Ossman 		host->clock = 0;
1681c6a0718SPierre Ossman 
1691c6a0718SPierre Ossman 	/* Wait max 100 ms */
1701c6a0718SPierre Ossman 	timeout = 100;
1711c6a0718SPierre Ossman 
1721c6a0718SPierre Ossman 	/* hw clears the bit when it's done */
1734e4141a5SAnton Vorontsov 	while (sdhci_readb(host, SDHCI_SOFTWARE_RESET) & mask) {
1741c6a0718SPierre Ossman 		if (timeout == 0) {
1751c6a0718SPierre Ossman 			printk(KERN_ERR "%s: Reset 0x%x never completed.\n",
1761c6a0718SPierre Ossman 				mmc_hostname(host->mmc), (int)mask);
1771c6a0718SPierre Ossman 			sdhci_dumpregs(host);
1781c6a0718SPierre Ossman 			return;
1791c6a0718SPierre Ossman 		}
1801c6a0718SPierre Ossman 		timeout--;
1811c6a0718SPierre Ossman 		mdelay(1);
1821c6a0718SPierre Ossman 	}
183063a9dbbSAnton Vorontsov 
184393c1a34SPhilip Rakity 	if (host->ops->platform_reset_exit)
185393c1a34SPhilip Rakity 		host->ops->platform_reset_exit(host, mask);
186393c1a34SPhilip Rakity 
187063a9dbbSAnton Vorontsov 	if (host->quirks & SDHCI_QUIRK_RESTORE_IRQS_AFTER_RESET)
188063a9dbbSAnton Vorontsov 		sdhci_clear_set_irqs(host, SDHCI_INT_ALL_MASK, ier);
1891c6a0718SPierre Ossman }
1901c6a0718SPierre Ossman 
1912f4cbb3dSNicolas Pitre static void sdhci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios);
1922f4cbb3dSNicolas Pitre 
1932f4cbb3dSNicolas Pitre static void sdhci_init(struct sdhci_host *host, int soft)
1941c6a0718SPierre Ossman {
1952f4cbb3dSNicolas Pitre 	if (soft)
1962f4cbb3dSNicolas Pitre 		sdhci_reset(host, SDHCI_RESET_CMD|SDHCI_RESET_DATA);
1972f4cbb3dSNicolas Pitre 	else
1981c6a0718SPierre Ossman 		sdhci_reset(host, SDHCI_RESET_ALL);
1991c6a0718SPierre Ossman 
2007260cf5eSAnton Vorontsov 	sdhci_clear_set_irqs(host, SDHCI_INT_ALL_MASK,
2017260cf5eSAnton Vorontsov 		SDHCI_INT_BUS_POWER | SDHCI_INT_DATA_END_BIT |
2021c6a0718SPierre Ossman 		SDHCI_INT_DATA_CRC | SDHCI_INT_DATA_TIMEOUT | SDHCI_INT_INDEX |
2031c6a0718SPierre Ossman 		SDHCI_INT_END_BIT | SDHCI_INT_CRC | SDHCI_INT_TIMEOUT |
2046aa943abSAnton Vorontsov 		SDHCI_INT_DATA_END | SDHCI_INT_RESPONSE);
2052f4cbb3dSNicolas Pitre 
2062f4cbb3dSNicolas Pitre 	if (soft) {
2072f4cbb3dSNicolas Pitre 		/* force clock reconfiguration */
2082f4cbb3dSNicolas Pitre 		host->clock = 0;
2092f4cbb3dSNicolas Pitre 		sdhci_set_ios(host->mmc, &host->mmc->ios);
2102f4cbb3dSNicolas Pitre 	}
2117260cf5eSAnton Vorontsov }
2121c6a0718SPierre Ossman 
2137260cf5eSAnton Vorontsov static void sdhci_reinit(struct sdhci_host *host)
2147260cf5eSAnton Vorontsov {
2152f4cbb3dSNicolas Pitre 	sdhci_init(host, 0);
2167260cf5eSAnton Vorontsov 	sdhci_enable_card_detection(host);
2171c6a0718SPierre Ossman }
2181c6a0718SPierre Ossman 
2191c6a0718SPierre Ossman static void sdhci_activate_led(struct sdhci_host *host)
2201c6a0718SPierre Ossman {
2211c6a0718SPierre Ossman 	u8 ctrl;
2221c6a0718SPierre Ossman 
2234e4141a5SAnton Vorontsov 	ctrl = sdhci_readb(host, SDHCI_HOST_CONTROL);
2241c6a0718SPierre Ossman 	ctrl |= SDHCI_CTRL_LED;
2254e4141a5SAnton Vorontsov 	sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
2261c6a0718SPierre Ossman }
2271c6a0718SPierre Ossman 
2281c6a0718SPierre Ossman static void sdhci_deactivate_led(struct sdhci_host *host)
2291c6a0718SPierre Ossman {
2301c6a0718SPierre Ossman 	u8 ctrl;
2311c6a0718SPierre Ossman 
2324e4141a5SAnton Vorontsov 	ctrl = sdhci_readb(host, SDHCI_HOST_CONTROL);
2331c6a0718SPierre Ossman 	ctrl &= ~SDHCI_CTRL_LED;
2344e4141a5SAnton Vorontsov 	sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
2351c6a0718SPierre Ossman }
2361c6a0718SPierre Ossman 
237f9134319SPierre Ossman #ifdef SDHCI_USE_LEDS_CLASS
2382f730fecSPierre Ossman static void sdhci_led_control(struct led_classdev *led,
2392f730fecSPierre Ossman 	enum led_brightness brightness)
2402f730fecSPierre Ossman {
2412f730fecSPierre Ossman 	struct sdhci_host *host = container_of(led, struct sdhci_host, led);
2422f730fecSPierre Ossman 	unsigned long flags;
2432f730fecSPierre Ossman 
2442f730fecSPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
2452f730fecSPierre Ossman 
2462f730fecSPierre Ossman 	if (brightness == LED_OFF)
2472f730fecSPierre Ossman 		sdhci_deactivate_led(host);
2482f730fecSPierre Ossman 	else
2492f730fecSPierre Ossman 		sdhci_activate_led(host);
2502f730fecSPierre Ossman 
2512f730fecSPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
2522f730fecSPierre Ossman }
2532f730fecSPierre Ossman #endif
2542f730fecSPierre Ossman 
2551c6a0718SPierre Ossman /*****************************************************************************\
2561c6a0718SPierre Ossman  *                                                                           *
2571c6a0718SPierre Ossman  * Core functions                                                            *
2581c6a0718SPierre Ossman  *                                                                           *
2591c6a0718SPierre Ossman \*****************************************************************************/
2601c6a0718SPierre Ossman 
2611c6a0718SPierre Ossman static void sdhci_read_block_pio(struct sdhci_host *host)
2621c6a0718SPierre Ossman {
2637659150cSPierre Ossman 	unsigned long flags;
2647659150cSPierre Ossman 	size_t blksize, len, chunk;
2657244b85bSSteven Noonan 	u32 uninitialized_var(scratch);
2667659150cSPierre Ossman 	u8 *buf;
2671c6a0718SPierre Ossman 
2681c6a0718SPierre Ossman 	DBG("PIO reading\n");
2691c6a0718SPierre Ossman 
2701c6a0718SPierre Ossman 	blksize = host->data->blksz;
2717659150cSPierre Ossman 	chunk = 0;
2721c6a0718SPierre Ossman 
2737659150cSPierre Ossman 	local_irq_save(flags);
2741c6a0718SPierre Ossman 
2751c6a0718SPierre Ossman 	while (blksize) {
2767659150cSPierre Ossman 		if (!sg_miter_next(&host->sg_miter))
2777659150cSPierre Ossman 			BUG();
2787659150cSPierre Ossman 
2797659150cSPierre Ossman 		len = min(host->sg_miter.length, blksize);
2807659150cSPierre Ossman 
2817659150cSPierre Ossman 		blksize -= len;
2827659150cSPierre Ossman 		host->sg_miter.consumed = len;
2837659150cSPierre Ossman 
2847659150cSPierre Ossman 		buf = host->sg_miter.addr;
2857659150cSPierre Ossman 
2867659150cSPierre Ossman 		while (len) {
2877659150cSPierre Ossman 			if (chunk == 0) {
2884e4141a5SAnton Vorontsov 				scratch = sdhci_readl(host, SDHCI_BUFFER);
2897659150cSPierre Ossman 				chunk = 4;
2901c6a0718SPierre Ossman 			}
2911c6a0718SPierre Ossman 
2927659150cSPierre Ossman 			*buf = scratch & 0xFF;
2931c6a0718SPierre Ossman 
2947659150cSPierre Ossman 			buf++;
2957659150cSPierre Ossman 			scratch >>= 8;
2967659150cSPierre Ossman 			chunk--;
2977659150cSPierre Ossman 			len--;
2987659150cSPierre Ossman 		}
2991c6a0718SPierre Ossman 	}
3001c6a0718SPierre Ossman 
3017659150cSPierre Ossman 	sg_miter_stop(&host->sg_miter);
3027659150cSPierre Ossman 
3037659150cSPierre Ossman 	local_irq_restore(flags);
3041c6a0718SPierre Ossman }
3051c6a0718SPierre Ossman 
3061c6a0718SPierre Ossman static void sdhci_write_block_pio(struct sdhci_host *host)
3071c6a0718SPierre Ossman {
3087659150cSPierre Ossman 	unsigned long flags;
3097659150cSPierre Ossman 	size_t blksize, len, chunk;
3107659150cSPierre Ossman 	u32 scratch;
3117659150cSPierre Ossman 	u8 *buf;
3121c6a0718SPierre Ossman 
3131c6a0718SPierre Ossman 	DBG("PIO writing\n");
3141c6a0718SPierre Ossman 
3151c6a0718SPierre Ossman 	blksize = host->data->blksz;
3167659150cSPierre Ossman 	chunk = 0;
3177659150cSPierre Ossman 	scratch = 0;
3181c6a0718SPierre Ossman 
3197659150cSPierre Ossman 	local_irq_save(flags);
3201c6a0718SPierre Ossman 
3211c6a0718SPierre Ossman 	while (blksize) {
3227659150cSPierre Ossman 		if (!sg_miter_next(&host->sg_miter))
3237659150cSPierre Ossman 			BUG();
3241c6a0718SPierre Ossman 
3257659150cSPierre Ossman 		len = min(host->sg_miter.length, blksize);
3261c6a0718SPierre Ossman 
3277659150cSPierre Ossman 		blksize -= len;
3287659150cSPierre Ossman 		host->sg_miter.consumed = len;
3297659150cSPierre Ossman 
3307659150cSPierre Ossman 		buf = host->sg_miter.addr;
3317659150cSPierre Ossman 
3327659150cSPierre Ossman 		while (len) {
3337659150cSPierre Ossman 			scratch |= (u32)*buf << (chunk * 8);
3347659150cSPierre Ossman 
3357659150cSPierre Ossman 			buf++;
3367659150cSPierre Ossman 			chunk++;
3377659150cSPierre Ossman 			len--;
3387659150cSPierre Ossman 
3397659150cSPierre Ossman 			if ((chunk == 4) || ((len == 0) && (blksize == 0))) {
3404e4141a5SAnton Vorontsov 				sdhci_writel(host, scratch, SDHCI_BUFFER);
3417659150cSPierre Ossman 				chunk = 0;
3427659150cSPierre Ossman 				scratch = 0;
3437659150cSPierre Ossman 			}
3447659150cSPierre Ossman 		}
3451c6a0718SPierre Ossman 	}
3461c6a0718SPierre Ossman 
3477659150cSPierre Ossman 	sg_miter_stop(&host->sg_miter);
3481c6a0718SPierre Ossman 
3497659150cSPierre Ossman 	local_irq_restore(flags);
3501c6a0718SPierre Ossman }
3511c6a0718SPierre Ossman 
3521c6a0718SPierre Ossman static void sdhci_transfer_pio(struct sdhci_host *host)
3531c6a0718SPierre Ossman {
3541c6a0718SPierre Ossman 	u32 mask;
3551c6a0718SPierre Ossman 
3561c6a0718SPierre Ossman 	BUG_ON(!host->data);
3571c6a0718SPierre Ossman 
3587659150cSPierre Ossman 	if (host->blocks == 0)
3591c6a0718SPierre Ossman 		return;
3601c6a0718SPierre Ossman 
3611c6a0718SPierre Ossman 	if (host->data->flags & MMC_DATA_READ)
3621c6a0718SPierre Ossman 		mask = SDHCI_DATA_AVAILABLE;
3631c6a0718SPierre Ossman 	else
3641c6a0718SPierre Ossman 		mask = SDHCI_SPACE_AVAILABLE;
3651c6a0718SPierre Ossman 
3664a3cba32SPierre Ossman 	/*
3674a3cba32SPierre Ossman 	 * Some controllers (JMicron JMB38x) mess up the buffer bits
3684a3cba32SPierre Ossman 	 * for transfers < 4 bytes. As long as it is just one block,
3694a3cba32SPierre Ossman 	 * we can ignore the bits.
3704a3cba32SPierre Ossman 	 */
3714a3cba32SPierre Ossman 	if ((host->quirks & SDHCI_QUIRK_BROKEN_SMALL_PIO) &&
3724a3cba32SPierre Ossman 		(host->data->blocks == 1))
3734a3cba32SPierre Ossman 		mask = ~0;
3744a3cba32SPierre Ossman 
3754e4141a5SAnton Vorontsov 	while (sdhci_readl(host, SDHCI_PRESENT_STATE) & mask) {
3763e3bf207SAnton Vorontsov 		if (host->quirks & SDHCI_QUIRK_PIO_NEEDS_DELAY)
3773e3bf207SAnton Vorontsov 			udelay(100);
3783e3bf207SAnton Vorontsov 
3791c6a0718SPierre Ossman 		if (host->data->flags & MMC_DATA_READ)
3801c6a0718SPierre Ossman 			sdhci_read_block_pio(host);
3811c6a0718SPierre Ossman 		else
3821c6a0718SPierre Ossman 			sdhci_write_block_pio(host);
3831c6a0718SPierre Ossman 
3847659150cSPierre Ossman 		host->blocks--;
3857659150cSPierre Ossman 		if (host->blocks == 0)
3861c6a0718SPierre Ossman 			break;
3871c6a0718SPierre Ossman 	}
3881c6a0718SPierre Ossman 
3891c6a0718SPierre Ossman 	DBG("PIO transfer complete.\n");
3901c6a0718SPierre Ossman }
3911c6a0718SPierre Ossman 
3922134a922SPierre Ossman static char *sdhci_kmap_atomic(struct scatterlist *sg, unsigned long *flags)
3932134a922SPierre Ossman {
3942134a922SPierre Ossman 	local_irq_save(*flags);
3952134a922SPierre Ossman 	return kmap_atomic(sg_page(sg), KM_BIO_SRC_IRQ) + sg->offset;
3962134a922SPierre Ossman }
3972134a922SPierre Ossman 
3982134a922SPierre Ossman static void sdhci_kunmap_atomic(void *buffer, unsigned long *flags)
3992134a922SPierre Ossman {
4002134a922SPierre Ossman 	kunmap_atomic(buffer, KM_BIO_SRC_IRQ);
4012134a922SPierre Ossman 	local_irq_restore(*flags);
4022134a922SPierre Ossman }
4032134a922SPierre Ossman 
404118cd17dSBen Dooks static void sdhci_set_adma_desc(u8 *desc, u32 addr, int len, unsigned cmd)
405118cd17dSBen Dooks {
4069e506f35SBen Dooks 	__le32 *dataddr = (__le32 __force *)(desc + 4);
4079e506f35SBen Dooks 	__le16 *cmdlen = (__le16 __force *)desc;
408118cd17dSBen Dooks 
4099e506f35SBen Dooks 	/* SDHCI specification says ADMA descriptors should be 4 byte
4109e506f35SBen Dooks 	 * aligned, so using 16 or 32bit operations should be safe. */
411118cd17dSBen Dooks 
4129e506f35SBen Dooks 	cmdlen[0] = cpu_to_le16(cmd);
4139e506f35SBen Dooks 	cmdlen[1] = cpu_to_le16(len);
4149e506f35SBen Dooks 
4159e506f35SBen Dooks 	dataddr[0] = cpu_to_le32(addr);
416118cd17dSBen Dooks }
417118cd17dSBen Dooks 
4188f1934ceSPierre Ossman static int sdhci_adma_table_pre(struct sdhci_host *host,
4192134a922SPierre Ossman 	struct mmc_data *data)
4202134a922SPierre Ossman {
4212134a922SPierre Ossman 	int direction;
4222134a922SPierre Ossman 
4232134a922SPierre Ossman 	u8 *desc;
4242134a922SPierre Ossman 	u8 *align;
4252134a922SPierre Ossman 	dma_addr_t addr;
4262134a922SPierre Ossman 	dma_addr_t align_addr;
4272134a922SPierre Ossman 	int len, offset;
4282134a922SPierre Ossman 
4292134a922SPierre Ossman 	struct scatterlist *sg;
4302134a922SPierre Ossman 	int i;
4312134a922SPierre Ossman 	char *buffer;
4322134a922SPierre Ossman 	unsigned long flags;
4332134a922SPierre Ossman 
4342134a922SPierre Ossman 	/*
4352134a922SPierre Ossman 	 * The spec does not specify endianness of descriptor table.
4362134a922SPierre Ossman 	 * We currently guess that it is LE.
4372134a922SPierre Ossman 	 */
4382134a922SPierre Ossman 
4392134a922SPierre Ossman 	if (data->flags & MMC_DATA_READ)
4402134a922SPierre Ossman 		direction = DMA_FROM_DEVICE;
4412134a922SPierre Ossman 	else
4422134a922SPierre Ossman 		direction = DMA_TO_DEVICE;
4432134a922SPierre Ossman 
4442134a922SPierre Ossman 	/*
4452134a922SPierre Ossman 	 * The ADMA descriptor table is mapped further down as we
4462134a922SPierre Ossman 	 * need to fill it with data first.
4472134a922SPierre Ossman 	 */
4482134a922SPierre Ossman 
4492134a922SPierre Ossman 	host->align_addr = dma_map_single(mmc_dev(host->mmc),
4502134a922SPierre Ossman 		host->align_buffer, 128 * 4, direction);
4518d8bb39bSFUJITA Tomonori 	if (dma_mapping_error(mmc_dev(host->mmc), host->align_addr))
4528f1934ceSPierre Ossman 		goto fail;
4532134a922SPierre Ossman 	BUG_ON(host->align_addr & 0x3);
4542134a922SPierre Ossman 
4552134a922SPierre Ossman 	host->sg_count = dma_map_sg(mmc_dev(host->mmc),
4562134a922SPierre Ossman 		data->sg, data->sg_len, direction);
4578f1934ceSPierre Ossman 	if (host->sg_count == 0)
4588f1934ceSPierre Ossman 		goto unmap_align;
4592134a922SPierre Ossman 
4602134a922SPierre Ossman 	desc = host->adma_desc;
4612134a922SPierre Ossman 	align = host->align_buffer;
4622134a922SPierre Ossman 
4632134a922SPierre Ossman 	align_addr = host->align_addr;
4642134a922SPierre Ossman 
4652134a922SPierre Ossman 	for_each_sg(data->sg, sg, host->sg_count, i) {
4662134a922SPierre Ossman 		addr = sg_dma_address(sg);
4672134a922SPierre Ossman 		len = sg_dma_len(sg);
4682134a922SPierre Ossman 
4692134a922SPierre Ossman 		/*
4702134a922SPierre Ossman 		 * The SDHCI specification states that ADMA
4712134a922SPierre Ossman 		 * addresses must be 32-bit aligned. If they
4722134a922SPierre Ossman 		 * aren't, then we use a bounce buffer for
4732134a922SPierre Ossman 		 * the (up to three) bytes that screw up the
4742134a922SPierre Ossman 		 * alignment.
4752134a922SPierre Ossman 		 */
4762134a922SPierre Ossman 		offset = (4 - (addr & 0x3)) & 0x3;
4772134a922SPierre Ossman 		if (offset) {
4782134a922SPierre Ossman 			if (data->flags & MMC_DATA_WRITE) {
4792134a922SPierre Ossman 				buffer = sdhci_kmap_atomic(sg, &flags);
4806cefd05fSPierre Ossman 				WARN_ON(((long)buffer & PAGE_MASK) > (PAGE_SIZE - 3));
4812134a922SPierre Ossman 				memcpy(align, buffer, offset);
4822134a922SPierre Ossman 				sdhci_kunmap_atomic(buffer, &flags);
4832134a922SPierre Ossman 			}
4842134a922SPierre Ossman 
485118cd17dSBen Dooks 			/* tran, valid */
486118cd17dSBen Dooks 			sdhci_set_adma_desc(desc, align_addr, offset, 0x21);
4872134a922SPierre Ossman 
4882134a922SPierre Ossman 			BUG_ON(offset > 65536);
4892134a922SPierre Ossman 
4902134a922SPierre Ossman 			align += 4;
4912134a922SPierre Ossman 			align_addr += 4;
4922134a922SPierre Ossman 
4932134a922SPierre Ossman 			desc += 8;
4942134a922SPierre Ossman 
4952134a922SPierre Ossman 			addr += offset;
4962134a922SPierre Ossman 			len -= offset;
4972134a922SPierre Ossman 		}
4982134a922SPierre Ossman 
4992134a922SPierre Ossman 		BUG_ON(len > 65536);
5002134a922SPierre Ossman 
501118cd17dSBen Dooks 		/* tran, valid */
502118cd17dSBen Dooks 		sdhci_set_adma_desc(desc, addr, len, 0x21);
5032134a922SPierre Ossman 		desc += 8;
5042134a922SPierre Ossman 
5052134a922SPierre Ossman 		/*
5062134a922SPierre Ossman 		 * If this triggers then we have a calculation bug
5072134a922SPierre Ossman 		 * somewhere. :/
5082134a922SPierre Ossman 		 */
5092134a922SPierre Ossman 		WARN_ON((desc - host->adma_desc) > (128 * 2 + 1) * 4);
5102134a922SPierre Ossman 	}
5112134a922SPierre Ossman 
51270764a90SThomas Abraham 	if (host->quirks & SDHCI_QUIRK_NO_ENDATTR_IN_NOPDESC) {
51370764a90SThomas Abraham 		/*
51470764a90SThomas Abraham 		* Mark the last descriptor as the terminating descriptor
51570764a90SThomas Abraham 		*/
51670764a90SThomas Abraham 		if (desc != host->adma_desc) {
51770764a90SThomas Abraham 			desc -= 8;
51870764a90SThomas Abraham 			desc[0] |= 0x2; /* end */
51970764a90SThomas Abraham 		}
52070764a90SThomas Abraham 	} else {
5212134a922SPierre Ossman 		/*
5222134a922SPierre Ossman 		* Add a terminating entry.
5232134a922SPierre Ossman 		*/
5242134a922SPierre Ossman 
525118cd17dSBen Dooks 		/* nop, end, valid */
526118cd17dSBen Dooks 		sdhci_set_adma_desc(desc, 0, 0, 0x3);
52770764a90SThomas Abraham 	}
5282134a922SPierre Ossman 
5292134a922SPierre Ossman 	/*
5302134a922SPierre Ossman 	 * Resync align buffer as we might have changed it.
5312134a922SPierre Ossman 	 */
5322134a922SPierre Ossman 	if (data->flags & MMC_DATA_WRITE) {
5332134a922SPierre Ossman 		dma_sync_single_for_device(mmc_dev(host->mmc),
5342134a922SPierre Ossman 			host->align_addr, 128 * 4, direction);
5352134a922SPierre Ossman 	}
5362134a922SPierre Ossman 
5372134a922SPierre Ossman 	host->adma_addr = dma_map_single(mmc_dev(host->mmc),
5382134a922SPierre Ossman 		host->adma_desc, (128 * 2 + 1) * 4, DMA_TO_DEVICE);
539980167b7SPierre Ossman 	if (dma_mapping_error(mmc_dev(host->mmc), host->adma_addr))
5408f1934ceSPierre Ossman 		goto unmap_entries;
5412134a922SPierre Ossman 	BUG_ON(host->adma_addr & 0x3);
5428f1934ceSPierre Ossman 
5438f1934ceSPierre Ossman 	return 0;
5448f1934ceSPierre Ossman 
5458f1934ceSPierre Ossman unmap_entries:
5468f1934ceSPierre Ossman 	dma_unmap_sg(mmc_dev(host->mmc), data->sg,
5478f1934ceSPierre Ossman 		data->sg_len, direction);
5488f1934ceSPierre Ossman unmap_align:
5498f1934ceSPierre Ossman 	dma_unmap_single(mmc_dev(host->mmc), host->align_addr,
5508f1934ceSPierre Ossman 		128 * 4, direction);
5518f1934ceSPierre Ossman fail:
5528f1934ceSPierre Ossman 	return -EINVAL;
5532134a922SPierre Ossman }
5542134a922SPierre Ossman 
5552134a922SPierre Ossman static void sdhci_adma_table_post(struct sdhci_host *host,
5562134a922SPierre Ossman 	struct mmc_data *data)
5572134a922SPierre Ossman {
5582134a922SPierre Ossman 	int direction;
5592134a922SPierre Ossman 
5602134a922SPierre Ossman 	struct scatterlist *sg;
5612134a922SPierre Ossman 	int i, size;
5622134a922SPierre Ossman 	u8 *align;
5632134a922SPierre Ossman 	char *buffer;
5642134a922SPierre Ossman 	unsigned long flags;
5652134a922SPierre Ossman 
5662134a922SPierre Ossman 	if (data->flags & MMC_DATA_READ)
5672134a922SPierre Ossman 		direction = DMA_FROM_DEVICE;
5682134a922SPierre Ossman 	else
5692134a922SPierre Ossman 		direction = DMA_TO_DEVICE;
5702134a922SPierre Ossman 
5712134a922SPierre Ossman 	dma_unmap_single(mmc_dev(host->mmc), host->adma_addr,
5722134a922SPierre Ossman 		(128 * 2 + 1) * 4, DMA_TO_DEVICE);
5732134a922SPierre Ossman 
5742134a922SPierre Ossman 	dma_unmap_single(mmc_dev(host->mmc), host->align_addr,
5752134a922SPierre Ossman 		128 * 4, direction);
5762134a922SPierre Ossman 
5772134a922SPierre Ossman 	if (data->flags & MMC_DATA_READ) {
5782134a922SPierre Ossman 		dma_sync_sg_for_cpu(mmc_dev(host->mmc), data->sg,
5792134a922SPierre Ossman 			data->sg_len, direction);
5802134a922SPierre Ossman 
5812134a922SPierre Ossman 		align = host->align_buffer;
5822134a922SPierre Ossman 
5832134a922SPierre Ossman 		for_each_sg(data->sg, sg, host->sg_count, i) {
5842134a922SPierre Ossman 			if (sg_dma_address(sg) & 0x3) {
5852134a922SPierre Ossman 				size = 4 - (sg_dma_address(sg) & 0x3);
5862134a922SPierre Ossman 
5872134a922SPierre Ossman 				buffer = sdhci_kmap_atomic(sg, &flags);
5886cefd05fSPierre Ossman 				WARN_ON(((long)buffer & PAGE_MASK) > (PAGE_SIZE - 3));
5892134a922SPierre Ossman 				memcpy(buffer, align, size);
5902134a922SPierre Ossman 				sdhci_kunmap_atomic(buffer, &flags);
5912134a922SPierre Ossman 
5922134a922SPierre Ossman 				align += 4;
5932134a922SPierre Ossman 			}
5942134a922SPierre Ossman 		}
5952134a922SPierre Ossman 	}
5962134a922SPierre Ossman 
5972134a922SPierre Ossman 	dma_unmap_sg(mmc_dev(host->mmc), data->sg,
5982134a922SPierre Ossman 		data->sg_len, direction);
5992134a922SPierre Ossman }
6002134a922SPierre Ossman 
601a3c7778fSAndrei Warkentin static u8 sdhci_calc_timeout(struct sdhci_host *host, struct mmc_command *cmd)
6021c6a0718SPierre Ossman {
6031c6a0718SPierre Ossman 	u8 count;
604a3c7778fSAndrei Warkentin 	struct mmc_data *data = cmd->data;
6051c6a0718SPierre Ossman 	unsigned target_timeout, current_timeout;
6061c6a0718SPierre Ossman 
607ee53ab5dSPierre Ossman 	/*
608ee53ab5dSPierre Ossman 	 * If the host controller provides us with an incorrect timeout
609ee53ab5dSPierre Ossman 	 * value, just skip the check and use 0xE.  The hardware may take
610ee53ab5dSPierre Ossman 	 * longer to time out, but that's much better than having a too-short
611ee53ab5dSPierre Ossman 	 * timeout value.
612ee53ab5dSPierre Ossman 	 */
61311a2f1b7SPierre Ossman 	if (host->quirks & SDHCI_QUIRK_BROKEN_TIMEOUT_VAL)
614ee53ab5dSPierre Ossman 		return 0xE;
615e538fbe8SPierre Ossman 
616a3c7778fSAndrei Warkentin 	/* Unspecified timeout, assume max */
617a3c7778fSAndrei Warkentin 	if (!data && !cmd->cmd_timeout_ms)
618a3c7778fSAndrei Warkentin 		return 0xE;
619a3c7778fSAndrei Warkentin 
6201c6a0718SPierre Ossman 	/* timeout in us */
621a3c7778fSAndrei Warkentin 	if (!data)
622a3c7778fSAndrei Warkentin 		target_timeout = cmd->cmd_timeout_ms * 1000;
623a3c7778fSAndrei Warkentin 	else
6241c6a0718SPierre Ossman 		target_timeout = data->timeout_ns / 1000 +
6251c6a0718SPierre Ossman 			data->timeout_clks / host->clock;
6261c6a0718SPierre Ossman 
6274b01681cSMark Brown 	if (host->quirks & SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK)
6284b01681cSMark Brown 		host->timeout_clk = host->clock / 1000;
6294b01681cSMark Brown 
6301c6a0718SPierre Ossman 	/*
6311c6a0718SPierre Ossman 	 * Figure out needed cycles.
6321c6a0718SPierre Ossman 	 * We do this in steps in order to fit inside a 32 bit int.
6331c6a0718SPierre Ossman 	 * The first step is the minimum timeout, which will have a
6341c6a0718SPierre Ossman 	 * minimum resolution of 6 bits:
6351c6a0718SPierre Ossman 	 * (1) 2^13*1000 > 2^22,
6361c6a0718SPierre Ossman 	 * (2) host->timeout_clk < 2^16
6371c6a0718SPierre Ossman 	 *     =>
6381c6a0718SPierre Ossman 	 *     (1) / (2) > 2^6
6391c6a0718SPierre Ossman 	 */
6404b01681cSMark Brown 	BUG_ON(!host->timeout_clk);
6411c6a0718SPierre Ossman 	count = 0;
6421c6a0718SPierre Ossman 	current_timeout = (1 << 13) * 1000 / host->timeout_clk;
6431c6a0718SPierre Ossman 	while (current_timeout < target_timeout) {
6441c6a0718SPierre Ossman 		count++;
6451c6a0718SPierre Ossman 		current_timeout <<= 1;
6461c6a0718SPierre Ossman 		if (count >= 0xF)
6471c6a0718SPierre Ossman 			break;
6481c6a0718SPierre Ossman 	}
6491c6a0718SPierre Ossman 
6501c6a0718SPierre Ossman 	if (count >= 0xF) {
651a3c7778fSAndrei Warkentin 		printk(KERN_WARNING "%s: Too large timeout requested for CMD%d!\n",
652a3c7778fSAndrei Warkentin 		       mmc_hostname(host->mmc), cmd->opcode);
6531c6a0718SPierre Ossman 		count = 0xE;
6541c6a0718SPierre Ossman 	}
6551c6a0718SPierre Ossman 
656ee53ab5dSPierre Ossman 	return count;
657ee53ab5dSPierre Ossman }
658ee53ab5dSPierre Ossman 
6596aa943abSAnton Vorontsov static void sdhci_set_transfer_irqs(struct sdhci_host *host)
6606aa943abSAnton Vorontsov {
6616aa943abSAnton Vorontsov 	u32 pio_irqs = SDHCI_INT_DATA_AVAIL | SDHCI_INT_SPACE_AVAIL;
6626aa943abSAnton Vorontsov 	u32 dma_irqs = SDHCI_INT_DMA_END | SDHCI_INT_ADMA_ERROR;
6636aa943abSAnton Vorontsov 
6646aa943abSAnton Vorontsov 	if (host->flags & SDHCI_REQ_USE_DMA)
6656aa943abSAnton Vorontsov 		sdhci_clear_set_irqs(host, pio_irqs, dma_irqs);
6666aa943abSAnton Vorontsov 	else
6676aa943abSAnton Vorontsov 		sdhci_clear_set_irqs(host, dma_irqs, pio_irqs);
6686aa943abSAnton Vorontsov }
6696aa943abSAnton Vorontsov 
670a3c7778fSAndrei Warkentin static void sdhci_prepare_data(struct sdhci_host *host, struct mmc_command *cmd)
671ee53ab5dSPierre Ossman {
672ee53ab5dSPierre Ossman 	u8 count;
6732134a922SPierre Ossman 	u8 ctrl;
674a3c7778fSAndrei Warkentin 	struct mmc_data *data = cmd->data;
6758f1934ceSPierre Ossman 	int ret;
676ee53ab5dSPierre Ossman 
677ee53ab5dSPierre Ossman 	WARN_ON(host->data);
678ee53ab5dSPierre Ossman 
679a3c7778fSAndrei Warkentin 	if (data || (cmd->flags & MMC_RSP_BUSY)) {
680a3c7778fSAndrei Warkentin 		count = sdhci_calc_timeout(host, cmd);
681a3c7778fSAndrei Warkentin 		sdhci_writeb(host, count, SDHCI_TIMEOUT_CONTROL);
682a3c7778fSAndrei Warkentin 	}
683a3c7778fSAndrei Warkentin 
684a3c7778fSAndrei Warkentin 	if (!data)
685ee53ab5dSPierre Ossman 		return;
686ee53ab5dSPierre Ossman 
687ee53ab5dSPierre Ossman 	/* Sanity checks */
688ee53ab5dSPierre Ossman 	BUG_ON(data->blksz * data->blocks > 524288);
689ee53ab5dSPierre Ossman 	BUG_ON(data->blksz > host->mmc->max_blk_size);
690ee53ab5dSPierre Ossman 	BUG_ON(data->blocks > 65535);
691ee53ab5dSPierre Ossman 
692ee53ab5dSPierre Ossman 	host->data = data;
693ee53ab5dSPierre Ossman 	host->data_early = 0;
694f6a03cbfSMikko Vinni 	host->data->bytes_xfered = 0;
695ee53ab5dSPierre Ossman 
696a13abc7bSRichard Röjfors 	if (host->flags & (SDHCI_USE_SDMA | SDHCI_USE_ADMA))
697c9fddbc4SPierre Ossman 		host->flags |= SDHCI_REQ_USE_DMA;
698c9fddbc4SPierre Ossman 
6992134a922SPierre Ossman 	/*
7002134a922SPierre Ossman 	 * FIXME: This doesn't account for merging when mapping the
7012134a922SPierre Ossman 	 * scatterlist.
7022134a922SPierre Ossman 	 */
7032134a922SPierre Ossman 	if (host->flags & SDHCI_REQ_USE_DMA) {
7042134a922SPierre Ossman 		int broken, i;
7052134a922SPierre Ossman 		struct scatterlist *sg;
7062134a922SPierre Ossman 
7072134a922SPierre Ossman 		broken = 0;
7082134a922SPierre Ossman 		if (host->flags & SDHCI_USE_ADMA) {
7092134a922SPierre Ossman 			if (host->quirks & SDHCI_QUIRK_32BIT_ADMA_SIZE)
7102134a922SPierre Ossman 				broken = 1;
7112134a922SPierre Ossman 		} else {
7122134a922SPierre Ossman 			if (host->quirks & SDHCI_QUIRK_32BIT_DMA_SIZE)
7132134a922SPierre Ossman 				broken = 1;
7142134a922SPierre Ossman 		}
7152134a922SPierre Ossman 
7162134a922SPierre Ossman 		if (unlikely(broken)) {
7172134a922SPierre Ossman 			for_each_sg(data->sg, sg, data->sg_len, i) {
7182134a922SPierre Ossman 				if (sg->length & 0x3) {
7192134a922SPierre Ossman 					DBG("Reverting to PIO because of "
7202134a922SPierre Ossman 						"transfer size (%d)\n",
7212134a922SPierre Ossman 						sg->length);
722c9fddbc4SPierre Ossman 					host->flags &= ~SDHCI_REQ_USE_DMA;
7232134a922SPierre Ossman 					break;
7242134a922SPierre Ossman 				}
7252134a922SPierre Ossman 			}
7262134a922SPierre Ossman 		}
727c9fddbc4SPierre Ossman 	}
728c9fddbc4SPierre Ossman 
729c9fddbc4SPierre Ossman 	/*
730c9fddbc4SPierre Ossman 	 * The assumption here being that alignment is the same after
731c9fddbc4SPierre Ossman 	 * translation to device address space.
732c9fddbc4SPierre Ossman 	 */
7332134a922SPierre Ossman 	if (host->flags & SDHCI_REQ_USE_DMA) {
7342134a922SPierre Ossman 		int broken, i;
7352134a922SPierre Ossman 		struct scatterlist *sg;
7362134a922SPierre Ossman 
7372134a922SPierre Ossman 		broken = 0;
7382134a922SPierre Ossman 		if (host->flags & SDHCI_USE_ADMA) {
7392134a922SPierre Ossman 			/*
7402134a922SPierre Ossman 			 * As we use 3 byte chunks to work around
7412134a922SPierre Ossman 			 * alignment problems, we need to check this
7422134a922SPierre Ossman 			 * quirk.
7432134a922SPierre Ossman 			 */
7442134a922SPierre Ossman 			if (host->quirks & SDHCI_QUIRK_32BIT_ADMA_SIZE)
7452134a922SPierre Ossman 				broken = 1;
7462134a922SPierre Ossman 		} else {
7472134a922SPierre Ossman 			if (host->quirks & SDHCI_QUIRK_32BIT_DMA_ADDR)
7482134a922SPierre Ossman 				broken = 1;
7492134a922SPierre Ossman 		}
7502134a922SPierre Ossman 
7512134a922SPierre Ossman 		if (unlikely(broken)) {
7522134a922SPierre Ossman 			for_each_sg(data->sg, sg, data->sg_len, i) {
7532134a922SPierre Ossman 				if (sg->offset & 0x3) {
7542134a922SPierre Ossman 					DBG("Reverting to PIO because of "
7552134a922SPierre Ossman 						"bad alignment\n");
756c9fddbc4SPierre Ossman 					host->flags &= ~SDHCI_REQ_USE_DMA;
7572134a922SPierre Ossman 					break;
7582134a922SPierre Ossman 				}
7592134a922SPierre Ossman 			}
7602134a922SPierre Ossman 		}
7612134a922SPierre Ossman 	}
7622134a922SPierre Ossman 
7638f1934ceSPierre Ossman 	if (host->flags & SDHCI_REQ_USE_DMA) {
7648f1934ceSPierre Ossman 		if (host->flags & SDHCI_USE_ADMA) {
7658f1934ceSPierre Ossman 			ret = sdhci_adma_table_pre(host, data);
7668f1934ceSPierre Ossman 			if (ret) {
7678f1934ceSPierre Ossman 				/*
7688f1934ceSPierre Ossman 				 * This only happens when someone fed
7698f1934ceSPierre Ossman 				 * us an invalid request.
7708f1934ceSPierre Ossman 				 */
7718f1934ceSPierre Ossman 				WARN_ON(1);
772ebd6d357SPierre Ossman 				host->flags &= ~SDHCI_REQ_USE_DMA;
7738f1934ceSPierre Ossman 			} else {
7744e4141a5SAnton Vorontsov 				sdhci_writel(host, host->adma_addr,
7754e4141a5SAnton Vorontsov 					SDHCI_ADMA_ADDRESS);
7768f1934ceSPierre Ossman 			}
7778f1934ceSPierre Ossman 		} else {
778c8b3e02eSTomas Winkler 			int sg_cnt;
7798f1934ceSPierre Ossman 
780c8b3e02eSTomas Winkler 			sg_cnt = dma_map_sg(mmc_dev(host->mmc),
7818f1934ceSPierre Ossman 					data->sg, data->sg_len,
7828f1934ceSPierre Ossman 					(data->flags & MMC_DATA_READ) ?
7838f1934ceSPierre Ossman 						DMA_FROM_DEVICE :
7848f1934ceSPierre Ossman 						DMA_TO_DEVICE);
785c8b3e02eSTomas Winkler 			if (sg_cnt == 0) {
7868f1934ceSPierre Ossman 				/*
7878f1934ceSPierre Ossman 				 * This only happens when someone fed
7888f1934ceSPierre Ossman 				 * us an invalid request.
7898f1934ceSPierre Ossman 				 */
7908f1934ceSPierre Ossman 				WARN_ON(1);
791ebd6d357SPierre Ossman 				host->flags &= ~SDHCI_REQ_USE_DMA;
7928f1934ceSPierre Ossman 			} else {
793719a61b4SPierre Ossman 				WARN_ON(sg_cnt != 1);
7944e4141a5SAnton Vorontsov 				sdhci_writel(host, sg_dma_address(data->sg),
7954e4141a5SAnton Vorontsov 					SDHCI_DMA_ADDRESS);
7968f1934ceSPierre Ossman 			}
7978f1934ceSPierre Ossman 		}
7988f1934ceSPierre Ossman 	}
7998f1934ceSPierre Ossman 
8002134a922SPierre Ossman 	/*
8012134a922SPierre Ossman 	 * Always adjust the DMA selection as some controllers
8022134a922SPierre Ossman 	 * (e.g. JMicron) can't do PIO properly when the selection
8032134a922SPierre Ossman 	 * is ADMA.
8042134a922SPierre Ossman 	 */
8052134a922SPierre Ossman 	if (host->version >= SDHCI_SPEC_200) {
8064e4141a5SAnton Vorontsov 		ctrl = sdhci_readb(host, SDHCI_HOST_CONTROL);
8072134a922SPierre Ossman 		ctrl &= ~SDHCI_CTRL_DMA_MASK;
8082134a922SPierre Ossman 		if ((host->flags & SDHCI_REQ_USE_DMA) &&
8092134a922SPierre Ossman 			(host->flags & SDHCI_USE_ADMA))
8102134a922SPierre Ossman 			ctrl |= SDHCI_CTRL_ADMA32;
8112134a922SPierre Ossman 		else
8122134a922SPierre Ossman 			ctrl |= SDHCI_CTRL_SDMA;
8134e4141a5SAnton Vorontsov 		sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
814c9fddbc4SPierre Ossman 	}
815c9fddbc4SPierre Ossman 
8168f1934ceSPierre Ossman 	if (!(host->flags & SDHCI_REQ_USE_DMA)) {
817da60a91dSSebastian Andrzej Siewior 		int flags;
818da60a91dSSebastian Andrzej Siewior 
819da60a91dSSebastian Andrzej Siewior 		flags = SG_MITER_ATOMIC;
820da60a91dSSebastian Andrzej Siewior 		if (host->data->flags & MMC_DATA_READ)
821da60a91dSSebastian Andrzej Siewior 			flags |= SG_MITER_TO_SG;
822da60a91dSSebastian Andrzej Siewior 		else
823da60a91dSSebastian Andrzej Siewior 			flags |= SG_MITER_FROM_SG;
824da60a91dSSebastian Andrzej Siewior 		sg_miter_start(&host->sg_miter, data->sg, data->sg_len, flags);
8257659150cSPierre Ossman 		host->blocks = data->blocks;
8261c6a0718SPierre Ossman 	}
8271c6a0718SPierre Ossman 
8286aa943abSAnton Vorontsov 	sdhci_set_transfer_irqs(host);
8296aa943abSAnton Vorontsov 
830f6a03cbfSMikko Vinni 	/* Set the DMA boundary value and block size */
831f6a03cbfSMikko Vinni 	sdhci_writew(host, SDHCI_MAKE_BLKSZ(SDHCI_DEFAULT_BOUNDARY_ARG,
832f6a03cbfSMikko Vinni 		data->blksz), SDHCI_BLOCK_SIZE);
8334e4141a5SAnton Vorontsov 	sdhci_writew(host, data->blocks, SDHCI_BLOCK_COUNT);
8341c6a0718SPierre Ossman }
8351c6a0718SPierre Ossman 
8361c6a0718SPierre Ossman static void sdhci_set_transfer_mode(struct sdhci_host *host,
8371c6a0718SPierre Ossman 	struct mmc_data *data)
8381c6a0718SPierre Ossman {
8391c6a0718SPierre Ossman 	u16 mode;
8401c6a0718SPierre Ossman 
8411c6a0718SPierre Ossman 	if (data == NULL)
8421c6a0718SPierre Ossman 		return;
8431c6a0718SPierre Ossman 
844e538fbe8SPierre Ossman 	WARN_ON(!host->data);
845e538fbe8SPierre Ossman 
8461c6a0718SPierre Ossman 	mode = SDHCI_TRNS_BLK_CNT_EN;
847c4512f79SJerry Huang 	if (data->blocks > 1) {
848c4512f79SJerry Huang 		if (host->quirks & SDHCI_QUIRK_MULTIBLOCK_READ_ACMD12)
849c4512f79SJerry Huang 			mode |= SDHCI_TRNS_MULTI | SDHCI_TRNS_ACMD12;
850c4512f79SJerry Huang 		else
8511c6a0718SPierre Ossman 			mode |= SDHCI_TRNS_MULTI;
852c4512f79SJerry Huang 	}
8531c6a0718SPierre Ossman 	if (data->flags & MMC_DATA_READ)
8541c6a0718SPierre Ossman 		mode |= SDHCI_TRNS_READ;
855c9fddbc4SPierre Ossman 	if (host->flags & SDHCI_REQ_USE_DMA)
8561c6a0718SPierre Ossman 		mode |= SDHCI_TRNS_DMA;
8571c6a0718SPierre Ossman 
8584e4141a5SAnton Vorontsov 	sdhci_writew(host, mode, SDHCI_TRANSFER_MODE);
8591c6a0718SPierre Ossman }
8601c6a0718SPierre Ossman 
8611c6a0718SPierre Ossman static void sdhci_finish_data(struct sdhci_host *host)
8621c6a0718SPierre Ossman {
8631c6a0718SPierre Ossman 	struct mmc_data *data;
8641c6a0718SPierre Ossman 
8651c6a0718SPierre Ossman 	BUG_ON(!host->data);
8661c6a0718SPierre Ossman 
8671c6a0718SPierre Ossman 	data = host->data;
8681c6a0718SPierre Ossman 	host->data = NULL;
8691c6a0718SPierre Ossman 
870c9fddbc4SPierre Ossman 	if (host->flags & SDHCI_REQ_USE_DMA) {
8712134a922SPierre Ossman 		if (host->flags & SDHCI_USE_ADMA)
8722134a922SPierre Ossman 			sdhci_adma_table_post(host, data);
8732134a922SPierre Ossman 		else {
8742134a922SPierre Ossman 			dma_unmap_sg(mmc_dev(host->mmc), data->sg,
8752134a922SPierre Ossman 				data->sg_len, (data->flags & MMC_DATA_READ) ?
876b8c86fc5SPierre Ossman 					DMA_FROM_DEVICE : DMA_TO_DEVICE);
8771c6a0718SPierre Ossman 		}
8782134a922SPierre Ossman 	}
8791c6a0718SPierre Ossman 
8801c6a0718SPierre Ossman 	/*
881c9b74c5bSPierre Ossman 	 * The specification states that the block count register must
882c9b74c5bSPierre Ossman 	 * be updated, but it does not specify at what point in the
883c9b74c5bSPierre Ossman 	 * data flow. That makes the register entirely useless to read
884c9b74c5bSPierre Ossman 	 * back so we have to assume that nothing made it to the card
885c9b74c5bSPierre Ossman 	 * in the event of an error.
8861c6a0718SPierre Ossman 	 */
887c9b74c5bSPierre Ossman 	if (data->error)
888c9b74c5bSPierre Ossman 		data->bytes_xfered = 0;
8891c6a0718SPierre Ossman 	else
890c9b74c5bSPierre Ossman 		data->bytes_xfered = data->blksz * data->blocks;
8911c6a0718SPierre Ossman 
8921c6a0718SPierre Ossman 	if (data->stop) {
8931c6a0718SPierre Ossman 		/*
8941c6a0718SPierre Ossman 		 * The controller needs a reset of internal state machines
8951c6a0718SPierre Ossman 		 * upon error conditions.
8961c6a0718SPierre Ossman 		 */
89717b0429dSPierre Ossman 		if (data->error) {
8981c6a0718SPierre Ossman 			sdhci_reset(host, SDHCI_RESET_CMD);
8991c6a0718SPierre Ossman 			sdhci_reset(host, SDHCI_RESET_DATA);
9001c6a0718SPierre Ossman 		}
9011c6a0718SPierre Ossman 
9021c6a0718SPierre Ossman 		sdhci_send_command(host, data->stop);
9031c6a0718SPierre Ossman 	} else
9041c6a0718SPierre Ossman 		tasklet_schedule(&host->finish_tasklet);
9051c6a0718SPierre Ossman }
9061c6a0718SPierre Ossman 
9071c6a0718SPierre Ossman static void sdhci_send_command(struct sdhci_host *host, struct mmc_command *cmd)
9081c6a0718SPierre Ossman {
9091c6a0718SPierre Ossman 	int flags;
9101c6a0718SPierre Ossman 	u32 mask;
9111c6a0718SPierre Ossman 	unsigned long timeout;
9121c6a0718SPierre Ossman 
9131c6a0718SPierre Ossman 	WARN_ON(host->cmd);
9141c6a0718SPierre Ossman 
9151c6a0718SPierre Ossman 	/* Wait max 10 ms */
9161c6a0718SPierre Ossman 	timeout = 10;
9171c6a0718SPierre Ossman 
9181c6a0718SPierre Ossman 	mask = SDHCI_CMD_INHIBIT;
9191c6a0718SPierre Ossman 	if ((cmd->data != NULL) || (cmd->flags & MMC_RSP_BUSY))
9201c6a0718SPierre Ossman 		mask |= SDHCI_DATA_INHIBIT;
9211c6a0718SPierre Ossman 
9221c6a0718SPierre Ossman 	/* We shouldn't wait for data inihibit for stop commands, even
9231c6a0718SPierre Ossman 	   though they might use busy signaling */
9241c6a0718SPierre Ossman 	if (host->mrq->data && (cmd == host->mrq->data->stop))
9251c6a0718SPierre Ossman 		mask &= ~SDHCI_DATA_INHIBIT;
9261c6a0718SPierre Ossman 
9274e4141a5SAnton Vorontsov 	while (sdhci_readl(host, SDHCI_PRESENT_STATE) & mask) {
9281c6a0718SPierre Ossman 		if (timeout == 0) {
9291c6a0718SPierre Ossman 			printk(KERN_ERR "%s: Controller never released "
9301c6a0718SPierre Ossman 				"inhibit bit(s).\n", mmc_hostname(host->mmc));
9311c6a0718SPierre Ossman 			sdhci_dumpregs(host);
93217b0429dSPierre Ossman 			cmd->error = -EIO;
9331c6a0718SPierre Ossman 			tasklet_schedule(&host->finish_tasklet);
9341c6a0718SPierre Ossman 			return;
9351c6a0718SPierre Ossman 		}
9361c6a0718SPierre Ossman 		timeout--;
9371c6a0718SPierre Ossman 		mdelay(1);
9381c6a0718SPierre Ossman 	}
9391c6a0718SPierre Ossman 
9401c6a0718SPierre Ossman 	mod_timer(&host->timer, jiffies + 10 * HZ);
9411c6a0718SPierre Ossman 
9421c6a0718SPierre Ossman 	host->cmd = cmd;
9431c6a0718SPierre Ossman 
944a3c7778fSAndrei Warkentin 	sdhci_prepare_data(host, cmd);
9451c6a0718SPierre Ossman 
9464e4141a5SAnton Vorontsov 	sdhci_writel(host, cmd->arg, SDHCI_ARGUMENT);
9471c6a0718SPierre Ossman 
9481c6a0718SPierre Ossman 	sdhci_set_transfer_mode(host, cmd->data);
9491c6a0718SPierre Ossman 
9501c6a0718SPierre Ossman 	if ((cmd->flags & MMC_RSP_136) && (cmd->flags & MMC_RSP_BUSY)) {
9511c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Unsupported response type!\n",
9521c6a0718SPierre Ossman 			mmc_hostname(host->mmc));
95317b0429dSPierre Ossman 		cmd->error = -EINVAL;
9541c6a0718SPierre Ossman 		tasklet_schedule(&host->finish_tasklet);
9551c6a0718SPierre Ossman 		return;
9561c6a0718SPierre Ossman 	}
9571c6a0718SPierre Ossman 
9581c6a0718SPierre Ossman 	if (!(cmd->flags & MMC_RSP_PRESENT))
9591c6a0718SPierre Ossman 		flags = SDHCI_CMD_RESP_NONE;
9601c6a0718SPierre Ossman 	else if (cmd->flags & MMC_RSP_136)
9611c6a0718SPierre Ossman 		flags = SDHCI_CMD_RESP_LONG;
9621c6a0718SPierre Ossman 	else if (cmd->flags & MMC_RSP_BUSY)
9631c6a0718SPierre Ossman 		flags = SDHCI_CMD_RESP_SHORT_BUSY;
9641c6a0718SPierre Ossman 	else
9651c6a0718SPierre Ossman 		flags = SDHCI_CMD_RESP_SHORT;
9661c6a0718SPierre Ossman 
9671c6a0718SPierre Ossman 	if (cmd->flags & MMC_RSP_CRC)
9681c6a0718SPierre Ossman 		flags |= SDHCI_CMD_CRC;
9691c6a0718SPierre Ossman 	if (cmd->flags & MMC_RSP_OPCODE)
9701c6a0718SPierre Ossman 		flags |= SDHCI_CMD_INDEX;
9711c6a0718SPierre Ossman 	if (cmd->data)
9721c6a0718SPierre Ossman 		flags |= SDHCI_CMD_DATA;
9731c6a0718SPierre Ossman 
9744e4141a5SAnton Vorontsov 	sdhci_writew(host, SDHCI_MAKE_CMD(cmd->opcode, flags), SDHCI_COMMAND);
9751c6a0718SPierre Ossman }
9761c6a0718SPierre Ossman 
9771c6a0718SPierre Ossman static void sdhci_finish_command(struct sdhci_host *host)
9781c6a0718SPierre Ossman {
9791c6a0718SPierre Ossman 	int i;
9801c6a0718SPierre Ossman 
9811c6a0718SPierre Ossman 	BUG_ON(host->cmd == NULL);
9821c6a0718SPierre Ossman 
9831c6a0718SPierre Ossman 	if (host->cmd->flags & MMC_RSP_PRESENT) {
9841c6a0718SPierre Ossman 		if (host->cmd->flags & MMC_RSP_136) {
9851c6a0718SPierre Ossman 			/* CRC is stripped so we need to do some shifting. */
9861c6a0718SPierre Ossman 			for (i = 0;i < 4;i++) {
9874e4141a5SAnton Vorontsov 				host->cmd->resp[i] = sdhci_readl(host,
9881c6a0718SPierre Ossman 					SDHCI_RESPONSE + (3-i)*4) << 8;
9891c6a0718SPierre Ossman 				if (i != 3)
9901c6a0718SPierre Ossman 					host->cmd->resp[i] |=
9914e4141a5SAnton Vorontsov 						sdhci_readb(host,
9921c6a0718SPierre Ossman 						SDHCI_RESPONSE + (3-i)*4-1);
9931c6a0718SPierre Ossman 			}
9941c6a0718SPierre Ossman 		} else {
9954e4141a5SAnton Vorontsov 			host->cmd->resp[0] = sdhci_readl(host, SDHCI_RESPONSE);
9961c6a0718SPierre Ossman 		}
9971c6a0718SPierre Ossman 	}
9981c6a0718SPierre Ossman 
99917b0429dSPierre Ossman 	host->cmd->error = 0;
10001c6a0718SPierre Ossman 
1001e538fbe8SPierre Ossman 	if (host->data && host->data_early)
1002e538fbe8SPierre Ossman 		sdhci_finish_data(host);
1003e538fbe8SPierre Ossman 
1004e538fbe8SPierre Ossman 	if (!host->cmd->data)
10051c6a0718SPierre Ossman 		tasklet_schedule(&host->finish_tasklet);
10061c6a0718SPierre Ossman 
10071c6a0718SPierre Ossman 	host->cmd = NULL;
10081c6a0718SPierre Ossman }
10091c6a0718SPierre Ossman 
10101c6a0718SPierre Ossman static void sdhci_set_clock(struct sdhci_host *host, unsigned int clock)
10111c6a0718SPierre Ossman {
10121c6a0718SPierre Ossman 	int div;
10131c6a0718SPierre Ossman 	u16 clk;
10141c6a0718SPierre Ossman 	unsigned long timeout;
10151c6a0718SPierre Ossman 
10161c6a0718SPierre Ossman 	if (clock == host->clock)
10171c6a0718SPierre Ossman 		return;
10181c6a0718SPierre Ossman 
10198114634cSAnton Vorontsov 	if (host->ops->set_clock) {
10208114634cSAnton Vorontsov 		host->ops->set_clock(host, clock);
10218114634cSAnton Vorontsov 		if (host->quirks & SDHCI_QUIRK_NONSTANDARD_CLOCK)
10228114634cSAnton Vorontsov 			return;
10238114634cSAnton Vorontsov 	}
10248114634cSAnton Vorontsov 
10254e4141a5SAnton Vorontsov 	sdhci_writew(host, 0, SDHCI_CLOCK_CONTROL);
10261c6a0718SPierre Ossman 
10271c6a0718SPierre Ossman 	if (clock == 0)
10281c6a0718SPierre Ossman 		goto out;
10291c6a0718SPierre Ossman 
103085105c53SZhangfei Gao 	if (host->version >= SDHCI_SPEC_300) {
103185105c53SZhangfei Gao 		/* Version 3.00 divisors must be a multiple of 2. */
103285105c53SZhangfei Gao 		if (host->max_clk <= clock)
103385105c53SZhangfei Gao 			div = 1;
103485105c53SZhangfei Gao 		else {
10350397526dSZhangfei Gao 			for (div = 2; div < SDHCI_MAX_DIV_SPEC_300; div += 2) {
103685105c53SZhangfei Gao 				if ((host->max_clk / div) <= clock)
103785105c53SZhangfei Gao 					break;
103885105c53SZhangfei Gao 			}
103985105c53SZhangfei Gao 		}
104085105c53SZhangfei Gao 	} else {
104185105c53SZhangfei Gao 		/* Version 2.00 divisors must be a power of 2. */
10420397526dSZhangfei Gao 		for (div = 1; div < SDHCI_MAX_DIV_SPEC_200; div *= 2) {
10431c6a0718SPierre Ossman 			if ((host->max_clk / div) <= clock)
10441c6a0718SPierre Ossman 				break;
10451c6a0718SPierre Ossman 		}
104685105c53SZhangfei Gao 	}
10471c6a0718SPierre Ossman 	div >>= 1;
10481c6a0718SPierre Ossman 
104985105c53SZhangfei Gao 	clk = (div & SDHCI_DIV_MASK) << SDHCI_DIVIDER_SHIFT;
105085105c53SZhangfei Gao 	clk |= ((div & SDHCI_DIV_HI_MASK) >> SDHCI_DIV_MASK_LEN)
105185105c53SZhangfei Gao 		<< SDHCI_DIVIDER_HI_SHIFT;
10521c6a0718SPierre Ossman 	clk |= SDHCI_CLOCK_INT_EN;
10534e4141a5SAnton Vorontsov 	sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
10541c6a0718SPierre Ossman 
105527f6cb16SChris Ball 	/* Wait max 20 ms */
105627f6cb16SChris Ball 	timeout = 20;
10574e4141a5SAnton Vorontsov 	while (!((clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL))
10581c6a0718SPierre Ossman 		& SDHCI_CLOCK_INT_STABLE)) {
10591c6a0718SPierre Ossman 		if (timeout == 0) {
10601c6a0718SPierre Ossman 			printk(KERN_ERR "%s: Internal clock never "
10611c6a0718SPierre Ossman 				"stabilised.\n", mmc_hostname(host->mmc));
10621c6a0718SPierre Ossman 			sdhci_dumpregs(host);
10631c6a0718SPierre Ossman 			return;
10641c6a0718SPierre Ossman 		}
10651c6a0718SPierre Ossman 		timeout--;
10661c6a0718SPierre Ossman 		mdelay(1);
10671c6a0718SPierre Ossman 	}
10681c6a0718SPierre Ossman 
10691c6a0718SPierre Ossman 	clk |= SDHCI_CLOCK_CARD_EN;
10704e4141a5SAnton Vorontsov 	sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
10711c6a0718SPierre Ossman 
10721c6a0718SPierre Ossman out:
10731c6a0718SPierre Ossman 	host->clock = clock;
10741c6a0718SPierre Ossman }
10751c6a0718SPierre Ossman 
10761c6a0718SPierre Ossman static void sdhci_set_power(struct sdhci_host *host, unsigned short power)
10771c6a0718SPierre Ossman {
10788364248aSGiuseppe Cavallaro 	u8 pwr = 0;
10791c6a0718SPierre Ossman 
10808364248aSGiuseppe Cavallaro 	if (power != (unsigned short)-1) {
1081ae628903SPierre Ossman 		switch (1 << power) {
1082ae628903SPierre Ossman 		case MMC_VDD_165_195:
1083ae628903SPierre Ossman 			pwr = SDHCI_POWER_180;
1084ae628903SPierre Ossman 			break;
1085ae628903SPierre Ossman 		case MMC_VDD_29_30:
1086ae628903SPierre Ossman 		case MMC_VDD_30_31:
1087ae628903SPierre Ossman 			pwr = SDHCI_POWER_300;
1088ae628903SPierre Ossman 			break;
1089ae628903SPierre Ossman 		case MMC_VDD_32_33:
1090ae628903SPierre Ossman 		case MMC_VDD_33_34:
1091ae628903SPierre Ossman 			pwr = SDHCI_POWER_330;
1092ae628903SPierre Ossman 			break;
1093ae628903SPierre Ossman 		default:
1094ae628903SPierre Ossman 			BUG();
1095ae628903SPierre Ossman 		}
1096ae628903SPierre Ossman 	}
1097ae628903SPierre Ossman 
1098ae628903SPierre Ossman 	if (host->pwr == pwr)
10991c6a0718SPierre Ossman 		return;
11001c6a0718SPierre Ossman 
1101ae628903SPierre Ossman 	host->pwr = pwr;
1102ae628903SPierre Ossman 
1103ae628903SPierre Ossman 	if (pwr == 0) {
11044e4141a5SAnton Vorontsov 		sdhci_writeb(host, 0, SDHCI_POWER_CONTROL);
1105ae628903SPierre Ossman 		return;
11061c6a0718SPierre Ossman 	}
11071c6a0718SPierre Ossman 
11081c6a0718SPierre Ossman 	/*
11091c6a0718SPierre Ossman 	 * Spec says that we should clear the power reg before setting
11101c6a0718SPierre Ossman 	 * a new value. Some controllers don't seem to like this though.
11111c6a0718SPierre Ossman 	 */
1112b8c86fc5SPierre Ossman 	if (!(host->quirks & SDHCI_QUIRK_SINGLE_POWER_WRITE))
11134e4141a5SAnton Vorontsov 		sdhci_writeb(host, 0, SDHCI_POWER_CONTROL);
11141c6a0718SPierre Ossman 
1115e08c1694SAndres Salomon 	/*
1116c71f6512SAndres Salomon 	 * At least the Marvell CaFe chip gets confused if we set the voltage
1117e08c1694SAndres Salomon 	 * and set turn on power at the same time, so set the voltage first.
1118e08c1694SAndres Salomon 	 */
111911a2f1b7SPierre Ossman 	if (host->quirks & SDHCI_QUIRK_NO_SIMULT_VDD_AND_POWER)
11204e4141a5SAnton Vorontsov 		sdhci_writeb(host, pwr, SDHCI_POWER_CONTROL);
11211c6a0718SPierre Ossman 
1122ae628903SPierre Ossman 	pwr |= SDHCI_POWER_ON;
1123ae628903SPierre Ossman 
1124ae628903SPierre Ossman 	sdhci_writeb(host, pwr, SDHCI_POWER_CONTROL);
1125557b0697SHarald Welte 
1126557b0697SHarald Welte 	/*
1127557b0697SHarald Welte 	 * Some controllers need an extra 10ms delay of 10ms before they
1128557b0697SHarald Welte 	 * can apply clock after applying power
1129557b0697SHarald Welte 	 */
113011a2f1b7SPierre Ossman 	if (host->quirks & SDHCI_QUIRK_DELAY_AFTER_POWER)
1131557b0697SHarald Welte 		mdelay(10);
11321c6a0718SPierre Ossman }
11331c6a0718SPierre Ossman 
11341c6a0718SPierre Ossman /*****************************************************************************\
11351c6a0718SPierre Ossman  *                                                                           *
11361c6a0718SPierre Ossman  * MMC callbacks                                                             *
11371c6a0718SPierre Ossman  *                                                                           *
11381c6a0718SPierre Ossman \*****************************************************************************/
11391c6a0718SPierre Ossman 
11401c6a0718SPierre Ossman static void sdhci_request(struct mmc_host *mmc, struct mmc_request *mrq)
11411c6a0718SPierre Ossman {
11421c6a0718SPierre Ossman 	struct sdhci_host *host;
114368d1fb7eSAnton Vorontsov 	bool present;
11441c6a0718SPierre Ossman 	unsigned long flags;
11451c6a0718SPierre Ossman 
11461c6a0718SPierre Ossman 	host = mmc_priv(mmc);
11471c6a0718SPierre Ossman 
11481c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
11491c6a0718SPierre Ossman 
11501c6a0718SPierre Ossman 	WARN_ON(host->mrq != NULL);
11511c6a0718SPierre Ossman 
1152f9134319SPierre Ossman #ifndef SDHCI_USE_LEDS_CLASS
11531c6a0718SPierre Ossman 	sdhci_activate_led(host);
11542f730fecSPierre Ossman #endif
1155c4512f79SJerry Huang 	if (host->quirks & SDHCI_QUIRK_MULTIBLOCK_READ_ACMD12) {
1156c4512f79SJerry Huang 		if (mrq->stop) {
1157c4512f79SJerry Huang 			mrq->data->stop = NULL;
1158c4512f79SJerry Huang 			mrq->stop = NULL;
1159c4512f79SJerry Huang 		}
1160c4512f79SJerry Huang 	}
11611c6a0718SPierre Ossman 
11621c6a0718SPierre Ossman 	host->mrq = mrq;
11631c6a0718SPierre Ossman 
116468d1fb7eSAnton Vorontsov 	/* If polling, assume that the card is always present. */
116568d1fb7eSAnton Vorontsov 	if (host->quirks & SDHCI_QUIRK_BROKEN_CARD_DETECTION)
116668d1fb7eSAnton Vorontsov 		present = true;
116768d1fb7eSAnton Vorontsov 	else
116868d1fb7eSAnton Vorontsov 		present = sdhci_readl(host, SDHCI_PRESENT_STATE) &
116968d1fb7eSAnton Vorontsov 				SDHCI_CARD_PRESENT;
117068d1fb7eSAnton Vorontsov 
117168d1fb7eSAnton Vorontsov 	if (!present || host->flags & SDHCI_DEVICE_DEAD) {
117217b0429dSPierre Ossman 		host->mrq->cmd->error = -ENOMEDIUM;
11731c6a0718SPierre Ossman 		tasklet_schedule(&host->finish_tasklet);
11741c6a0718SPierre Ossman 	} else
11751c6a0718SPierre Ossman 		sdhci_send_command(host, mrq->cmd);
11761c6a0718SPierre Ossman 
11771c6a0718SPierre Ossman 	mmiowb();
11781c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
11791c6a0718SPierre Ossman }
11801c6a0718SPierre Ossman 
11811c6a0718SPierre Ossman static void sdhci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
11821c6a0718SPierre Ossman {
11831c6a0718SPierre Ossman 	struct sdhci_host *host;
11841c6a0718SPierre Ossman 	unsigned long flags;
11851c6a0718SPierre Ossman 	u8 ctrl;
11861c6a0718SPierre Ossman 
11871c6a0718SPierre Ossman 	host = mmc_priv(mmc);
11881c6a0718SPierre Ossman 
11891c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
11901c6a0718SPierre Ossman 
11911e72859eSPierre Ossman 	if (host->flags & SDHCI_DEVICE_DEAD)
11921e72859eSPierre Ossman 		goto out;
11931e72859eSPierre Ossman 
11941c6a0718SPierre Ossman 	/*
11951c6a0718SPierre Ossman 	 * Reset the chip on each power off.
11961c6a0718SPierre Ossman 	 * Should clear out any weird states.
11971c6a0718SPierre Ossman 	 */
11981c6a0718SPierre Ossman 	if (ios->power_mode == MMC_POWER_OFF) {
11994e4141a5SAnton Vorontsov 		sdhci_writel(host, 0, SDHCI_SIGNAL_ENABLE);
12007260cf5eSAnton Vorontsov 		sdhci_reinit(host);
12011c6a0718SPierre Ossman 	}
12021c6a0718SPierre Ossman 
12031c6a0718SPierre Ossman 	sdhci_set_clock(host, ios->clock);
12041c6a0718SPierre Ossman 
12051c6a0718SPierre Ossman 	if (ios->power_mode == MMC_POWER_OFF)
12061c6a0718SPierre Ossman 		sdhci_set_power(host, -1);
12071c6a0718SPierre Ossman 	else
12081c6a0718SPierre Ossman 		sdhci_set_power(host, ios->vdd);
12091c6a0718SPierre Ossman 
1210643a81ffSPhilip Rakity 	if (host->ops->platform_send_init_74_clocks)
1211643a81ffSPhilip Rakity 		host->ops->platform_send_init_74_clocks(host, ios->power_mode);
1212643a81ffSPhilip Rakity 
121315ec4461SPhilip Rakity 	/*
121415ec4461SPhilip Rakity 	 * If your platform has 8-bit width support but is not a v3 controller,
121515ec4461SPhilip Rakity 	 * or if it requires special setup code, you should implement that in
121615ec4461SPhilip Rakity 	 * platform_8bit_width().
121715ec4461SPhilip Rakity 	 */
121815ec4461SPhilip Rakity 	if (host->ops->platform_8bit_width)
121915ec4461SPhilip Rakity 		host->ops->platform_8bit_width(host, ios->bus_width);
122015ec4461SPhilip Rakity 	else {
12214e4141a5SAnton Vorontsov 		ctrl = sdhci_readb(host, SDHCI_HOST_CONTROL);
122215ec4461SPhilip Rakity 		if (ios->bus_width == MMC_BUS_WIDTH_8) {
122315ec4461SPhilip Rakity 			ctrl &= ~SDHCI_CTRL_4BITBUS;
122415ec4461SPhilip Rakity 			if (host->version >= SDHCI_SPEC_300)
1225ae6d6c92SKyungmin Park 				ctrl |= SDHCI_CTRL_8BITBUS;
122615ec4461SPhilip Rakity 		} else {
122715ec4461SPhilip Rakity 			if (host->version >= SDHCI_SPEC_300)
1228ae6d6c92SKyungmin Park 				ctrl &= ~SDHCI_CTRL_8BITBUS;
12291c6a0718SPierre Ossman 			if (ios->bus_width == MMC_BUS_WIDTH_4)
12301c6a0718SPierre Ossman 				ctrl |= SDHCI_CTRL_4BITBUS;
12311c6a0718SPierre Ossman 			else
12321c6a0718SPierre Ossman 				ctrl &= ~SDHCI_CTRL_4BITBUS;
123315ec4461SPhilip Rakity 		}
123415ec4461SPhilip Rakity 		sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
123515ec4461SPhilip Rakity 	}
123615ec4461SPhilip Rakity 
123715ec4461SPhilip Rakity 	ctrl = sdhci_readb(host, SDHCI_HOST_CONTROL);
12381c6a0718SPierre Ossman 
12393ab9c8daSPhilip Rakity 	if ((ios->timing == MMC_TIMING_SD_HS ||
12403ab9c8daSPhilip Rakity 	     ios->timing == MMC_TIMING_MMC_HS)
12413ab9c8daSPhilip Rakity 	    && !(host->quirks & SDHCI_QUIRK_NO_HISPD_BIT))
12421c6a0718SPierre Ossman 		ctrl |= SDHCI_CTRL_HISPD;
12431c6a0718SPierre Ossman 	else
12441c6a0718SPierre Ossman 		ctrl &= ~SDHCI_CTRL_HISPD;
12451c6a0718SPierre Ossman 
1246d6d50a15SArindam Nath 	if (host->version >= SDHCI_SPEC_300) {
124749c468fcSArindam Nath 		u16 clk, ctrl_2;
124849c468fcSArindam Nath 		unsigned int clock;
124949c468fcSArindam Nath 
125049c468fcSArindam Nath 		/* In case of UHS-I modes, set High Speed Enable */
125149c468fcSArindam Nath 		if ((ios->timing == MMC_TIMING_UHS_SDR50) ||
125249c468fcSArindam Nath 		    (ios->timing == MMC_TIMING_UHS_SDR104) ||
125349c468fcSArindam Nath 		    (ios->timing == MMC_TIMING_UHS_DDR50) ||
125449c468fcSArindam Nath 		    (ios->timing == MMC_TIMING_UHS_SDR25) ||
125549c468fcSArindam Nath 		    (ios->timing == MMC_TIMING_UHS_SDR12))
125649c468fcSArindam Nath 			ctrl |= SDHCI_CTRL_HISPD;
1257d6d50a15SArindam Nath 
1258d6d50a15SArindam Nath 		ctrl_2 = sdhci_readw(host, SDHCI_HOST_CONTROL2);
1259d6d50a15SArindam Nath 		if (!(ctrl_2 & SDHCI_CTRL_PRESET_VAL_ENABLE)) {
1260758535c4SArindam Nath 			sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
1261d6d50a15SArindam Nath 			/*
1262d6d50a15SArindam Nath 			 * We only need to set Driver Strength if the
1263d6d50a15SArindam Nath 			 * preset value enable is not set.
1264d6d50a15SArindam Nath 			 */
1265d6d50a15SArindam Nath 			ctrl_2 &= ~SDHCI_CTRL_DRV_TYPE_MASK;
1266d6d50a15SArindam Nath 			if (ios->drv_type == MMC_SET_DRIVER_TYPE_A)
1267d6d50a15SArindam Nath 				ctrl_2 |= SDHCI_CTRL_DRV_TYPE_A;
1268d6d50a15SArindam Nath 			else if (ios->drv_type == MMC_SET_DRIVER_TYPE_C)
1269d6d50a15SArindam Nath 				ctrl_2 |= SDHCI_CTRL_DRV_TYPE_C;
1270d6d50a15SArindam Nath 
1271d6d50a15SArindam Nath 			sdhci_writew(host, ctrl_2, SDHCI_HOST_CONTROL2);
1272758535c4SArindam Nath 		} else {
1273758535c4SArindam Nath 			/*
1274758535c4SArindam Nath 			 * According to SDHC Spec v3.00, if the Preset Value
1275758535c4SArindam Nath 			 * Enable in the Host Control 2 register is set, we
1276758535c4SArindam Nath 			 * need to reset SD Clock Enable before changing High
1277758535c4SArindam Nath 			 * Speed Enable to avoid generating clock gliches.
1278758535c4SArindam Nath 			 */
1279758535c4SArindam Nath 
1280758535c4SArindam Nath 			/* Reset SD Clock Enable */
1281758535c4SArindam Nath 			clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
1282758535c4SArindam Nath 			clk &= ~SDHCI_CLOCK_CARD_EN;
1283758535c4SArindam Nath 			sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
1284758535c4SArindam Nath 
1285758535c4SArindam Nath 			sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
1286758535c4SArindam Nath 
1287758535c4SArindam Nath 			/* Re-enable SD Clock */
1288758535c4SArindam Nath 			clock = host->clock;
1289758535c4SArindam Nath 			host->clock = 0;
1290758535c4SArindam Nath 			sdhci_set_clock(host, clock);
1291d6d50a15SArindam Nath 		}
129249c468fcSArindam Nath 
129349c468fcSArindam Nath 		ctrl_2 = sdhci_readw(host, SDHCI_HOST_CONTROL2);
129449c468fcSArindam Nath 
129549c468fcSArindam Nath 		/* Select Bus Speed Mode for host */
129649c468fcSArindam Nath 		ctrl_2 &= ~SDHCI_CTRL_UHS_MASK;
129749c468fcSArindam Nath 		if (ios->timing == MMC_TIMING_UHS_SDR12)
129849c468fcSArindam Nath 			ctrl_2 |= SDHCI_CTRL_UHS_SDR12;
129949c468fcSArindam Nath 		else if (ios->timing == MMC_TIMING_UHS_SDR25)
130049c468fcSArindam Nath 			ctrl_2 |= SDHCI_CTRL_UHS_SDR25;
130149c468fcSArindam Nath 		else if (ios->timing == MMC_TIMING_UHS_SDR50)
130249c468fcSArindam Nath 			ctrl_2 |= SDHCI_CTRL_UHS_SDR50;
130349c468fcSArindam Nath 		else if (ios->timing == MMC_TIMING_UHS_SDR104)
130449c468fcSArindam Nath 			ctrl_2 |= SDHCI_CTRL_UHS_SDR104;
130549c468fcSArindam Nath 		else if (ios->timing == MMC_TIMING_UHS_DDR50)
130649c468fcSArindam Nath 			ctrl_2 |= SDHCI_CTRL_UHS_DDR50;
130749c468fcSArindam Nath 
130849c468fcSArindam Nath 		/* Reset SD Clock Enable */
130949c468fcSArindam Nath 		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
131049c468fcSArindam Nath 		clk &= ~SDHCI_CLOCK_CARD_EN;
131149c468fcSArindam Nath 		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
131249c468fcSArindam Nath 
131349c468fcSArindam Nath 		sdhci_writew(host, ctrl_2, SDHCI_HOST_CONTROL2);
131449c468fcSArindam Nath 
131549c468fcSArindam Nath 		/* Re-enable SD Clock */
131649c468fcSArindam Nath 		clock = host->clock;
131749c468fcSArindam Nath 		host->clock = 0;
131849c468fcSArindam Nath 		sdhci_set_clock(host, clock);
1319758535c4SArindam Nath 	} else
1320758535c4SArindam Nath 		sdhci_writeb(host, ctrl, SDHCI_HOST_CONTROL);
1321d6d50a15SArindam Nath 
1322b8352260SLeandro Dorileo 	/*
1323b8352260SLeandro Dorileo 	 * Some (ENE) controllers go apeshit on some ios operation,
1324b8352260SLeandro Dorileo 	 * signalling timeout and CRC errors even on CMD0. Resetting
1325b8352260SLeandro Dorileo 	 * it on each ios seems to solve the problem.
1326b8352260SLeandro Dorileo 	 */
1327b8c86fc5SPierre Ossman 	if(host->quirks & SDHCI_QUIRK_RESET_CMD_DATA_ON_IOS)
1328b8352260SLeandro Dorileo 		sdhci_reset(host, SDHCI_RESET_CMD | SDHCI_RESET_DATA);
1329b8352260SLeandro Dorileo 
13301e72859eSPierre Ossman out:
13311c6a0718SPierre Ossman 	mmiowb();
13321c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
13331c6a0718SPierre Ossman }
13341c6a0718SPierre Ossman 
133582b0e23aSTakashi Iwai static int check_ro(struct sdhci_host *host)
13361c6a0718SPierre Ossman {
13371c6a0718SPierre Ossman 	unsigned long flags;
13382dfb579cSWolfram Sang 	int is_readonly;
13391c6a0718SPierre Ossman 
13401c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
13411c6a0718SPierre Ossman 
13421e72859eSPierre Ossman 	if (host->flags & SDHCI_DEVICE_DEAD)
13432dfb579cSWolfram Sang 		is_readonly = 0;
13442dfb579cSWolfram Sang 	else if (host->ops->get_ro)
13452dfb579cSWolfram Sang 		is_readonly = host->ops->get_ro(host);
13461e72859eSPierre Ossman 	else
13472dfb579cSWolfram Sang 		is_readonly = !(sdhci_readl(host, SDHCI_PRESENT_STATE)
13482dfb579cSWolfram Sang 				& SDHCI_WRITE_PROTECT);
13491c6a0718SPierre Ossman 
13501c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
13511c6a0718SPierre Ossman 
13522dfb579cSWolfram Sang 	/* This quirk needs to be replaced by a callback-function later */
13532dfb579cSWolfram Sang 	return host->quirks & SDHCI_QUIRK_INVERTED_WRITE_PROTECT ?
13542dfb579cSWolfram Sang 		!is_readonly : is_readonly;
13551c6a0718SPierre Ossman }
13561c6a0718SPierre Ossman 
135782b0e23aSTakashi Iwai #define SAMPLE_COUNT	5
135882b0e23aSTakashi Iwai 
135982b0e23aSTakashi Iwai static int sdhci_get_ro(struct mmc_host *mmc)
136082b0e23aSTakashi Iwai {
136182b0e23aSTakashi Iwai 	struct sdhci_host *host;
136282b0e23aSTakashi Iwai 	int i, ro_count;
136382b0e23aSTakashi Iwai 
136482b0e23aSTakashi Iwai 	host = mmc_priv(mmc);
136582b0e23aSTakashi Iwai 
136682b0e23aSTakashi Iwai 	if (!(host->quirks & SDHCI_QUIRK_UNSTABLE_RO_DETECT))
136782b0e23aSTakashi Iwai 		return check_ro(host);
136882b0e23aSTakashi Iwai 
136982b0e23aSTakashi Iwai 	ro_count = 0;
137082b0e23aSTakashi Iwai 	for (i = 0; i < SAMPLE_COUNT; i++) {
137182b0e23aSTakashi Iwai 		if (check_ro(host)) {
137282b0e23aSTakashi Iwai 			if (++ro_count > SAMPLE_COUNT / 2)
137382b0e23aSTakashi Iwai 				return 1;
137482b0e23aSTakashi Iwai 		}
137582b0e23aSTakashi Iwai 		msleep(30);
137682b0e23aSTakashi Iwai 	}
137782b0e23aSTakashi Iwai 	return 0;
137882b0e23aSTakashi Iwai }
137982b0e23aSTakashi Iwai 
1380f75979b7SPierre Ossman static void sdhci_enable_sdio_irq(struct mmc_host *mmc, int enable)
1381f75979b7SPierre Ossman {
1382f75979b7SPierre Ossman 	struct sdhci_host *host;
1383f75979b7SPierre Ossman 	unsigned long flags;
1384f75979b7SPierre Ossman 
1385f75979b7SPierre Ossman 	host = mmc_priv(mmc);
1386f75979b7SPierre Ossman 
1387f75979b7SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
1388f75979b7SPierre Ossman 
13891e72859eSPierre Ossman 	if (host->flags & SDHCI_DEVICE_DEAD)
13901e72859eSPierre Ossman 		goto out;
13911e72859eSPierre Ossman 
1392f75979b7SPierre Ossman 	if (enable)
13937260cf5eSAnton Vorontsov 		sdhci_unmask_irqs(host, SDHCI_INT_CARD_INT);
13947260cf5eSAnton Vorontsov 	else
13957260cf5eSAnton Vorontsov 		sdhci_mask_irqs(host, SDHCI_INT_CARD_INT);
13961e72859eSPierre Ossman out:
1397f75979b7SPierre Ossman 	mmiowb();
1398f75979b7SPierre Ossman 
1399f75979b7SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
1400f75979b7SPierre Ossman }
1401f75979b7SPierre Ossman 
1402f2119df6SArindam Nath static int sdhci_start_signal_voltage_switch(struct mmc_host *mmc,
1403f2119df6SArindam Nath 	struct mmc_ios *ios)
1404f2119df6SArindam Nath {
1405f2119df6SArindam Nath 	struct sdhci_host *host;
1406f2119df6SArindam Nath 	u8 pwr;
1407f2119df6SArindam Nath 	u16 clk, ctrl;
1408f2119df6SArindam Nath 	u32 present_state;
1409f2119df6SArindam Nath 
1410f2119df6SArindam Nath 	host = mmc_priv(mmc);
1411f2119df6SArindam Nath 
1412f2119df6SArindam Nath 	/*
1413f2119df6SArindam Nath 	 * Signal Voltage Switching is only applicable for Host Controllers
1414f2119df6SArindam Nath 	 * v3.00 and above.
1415f2119df6SArindam Nath 	 */
1416f2119df6SArindam Nath 	if (host->version < SDHCI_SPEC_300)
1417f2119df6SArindam Nath 		return 0;
1418f2119df6SArindam Nath 
1419f2119df6SArindam Nath 	/*
1420f2119df6SArindam Nath 	 * We first check whether the request is to set signalling voltage
1421f2119df6SArindam Nath 	 * to 3.3V. If so, we change the voltage to 3.3V and return quickly.
1422f2119df6SArindam Nath 	 */
1423f2119df6SArindam Nath 	ctrl = sdhci_readw(host, SDHCI_HOST_CONTROL2);
1424f2119df6SArindam Nath 	if (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_330) {
1425f2119df6SArindam Nath 		/* Set 1.8V Signal Enable in the Host Control2 register to 0 */
1426f2119df6SArindam Nath 		ctrl &= ~SDHCI_CTRL_VDD_180;
1427f2119df6SArindam Nath 		sdhci_writew(host, ctrl, SDHCI_HOST_CONTROL2);
1428f2119df6SArindam Nath 
1429f2119df6SArindam Nath 		/* Wait for 5ms */
1430f2119df6SArindam Nath 		usleep_range(5000, 5500);
1431f2119df6SArindam Nath 
1432f2119df6SArindam Nath 		/* 3.3V regulator output should be stable within 5 ms */
1433f2119df6SArindam Nath 		ctrl = sdhci_readw(host, SDHCI_HOST_CONTROL2);
1434f2119df6SArindam Nath 		if (!(ctrl & SDHCI_CTRL_VDD_180))
1435f2119df6SArindam Nath 			return 0;
1436f2119df6SArindam Nath 		else {
1437f2119df6SArindam Nath 			printk(KERN_INFO DRIVER_NAME ": Switching to 3.3V "
1438f2119df6SArindam Nath 				"signalling voltage failed\n");
1439f2119df6SArindam Nath 			return -EIO;
1440f2119df6SArindam Nath 		}
1441f2119df6SArindam Nath 	} else if (!(ctrl & SDHCI_CTRL_VDD_180) &&
1442f2119df6SArindam Nath 		  (ios->signal_voltage == MMC_SIGNAL_VOLTAGE_180)) {
1443f2119df6SArindam Nath 		/* Stop SDCLK */
1444f2119df6SArindam Nath 		clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
1445f2119df6SArindam Nath 		clk &= ~SDHCI_CLOCK_CARD_EN;
1446f2119df6SArindam Nath 		sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
1447f2119df6SArindam Nath 
1448f2119df6SArindam Nath 		/* Check whether DAT[3:0] is 0000 */
1449f2119df6SArindam Nath 		present_state = sdhci_readl(host, SDHCI_PRESENT_STATE);
1450f2119df6SArindam Nath 		if (!((present_state & SDHCI_DATA_LVL_MASK) >>
1451f2119df6SArindam Nath 		       SDHCI_DATA_LVL_SHIFT)) {
1452f2119df6SArindam Nath 			/*
1453f2119df6SArindam Nath 			 * Enable 1.8V Signal Enable in the Host Control2
1454f2119df6SArindam Nath 			 * register
1455f2119df6SArindam Nath 			 */
1456f2119df6SArindam Nath 			ctrl |= SDHCI_CTRL_VDD_180;
1457f2119df6SArindam Nath 			sdhci_writew(host, ctrl, SDHCI_HOST_CONTROL2);
1458f2119df6SArindam Nath 
1459f2119df6SArindam Nath 			/* Wait for 5ms */
1460f2119df6SArindam Nath 			usleep_range(5000, 5500);
1461f2119df6SArindam Nath 
1462f2119df6SArindam Nath 			ctrl = sdhci_readw(host, SDHCI_HOST_CONTROL2);
1463f2119df6SArindam Nath 			if (ctrl & SDHCI_CTRL_VDD_180) {
1464f2119df6SArindam Nath 				/* Provide SDCLK again and wait for 1ms*/
1465f2119df6SArindam Nath 				clk = sdhci_readw(host, SDHCI_CLOCK_CONTROL);
1466f2119df6SArindam Nath 				clk |= SDHCI_CLOCK_CARD_EN;
1467f2119df6SArindam Nath 				sdhci_writew(host, clk, SDHCI_CLOCK_CONTROL);
1468f2119df6SArindam Nath 				usleep_range(1000, 1500);
1469f2119df6SArindam Nath 
1470f2119df6SArindam Nath 				/*
1471f2119df6SArindam Nath 				 * If DAT[3:0] level is 1111b, then the card
1472f2119df6SArindam Nath 				 * was successfully switched to 1.8V signaling.
1473f2119df6SArindam Nath 				 */
1474f2119df6SArindam Nath 				present_state = sdhci_readl(host,
1475f2119df6SArindam Nath 							SDHCI_PRESENT_STATE);
1476f2119df6SArindam Nath 				if ((present_state & SDHCI_DATA_LVL_MASK) ==
1477f2119df6SArindam Nath 				     SDHCI_DATA_LVL_MASK)
1478f2119df6SArindam Nath 					return 0;
1479f2119df6SArindam Nath 			}
1480f2119df6SArindam Nath 		}
1481f2119df6SArindam Nath 
1482f2119df6SArindam Nath 		/*
1483f2119df6SArindam Nath 		 * If we are here, that means the switch to 1.8V signaling
1484f2119df6SArindam Nath 		 * failed. We power cycle the card, and retry initialization
1485f2119df6SArindam Nath 		 * sequence by setting S18R to 0.
1486f2119df6SArindam Nath 		 */
1487f2119df6SArindam Nath 		pwr = sdhci_readb(host, SDHCI_POWER_CONTROL);
1488f2119df6SArindam Nath 		pwr &= ~SDHCI_POWER_ON;
1489f2119df6SArindam Nath 		sdhci_writeb(host, pwr, SDHCI_POWER_CONTROL);
1490f2119df6SArindam Nath 
1491f2119df6SArindam Nath 		/* Wait for 1ms as per the spec */
1492f2119df6SArindam Nath 		usleep_range(1000, 1500);
1493f2119df6SArindam Nath 		pwr |= SDHCI_POWER_ON;
1494f2119df6SArindam Nath 		sdhci_writeb(host, pwr, SDHCI_POWER_CONTROL);
1495f2119df6SArindam Nath 
1496f2119df6SArindam Nath 		printk(KERN_INFO DRIVER_NAME ": Switching to 1.8V signalling "
1497f2119df6SArindam Nath 			"voltage failed, retrying with S18R set to 0\n");
1498f2119df6SArindam Nath 		return -EAGAIN;
1499f2119df6SArindam Nath 	} else
1500f2119df6SArindam Nath 		/* No signal voltage switch required */
1501f2119df6SArindam Nath 		return 0;
1502f2119df6SArindam Nath }
1503f2119df6SArindam Nath 
15041c6a0718SPierre Ossman static const struct mmc_host_ops sdhci_ops = {
15051c6a0718SPierre Ossman 	.request	= sdhci_request,
15061c6a0718SPierre Ossman 	.set_ios	= sdhci_set_ios,
15071c6a0718SPierre Ossman 	.get_ro		= sdhci_get_ro,
1508f75979b7SPierre Ossman 	.enable_sdio_irq = sdhci_enable_sdio_irq,
1509f2119df6SArindam Nath 	.start_signal_voltage_switch	= sdhci_start_signal_voltage_switch,
15101c6a0718SPierre Ossman };
15111c6a0718SPierre Ossman 
15121c6a0718SPierre Ossman /*****************************************************************************\
15131c6a0718SPierre Ossman  *                                                                           *
15141c6a0718SPierre Ossman  * Tasklets                                                                  *
15151c6a0718SPierre Ossman  *                                                                           *
15161c6a0718SPierre Ossman \*****************************************************************************/
15171c6a0718SPierre Ossman 
15181c6a0718SPierre Ossman static void sdhci_tasklet_card(unsigned long param)
15191c6a0718SPierre Ossman {
15201c6a0718SPierre Ossman 	struct sdhci_host *host;
15211c6a0718SPierre Ossman 	unsigned long flags;
15221c6a0718SPierre Ossman 
15231c6a0718SPierre Ossman 	host = (struct sdhci_host*)param;
15241c6a0718SPierre Ossman 
15251c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
15261c6a0718SPierre Ossman 
15274e4141a5SAnton Vorontsov 	if (!(sdhci_readl(host, SDHCI_PRESENT_STATE) & SDHCI_CARD_PRESENT)) {
15281c6a0718SPierre Ossman 		if (host->mrq) {
15291c6a0718SPierre Ossman 			printk(KERN_ERR "%s: Card removed during transfer!\n",
15301c6a0718SPierre Ossman 				mmc_hostname(host->mmc));
15311c6a0718SPierre Ossman 			printk(KERN_ERR "%s: Resetting controller.\n",
15321c6a0718SPierre Ossman 				mmc_hostname(host->mmc));
15331c6a0718SPierre Ossman 
15341c6a0718SPierre Ossman 			sdhci_reset(host, SDHCI_RESET_CMD);
15351c6a0718SPierre Ossman 			sdhci_reset(host, SDHCI_RESET_DATA);
15361c6a0718SPierre Ossman 
153717b0429dSPierre Ossman 			host->mrq->cmd->error = -ENOMEDIUM;
15381c6a0718SPierre Ossman 			tasklet_schedule(&host->finish_tasklet);
15391c6a0718SPierre Ossman 		}
15401c6a0718SPierre Ossman 	}
15411c6a0718SPierre Ossman 
15421c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
15431c6a0718SPierre Ossman 
154404cf585dSPierre Ossman 	mmc_detect_change(host->mmc, msecs_to_jiffies(200));
15451c6a0718SPierre Ossman }
15461c6a0718SPierre Ossman 
15471c6a0718SPierre Ossman static void sdhci_tasklet_finish(unsigned long param)
15481c6a0718SPierre Ossman {
15491c6a0718SPierre Ossman 	struct sdhci_host *host;
15501c6a0718SPierre Ossman 	unsigned long flags;
15511c6a0718SPierre Ossman 	struct mmc_request *mrq;
15521c6a0718SPierre Ossman 
15531c6a0718SPierre Ossman 	host = (struct sdhci_host*)param;
15541c6a0718SPierre Ossman 
15550c9c99a7SChris Ball         /*
15560c9c99a7SChris Ball          * If this tasklet gets rescheduled while running, it will
15570c9c99a7SChris Ball          * be run again afterwards but without any active request.
15580c9c99a7SChris Ball          */
15590c9c99a7SChris Ball 	if (!host->mrq)
15600c9c99a7SChris Ball 		return;
15610c9c99a7SChris Ball 
15621c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
15631c6a0718SPierre Ossman 
15641c6a0718SPierre Ossman 	del_timer(&host->timer);
15651c6a0718SPierre Ossman 
15661c6a0718SPierre Ossman 	mrq = host->mrq;
15671c6a0718SPierre Ossman 
15681c6a0718SPierre Ossman 	/*
15691c6a0718SPierre Ossman 	 * The controller needs a reset of internal state machines
15701c6a0718SPierre Ossman 	 * upon error conditions.
15711c6a0718SPierre Ossman 	 */
15721e72859eSPierre Ossman 	if (!(host->flags & SDHCI_DEVICE_DEAD) &&
1573b7b4d342SBen Dooks 	    ((mrq->cmd && mrq->cmd->error) ||
157417b0429dSPierre Ossman 		 (mrq->data && (mrq->data->error ||
157584c46a53SPierre Ossman 		  (mrq->data->stop && mrq->data->stop->error))) ||
15761e72859eSPierre Ossman 		   (host->quirks & SDHCI_QUIRK_RESET_AFTER_REQUEST))) {
15771c6a0718SPierre Ossman 
15781c6a0718SPierre Ossman 		/* Some controllers need this kick or reset won't work here */
1579b8c86fc5SPierre Ossman 		if (host->quirks & SDHCI_QUIRK_CLOCK_BEFORE_RESET) {
15801c6a0718SPierre Ossman 			unsigned int clock;
15811c6a0718SPierre Ossman 
15821c6a0718SPierre Ossman 			/* This is to force an update */
15831c6a0718SPierre Ossman 			clock = host->clock;
15841c6a0718SPierre Ossman 			host->clock = 0;
15851c6a0718SPierre Ossman 			sdhci_set_clock(host, clock);
15861c6a0718SPierre Ossman 		}
15871c6a0718SPierre Ossman 
15881c6a0718SPierre Ossman 		/* Spec says we should do both at the same time, but Ricoh
15891c6a0718SPierre Ossman 		   controllers do not like that. */
15901c6a0718SPierre Ossman 		sdhci_reset(host, SDHCI_RESET_CMD);
15911c6a0718SPierre Ossman 		sdhci_reset(host, SDHCI_RESET_DATA);
15921c6a0718SPierre Ossman 	}
15931c6a0718SPierre Ossman 
15941c6a0718SPierre Ossman 	host->mrq = NULL;
15951c6a0718SPierre Ossman 	host->cmd = NULL;
15961c6a0718SPierre Ossman 	host->data = NULL;
15971c6a0718SPierre Ossman 
1598f9134319SPierre Ossman #ifndef SDHCI_USE_LEDS_CLASS
15991c6a0718SPierre Ossman 	sdhci_deactivate_led(host);
16002f730fecSPierre Ossman #endif
16011c6a0718SPierre Ossman 
16021c6a0718SPierre Ossman 	mmiowb();
16031c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
16041c6a0718SPierre Ossman 
16051c6a0718SPierre Ossman 	mmc_request_done(host->mmc, mrq);
16061c6a0718SPierre Ossman }
16071c6a0718SPierre Ossman 
16081c6a0718SPierre Ossman static void sdhci_timeout_timer(unsigned long data)
16091c6a0718SPierre Ossman {
16101c6a0718SPierre Ossman 	struct sdhci_host *host;
16111c6a0718SPierre Ossman 	unsigned long flags;
16121c6a0718SPierre Ossman 
16131c6a0718SPierre Ossman 	host = (struct sdhci_host*)data;
16141c6a0718SPierre Ossman 
16151c6a0718SPierre Ossman 	spin_lock_irqsave(&host->lock, flags);
16161c6a0718SPierre Ossman 
16171c6a0718SPierre Ossman 	if (host->mrq) {
16181c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Timeout waiting for hardware "
16191c6a0718SPierre Ossman 			"interrupt.\n", mmc_hostname(host->mmc));
16201c6a0718SPierre Ossman 		sdhci_dumpregs(host);
16211c6a0718SPierre Ossman 
16221c6a0718SPierre Ossman 		if (host->data) {
162317b0429dSPierre Ossman 			host->data->error = -ETIMEDOUT;
16241c6a0718SPierre Ossman 			sdhci_finish_data(host);
16251c6a0718SPierre Ossman 		} else {
16261c6a0718SPierre Ossman 			if (host->cmd)
162717b0429dSPierre Ossman 				host->cmd->error = -ETIMEDOUT;
16281c6a0718SPierre Ossman 			else
162917b0429dSPierre Ossman 				host->mrq->cmd->error = -ETIMEDOUT;
16301c6a0718SPierre Ossman 
16311c6a0718SPierre Ossman 			tasklet_schedule(&host->finish_tasklet);
16321c6a0718SPierre Ossman 		}
16331c6a0718SPierre Ossman 	}
16341c6a0718SPierre Ossman 
16351c6a0718SPierre Ossman 	mmiowb();
16361c6a0718SPierre Ossman 	spin_unlock_irqrestore(&host->lock, flags);
16371c6a0718SPierre Ossman }
16381c6a0718SPierre Ossman 
16391c6a0718SPierre Ossman /*****************************************************************************\
16401c6a0718SPierre Ossman  *                                                                           *
16411c6a0718SPierre Ossman  * Interrupt handling                                                        *
16421c6a0718SPierre Ossman  *                                                                           *
16431c6a0718SPierre Ossman \*****************************************************************************/
16441c6a0718SPierre Ossman 
16451c6a0718SPierre Ossman static void sdhci_cmd_irq(struct sdhci_host *host, u32 intmask)
16461c6a0718SPierre Ossman {
16471c6a0718SPierre Ossman 	BUG_ON(intmask == 0);
16481c6a0718SPierre Ossman 
16491c6a0718SPierre Ossman 	if (!host->cmd) {
1650b67ac3f3SPierre Ossman 		printk(KERN_ERR "%s: Got command interrupt 0x%08x even "
1651b67ac3f3SPierre Ossman 			"though no command operation was in progress.\n",
1652b67ac3f3SPierre Ossman 			mmc_hostname(host->mmc), (unsigned)intmask);
16531c6a0718SPierre Ossman 		sdhci_dumpregs(host);
16541c6a0718SPierre Ossman 		return;
16551c6a0718SPierre Ossman 	}
16561c6a0718SPierre Ossman 
16571c6a0718SPierre Ossman 	if (intmask & SDHCI_INT_TIMEOUT)
165817b0429dSPierre Ossman 		host->cmd->error = -ETIMEDOUT;
165917b0429dSPierre Ossman 	else if (intmask & (SDHCI_INT_CRC | SDHCI_INT_END_BIT |
166017b0429dSPierre Ossman 			SDHCI_INT_INDEX))
166117b0429dSPierre Ossman 		host->cmd->error = -EILSEQ;
16621c6a0718SPierre Ossman 
1663e809517fSPierre Ossman 	if (host->cmd->error) {
16641c6a0718SPierre Ossman 		tasklet_schedule(&host->finish_tasklet);
1665e809517fSPierre Ossman 		return;
1666e809517fSPierre Ossman 	}
1667e809517fSPierre Ossman 
1668e809517fSPierre Ossman 	/*
1669e809517fSPierre Ossman 	 * The host can send and interrupt when the busy state has
1670e809517fSPierre Ossman 	 * ended, allowing us to wait without wasting CPU cycles.
1671e809517fSPierre Ossman 	 * Unfortunately this is overloaded on the "data complete"
1672e809517fSPierre Ossman 	 * interrupt, so we need to take some care when handling
1673e809517fSPierre Ossman 	 * it.
1674e809517fSPierre Ossman 	 *
1675e809517fSPierre Ossman 	 * Note: The 1.0 specification is a bit ambiguous about this
1676e809517fSPierre Ossman 	 *       feature so there might be some problems with older
1677e809517fSPierre Ossman 	 *       controllers.
1678e809517fSPierre Ossman 	 */
1679e809517fSPierre Ossman 	if (host->cmd->flags & MMC_RSP_BUSY) {
1680e809517fSPierre Ossman 		if (host->cmd->data)
1681e809517fSPierre Ossman 			DBG("Cannot wait for busy signal when also "
1682e809517fSPierre Ossman 				"doing a data transfer");
1683f945405cSBen Dooks 		else if (!(host->quirks & SDHCI_QUIRK_NO_BUSY_IRQ))
1684e809517fSPierre Ossman 			return;
1685f945405cSBen Dooks 
1686f945405cSBen Dooks 		/* The controller does not support the end-of-busy IRQ,
1687f945405cSBen Dooks 		 * fall through and take the SDHCI_INT_RESPONSE */
1688e809517fSPierre Ossman 	}
1689e809517fSPierre Ossman 
1690e809517fSPierre Ossman 	if (intmask & SDHCI_INT_RESPONSE)
169143b58b36SPierre Ossman 		sdhci_finish_command(host);
16921c6a0718SPierre Ossman }
16931c6a0718SPierre Ossman 
16940957c333SGeorge G. Davis #ifdef CONFIG_MMC_DEBUG
16956882a8c0SBen Dooks static void sdhci_show_adma_error(struct sdhci_host *host)
16966882a8c0SBen Dooks {
16976882a8c0SBen Dooks 	const char *name = mmc_hostname(host->mmc);
16986882a8c0SBen Dooks 	u8 *desc = host->adma_desc;
16996882a8c0SBen Dooks 	__le32 *dma;
17006882a8c0SBen Dooks 	__le16 *len;
17016882a8c0SBen Dooks 	u8 attr;
17026882a8c0SBen Dooks 
17036882a8c0SBen Dooks 	sdhci_dumpregs(host);
17046882a8c0SBen Dooks 
17056882a8c0SBen Dooks 	while (true) {
17066882a8c0SBen Dooks 		dma = (__le32 *)(desc + 4);
17076882a8c0SBen Dooks 		len = (__le16 *)(desc + 2);
17086882a8c0SBen Dooks 		attr = *desc;
17096882a8c0SBen Dooks 
17106882a8c0SBen Dooks 		DBG("%s: %p: DMA 0x%08x, LEN 0x%04x, Attr=0x%02x\n",
17116882a8c0SBen Dooks 		    name, desc, le32_to_cpu(*dma), le16_to_cpu(*len), attr);
17126882a8c0SBen Dooks 
17136882a8c0SBen Dooks 		desc += 8;
17146882a8c0SBen Dooks 
17156882a8c0SBen Dooks 		if (attr & 2)
17166882a8c0SBen Dooks 			break;
17176882a8c0SBen Dooks 	}
17186882a8c0SBen Dooks }
17196882a8c0SBen Dooks #else
17206882a8c0SBen Dooks static void sdhci_show_adma_error(struct sdhci_host *host) { }
17216882a8c0SBen Dooks #endif
17226882a8c0SBen Dooks 
17231c6a0718SPierre Ossman static void sdhci_data_irq(struct sdhci_host *host, u32 intmask)
17241c6a0718SPierre Ossman {
17251c6a0718SPierre Ossman 	BUG_ON(intmask == 0);
17261c6a0718SPierre Ossman 
17271c6a0718SPierre Ossman 	if (!host->data) {
17281c6a0718SPierre Ossman 		/*
1729e809517fSPierre Ossman 		 * The "data complete" interrupt is also used to
1730e809517fSPierre Ossman 		 * indicate that a busy state has ended. See comment
1731e809517fSPierre Ossman 		 * above in sdhci_cmd_irq().
17321c6a0718SPierre Ossman 		 */
1733e809517fSPierre Ossman 		if (host->cmd && (host->cmd->flags & MMC_RSP_BUSY)) {
1734e809517fSPierre Ossman 			if (intmask & SDHCI_INT_DATA_END) {
1735e809517fSPierre Ossman 				sdhci_finish_command(host);
17361c6a0718SPierre Ossman 				return;
1737e809517fSPierre Ossman 			}
1738e809517fSPierre Ossman 		}
17391c6a0718SPierre Ossman 
1740b67ac3f3SPierre Ossman 		printk(KERN_ERR "%s: Got data interrupt 0x%08x even "
1741b67ac3f3SPierre Ossman 			"though no data operation was in progress.\n",
1742b67ac3f3SPierre Ossman 			mmc_hostname(host->mmc), (unsigned)intmask);
17431c6a0718SPierre Ossman 		sdhci_dumpregs(host);
17441c6a0718SPierre Ossman 
17451c6a0718SPierre Ossman 		return;
17461c6a0718SPierre Ossman 	}
17471c6a0718SPierre Ossman 
17481c6a0718SPierre Ossman 	if (intmask & SDHCI_INT_DATA_TIMEOUT)
174917b0429dSPierre Ossman 		host->data->error = -ETIMEDOUT;
175022113efdSAries Lee 	else if (intmask & SDHCI_INT_DATA_END_BIT)
175122113efdSAries Lee 		host->data->error = -EILSEQ;
175222113efdSAries Lee 	else if ((intmask & SDHCI_INT_DATA_CRC) &&
175322113efdSAries Lee 		SDHCI_GET_CMD(sdhci_readw(host, SDHCI_COMMAND))
175422113efdSAries Lee 			!= MMC_BUS_TEST_R)
175517b0429dSPierre Ossman 		host->data->error = -EILSEQ;
17566882a8c0SBen Dooks 	else if (intmask & SDHCI_INT_ADMA_ERROR) {
17576882a8c0SBen Dooks 		printk(KERN_ERR "%s: ADMA error\n", mmc_hostname(host->mmc));
17586882a8c0SBen Dooks 		sdhci_show_adma_error(host);
17592134a922SPierre Ossman 		host->data->error = -EIO;
17606882a8c0SBen Dooks 	}
17611c6a0718SPierre Ossman 
176217b0429dSPierre Ossman 	if (host->data->error)
17631c6a0718SPierre Ossman 		sdhci_finish_data(host);
17641c6a0718SPierre Ossman 	else {
17651c6a0718SPierre Ossman 		if (intmask & (SDHCI_INT_DATA_AVAIL | SDHCI_INT_SPACE_AVAIL))
17661c6a0718SPierre Ossman 			sdhci_transfer_pio(host);
17671c6a0718SPierre Ossman 
17686ba736a1SPierre Ossman 		/*
17696ba736a1SPierre Ossman 		 * We currently don't do anything fancy with DMA
17706ba736a1SPierre Ossman 		 * boundaries, but as we can't disable the feature
17716ba736a1SPierre Ossman 		 * we need to at least restart the transfer.
1772f6a03cbfSMikko Vinni 		 *
1773f6a03cbfSMikko Vinni 		 * According to the spec sdhci_readl(host, SDHCI_DMA_ADDRESS)
1774f6a03cbfSMikko Vinni 		 * should return a valid address to continue from, but as
1775f6a03cbfSMikko Vinni 		 * some controllers are faulty, don't trust them.
17766ba736a1SPierre Ossman 		 */
1777f6a03cbfSMikko Vinni 		if (intmask & SDHCI_INT_DMA_END) {
1778f6a03cbfSMikko Vinni 			u32 dmastart, dmanow;
1779f6a03cbfSMikko Vinni 			dmastart = sg_dma_address(host->data->sg);
1780f6a03cbfSMikko Vinni 			dmanow = dmastart + host->data->bytes_xfered;
1781f6a03cbfSMikko Vinni 			/*
1782f6a03cbfSMikko Vinni 			 * Force update to the next DMA block boundary.
1783f6a03cbfSMikko Vinni 			 */
1784f6a03cbfSMikko Vinni 			dmanow = (dmanow &
1785f6a03cbfSMikko Vinni 				~(SDHCI_DEFAULT_BOUNDARY_SIZE - 1)) +
1786f6a03cbfSMikko Vinni 				SDHCI_DEFAULT_BOUNDARY_SIZE;
1787f6a03cbfSMikko Vinni 			host->data->bytes_xfered = dmanow - dmastart;
1788f6a03cbfSMikko Vinni 			DBG("%s: DMA base 0x%08x, transferred 0x%06x bytes,"
1789f6a03cbfSMikko Vinni 				" next 0x%08x\n",
1790f6a03cbfSMikko Vinni 				mmc_hostname(host->mmc), dmastart,
1791f6a03cbfSMikko Vinni 				host->data->bytes_xfered, dmanow);
1792f6a03cbfSMikko Vinni 			sdhci_writel(host, dmanow, SDHCI_DMA_ADDRESS);
1793f6a03cbfSMikko Vinni 		}
17946ba736a1SPierre Ossman 
1795e538fbe8SPierre Ossman 		if (intmask & SDHCI_INT_DATA_END) {
1796e538fbe8SPierre Ossman 			if (host->cmd) {
1797e538fbe8SPierre Ossman 				/*
1798e538fbe8SPierre Ossman 				 * Data managed to finish before the
1799e538fbe8SPierre Ossman 				 * command completed. Make sure we do
1800e538fbe8SPierre Ossman 				 * things in the proper order.
1801e538fbe8SPierre Ossman 				 */
1802e538fbe8SPierre Ossman 				host->data_early = 1;
1803e538fbe8SPierre Ossman 			} else {
18041c6a0718SPierre Ossman 				sdhci_finish_data(host);
18051c6a0718SPierre Ossman 			}
18061c6a0718SPierre Ossman 		}
1807e538fbe8SPierre Ossman 	}
1808e538fbe8SPierre Ossman }
18091c6a0718SPierre Ossman 
18101c6a0718SPierre Ossman static irqreturn_t sdhci_irq(int irq, void *dev_id)
18111c6a0718SPierre Ossman {
18121c6a0718SPierre Ossman 	irqreturn_t result;
18131c6a0718SPierre Ossman 	struct sdhci_host* host = dev_id;
18141c6a0718SPierre Ossman 	u32 intmask;
1815f75979b7SPierre Ossman 	int cardint = 0;
18161c6a0718SPierre Ossman 
18171c6a0718SPierre Ossman 	spin_lock(&host->lock);
18181c6a0718SPierre Ossman 
18194e4141a5SAnton Vorontsov 	intmask = sdhci_readl(host, SDHCI_INT_STATUS);
18201c6a0718SPierre Ossman 
18211c6a0718SPierre Ossman 	if (!intmask || intmask == 0xffffffff) {
18221c6a0718SPierre Ossman 		result = IRQ_NONE;
18231c6a0718SPierre Ossman 		goto out;
18241c6a0718SPierre Ossman 	}
18251c6a0718SPierre Ossman 
1826b69c9058SPierre Ossman 	DBG("*** %s got interrupt: 0x%08x\n",
1827b69c9058SPierre Ossman 		mmc_hostname(host->mmc), intmask);
18281c6a0718SPierre Ossman 
18291c6a0718SPierre Ossman 	if (intmask & (SDHCI_INT_CARD_INSERT | SDHCI_INT_CARD_REMOVE)) {
18304e4141a5SAnton Vorontsov 		sdhci_writel(host, intmask & (SDHCI_INT_CARD_INSERT |
18314e4141a5SAnton Vorontsov 			SDHCI_INT_CARD_REMOVE), SDHCI_INT_STATUS);
18321c6a0718SPierre Ossman 		tasklet_schedule(&host->card_tasklet);
18331c6a0718SPierre Ossman 	}
18341c6a0718SPierre Ossman 
18351c6a0718SPierre Ossman 	intmask &= ~(SDHCI_INT_CARD_INSERT | SDHCI_INT_CARD_REMOVE);
18361c6a0718SPierre Ossman 
18371c6a0718SPierre Ossman 	if (intmask & SDHCI_INT_CMD_MASK) {
18384e4141a5SAnton Vorontsov 		sdhci_writel(host, intmask & SDHCI_INT_CMD_MASK,
18394e4141a5SAnton Vorontsov 			SDHCI_INT_STATUS);
18401c6a0718SPierre Ossman 		sdhci_cmd_irq(host, intmask & SDHCI_INT_CMD_MASK);
18411c6a0718SPierre Ossman 	}
18421c6a0718SPierre Ossman 
18431c6a0718SPierre Ossman 	if (intmask & SDHCI_INT_DATA_MASK) {
18444e4141a5SAnton Vorontsov 		sdhci_writel(host, intmask & SDHCI_INT_DATA_MASK,
18454e4141a5SAnton Vorontsov 			SDHCI_INT_STATUS);
18461c6a0718SPierre Ossman 		sdhci_data_irq(host, intmask & SDHCI_INT_DATA_MASK);
18471c6a0718SPierre Ossman 	}
18481c6a0718SPierre Ossman 
18491c6a0718SPierre Ossman 	intmask &= ~(SDHCI_INT_CMD_MASK | SDHCI_INT_DATA_MASK);
18501c6a0718SPierre Ossman 
1851964f9ce2SPierre Ossman 	intmask &= ~SDHCI_INT_ERROR;
1852964f9ce2SPierre Ossman 
18531c6a0718SPierre Ossman 	if (intmask & SDHCI_INT_BUS_POWER) {
18541c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Card is consuming too much power!\n",
18551c6a0718SPierre Ossman 			mmc_hostname(host->mmc));
18564e4141a5SAnton Vorontsov 		sdhci_writel(host, SDHCI_INT_BUS_POWER, SDHCI_INT_STATUS);
18571c6a0718SPierre Ossman 	}
18581c6a0718SPierre Ossman 
18599d26a5d3SRolf Eike Beer 	intmask &= ~SDHCI_INT_BUS_POWER;
18601c6a0718SPierre Ossman 
1861f75979b7SPierre Ossman 	if (intmask & SDHCI_INT_CARD_INT)
1862f75979b7SPierre Ossman 		cardint = 1;
1863f75979b7SPierre Ossman 
1864f75979b7SPierre Ossman 	intmask &= ~SDHCI_INT_CARD_INT;
1865f75979b7SPierre Ossman 
18661c6a0718SPierre Ossman 	if (intmask) {
18671c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Unexpected interrupt 0x%08x.\n",
18681c6a0718SPierre Ossman 			mmc_hostname(host->mmc), intmask);
18691c6a0718SPierre Ossman 		sdhci_dumpregs(host);
18701c6a0718SPierre Ossman 
18714e4141a5SAnton Vorontsov 		sdhci_writel(host, intmask, SDHCI_INT_STATUS);
18721c6a0718SPierre Ossman 	}
18731c6a0718SPierre Ossman 
18741c6a0718SPierre Ossman 	result = IRQ_HANDLED;
18751c6a0718SPierre Ossman 
18761c6a0718SPierre Ossman 	mmiowb();
18771c6a0718SPierre Ossman out:
18781c6a0718SPierre Ossman 	spin_unlock(&host->lock);
18791c6a0718SPierre Ossman 
1880f75979b7SPierre Ossman 	/*
1881f75979b7SPierre Ossman 	 * We have to delay this as it calls back into the driver.
1882f75979b7SPierre Ossman 	 */
1883f75979b7SPierre Ossman 	if (cardint)
1884f75979b7SPierre Ossman 		mmc_signal_sdio_irq(host->mmc);
1885f75979b7SPierre Ossman 
18861c6a0718SPierre Ossman 	return result;
18871c6a0718SPierre Ossman }
18881c6a0718SPierre Ossman 
18891c6a0718SPierre Ossman /*****************************************************************************\
18901c6a0718SPierre Ossman  *                                                                           *
18911c6a0718SPierre Ossman  * Suspend/resume                                                            *
18921c6a0718SPierre Ossman  *                                                                           *
18931c6a0718SPierre Ossman \*****************************************************************************/
18941c6a0718SPierre Ossman 
18951c6a0718SPierre Ossman #ifdef CONFIG_PM
18961c6a0718SPierre Ossman 
1897b8c86fc5SPierre Ossman int sdhci_suspend_host(struct sdhci_host *host, pm_message_t state)
18981c6a0718SPierre Ossman {
1899b8c86fc5SPierre Ossman 	int ret;
19001c6a0718SPierre Ossman 
19017260cf5eSAnton Vorontsov 	sdhci_disable_card_detection(host);
19027260cf5eSAnton Vorontsov 
19031a13f8faSMatt Fleming 	ret = mmc_suspend_host(host->mmc);
19041c6a0718SPierre Ossman 	if (ret)
19051c6a0718SPierre Ossman 		return ret;
19061c6a0718SPierre Ossman 
1907b8c86fc5SPierre Ossman 	free_irq(host->irq, host);
1908b8c86fc5SPierre Ossman 
19099bea3c85SMarek Szyprowski 	if (host->vmmc)
19109bea3c85SMarek Szyprowski 		ret = regulator_disable(host->vmmc);
19119bea3c85SMarek Szyprowski 
19129bea3c85SMarek Szyprowski 	return ret;
1913b8c86fc5SPierre Ossman }
1914b8c86fc5SPierre Ossman 
1915b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_suspend_host);
1916b8c86fc5SPierre Ossman 
1917b8c86fc5SPierre Ossman int sdhci_resume_host(struct sdhci_host *host)
1918b8c86fc5SPierre Ossman {
1919b8c86fc5SPierre Ossman 	int ret;
1920b8c86fc5SPierre Ossman 
19219bea3c85SMarek Szyprowski 	if (host->vmmc) {
19229bea3c85SMarek Szyprowski 		int ret = regulator_enable(host->vmmc);
19239bea3c85SMarek Szyprowski 		if (ret)
19249bea3c85SMarek Szyprowski 			return ret;
19259bea3c85SMarek Szyprowski 	}
19269bea3c85SMarek Szyprowski 
19279bea3c85SMarek Szyprowski 
1928a13abc7bSRichard Röjfors 	if (host->flags & (SDHCI_USE_SDMA | SDHCI_USE_ADMA)) {
1929b8c86fc5SPierre Ossman 		if (host->ops->enable_dma)
1930b8c86fc5SPierre Ossman 			host->ops->enable_dma(host);
1931b8c86fc5SPierre Ossman 	}
1932b8c86fc5SPierre Ossman 
1933b8c86fc5SPierre Ossman 	ret = request_irq(host->irq, sdhci_irq, IRQF_SHARED,
1934b8c86fc5SPierre Ossman 			  mmc_hostname(host->mmc), host);
19351c6a0718SPierre Ossman 	if (ret)
19361c6a0718SPierre Ossman 		return ret;
1937b8c86fc5SPierre Ossman 
19382f4cbb3dSNicolas Pitre 	sdhci_init(host, (host->mmc->pm_flags & MMC_PM_KEEP_POWER));
19391c6a0718SPierre Ossman 	mmiowb();
1940b8c86fc5SPierre Ossman 
1941b8c86fc5SPierre Ossman 	ret = mmc_resume_host(host->mmc);
19427260cf5eSAnton Vorontsov 	sdhci_enable_card_detection(host);
19437260cf5eSAnton Vorontsov 
19442f4cbb3dSNicolas Pitre 	return ret;
19451c6a0718SPierre Ossman }
19461c6a0718SPierre Ossman 
1947b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_resume_host);
19481c6a0718SPierre Ossman 
19495f619704SDaniel Drake void sdhci_enable_irq_wakeups(struct sdhci_host *host)
19505f619704SDaniel Drake {
19515f619704SDaniel Drake 	u8 val;
19525f619704SDaniel Drake 	val = sdhci_readb(host, SDHCI_WAKE_UP_CONTROL);
19535f619704SDaniel Drake 	val |= SDHCI_WAKE_ON_INT;
19545f619704SDaniel Drake 	sdhci_writeb(host, val, SDHCI_WAKE_UP_CONTROL);
19555f619704SDaniel Drake }
19565f619704SDaniel Drake 
19575f619704SDaniel Drake EXPORT_SYMBOL_GPL(sdhci_enable_irq_wakeups);
19585f619704SDaniel Drake 
19591c6a0718SPierre Ossman #endif /* CONFIG_PM */
19601c6a0718SPierre Ossman 
19611c6a0718SPierre Ossman /*****************************************************************************\
19621c6a0718SPierre Ossman  *                                                                           *
1963b8c86fc5SPierre Ossman  * Device allocation/registration                                            *
19641c6a0718SPierre Ossman  *                                                                           *
19651c6a0718SPierre Ossman \*****************************************************************************/
19661c6a0718SPierre Ossman 
1967b8c86fc5SPierre Ossman struct sdhci_host *sdhci_alloc_host(struct device *dev,
1968b8c86fc5SPierre Ossman 	size_t priv_size)
19691c6a0718SPierre Ossman {
19701c6a0718SPierre Ossman 	struct mmc_host *mmc;
19711c6a0718SPierre Ossman 	struct sdhci_host *host;
19721c6a0718SPierre Ossman 
1973b8c86fc5SPierre Ossman 	WARN_ON(dev == NULL);
19741c6a0718SPierre Ossman 
1975b8c86fc5SPierre Ossman 	mmc = mmc_alloc_host(sizeof(struct sdhci_host) + priv_size, dev);
19761c6a0718SPierre Ossman 	if (!mmc)
1977b8c86fc5SPierre Ossman 		return ERR_PTR(-ENOMEM);
19781c6a0718SPierre Ossman 
19791c6a0718SPierre Ossman 	host = mmc_priv(mmc);
19801c6a0718SPierre Ossman 	host->mmc = mmc;
19811c6a0718SPierre Ossman 
1982b8c86fc5SPierre Ossman 	return host;
19831c6a0718SPierre Ossman }
19841c6a0718SPierre Ossman 
1985b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_alloc_host);
1986b8c86fc5SPierre Ossman 
1987b8c86fc5SPierre Ossman int sdhci_add_host(struct sdhci_host *host)
1988b8c86fc5SPierre Ossman {
1989b8c86fc5SPierre Ossman 	struct mmc_host *mmc;
1990f2119df6SArindam Nath 	u32 caps[2];
1991f2119df6SArindam Nath 	u32 max_current_caps;
1992f2119df6SArindam Nath 	unsigned int ocr_avail;
1993b8c86fc5SPierre Ossman 	int ret;
1994b8c86fc5SPierre Ossman 
1995b8c86fc5SPierre Ossman 	WARN_ON(host == NULL);
1996b8c86fc5SPierre Ossman 	if (host == NULL)
1997b8c86fc5SPierre Ossman 		return -EINVAL;
1998b8c86fc5SPierre Ossman 
1999b8c86fc5SPierre Ossman 	mmc = host->mmc;
2000b8c86fc5SPierre Ossman 
2001b8c86fc5SPierre Ossman 	if (debug_quirks)
2002b8c86fc5SPierre Ossman 		host->quirks = debug_quirks;
2003b8c86fc5SPierre Ossman 
20041c6a0718SPierre Ossman 	sdhci_reset(host, SDHCI_RESET_ALL);
20051c6a0718SPierre Ossman 
20064e4141a5SAnton Vorontsov 	host->version = sdhci_readw(host, SDHCI_HOST_VERSION);
20072134a922SPierre Ossman 	host->version = (host->version & SDHCI_SPEC_VER_MASK)
20082134a922SPierre Ossman 				>> SDHCI_SPEC_VER_SHIFT;
200985105c53SZhangfei Gao 	if (host->version > SDHCI_SPEC_300) {
20101c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Unknown controller version (%d). "
2011b69c9058SPierre Ossman 			"You may experience problems.\n", mmc_hostname(mmc),
20122134a922SPierre Ossman 			host->version);
20131c6a0718SPierre Ossman 	}
20141c6a0718SPierre Ossman 
2015f2119df6SArindam Nath 	caps[0] = (host->quirks & SDHCI_QUIRK_MISSING_CAPS) ? host->caps :
2016ccc92c23SMaxim Levitsky 		sdhci_readl(host, SDHCI_CAPABILITIES);
20171c6a0718SPierre Ossman 
2018f2119df6SArindam Nath 	caps[1] = (host->version >= SDHCI_SPEC_300) ?
2019f2119df6SArindam Nath 		sdhci_readl(host, SDHCI_CAPABILITIES_1) : 0;
2020f2119df6SArindam Nath 
2021b8c86fc5SPierre Ossman 	if (host->quirks & SDHCI_QUIRK_FORCE_DMA)
2022a13abc7bSRichard Röjfors 		host->flags |= SDHCI_USE_SDMA;
2023f2119df6SArindam Nath 	else if (!(caps[0] & SDHCI_CAN_DO_SDMA))
2024a13abc7bSRichard Röjfors 		DBG("Controller doesn't have SDMA capability\n");
20251c6a0718SPierre Ossman 	else
2026a13abc7bSRichard Röjfors 		host->flags |= SDHCI_USE_SDMA;
20271c6a0718SPierre Ossman 
2028b8c86fc5SPierre Ossman 	if ((host->quirks & SDHCI_QUIRK_BROKEN_DMA) &&
2029a13abc7bSRichard Röjfors 		(host->flags & SDHCI_USE_SDMA)) {
2030cee687ceSRolf Eike Beer 		DBG("Disabling DMA as it is marked broken\n");
2031a13abc7bSRichard Röjfors 		host->flags &= ~SDHCI_USE_SDMA;
20327c168e3dSFeng Tang 	}
20337c168e3dSFeng Tang 
2034f2119df6SArindam Nath 	if ((host->version >= SDHCI_SPEC_200) &&
2035f2119df6SArindam Nath 		(caps[0] & SDHCI_CAN_DO_ADMA2))
20362134a922SPierre Ossman 		host->flags |= SDHCI_USE_ADMA;
20372134a922SPierre Ossman 
20382134a922SPierre Ossman 	if ((host->quirks & SDHCI_QUIRK_BROKEN_ADMA) &&
20392134a922SPierre Ossman 		(host->flags & SDHCI_USE_ADMA)) {
20402134a922SPierre Ossman 		DBG("Disabling ADMA as it is marked broken\n");
20412134a922SPierre Ossman 		host->flags &= ~SDHCI_USE_ADMA;
20422134a922SPierre Ossman 	}
20432134a922SPierre Ossman 
2044a13abc7bSRichard Röjfors 	if (host->flags & (SDHCI_USE_SDMA | SDHCI_USE_ADMA)) {
2045b8c86fc5SPierre Ossman 		if (host->ops->enable_dma) {
2046b8c86fc5SPierre Ossman 			if (host->ops->enable_dma(host)) {
2047b8c86fc5SPierre Ossman 				printk(KERN_WARNING "%s: No suitable DMA "
2048b8c86fc5SPierre Ossman 					"available. Falling back to PIO.\n",
2049b8c86fc5SPierre Ossman 					mmc_hostname(mmc));
2050a13abc7bSRichard Röjfors 				host->flags &=
2051a13abc7bSRichard Röjfors 					~(SDHCI_USE_SDMA | SDHCI_USE_ADMA);
20521c6a0718SPierre Ossman 			}
20531c6a0718SPierre Ossman 		}
2054b8c86fc5SPierre Ossman 	}
20551c6a0718SPierre Ossman 
20562134a922SPierre Ossman 	if (host->flags & SDHCI_USE_ADMA) {
20572134a922SPierre Ossman 		/*
20582134a922SPierre Ossman 		 * We need to allocate descriptors for all sg entries
20592134a922SPierre Ossman 		 * (128) and potentially one alignment transfer for
20602134a922SPierre Ossman 		 * each of those entries.
20612134a922SPierre Ossman 		 */
20622134a922SPierre Ossman 		host->adma_desc = kmalloc((128 * 2 + 1) * 4, GFP_KERNEL);
20632134a922SPierre Ossman 		host->align_buffer = kmalloc(128 * 4, GFP_KERNEL);
20642134a922SPierre Ossman 		if (!host->adma_desc || !host->align_buffer) {
20652134a922SPierre Ossman 			kfree(host->adma_desc);
20662134a922SPierre Ossman 			kfree(host->align_buffer);
20672134a922SPierre Ossman 			printk(KERN_WARNING "%s: Unable to allocate ADMA "
20682134a922SPierre Ossman 				"buffers. Falling back to standard DMA.\n",
20692134a922SPierre Ossman 				mmc_hostname(mmc));
20702134a922SPierre Ossman 			host->flags &= ~SDHCI_USE_ADMA;
20712134a922SPierre Ossman 		}
20722134a922SPierre Ossman 	}
20732134a922SPierre Ossman 
20747659150cSPierre Ossman 	/*
20757659150cSPierre Ossman 	 * If we use DMA, then it's up to the caller to set the DMA
20767659150cSPierre Ossman 	 * mask, but PIO does not need the hw shim so we set a new
20777659150cSPierre Ossman 	 * mask here in that case.
20787659150cSPierre Ossman 	 */
2079a13abc7bSRichard Röjfors 	if (!(host->flags & (SDHCI_USE_SDMA | SDHCI_USE_ADMA))) {
20807659150cSPierre Ossman 		host->dma_mask = DMA_BIT_MASK(64);
20817659150cSPierre Ossman 		mmc_dev(host->mmc)->dma_mask = &host->dma_mask;
20827659150cSPierre Ossman 	}
20831c6a0718SPierre Ossman 
2084c4687d5fSZhangfei Gao 	if (host->version >= SDHCI_SPEC_300)
2085f2119df6SArindam Nath 		host->max_clk = (caps[0] & SDHCI_CLOCK_V3_BASE_MASK)
2086c4687d5fSZhangfei Gao 			>> SDHCI_CLOCK_BASE_SHIFT;
2087c4687d5fSZhangfei Gao 	else
2088f2119df6SArindam Nath 		host->max_clk = (caps[0] & SDHCI_CLOCK_BASE_MASK)
2089c4687d5fSZhangfei Gao 			>> SDHCI_CLOCK_BASE_SHIFT;
2090c4687d5fSZhangfei Gao 
20914240ff0aSBen Dooks 	host->max_clk *= 1000000;
2092f27f47efSAnton Vorontsov 	if (host->max_clk == 0 || host->quirks &
2093f27f47efSAnton Vorontsov 			SDHCI_QUIRK_CAP_CLOCK_BASE_BROKEN) {
20944240ff0aSBen Dooks 		if (!host->ops->get_max_clock) {
20954240ff0aSBen Dooks 			printk(KERN_ERR
20964240ff0aSBen Dooks 			       "%s: Hardware doesn't specify base clock "
2097b69c9058SPierre Ossman 			       "frequency.\n", mmc_hostname(mmc));
2098b8c86fc5SPierre Ossman 			return -ENODEV;
20991c6a0718SPierre Ossman 		}
21004240ff0aSBen Dooks 		host->max_clk = host->ops->get_max_clock(host);
21014240ff0aSBen Dooks 	}
21021c6a0718SPierre Ossman 
21031c6a0718SPierre Ossman 	host->timeout_clk =
2104f2119df6SArindam Nath 		(caps[0] & SDHCI_TIMEOUT_CLK_MASK) >> SDHCI_TIMEOUT_CLK_SHIFT;
21051c6a0718SPierre Ossman 	if (host->timeout_clk == 0) {
210681b39802SAnton Vorontsov 		if (host->ops->get_timeout_clock) {
210781b39802SAnton Vorontsov 			host->timeout_clk = host->ops->get_timeout_clock(host);
210881b39802SAnton Vorontsov 		} else if (!(host->quirks &
210981b39802SAnton Vorontsov 				SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK)) {
21104240ff0aSBen Dooks 			printk(KERN_ERR
21114240ff0aSBen Dooks 			       "%s: Hardware doesn't specify timeout clock "
2112b69c9058SPierre Ossman 			       "frequency.\n", mmc_hostname(mmc));
2113b8c86fc5SPierre Ossman 			return -ENODEV;
21141c6a0718SPierre Ossman 		}
21154240ff0aSBen Dooks 	}
2116f2119df6SArindam Nath 	if (caps[0] & SDHCI_TIMEOUT_CLK_UNIT)
21171c6a0718SPierre Ossman 		host->timeout_clk *= 1000;
21181c6a0718SPierre Ossman 
21191c6a0718SPierre Ossman 	/*
21201c6a0718SPierre Ossman 	 * Set host parameters.
21211c6a0718SPierre Ossman 	 */
21221c6a0718SPierre Ossman 	mmc->ops = &sdhci_ops;
2123ce5f036bSMarek Szyprowski 	if (host->ops->get_min_clock)
2124a9e58f25SAnton Vorontsov 		mmc->f_min = host->ops->get_min_clock(host);
21250397526dSZhangfei Gao 	else if (host->version >= SDHCI_SPEC_300)
21260397526dSZhangfei Gao 		mmc->f_min = host->max_clk / SDHCI_MAX_DIV_SPEC_300;
2127a9e58f25SAnton Vorontsov 	else
21280397526dSZhangfei Gao 		mmc->f_min = host->max_clk / SDHCI_MAX_DIV_SPEC_200;
212915ec4461SPhilip Rakity 
21301c6a0718SPierre Ossman 	mmc->f_max = host->max_clk;
2131a3c7778fSAndrei Warkentin 	mmc->caps |= MMC_CAP_SDIO_IRQ | MMC_CAP_ERASE;
21325fe23c7fSAnton Vorontsov 
213315ec4461SPhilip Rakity 	/*
213415ec4461SPhilip Rakity 	 * A controller may support 8-bit width, but the board itself
213515ec4461SPhilip Rakity 	 * might not have the pins brought out.  Boards that support
213615ec4461SPhilip Rakity 	 * 8-bit width must set "mmc->caps |= MMC_CAP_8_BIT_DATA;" in
213715ec4461SPhilip Rakity 	 * their platform code before calling sdhci_add_host(), and we
213815ec4461SPhilip Rakity 	 * won't assume 8-bit width for hosts without that CAP.
213915ec4461SPhilip Rakity 	 */
21405fe23c7fSAnton Vorontsov 	if (!(host->quirks & SDHCI_QUIRK_FORCE_1_BIT_DATA))
214115ec4461SPhilip Rakity 		mmc->caps |= MMC_CAP_4_BIT_DATA;
21421c6a0718SPierre Ossman 
2143f2119df6SArindam Nath 	if (caps[0] & SDHCI_CAN_DO_HISPD)
2144a29e7e18SZhangfei Gao 		mmc->caps |= MMC_CAP_SD_HIGHSPEED | MMC_CAP_MMC_HIGHSPEED;
21451c6a0718SPierre Ossman 
2146176d1ed4SJaehoon Chung 	if ((host->quirks & SDHCI_QUIRK_BROKEN_CARD_DETECTION) &&
2147176d1ed4SJaehoon Chung 	    mmc_card_is_removable(mmc))
214868d1fb7eSAnton Vorontsov 		mmc->caps |= MMC_CAP_NEEDS_POLL;
214968d1fb7eSAnton Vorontsov 
2150f2119df6SArindam Nath 	/* UHS-I mode(s) supported by the host controller. */
2151f2119df6SArindam Nath 	if (host->version >= SDHCI_SPEC_300)
2152f2119df6SArindam Nath 		mmc->caps |= MMC_CAP_UHS_SDR12 | MMC_CAP_UHS_SDR25;
2153f2119df6SArindam Nath 
2154f2119df6SArindam Nath 	/* SDR104 supports also implies SDR50 support */
2155f2119df6SArindam Nath 	if (caps[1] & SDHCI_SUPPORT_SDR104)
2156f2119df6SArindam Nath 		mmc->caps |= MMC_CAP_UHS_SDR104 | MMC_CAP_UHS_SDR50;
2157f2119df6SArindam Nath 	else if (caps[1] & SDHCI_SUPPORT_SDR50)
2158f2119df6SArindam Nath 		mmc->caps |= MMC_CAP_UHS_SDR50;
2159f2119df6SArindam Nath 
2160f2119df6SArindam Nath 	if (caps[1] & SDHCI_SUPPORT_DDR50)
2161f2119df6SArindam Nath 		mmc->caps |= MMC_CAP_UHS_DDR50;
2162f2119df6SArindam Nath 
2163d6d50a15SArindam Nath 	/* Driver Type(s) (A, C, D) supported by the host */
2164d6d50a15SArindam Nath 	if (caps[1] & SDHCI_DRIVER_TYPE_A)
2165d6d50a15SArindam Nath 		mmc->caps |= MMC_CAP_DRIVER_TYPE_A;
2166d6d50a15SArindam Nath 	if (caps[1] & SDHCI_DRIVER_TYPE_C)
2167d6d50a15SArindam Nath 		mmc->caps |= MMC_CAP_DRIVER_TYPE_C;
2168d6d50a15SArindam Nath 	if (caps[1] & SDHCI_DRIVER_TYPE_D)
2169d6d50a15SArindam Nath 		mmc->caps |= MMC_CAP_DRIVER_TYPE_D;
2170d6d50a15SArindam Nath 
21718f230f45STakashi Iwai 	ocr_avail = 0;
2172f2119df6SArindam Nath 	/*
2173f2119df6SArindam Nath 	 * According to SD Host Controller spec v3.00, if the Host System
2174f2119df6SArindam Nath 	 * can afford more than 150mA, Host Driver should set XPC to 1. Also
2175f2119df6SArindam Nath 	 * the value is meaningful only if Voltage Support in the Capabilities
2176f2119df6SArindam Nath 	 * register is set. The actual current value is 4 times the register
2177f2119df6SArindam Nath 	 * value.
2178f2119df6SArindam Nath 	 */
2179f2119df6SArindam Nath 	max_current_caps = sdhci_readl(host, SDHCI_MAX_CURRENT);
2180f2119df6SArindam Nath 
2181f2119df6SArindam Nath 	if (caps[0] & SDHCI_CAN_VDD_330) {
2182f2119df6SArindam Nath 		int max_current_330;
2183f2119df6SArindam Nath 
21848f230f45STakashi Iwai 		ocr_avail |= MMC_VDD_32_33 | MMC_VDD_33_34;
2185f2119df6SArindam Nath 
2186f2119df6SArindam Nath 		max_current_330 = ((max_current_caps &
2187f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_330_MASK) >>
2188f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_330_SHIFT) *
2189f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_MULTIPLIER;
2190f2119df6SArindam Nath 
2191f2119df6SArindam Nath 		if (max_current_330 > 150)
2192f2119df6SArindam Nath 			mmc->caps |= MMC_CAP_SET_XPC_330;
2193f2119df6SArindam Nath 	}
2194f2119df6SArindam Nath 	if (caps[0] & SDHCI_CAN_VDD_300) {
2195f2119df6SArindam Nath 		int max_current_300;
2196f2119df6SArindam Nath 
21978f230f45STakashi Iwai 		ocr_avail |= MMC_VDD_29_30 | MMC_VDD_30_31;
2198f2119df6SArindam Nath 
2199f2119df6SArindam Nath 		max_current_300 = ((max_current_caps &
2200f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_300_MASK) >>
2201f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_300_SHIFT) *
2202f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_MULTIPLIER;
2203f2119df6SArindam Nath 
2204f2119df6SArindam Nath 		if (max_current_300 > 150)
2205f2119df6SArindam Nath 			mmc->caps |= MMC_CAP_SET_XPC_300;
2206f2119df6SArindam Nath 	}
2207f2119df6SArindam Nath 	if (caps[0] & SDHCI_CAN_VDD_180) {
2208f2119df6SArindam Nath 		int max_current_180;
2209f2119df6SArindam Nath 
22108f230f45STakashi Iwai 		ocr_avail |= MMC_VDD_165_195;
22118f230f45STakashi Iwai 
2212f2119df6SArindam Nath 		max_current_180 = ((max_current_caps &
2213f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_180_MASK) >>
2214f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_180_SHIFT) *
2215f2119df6SArindam Nath 				   SDHCI_MAX_CURRENT_MULTIPLIER;
2216f2119df6SArindam Nath 
2217f2119df6SArindam Nath 		if (max_current_180 > 150)
2218f2119df6SArindam Nath 			mmc->caps |= MMC_CAP_SET_XPC_180;
2219f2119df6SArindam Nath 	}
2220f2119df6SArindam Nath 
22218f230f45STakashi Iwai 	mmc->ocr_avail = ocr_avail;
22228f230f45STakashi Iwai 	mmc->ocr_avail_sdio = ocr_avail;
22238f230f45STakashi Iwai 	if (host->ocr_avail_sdio)
22248f230f45STakashi Iwai 		mmc->ocr_avail_sdio &= host->ocr_avail_sdio;
22258f230f45STakashi Iwai 	mmc->ocr_avail_sd = ocr_avail;
22268f230f45STakashi Iwai 	if (host->ocr_avail_sd)
22278f230f45STakashi Iwai 		mmc->ocr_avail_sd &= host->ocr_avail_sd;
22288f230f45STakashi Iwai 	else /* normal SD controllers don't support 1.8V */
22298f230f45STakashi Iwai 		mmc->ocr_avail_sd &= ~MMC_VDD_165_195;
22308f230f45STakashi Iwai 	mmc->ocr_avail_mmc = ocr_avail;
22318f230f45STakashi Iwai 	if (host->ocr_avail_mmc)
22328f230f45STakashi Iwai 		mmc->ocr_avail_mmc &= host->ocr_avail_mmc;
22331c6a0718SPierre Ossman 
22341c6a0718SPierre Ossman 	if (mmc->ocr_avail == 0) {
22351c6a0718SPierre Ossman 		printk(KERN_ERR "%s: Hardware doesn't report any "
2236b69c9058SPierre Ossman 			"support voltages.\n", mmc_hostname(mmc));
2237b8c86fc5SPierre Ossman 		return -ENODEV;
22381c6a0718SPierre Ossman 	}
22391c6a0718SPierre Ossman 
22401c6a0718SPierre Ossman 	spin_lock_init(&host->lock);
22411c6a0718SPierre Ossman 
22421c6a0718SPierre Ossman 	/*
22432134a922SPierre Ossman 	 * Maximum number of segments. Depends on if the hardware
22442134a922SPierre Ossman 	 * can do scatter/gather or not.
22451c6a0718SPierre Ossman 	 */
22462134a922SPierre Ossman 	if (host->flags & SDHCI_USE_ADMA)
2247a36274e0SMartin K. Petersen 		mmc->max_segs = 128;
2248a13abc7bSRichard Röjfors 	else if (host->flags & SDHCI_USE_SDMA)
2249a36274e0SMartin K. Petersen 		mmc->max_segs = 1;
22502134a922SPierre Ossman 	else /* PIO */
2251a36274e0SMartin K. Petersen 		mmc->max_segs = 128;
22521c6a0718SPierre Ossman 
22531c6a0718SPierre Ossman 	/*
22541c6a0718SPierre Ossman 	 * Maximum number of sectors in one transfer. Limited by DMA boundary
22551c6a0718SPierre Ossman 	 * size (512KiB).
22561c6a0718SPierre Ossman 	 */
22571c6a0718SPierre Ossman 	mmc->max_req_size = 524288;
22581c6a0718SPierre Ossman 
22591c6a0718SPierre Ossman 	/*
22601c6a0718SPierre Ossman 	 * Maximum segment size. Could be one segment with the maximum number
22612134a922SPierre Ossman 	 * of bytes. When doing hardware scatter/gather, each entry cannot
22622134a922SPierre Ossman 	 * be larger than 64 KiB though.
22631c6a0718SPierre Ossman 	 */
226430652aa3SOlof Johansson 	if (host->flags & SDHCI_USE_ADMA) {
226530652aa3SOlof Johansson 		if (host->quirks & SDHCI_QUIRK_BROKEN_ADMA_ZEROLEN_DESC)
226630652aa3SOlof Johansson 			mmc->max_seg_size = 65535;
22672134a922SPierre Ossman 		else
226830652aa3SOlof Johansson 			mmc->max_seg_size = 65536;
226930652aa3SOlof Johansson 	} else {
22701c6a0718SPierre Ossman 		mmc->max_seg_size = mmc->max_req_size;
227130652aa3SOlof Johansson 	}
22721c6a0718SPierre Ossman 
22731c6a0718SPierre Ossman 	/*
22741c6a0718SPierre Ossman 	 * Maximum block size. This varies from controller to controller and
22751c6a0718SPierre Ossman 	 * is specified in the capabilities register.
22761c6a0718SPierre Ossman 	 */
22770633f654SAnton Vorontsov 	if (host->quirks & SDHCI_QUIRK_FORCE_BLK_SZ_2048) {
22780633f654SAnton Vorontsov 		mmc->max_blk_size = 2;
22790633f654SAnton Vorontsov 	} else {
2280f2119df6SArindam Nath 		mmc->max_blk_size = (caps[0] & SDHCI_MAX_BLOCK_MASK) >>
22810633f654SAnton Vorontsov 				SDHCI_MAX_BLOCK_SHIFT;
22821c6a0718SPierre Ossman 		if (mmc->max_blk_size >= 3) {
2283b69c9058SPierre Ossman 			printk(KERN_WARNING "%s: Invalid maximum block size, "
2284b69c9058SPierre Ossman 				"assuming 512 bytes\n", mmc_hostname(mmc));
22850633f654SAnton Vorontsov 			mmc->max_blk_size = 0;
22860633f654SAnton Vorontsov 		}
22870633f654SAnton Vorontsov 	}
22880633f654SAnton Vorontsov 
22891c6a0718SPierre Ossman 	mmc->max_blk_size = 512 << mmc->max_blk_size;
22901c6a0718SPierre Ossman 
22911c6a0718SPierre Ossman 	/*
22921c6a0718SPierre Ossman 	 * Maximum block count.
22931c6a0718SPierre Ossman 	 */
22941388eefdSBen Dooks 	mmc->max_blk_count = (host->quirks & SDHCI_QUIRK_NO_MULTIBLOCK) ? 1 : 65535;
22951c6a0718SPierre Ossman 
22961c6a0718SPierre Ossman 	/*
22971c6a0718SPierre Ossman 	 * Init tasklets.
22981c6a0718SPierre Ossman 	 */
22991c6a0718SPierre Ossman 	tasklet_init(&host->card_tasklet,
23001c6a0718SPierre Ossman 		sdhci_tasklet_card, (unsigned long)host);
23011c6a0718SPierre Ossman 	tasklet_init(&host->finish_tasklet,
23021c6a0718SPierre Ossman 		sdhci_tasklet_finish, (unsigned long)host);
23031c6a0718SPierre Ossman 
23041c6a0718SPierre Ossman 	setup_timer(&host->timer, sdhci_timeout_timer, (unsigned long)host);
23051c6a0718SPierre Ossman 
23061c6a0718SPierre Ossman 	ret = request_irq(host->irq, sdhci_irq, IRQF_SHARED,
2307b69c9058SPierre Ossman 		mmc_hostname(mmc), host);
23081c6a0718SPierre Ossman 	if (ret)
23091c6a0718SPierre Ossman 		goto untasklet;
23101c6a0718SPierre Ossman 
23119bea3c85SMarek Szyprowski 	host->vmmc = regulator_get(mmc_dev(mmc), "vmmc");
23129bea3c85SMarek Szyprowski 	if (IS_ERR(host->vmmc)) {
23139bea3c85SMarek Szyprowski 		printk(KERN_INFO "%s: no vmmc regulator found\n", mmc_hostname(mmc));
23149bea3c85SMarek Szyprowski 		host->vmmc = NULL;
23159bea3c85SMarek Szyprowski 	} else {
23169bea3c85SMarek Szyprowski 		regulator_enable(host->vmmc);
23179bea3c85SMarek Szyprowski 	}
23189bea3c85SMarek Szyprowski 
23192f4cbb3dSNicolas Pitre 	sdhci_init(host, 0);
23201c6a0718SPierre Ossman 
23211c6a0718SPierre Ossman #ifdef CONFIG_MMC_DEBUG
23221c6a0718SPierre Ossman 	sdhci_dumpregs(host);
23231c6a0718SPierre Ossman #endif
23241c6a0718SPierre Ossman 
2325f9134319SPierre Ossman #ifdef SDHCI_USE_LEDS_CLASS
23265dbace0cSHelmut Schaa 	snprintf(host->led_name, sizeof(host->led_name),
23275dbace0cSHelmut Schaa 		"%s::", mmc_hostname(mmc));
23285dbace0cSHelmut Schaa 	host->led.name = host->led_name;
23292f730fecSPierre Ossman 	host->led.brightness = LED_OFF;
23302f730fecSPierre Ossman 	host->led.default_trigger = mmc_hostname(mmc);
23312f730fecSPierre Ossman 	host->led.brightness_set = sdhci_led_control;
23322f730fecSPierre Ossman 
2333b8c86fc5SPierre Ossman 	ret = led_classdev_register(mmc_dev(mmc), &host->led);
23342f730fecSPierre Ossman 	if (ret)
23352f730fecSPierre Ossman 		goto reset;
23362f730fecSPierre Ossman #endif
23372f730fecSPierre Ossman 
23381c6a0718SPierre Ossman 	mmiowb();
23391c6a0718SPierre Ossman 
23401c6a0718SPierre Ossman 	mmc_add_host(mmc);
23411c6a0718SPierre Ossman 
2342a13abc7bSRichard Röjfors 	printk(KERN_INFO "%s: SDHCI controller on %s [%s] using %s\n",
2343d1b26863SKay Sievers 		mmc_hostname(mmc), host->hw_name, dev_name(mmc_dev(mmc)),
2344a13abc7bSRichard Röjfors 		(host->flags & SDHCI_USE_ADMA) ? "ADMA" :
2345a13abc7bSRichard Röjfors 		(host->flags & SDHCI_USE_SDMA) ? "DMA" : "PIO");
23461c6a0718SPierre Ossman 
23477260cf5eSAnton Vorontsov 	sdhci_enable_card_detection(host);
23487260cf5eSAnton Vorontsov 
23491c6a0718SPierre Ossman 	return 0;
23501c6a0718SPierre Ossman 
2351f9134319SPierre Ossman #ifdef SDHCI_USE_LEDS_CLASS
23522f730fecSPierre Ossman reset:
23532f730fecSPierre Ossman 	sdhci_reset(host, SDHCI_RESET_ALL);
23542f730fecSPierre Ossman 	free_irq(host->irq, host);
23552f730fecSPierre Ossman #endif
23561c6a0718SPierre Ossman untasklet:
23571c6a0718SPierre Ossman 	tasklet_kill(&host->card_tasklet);
23581c6a0718SPierre Ossman 	tasklet_kill(&host->finish_tasklet);
23591c6a0718SPierre Ossman 
23601c6a0718SPierre Ossman 	return ret;
23611c6a0718SPierre Ossman }
23621c6a0718SPierre Ossman 
2363b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_add_host);
2364b8c86fc5SPierre Ossman 
23651e72859eSPierre Ossman void sdhci_remove_host(struct sdhci_host *host, int dead)
23661c6a0718SPierre Ossman {
23671e72859eSPierre Ossman 	unsigned long flags;
23681e72859eSPierre Ossman 
23691e72859eSPierre Ossman 	if (dead) {
23701e72859eSPierre Ossman 		spin_lock_irqsave(&host->lock, flags);
23711e72859eSPierre Ossman 
23721e72859eSPierre Ossman 		host->flags |= SDHCI_DEVICE_DEAD;
23731e72859eSPierre Ossman 
23741e72859eSPierre Ossman 		if (host->mrq) {
23751e72859eSPierre Ossman 			printk(KERN_ERR "%s: Controller removed during "
23761e72859eSPierre Ossman 				" transfer!\n", mmc_hostname(host->mmc));
23771e72859eSPierre Ossman 
23781e72859eSPierre Ossman 			host->mrq->cmd->error = -ENOMEDIUM;
23791e72859eSPierre Ossman 			tasklet_schedule(&host->finish_tasklet);
23801e72859eSPierre Ossman 		}
23811e72859eSPierre Ossman 
23821e72859eSPierre Ossman 		spin_unlock_irqrestore(&host->lock, flags);
23831e72859eSPierre Ossman 	}
23841e72859eSPierre Ossman 
23857260cf5eSAnton Vorontsov 	sdhci_disable_card_detection(host);
23867260cf5eSAnton Vorontsov 
2387b8c86fc5SPierre Ossman 	mmc_remove_host(host->mmc);
23881c6a0718SPierre Ossman 
2389f9134319SPierre Ossman #ifdef SDHCI_USE_LEDS_CLASS
23902f730fecSPierre Ossman 	led_classdev_unregister(&host->led);
23912f730fecSPierre Ossman #endif
23922f730fecSPierre Ossman 
23931e72859eSPierre Ossman 	if (!dead)
23941c6a0718SPierre Ossman 		sdhci_reset(host, SDHCI_RESET_ALL);
23951c6a0718SPierre Ossman 
23961c6a0718SPierre Ossman 	free_irq(host->irq, host);
23971c6a0718SPierre Ossman 
23981c6a0718SPierre Ossman 	del_timer_sync(&host->timer);
23991c6a0718SPierre Ossman 
24001c6a0718SPierre Ossman 	tasklet_kill(&host->card_tasklet);
24011c6a0718SPierre Ossman 	tasklet_kill(&host->finish_tasklet);
24022134a922SPierre Ossman 
24039bea3c85SMarek Szyprowski 	if (host->vmmc) {
24049bea3c85SMarek Szyprowski 		regulator_disable(host->vmmc);
24059bea3c85SMarek Szyprowski 		regulator_put(host->vmmc);
24069bea3c85SMarek Szyprowski 	}
24079bea3c85SMarek Szyprowski 
24082134a922SPierre Ossman 	kfree(host->adma_desc);
24092134a922SPierre Ossman 	kfree(host->align_buffer);
24102134a922SPierre Ossman 
24112134a922SPierre Ossman 	host->adma_desc = NULL;
24122134a922SPierre Ossman 	host->align_buffer = NULL;
24131c6a0718SPierre Ossman }
24141c6a0718SPierre Ossman 
2415b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_remove_host);
2416b8c86fc5SPierre Ossman 
2417b8c86fc5SPierre Ossman void sdhci_free_host(struct sdhci_host *host)
24181c6a0718SPierre Ossman {
2419b8c86fc5SPierre Ossman 	mmc_free_host(host->mmc);
24201c6a0718SPierre Ossman }
24211c6a0718SPierre Ossman 
2422b8c86fc5SPierre Ossman EXPORT_SYMBOL_GPL(sdhci_free_host);
24231c6a0718SPierre Ossman 
24241c6a0718SPierre Ossman /*****************************************************************************\
24251c6a0718SPierre Ossman  *                                                                           *
24261c6a0718SPierre Ossman  * Driver init/exit                                                          *
24271c6a0718SPierre Ossman  *                                                                           *
24281c6a0718SPierre Ossman \*****************************************************************************/
24291c6a0718SPierre Ossman 
24301c6a0718SPierre Ossman static int __init sdhci_drv_init(void)
24311c6a0718SPierre Ossman {
24321c6a0718SPierre Ossman 	printk(KERN_INFO DRIVER_NAME
24331c6a0718SPierre Ossman 		": Secure Digital Host Controller Interface driver\n");
24341c6a0718SPierre Ossman 	printk(KERN_INFO DRIVER_NAME ": Copyright(c) Pierre Ossman\n");
24351c6a0718SPierre Ossman 
2436b8c86fc5SPierre Ossman 	return 0;
24371c6a0718SPierre Ossman }
24381c6a0718SPierre Ossman 
24391c6a0718SPierre Ossman static void __exit sdhci_drv_exit(void)
24401c6a0718SPierre Ossman {
24411c6a0718SPierre Ossman }
24421c6a0718SPierre Ossman 
24431c6a0718SPierre Ossman module_init(sdhci_drv_init);
24441c6a0718SPierre Ossman module_exit(sdhci_drv_exit);
24451c6a0718SPierre Ossman 
24461c6a0718SPierre Ossman module_param(debug_quirks, uint, 0444);
24471c6a0718SPierre Ossman 
244832710e8fSPierre Ossman MODULE_AUTHOR("Pierre Ossman <pierre@ossman.eu>");
2449b8c86fc5SPierre Ossman MODULE_DESCRIPTION("Secure Digital Host Controller Interface core driver");
24501c6a0718SPierre Ossman MODULE_LICENSE("GPL");
24511c6a0718SPierre Ossman 
24521c6a0718SPierre Ossman MODULE_PARM_DESC(debug_quirks, "Force certain quirks.");
2453