diff options
Diffstat (limited to 'drivers/mmc')
-rw-r--r-- | drivers/mmc/card/Kconfig | 1 | ||||
-rw-r--r-- | drivers/mmc/card/sdio_uart.c | 13 | ||||
-rw-r--r-- | drivers/mmc/core/Kconfig | 3 | ||||
-rw-r--r-- | drivers/mmc/host/Kconfig | 22 | ||||
-rw-r--r-- | drivers/mmc/host/dw_mmc-pltfm.c | 7 | ||||
-rw-r--r-- | drivers/mmc/host/mmci.c | 306 | ||||
-rw-r--r-- | drivers/mmc/host/mmci.h | 3 | ||||
-rw-r--r-- | drivers/mmc/host/mxs-mmc.c | 6 | ||||
-rw-r--r-- | drivers/mmc/host/rtsx_pci_sdmmc.c | 18 | ||||
-rw-r--r-- | drivers/mmc/host/sdhci-s3c.c | 7 |
10 files changed, 226 insertions, 160 deletions
diff --git a/drivers/mmc/card/Kconfig b/drivers/mmc/card/Kconfig index 3b1f783bf924..5562308699bc 100644 --- a/drivers/mmc/card/Kconfig +++ b/drivers/mmc/card/Kconfig | |||
@@ -52,6 +52,7 @@ config MMC_BLOCK_BOUNCE | |||
52 | 52 | ||
53 | config SDIO_UART | 53 | config SDIO_UART |
54 | tristate "SDIO UART/GPS class support" | 54 | tristate "SDIO UART/GPS class support" |
55 | depends on TTY | ||
55 | help | 56 | help |
56 | SDIO function driver for SDIO cards that implements the UART | 57 | SDIO function driver for SDIO cards that implements the UART |
57 | class, as well as the GPS class which appears like a UART. | 58 | class, as well as the GPS class which appears like a UART. |
diff --git a/drivers/mmc/card/sdio_uart.c b/drivers/mmc/card/sdio_uart.c index bd57a11acc79..c931dfe6a59c 100644 --- a/drivers/mmc/card/sdio_uart.c +++ b/drivers/mmc/card/sdio_uart.c | |||
@@ -381,7 +381,6 @@ static void sdio_uart_stop_rx(struct sdio_uart_port *port) | |||
381 | static void sdio_uart_receive_chars(struct sdio_uart_port *port, | 381 | static void sdio_uart_receive_chars(struct sdio_uart_port *port, |
382 | unsigned int *status) | 382 | unsigned int *status) |
383 | { | 383 | { |
384 | struct tty_struct *tty = tty_port_tty_get(&port->port); | ||
385 | unsigned int ch, flag; | 384 | unsigned int ch, flag; |
386 | int max_count = 256; | 385 | int max_count = 256; |
387 | 386 | ||
@@ -418,23 +417,19 @@ static void sdio_uart_receive_chars(struct sdio_uart_port *port, | |||
418 | } | 417 | } |
419 | 418 | ||
420 | if ((*status & port->ignore_status_mask & ~UART_LSR_OE) == 0) | 419 | if ((*status & port->ignore_status_mask & ~UART_LSR_OE) == 0) |
421 | if (tty) | 420 | tty_insert_flip_char(&port->port, ch, flag); |
422 | tty_insert_flip_char(tty, ch, flag); | ||
423 | 421 | ||
424 | /* | 422 | /* |
425 | * Overrun is special. Since it's reported immediately, | 423 | * Overrun is special. Since it's reported immediately, |
426 | * it doesn't affect the current character. | 424 | * it doesn't affect the current character. |
427 | */ | 425 | */ |
428 | if (*status & ~port->ignore_status_mask & UART_LSR_OE) | 426 | if (*status & ~port->ignore_status_mask & UART_LSR_OE) |
429 | if (tty) | 427 | tty_insert_flip_char(&port->port, 0, TTY_OVERRUN); |
430 | tty_insert_flip_char(tty, 0, TTY_OVERRUN); | ||
431 | 428 | ||
432 | *status = sdio_in(port, UART_LSR); | 429 | *status = sdio_in(port, UART_LSR); |
433 | } while ((*status & UART_LSR_DR) && (max_count-- > 0)); | 430 | } while ((*status & UART_LSR_DR) && (max_count-- > 0)); |
434 | if (tty) { | 431 | |
435 | tty_flip_buffer_push(tty); | 432 | tty_flip_buffer_push(&port->port); |
436 | tty_kref_put(tty); | ||
437 | } | ||
438 | } | 433 | } |
439 | 434 | ||
440 | static void sdio_uart_transmit_chars(struct sdio_uart_port *port) | 435 | static void sdio_uart_transmit_chars(struct sdio_uart_port *port) |
diff --git a/drivers/mmc/core/Kconfig b/drivers/mmc/core/Kconfig index ef103871517f..269d072ef55e 100644 --- a/drivers/mmc/core/Kconfig +++ b/drivers/mmc/core/Kconfig | |||
@@ -18,8 +18,7 @@ config MMC_UNSAFE_RESUME | |||
18 | module parameter "removable=0" or "removable=1". | 18 | module parameter "removable=0" or "removable=1". |
19 | 19 | ||
20 | config MMC_CLKGATE | 20 | config MMC_CLKGATE |
21 | bool "MMC host clock gating (EXPERIMENTAL)" | 21 | bool "MMC host clock gating" |
22 | depends on EXPERIMENTAL | ||
23 | help | 22 | help |
24 | This will attempt to aggressively gate the clock to the MMC card. | 23 | This will attempt to aggressively gate the clock to the MMC card. |
25 | This is done to save power due to gating off the logic and bus | 24 | This is done to save power due to gating off the logic and bus |
diff --git a/drivers/mmc/host/Kconfig b/drivers/mmc/host/Kconfig index 961891fe61bb..d88219e1d86e 100644 --- a/drivers/mmc/host/Kconfig +++ b/drivers/mmc/host/Kconfig | |||
@@ -69,7 +69,7 @@ config MMC_SDHCI_PCI | |||
69 | If unsure, say N. | 69 | If unsure, say N. |
70 | 70 | ||
71 | config MMC_RICOH_MMC | 71 | config MMC_RICOH_MMC |
72 | bool "Ricoh MMC Controller Disabler (EXPERIMENTAL)" | 72 | bool "Ricoh MMC Controller Disabler" |
73 | depends on MMC_SDHCI_PCI | 73 | depends on MMC_SDHCI_PCI |
74 | help | 74 | help |
75 | This adds a pci quirk to disable Ricoh MMC Controller. This | 75 | This adds a pci quirk to disable Ricoh MMC Controller. This |
@@ -186,9 +186,6 @@ config MMC_SDHCI_S3C | |||
186 | often referrered to as the HSMMC block in some of the Samsung S3C | 186 | often referrered to as the HSMMC block in some of the Samsung S3C |
187 | range of SoC. | 187 | range of SoC. |
188 | 188 | ||
189 | Note, due to the problems with DMA, the DMA support is only | ||
190 | available with CONFIG_EXPERIMENTAL is selected. | ||
191 | |||
192 | If you have a controller with this interface, say Y or M here. | 189 | If you have a controller with this interface, say Y or M here. |
193 | 190 | ||
194 | If unsure, say N. | 191 | If unsure, say N. |
@@ -233,7 +230,7 @@ config MMC_SDHCI_SPEAR | |||
233 | 230 | ||
234 | config MMC_SDHCI_S3C_DMA | 231 | config MMC_SDHCI_S3C_DMA |
235 | bool "DMA support on S3C SDHCI" | 232 | bool "DMA support on S3C SDHCI" |
236 | depends on MMC_SDHCI_S3C && EXPERIMENTAL | 233 | depends on MMC_SDHCI_S3C |
237 | help | 234 | help |
238 | Enable DMA support on the Samsung S3C SDHCI glue. The DMA | 235 | Enable DMA support on the Samsung S3C SDHCI glue. The DMA |
239 | has proved to be problematic if the controller encounters | 236 | has proved to be problematic if the controller encounters |
@@ -341,8 +338,8 @@ config MMC_MXS | |||
341 | If unsure, say N. | 338 | If unsure, say N. |
342 | 339 | ||
343 | config MMC_TIFM_SD | 340 | config MMC_TIFM_SD |
344 | tristate "TI Flash Media MMC/SD Interface support (EXPERIMENTAL)" | 341 | tristate "TI Flash Media MMC/SD Interface support" |
345 | depends on EXPERIMENTAL && PCI | 342 | depends on PCI |
346 | select TIFM_CORE | 343 | select TIFM_CORE |
347 | help | 344 | help |
348 | Say Y here if you want to be able to access MMC/SD cards with | 345 | Say Y here if you want to be able to access MMC/SD cards with |
@@ -428,8 +425,7 @@ config MMC_S3C_PIO | |||
428 | the S3C MCI driver. | 425 | the S3C MCI driver. |
429 | 426 | ||
430 | config MMC_S3C_DMA | 427 | config MMC_S3C_DMA |
431 | bool "Use DMA transfers only (EXPERIMENTAL)" | 428 | bool "Use DMA transfers only" |
432 | depends on EXPERIMENTAL | ||
433 | help | 429 | help |
434 | Use DMA to transfer data between memory and the hardare. | 430 | Use DMA to transfer data between memory and the hardare. |
435 | 431 | ||
@@ -438,7 +434,7 @@ config MMC_S3C_DMA | |||
438 | option is useful. | 434 | option is useful. |
439 | 435 | ||
440 | config MMC_S3C_PIODMA | 436 | config MMC_S3C_PIODMA |
441 | bool "Support for both PIO and DMA (EXPERIMENTAL)" | 437 | bool "Support for both PIO and DMA" |
442 | help | 438 | help |
443 | Compile both the PIO and DMA transfer routines into the | 439 | Compile both the PIO and DMA transfer routines into the |
444 | driver and let the platform select at run-time which one | 440 | driver and let the platform select at run-time which one |
@@ -449,8 +445,8 @@ config MMC_S3C_PIODMA | |||
449 | endchoice | 445 | endchoice |
450 | 446 | ||
451 | config MMC_SDRICOH_CS | 447 | config MMC_SDRICOH_CS |
452 | tristate "MMC/SD driver for Ricoh Bay1Controllers (EXPERIMENTAL)" | 448 | tristate "MMC/SD driver for Ricoh Bay1Controllers" |
453 | depends on EXPERIMENTAL && PCI && PCMCIA | 449 | depends on PCI && PCMCIA |
454 | help | 450 | help |
455 | Say Y here if your Notebook reports a Ricoh Bay1Controller PCMCIA | 451 | Say Y here if your Notebook reports a Ricoh Bay1Controller PCMCIA |
456 | card whenever you insert a MMC or SD card into the card slot. | 452 | card whenever you insert a MMC or SD card into the card slot. |
@@ -479,7 +475,7 @@ config MMC_SDHI | |||
479 | 475 | ||
480 | config MMC_CB710 | 476 | config MMC_CB710 |
481 | tristate "ENE CB710 MMC/SD Interface support" | 477 | tristate "ENE CB710 MMC/SD Interface support" |
482 | depends on PCI | 478 | depends on PCI && GENERIC_HARDIRQS |
483 | select CB710_CORE | 479 | select CB710_CORE |
484 | help | 480 | help |
485 | This option enables support for MMC/SD part of ENE CB710/720 Flash | 481 | This option enables support for MMC/SD part of ENE CB710/720 Flash |
diff --git a/drivers/mmc/host/dw_mmc-pltfm.c b/drivers/mmc/host/dw_mmc-pltfm.c index 5e1fb1d2c422..41c27b74b003 100644 --- a/drivers/mmc/host/dw_mmc-pltfm.c +++ b/drivers/mmc/host/dw_mmc-pltfm.c | |||
@@ -10,6 +10,7 @@ | |||
10 | * (at your option) any later version. | 10 | * (at your option) any later version. |
11 | */ | 11 | */ |
12 | 12 | ||
13 | #include <linux/err.h> | ||
13 | #include <linux/interrupt.h> | 14 | #include <linux/interrupt.h> |
14 | #include <linux/module.h> | 15 | #include <linux/module.h> |
15 | #include <linux/io.h> | 16 | #include <linux/io.h> |
@@ -46,9 +47,9 @@ int dw_mci_pltfm_register(struct platform_device *pdev, | |||
46 | host->dev = &pdev->dev; | 47 | host->dev = &pdev->dev; |
47 | host->irq_flags = 0; | 48 | host->irq_flags = 0; |
48 | host->pdata = pdev->dev.platform_data; | 49 | host->pdata = pdev->dev.platform_data; |
49 | host->regs = devm_request_and_ioremap(&pdev->dev, regs); | 50 | host->regs = devm_ioremap_resource(&pdev->dev, regs); |
50 | if (!host->regs) | 51 | if (IS_ERR(host->regs)) |
51 | return -ENOMEM; | 52 | return PTR_ERR(host->regs); |
52 | 53 | ||
53 | if (drv_data && drv_data->init) { | 54 | if (drv_data && drv_data->init) { |
54 | ret = drv_data->init(host); | 55 | ret = drv_data->init(host); |
diff --git a/drivers/mmc/host/mmci.c b/drivers/mmc/host/mmci.c index 150772395cc6..372e921389c8 100644 --- a/drivers/mmc/host/mmci.c +++ b/drivers/mmc/host/mmci.c | |||
@@ -20,6 +20,7 @@ | |||
20 | #include <linux/err.h> | 20 | #include <linux/err.h> |
21 | #include <linux/highmem.h> | 21 | #include <linux/highmem.h> |
22 | #include <linux/log2.h> | 22 | #include <linux/log2.h> |
23 | #include <linux/mmc/pm.h> | ||
23 | #include <linux/mmc/host.h> | 24 | #include <linux/mmc/host.h> |
24 | #include <linux/mmc/card.h> | 25 | #include <linux/mmc/card.h> |
25 | #include <linux/amba/bus.h> | 26 | #include <linux/amba/bus.h> |
@@ -59,6 +60,7 @@ static unsigned int fmax = 515633; | |||
59 | * @blksz_datactrl16: true if Block size is at b16..b30 position in datactrl register | 60 | * @blksz_datactrl16: true if Block size is at b16..b30 position in datactrl register |
60 | * @pwrreg_powerup: power up value for MMCIPOWER register | 61 | * @pwrreg_powerup: power up value for MMCIPOWER register |
61 | * @signal_direction: input/out direction of bus signals can be indicated | 62 | * @signal_direction: input/out direction of bus signals can be indicated |
63 | * @pwrreg_clkgate: MMCIPOWER register must be used to gate the clock | ||
62 | */ | 64 | */ |
63 | struct variant_data { | 65 | struct variant_data { |
64 | unsigned int clkreg; | 66 | unsigned int clkreg; |
@@ -71,6 +73,7 @@ struct variant_data { | |||
71 | bool blksz_datactrl16; | 73 | bool blksz_datactrl16; |
72 | u32 pwrreg_powerup; | 74 | u32 pwrreg_powerup; |
73 | bool signal_direction; | 75 | bool signal_direction; |
76 | bool pwrreg_clkgate; | ||
74 | }; | 77 | }; |
75 | 78 | ||
76 | static struct variant_data variant_arm = { | 79 | static struct variant_data variant_arm = { |
@@ -87,6 +90,14 @@ static struct variant_data variant_arm_extended_fifo = { | |||
87 | .pwrreg_powerup = MCI_PWR_UP, | 90 | .pwrreg_powerup = MCI_PWR_UP, |
88 | }; | 91 | }; |
89 | 92 | ||
93 | static struct variant_data variant_arm_extended_fifo_hwfc = { | ||
94 | .fifosize = 128 * 4, | ||
95 | .fifohalfsize = 64 * 4, | ||
96 | .clkreg_enable = MCI_ARM_HWFCEN, | ||
97 | .datalength_bits = 16, | ||
98 | .pwrreg_powerup = MCI_PWR_UP, | ||
99 | }; | ||
100 | |||
90 | static struct variant_data variant_u300 = { | 101 | static struct variant_data variant_u300 = { |
91 | .fifosize = 16 * 4, | 102 | .fifosize = 16 * 4, |
92 | .fifohalfsize = 8 * 4, | 103 | .fifohalfsize = 8 * 4, |
@@ -95,6 +106,7 @@ static struct variant_data variant_u300 = { | |||
95 | .sdio = true, | 106 | .sdio = true, |
96 | .pwrreg_powerup = MCI_PWR_ON, | 107 | .pwrreg_powerup = MCI_PWR_ON, |
97 | .signal_direction = true, | 108 | .signal_direction = true, |
109 | .pwrreg_clkgate = true, | ||
98 | }; | 110 | }; |
99 | 111 | ||
100 | static struct variant_data variant_nomadik = { | 112 | static struct variant_data variant_nomadik = { |
@@ -106,6 +118,7 @@ static struct variant_data variant_nomadik = { | |||
106 | .st_clkdiv = true, | 118 | .st_clkdiv = true, |
107 | .pwrreg_powerup = MCI_PWR_ON, | 119 | .pwrreg_powerup = MCI_PWR_ON, |
108 | .signal_direction = true, | 120 | .signal_direction = true, |
121 | .pwrreg_clkgate = true, | ||
109 | }; | 122 | }; |
110 | 123 | ||
111 | static struct variant_data variant_ux500 = { | 124 | static struct variant_data variant_ux500 = { |
@@ -118,6 +131,7 @@ static struct variant_data variant_ux500 = { | |||
118 | .st_clkdiv = true, | 131 | .st_clkdiv = true, |
119 | .pwrreg_powerup = MCI_PWR_ON, | 132 | .pwrreg_powerup = MCI_PWR_ON, |
120 | .signal_direction = true, | 133 | .signal_direction = true, |
134 | .pwrreg_clkgate = true, | ||
121 | }; | 135 | }; |
122 | 136 | ||
123 | static struct variant_data variant_ux500v2 = { | 137 | static struct variant_data variant_ux500v2 = { |
@@ -131,9 +145,28 @@ static struct variant_data variant_ux500v2 = { | |||
131 | .blksz_datactrl16 = true, | 145 | .blksz_datactrl16 = true, |
132 | .pwrreg_powerup = MCI_PWR_ON, | 146 | .pwrreg_powerup = MCI_PWR_ON, |
133 | .signal_direction = true, | 147 | .signal_direction = true, |
148 | .pwrreg_clkgate = true, | ||
134 | }; | 149 | }; |
135 | 150 | ||
136 | /* | 151 | /* |
152 | * Validate mmc prerequisites | ||
153 | */ | ||
154 | static int mmci_validate_data(struct mmci_host *host, | ||
155 | struct mmc_data *data) | ||
156 | { | ||
157 | if (!data) | ||
158 | return 0; | ||
159 | |||
160 | if (!is_power_of_2(data->blksz)) { | ||
161 | dev_err(mmc_dev(host->mmc), | ||
162 | "unsupported block size (%d bytes)\n", data->blksz); | ||
163 | return -EINVAL; | ||
164 | } | ||
165 | |||
166 | return 0; | ||
167 | } | ||
168 | |||
169 | /* | ||
137 | * This must be called with host->lock held | 170 | * This must be called with host->lock held |
138 | */ | 171 | */ |
139 | static void mmci_write_clkreg(struct mmci_host *host, u32 clk) | 172 | static void mmci_write_clkreg(struct mmci_host *host, u32 clk) |
@@ -202,6 +235,9 @@ static void mmci_set_clkreg(struct mmci_host *host, unsigned int desired) | |||
202 | if (host->mmc->ios.bus_width == MMC_BUS_WIDTH_8) | 235 | if (host->mmc->ios.bus_width == MMC_BUS_WIDTH_8) |
203 | clk |= MCI_ST_8BIT_BUS; | 236 | clk |= MCI_ST_8BIT_BUS; |
204 | 237 | ||
238 | if (host->mmc->ios.timing == MMC_TIMING_UHS_DDR50) | ||
239 | clk |= MCI_ST_UX500_NEG_EDGE; | ||
240 | |||
205 | mmci_write_clkreg(host, clk); | 241 | mmci_write_clkreg(host, clk); |
206 | } | 242 | } |
207 | 243 | ||
@@ -352,10 +388,33 @@ static inline void mmci_dma_release(struct mmci_host *host) | |||
352 | host->dma_rx_channel = host->dma_tx_channel = NULL; | 388 | host->dma_rx_channel = host->dma_tx_channel = NULL; |
353 | } | 389 | } |
354 | 390 | ||
391 | static void mmci_dma_data_error(struct mmci_host *host) | ||
392 | { | ||
393 | dev_err(mmc_dev(host->mmc), "error during DMA transfer!\n"); | ||
394 | dmaengine_terminate_all(host->dma_current); | ||
395 | host->dma_current = NULL; | ||
396 | host->dma_desc_current = NULL; | ||
397 | host->data->host_cookie = 0; | ||
398 | } | ||
399 | |||
355 | static void mmci_dma_unmap(struct mmci_host *host, struct mmc_data *data) | 400 | static void mmci_dma_unmap(struct mmci_host *host, struct mmc_data *data) |
356 | { | 401 | { |
357 | struct dma_chan *chan = host->dma_current; | 402 | struct dma_chan *chan; |
358 | enum dma_data_direction dir; | 403 | enum dma_data_direction dir; |
404 | |||
405 | if (data->flags & MMC_DATA_READ) { | ||
406 | dir = DMA_FROM_DEVICE; | ||
407 | chan = host->dma_rx_channel; | ||
408 | } else { | ||
409 | dir = DMA_TO_DEVICE; | ||
410 | chan = host->dma_tx_channel; | ||
411 | } | ||
412 | |||
413 | dma_unmap_sg(chan->device->dev, data->sg, data->sg_len, dir); | ||
414 | } | ||
415 | |||
416 | static void mmci_dma_finalize(struct mmci_host *host, struct mmc_data *data) | ||
417 | { | ||
359 | u32 status; | 418 | u32 status; |
360 | int i; | 419 | int i; |
361 | 420 | ||
@@ -374,19 +433,13 @@ static void mmci_dma_unmap(struct mmci_host *host, struct mmc_data *data) | |||
374 | * contiguous buffers. On TX, we'll get a FIFO underrun error. | 433 | * contiguous buffers. On TX, we'll get a FIFO underrun error. |
375 | */ | 434 | */ |
376 | if (status & MCI_RXDATAAVLBLMASK) { | 435 | if (status & MCI_RXDATAAVLBLMASK) { |
377 | dmaengine_terminate_all(chan); | 436 | mmci_dma_data_error(host); |
378 | if (!data->error) | 437 | if (!data->error) |
379 | data->error = -EIO; | 438 | data->error = -EIO; |
380 | } | 439 | } |
381 | 440 | ||
382 | if (data->flags & MMC_DATA_WRITE) { | ||
383 | dir = DMA_TO_DEVICE; | ||
384 | } else { | ||
385 | dir = DMA_FROM_DEVICE; | ||
386 | } | ||
387 | |||
388 | if (!data->host_cookie) | 441 | if (!data->host_cookie) |
389 | dma_unmap_sg(chan->device->dev, data->sg, data->sg_len, dir); | 442 | mmci_dma_unmap(host, data); |
390 | 443 | ||
391 | /* | 444 | /* |
392 | * Use of DMA with scatter-gather is impossible. | 445 | * Use of DMA with scatter-gather is impossible. |
@@ -396,16 +449,15 @@ static void mmci_dma_unmap(struct mmci_host *host, struct mmc_data *data) | |||
396 | dev_err(mmc_dev(host->mmc), "buggy DMA detected. Taking evasive action.\n"); | 449 | dev_err(mmc_dev(host->mmc), "buggy DMA detected. Taking evasive action.\n"); |
397 | mmci_dma_release(host); | 450 | mmci_dma_release(host); |
398 | } | 451 | } |
399 | } | ||
400 | 452 | ||
401 | static void mmci_dma_data_error(struct mmci_host *host) | 453 | host->dma_current = NULL; |
402 | { | 454 | host->dma_desc_current = NULL; |
403 | dev_err(mmc_dev(host->mmc), "error during DMA transfer!\n"); | ||
404 | dmaengine_terminate_all(host->dma_current); | ||
405 | } | 455 | } |
406 | 456 | ||
407 | static int mmci_dma_prep_data(struct mmci_host *host, struct mmc_data *data, | 457 | /* prepares DMA channel and DMA descriptor, returns non-zero on failure */ |
408 | struct mmci_host_next *next) | 458 | static int __mmci_dma_prep_data(struct mmci_host *host, struct mmc_data *data, |
459 | struct dma_chan **dma_chan, | ||
460 | struct dma_async_tx_descriptor **dma_desc) | ||
409 | { | 461 | { |
410 | struct variant_data *variant = host->variant; | 462 | struct variant_data *variant = host->variant; |
411 | struct dma_slave_config conf = { | 463 | struct dma_slave_config conf = { |
@@ -423,16 +475,6 @@ static int mmci_dma_prep_data(struct mmci_host *host, struct mmc_data *data, | |||
423 | enum dma_data_direction buffer_dirn; | 475 | enum dma_data_direction buffer_dirn; |
424 | int nr_sg; | 476 | int nr_sg; |
425 | 477 | ||
426 | /* Check if next job is already prepared */ | ||
427 | if (data->host_cookie && !next && | ||
428 | host->dma_current && host->dma_desc_current) | ||
429 | return 0; | ||
430 | |||
431 | if (!next) { | ||
432 | host->dma_current = NULL; | ||
433 | host->dma_desc_current = NULL; | ||
434 | } | ||
435 | |||
436 | if (data->flags & MMC_DATA_READ) { | 478 | if (data->flags & MMC_DATA_READ) { |
437 | conf.direction = DMA_DEV_TO_MEM; | 479 | conf.direction = DMA_DEV_TO_MEM; |
438 | buffer_dirn = DMA_FROM_DEVICE; | 480 | buffer_dirn = DMA_FROM_DEVICE; |
@@ -462,29 +504,41 @@ static int mmci_dma_prep_data(struct mmci_host *host, struct mmc_data *data, | |||
462 | if (!desc) | 504 | if (!desc) |
463 | goto unmap_exit; | 505 | goto unmap_exit; |
464 | 506 | ||
465 | if (next) { | 507 | *dma_chan = chan; |
466 | next->dma_chan = chan; | 508 | *dma_desc = desc; |
467 | next->dma_desc = desc; | ||
468 | } else { | ||
469 | host->dma_current = chan; | ||
470 | host->dma_desc_current = desc; | ||
471 | } | ||
472 | 509 | ||
473 | return 0; | 510 | return 0; |
474 | 511 | ||
475 | unmap_exit: | 512 | unmap_exit: |
476 | if (!next) | ||
477 | dmaengine_terminate_all(chan); | ||
478 | dma_unmap_sg(device->dev, data->sg, data->sg_len, buffer_dirn); | 513 | dma_unmap_sg(device->dev, data->sg, data->sg_len, buffer_dirn); |
479 | return -ENOMEM; | 514 | return -ENOMEM; |
480 | } | 515 | } |
481 | 516 | ||
517 | static inline int mmci_dma_prep_data(struct mmci_host *host, | ||
518 | struct mmc_data *data) | ||
519 | { | ||
520 | /* Check if next job is already prepared. */ | ||
521 | if (host->dma_current && host->dma_desc_current) | ||
522 | return 0; | ||
523 | |||
524 | /* No job were prepared thus do it now. */ | ||
525 | return __mmci_dma_prep_data(host, data, &host->dma_current, | ||
526 | &host->dma_desc_current); | ||
527 | } | ||
528 | |||
529 | static inline int mmci_dma_prep_next(struct mmci_host *host, | ||
530 | struct mmc_data *data) | ||
531 | { | ||
532 | struct mmci_host_next *nd = &host->next_data; | ||
533 | return __mmci_dma_prep_data(host, data, &nd->dma_chan, &nd->dma_desc); | ||
534 | } | ||
535 | |||
482 | static int mmci_dma_start_data(struct mmci_host *host, unsigned int datactrl) | 536 | static int mmci_dma_start_data(struct mmci_host *host, unsigned int datactrl) |
483 | { | 537 | { |
484 | int ret; | 538 | int ret; |
485 | struct mmc_data *data = host->data; | 539 | struct mmc_data *data = host->data; |
486 | 540 | ||
487 | ret = mmci_dma_prep_data(host, host->data, NULL); | 541 | ret = mmci_dma_prep_data(host, host->data); |
488 | if (ret) | 542 | if (ret) |
489 | return ret; | 543 | return ret; |
490 | 544 | ||
@@ -514,19 +568,11 @@ static void mmci_get_next_data(struct mmci_host *host, struct mmc_data *data) | |||
514 | { | 568 | { |
515 | struct mmci_host_next *next = &host->next_data; | 569 | struct mmci_host_next *next = &host->next_data; |
516 | 570 | ||
517 | if (data->host_cookie && data->host_cookie != next->cookie) { | 571 | WARN_ON(data->host_cookie && data->host_cookie != next->cookie); |
518 | pr_warning("[%s] invalid cookie: data->host_cookie %d" | 572 | WARN_ON(!data->host_cookie && (next->dma_desc || next->dma_chan)); |
519 | " host->next_data.cookie %d\n", | ||
520 | __func__, data->host_cookie, host->next_data.cookie); | ||
521 | data->host_cookie = 0; | ||
522 | } | ||
523 | |||
524 | if (!data->host_cookie) | ||
525 | return; | ||
526 | 573 | ||
527 | host->dma_desc_current = next->dma_desc; | 574 | host->dma_desc_current = next->dma_desc; |
528 | host->dma_current = next->dma_chan; | 575 | host->dma_current = next->dma_chan; |
529 | |||
530 | next->dma_desc = NULL; | 576 | next->dma_desc = NULL; |
531 | next->dma_chan = NULL; | 577 | next->dma_chan = NULL; |
532 | } | 578 | } |
@@ -541,19 +587,13 @@ static void mmci_pre_request(struct mmc_host *mmc, struct mmc_request *mrq, | |||
541 | if (!data) | 587 | if (!data) |
542 | return; | 588 | return; |
543 | 589 | ||
544 | if (data->host_cookie) { | 590 | BUG_ON(data->host_cookie); |
545 | data->host_cookie = 0; | 591 | |
592 | if (mmci_validate_data(host, data)) | ||
546 | return; | 593 | return; |
547 | } | ||
548 | 594 | ||
549 | /* if config for dma */ | 595 | if (!mmci_dma_prep_next(host, data)) |
550 | if (((data->flags & MMC_DATA_WRITE) && host->dma_tx_channel) || | 596 | data->host_cookie = ++nd->cookie < 0 ? 1 : nd->cookie; |
551 | ((data->flags & MMC_DATA_READ) && host->dma_rx_channel)) { | ||
552 | if (mmci_dma_prep_data(host, data, nd)) | ||
553 | data->host_cookie = 0; | ||
554 | else | ||
555 | data->host_cookie = ++nd->cookie < 0 ? 1 : nd->cookie; | ||
556 | } | ||
557 | } | 597 | } |
558 | 598 | ||
559 | static void mmci_post_request(struct mmc_host *mmc, struct mmc_request *mrq, | 599 | static void mmci_post_request(struct mmc_host *mmc, struct mmc_request *mrq, |
@@ -561,29 +601,23 @@ static void mmci_post_request(struct mmc_host *mmc, struct mmc_request *mrq, | |||
561 | { | 601 | { |
562 | struct mmci_host *host = mmc_priv(mmc); | 602 | struct mmci_host *host = mmc_priv(mmc); |
563 | struct mmc_data *data = mrq->data; | 603 | struct mmc_data *data = mrq->data; |
564 | struct dma_chan *chan; | ||
565 | enum dma_data_direction dir; | ||
566 | 604 | ||
567 | if (!data) | 605 | if (!data || !data->host_cookie) |
568 | return; | 606 | return; |
569 | 607 | ||
570 | if (data->flags & MMC_DATA_READ) { | 608 | mmci_dma_unmap(host, data); |
571 | dir = DMA_FROM_DEVICE; | ||
572 | chan = host->dma_rx_channel; | ||
573 | } else { | ||
574 | dir = DMA_TO_DEVICE; | ||
575 | chan = host->dma_tx_channel; | ||
576 | } | ||
577 | 609 | ||
610 | if (err) { | ||
611 | struct mmci_host_next *next = &host->next_data; | ||
612 | struct dma_chan *chan; | ||
613 | if (data->flags & MMC_DATA_READ) | ||
614 | chan = host->dma_rx_channel; | ||
615 | else | ||
616 | chan = host->dma_tx_channel; | ||
617 | dmaengine_terminate_all(chan); | ||
578 | 618 | ||
579 | /* if config for dma */ | 619 | next->dma_desc = NULL; |
580 | if (chan) { | 620 | next->dma_chan = NULL; |
581 | if (err) | ||
582 | dmaengine_terminate_all(chan); | ||
583 | if (data->host_cookie) | ||
584 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, | ||
585 | data->sg_len, dir); | ||
586 | mrq->data->host_cookie = 0; | ||
587 | } | 621 | } |
588 | } | 622 | } |
589 | 623 | ||
@@ -604,6 +638,11 @@ static inline void mmci_dma_unmap(struct mmci_host *host, struct mmc_data *data) | |||
604 | { | 638 | { |
605 | } | 639 | } |
606 | 640 | ||
641 | static inline void mmci_dma_finalize(struct mmci_host *host, | ||
642 | struct mmc_data *data) | ||
643 | { | ||
644 | } | ||
645 | |||
607 | static inline void mmci_dma_data_error(struct mmci_host *host) | 646 | static inline void mmci_dma_data_error(struct mmci_host *host) |
608 | { | 647 | { |
609 | } | 648 | } |
@@ -680,6 +719,9 @@ static void mmci_start_data(struct mmci_host *host, struct mmc_data *data) | |||
680 | mmci_write_clkreg(host, clk); | 719 | mmci_write_clkreg(host, clk); |
681 | } | 720 | } |
682 | 721 | ||
722 | if (host->mmc->ios.timing == MMC_TIMING_UHS_DDR50) | ||
723 | datactrl |= MCI_ST_DPSM_DDRMODE; | ||
724 | |||
683 | /* | 725 | /* |
684 | * Attempt to use DMA operation mode, if this | 726 | * Attempt to use DMA operation mode, if this |
685 | * should fail, fall back to PIO mode | 727 | * should fail, fall back to PIO mode |
@@ -751,8 +793,10 @@ mmci_data_irq(struct mmci_host *host, struct mmc_data *data, | |||
751 | u32 remain, success; | 793 | u32 remain, success; |
752 | 794 | ||
753 | /* Terminate the DMA transfer */ | 795 | /* Terminate the DMA transfer */ |
754 | if (dma_inprogress(host)) | 796 | if (dma_inprogress(host)) { |
755 | mmci_dma_data_error(host); | 797 | mmci_dma_data_error(host); |
798 | mmci_dma_unmap(host, data); | ||
799 | } | ||
756 | 800 | ||
757 | /* | 801 | /* |
758 | * Calculate how far we are into the transfer. Note that | 802 | * Calculate how far we are into the transfer. Note that |
@@ -791,7 +835,7 @@ mmci_data_irq(struct mmci_host *host, struct mmc_data *data, | |||
791 | 835 | ||
792 | if (status & MCI_DATAEND || data->error) { | 836 | if (status & MCI_DATAEND || data->error) { |
793 | if (dma_inprogress(host)) | 837 | if (dma_inprogress(host)) |
794 | mmci_dma_unmap(host, data); | 838 | mmci_dma_finalize(host, data); |
795 | mmci_stop_data(host); | 839 | mmci_stop_data(host); |
796 | 840 | ||
797 | if (!data->error) | 841 | if (!data->error) |
@@ -828,8 +872,10 @@ mmci_cmd_irq(struct mmci_host *host, struct mmc_command *cmd, | |||
828 | if (!cmd->data || cmd->error) { | 872 | if (!cmd->data || cmd->error) { |
829 | if (host->data) { | 873 | if (host->data) { |
830 | /* Terminate the DMA transfer */ | 874 | /* Terminate the DMA transfer */ |
831 | if (dma_inprogress(host)) | 875 | if (dma_inprogress(host)) { |
832 | mmci_dma_data_error(host); | 876 | mmci_dma_data_error(host); |
877 | mmci_dma_unmap(host, host->data); | ||
878 | } | ||
833 | mmci_stop_data(host); | 879 | mmci_stop_data(host); |
834 | } | 880 | } |
835 | mmci_request_end(host, cmd->mrq); | 881 | mmci_request_end(host, cmd->mrq); |
@@ -1055,10 +1101,8 @@ static void mmci_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
1055 | 1101 | ||
1056 | WARN_ON(host->mrq != NULL); | 1102 | WARN_ON(host->mrq != NULL); |
1057 | 1103 | ||
1058 | if (mrq->data && !is_power_of_2(mrq->data->blksz)) { | 1104 | mrq->cmd->error = mmci_validate_data(host, mrq->data); |
1059 | dev_err(mmc_dev(mmc), "unsupported block size (%d bytes)\n", | 1105 | if (mrq->cmd->error) { |
1060 | mrq->data->blksz); | ||
1061 | mrq->cmd->error = -EINVAL; | ||
1062 | mmc_request_done(mmc, mrq); | 1106 | mmc_request_done(mmc, mrq); |
1063 | return; | 1107 | return; |
1064 | } | 1108 | } |
@@ -1086,7 +1130,6 @@ static void mmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
1086 | struct variant_data *variant = host->variant; | 1130 | struct variant_data *variant = host->variant; |
1087 | u32 pwr = 0; | 1131 | u32 pwr = 0; |
1088 | unsigned long flags; | 1132 | unsigned long flags; |
1089 | int ret; | ||
1090 | 1133 | ||
1091 | pm_runtime_get_sync(mmc_dev(mmc)); | 1134 | pm_runtime_get_sync(mmc_dev(mmc)); |
1092 | 1135 | ||
@@ -1096,23 +1139,13 @@ static void mmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
1096 | 1139 | ||
1097 | switch (ios->power_mode) { | 1140 | switch (ios->power_mode) { |
1098 | case MMC_POWER_OFF: | 1141 | case MMC_POWER_OFF: |
1099 | if (host->vcc) | 1142 | if (!IS_ERR(mmc->supply.vmmc)) |
1100 | ret = mmc_regulator_set_ocr(mmc, host->vcc, 0); | 1143 | mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, 0); |
1101 | break; | 1144 | break; |
1102 | case MMC_POWER_UP: | 1145 | case MMC_POWER_UP: |
1103 | if (host->vcc) { | 1146 | if (!IS_ERR(mmc->supply.vmmc)) |
1104 | ret = mmc_regulator_set_ocr(mmc, host->vcc, ios->vdd); | 1147 | mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, ios->vdd); |
1105 | if (ret) { | 1148 | |
1106 | dev_err(mmc_dev(mmc), "unable to set OCR\n"); | ||
1107 | /* | ||
1108 | * The .set_ios() function in the mmc_host_ops | ||
1109 | * struct return void, and failing to set the | ||
1110 | * power should be rare so we print an error | ||
1111 | * and return here. | ||
1112 | */ | ||
1113 | goto out; | ||
1114 | } | ||
1115 | } | ||
1116 | /* | 1149 | /* |
1117 | * The ST Micro variant doesn't have the PL180s MCI_PWR_UP | 1150 | * The ST Micro variant doesn't have the PL180s MCI_PWR_UP |
1118 | * and instead uses MCI_PWR_ON so apply whatever value is | 1151 | * and instead uses MCI_PWR_ON so apply whatever value is |
@@ -1154,6 +1187,13 @@ static void mmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
1154 | } | 1187 | } |
1155 | } | 1188 | } |
1156 | 1189 | ||
1190 | /* | ||
1191 | * If clock = 0 and the variant requires the MMCIPOWER to be used for | ||
1192 | * gating the clock, the MCI_PWR_ON bit is cleared. | ||
1193 | */ | ||
1194 | if (!ios->clock && variant->pwrreg_clkgate) | ||
1195 | pwr &= ~MCI_PWR_ON; | ||
1196 | |||
1157 | spin_lock_irqsave(&host->lock, flags); | 1197 | spin_lock_irqsave(&host->lock, flags); |
1158 | 1198 | ||
1159 | mmci_set_clkreg(host, ios->clock); | 1199 | mmci_set_clkreg(host, ios->clock); |
@@ -1161,7 +1201,6 @@ static void mmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
1161 | 1201 | ||
1162 | spin_unlock_irqrestore(&host->lock, flags); | 1202 | spin_unlock_irqrestore(&host->lock, flags); |
1163 | 1203 | ||
1164 | out: | ||
1165 | pm_runtime_mark_last_busy(mmc_dev(mmc)); | 1204 | pm_runtime_mark_last_busy(mmc_dev(mmc)); |
1166 | pm_runtime_put_autosuspend(mmc_dev(mmc)); | 1205 | pm_runtime_put_autosuspend(mmc_dev(mmc)); |
1167 | } | 1206 | } |
@@ -1384,32 +1423,19 @@ static int mmci_probe(struct amba_device *dev, | |||
1384 | } else | 1423 | } else |
1385 | dev_warn(&dev->dev, "could not get default pinstate\n"); | 1424 | dev_warn(&dev->dev, "could not get default pinstate\n"); |
1386 | 1425 | ||
1387 | #ifdef CONFIG_REGULATOR | 1426 | /* Get regulators and the supported OCR mask */ |
1388 | /* If we're using the regulator framework, try to fetch a regulator */ | 1427 | mmc_regulator_get_supply(mmc); |
1389 | host->vcc = regulator_get(&dev->dev, "vmmc"); | 1428 | if (!mmc->ocr_avail) |
1390 | if (IS_ERR(host->vcc)) | ||
1391 | host->vcc = NULL; | ||
1392 | else { | ||
1393 | int mask = mmc_regulator_get_ocrmask(host->vcc); | ||
1394 | |||
1395 | if (mask < 0) | ||
1396 | dev_err(&dev->dev, "error getting OCR mask (%d)\n", | ||
1397 | mask); | ||
1398 | else { | ||
1399 | host->mmc->ocr_avail = (u32) mask; | ||
1400 | if (plat->ocr_mask) | ||
1401 | dev_warn(&dev->dev, | ||
1402 | "Provided ocr_mask/setpower will not be used " | ||
1403 | "(using regulator instead)\n"); | ||
1404 | } | ||
1405 | } | ||
1406 | #endif | ||
1407 | /* Fall back to platform data if no regulator is found */ | ||
1408 | if (host->vcc == NULL) | ||
1409 | mmc->ocr_avail = plat->ocr_mask; | 1429 | mmc->ocr_avail = plat->ocr_mask; |
1430 | else if (plat->ocr_mask) | ||
1431 | dev_warn(mmc_dev(mmc), "Platform OCR mask is ignored\n"); | ||
1432 | |||
1410 | mmc->caps = plat->capabilities; | 1433 | mmc->caps = plat->capabilities; |
1411 | mmc->caps2 = plat->capabilities2; | 1434 | mmc->caps2 = plat->capabilities2; |
1412 | 1435 | ||
1436 | /* We support these PM capabilities. */ | ||
1437 | mmc->pm_caps = MMC_PM_KEEP_POWER; | ||
1438 | |||
1413 | /* | 1439 | /* |
1414 | * We can do SGIO | 1440 | * We can do SGIO |
1415 | */ | 1441 | */ |
@@ -1585,10 +1611,6 @@ static int mmci_remove(struct amba_device *dev) | |||
1585 | clk_disable_unprepare(host->clk); | 1611 | clk_disable_unprepare(host->clk); |
1586 | clk_put(host->clk); | 1612 | clk_put(host->clk); |
1587 | 1613 | ||
1588 | if (host->vcc) | ||
1589 | mmc_regulator_set_ocr(mmc, host->vcc, 0); | ||
1590 | regulator_put(host->vcc); | ||
1591 | |||
1592 | mmc_free_host(mmc); | 1614 | mmc_free_host(mmc); |
1593 | 1615 | ||
1594 | amba_release_regions(dev); | 1616 | amba_release_regions(dev); |
@@ -1636,8 +1658,37 @@ static int mmci_resume(struct device *dev) | |||
1636 | } | 1658 | } |
1637 | #endif | 1659 | #endif |
1638 | 1660 | ||
1661 | #ifdef CONFIG_PM_RUNTIME | ||
1662 | static int mmci_runtime_suspend(struct device *dev) | ||
1663 | { | ||
1664 | struct amba_device *adev = to_amba_device(dev); | ||
1665 | struct mmc_host *mmc = amba_get_drvdata(adev); | ||
1666 | |||
1667 | if (mmc) { | ||
1668 | struct mmci_host *host = mmc_priv(mmc); | ||
1669 | clk_disable_unprepare(host->clk); | ||
1670 | } | ||
1671 | |||
1672 | return 0; | ||
1673 | } | ||
1674 | |||
1675 | static int mmci_runtime_resume(struct device *dev) | ||
1676 | { | ||
1677 | struct amba_device *adev = to_amba_device(dev); | ||
1678 | struct mmc_host *mmc = amba_get_drvdata(adev); | ||
1679 | |||
1680 | if (mmc) { | ||
1681 | struct mmci_host *host = mmc_priv(mmc); | ||
1682 | clk_prepare_enable(host->clk); | ||
1683 | } | ||
1684 | |||
1685 | return 0; | ||
1686 | } | ||
1687 | #endif | ||
1688 | |||
1639 | static const struct dev_pm_ops mmci_dev_pm_ops = { | 1689 | static const struct dev_pm_ops mmci_dev_pm_ops = { |
1640 | SET_SYSTEM_SLEEP_PM_OPS(mmci_suspend, mmci_resume) | 1690 | SET_SYSTEM_SLEEP_PM_OPS(mmci_suspend, mmci_resume) |
1691 | SET_RUNTIME_PM_OPS(mmci_runtime_suspend, mmci_runtime_resume, NULL) | ||
1641 | }; | 1692 | }; |
1642 | 1693 | ||
1643 | static struct amba_id mmci_ids[] = { | 1694 | static struct amba_id mmci_ids[] = { |
@@ -1652,6 +1703,11 @@ static struct amba_id mmci_ids[] = { | |||
1652 | .data = &variant_arm_extended_fifo, | 1703 | .data = &variant_arm_extended_fifo, |
1653 | }, | 1704 | }, |
1654 | { | 1705 | { |
1706 | .id = 0x02041180, | ||
1707 | .mask = 0xff0fffff, | ||
1708 | .data = &variant_arm_extended_fifo_hwfc, | ||
1709 | }, | ||
1710 | { | ||
1655 | .id = 0x00041181, | 1711 | .id = 0x00041181, |
1656 | .mask = 0x000fffff, | 1712 | .mask = 0x000fffff, |
1657 | .data = &variant_arm, | 1713 | .data = &variant_arm, |
diff --git a/drivers/mmc/host/mmci.h b/drivers/mmc/host/mmci.h index d34d8c0add8e..1f33ad5333a0 100644 --- a/drivers/mmc/host/mmci.h +++ b/drivers/mmc/host/mmci.h | |||
@@ -28,6 +28,8 @@ | |||
28 | #define MCI_ST_UX500_NEG_EDGE (1 << 13) | 28 | #define MCI_ST_UX500_NEG_EDGE (1 << 13) |
29 | #define MCI_ST_UX500_HWFCEN (1 << 14) | 29 | #define MCI_ST_UX500_HWFCEN (1 << 14) |
30 | #define MCI_ST_UX500_CLK_INV (1 << 15) | 30 | #define MCI_ST_UX500_CLK_INV (1 << 15) |
31 | /* Modified PL180 on Versatile Express platform */ | ||
32 | #define MCI_ARM_HWFCEN (1 << 12) | ||
31 | 33 | ||
32 | #define MMCIARGUMENT 0x008 | 34 | #define MMCIARGUMENT 0x008 |
33 | #define MMCICOMMAND 0x00c | 35 | #define MMCICOMMAND 0x00c |
@@ -193,7 +195,6 @@ struct mmci_host { | |||
193 | /* pio stuff */ | 195 | /* pio stuff */ |
194 | struct sg_mapping_iter sg_miter; | 196 | struct sg_mapping_iter sg_miter; |
195 | unsigned int size; | 197 | unsigned int size; |
196 | struct regulator *vcc; | ||
197 | 198 | ||
198 | /* pinctrl handles */ | 199 | /* pinctrl handles */ |
199 | struct pinctrl *pinctrl; | 200 | struct pinctrl *pinctrl; |
diff --git a/drivers/mmc/host/mxs-mmc.c b/drivers/mmc/host/mxs-mmc.c index 493cd9eb8aa8..4efe3021b217 100644 --- a/drivers/mmc/host/mxs-mmc.c +++ b/drivers/mmc/host/mxs-mmc.c | |||
@@ -614,9 +614,9 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
614 | host = mmc_priv(mmc); | 614 | host = mmc_priv(mmc); |
615 | ssp = &host->ssp; | 615 | ssp = &host->ssp; |
616 | ssp->dev = &pdev->dev; | 616 | ssp->dev = &pdev->dev; |
617 | ssp->base = devm_request_and_ioremap(&pdev->dev, iores); | 617 | ssp->base = devm_ioremap_resource(&pdev->dev, iores); |
618 | if (!ssp->base) { | 618 | if (IS_ERR(ssp->base)) { |
619 | ret = -EADDRNOTAVAIL; | 619 | ret = PTR_ERR(ssp->base); |
620 | goto out_mmc_free; | 620 | goto out_mmc_free; |
621 | } | 621 | } |
622 | 622 | ||
diff --git a/drivers/mmc/host/rtsx_pci_sdmmc.c b/drivers/mmc/host/rtsx_pci_sdmmc.c index f93f100e81e5..f981f7d1f6e3 100644 --- a/drivers/mmc/host/rtsx_pci_sdmmc.c +++ b/drivers/mmc/host/rtsx_pci_sdmmc.c | |||
@@ -678,12 +678,19 @@ static void sdmmc_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
678 | struct mmc_command *cmd = mrq->cmd; | 678 | struct mmc_command *cmd = mrq->cmd; |
679 | struct mmc_data *data = mrq->data; | 679 | struct mmc_data *data = mrq->data; |
680 | unsigned int data_size = 0; | 680 | unsigned int data_size = 0; |
681 | int err; | ||
681 | 682 | ||
682 | if (host->eject) { | 683 | if (host->eject) { |
683 | cmd->error = -ENOMEDIUM; | 684 | cmd->error = -ENOMEDIUM; |
684 | goto finish; | 685 | goto finish; |
685 | } | 686 | } |
686 | 687 | ||
688 | err = rtsx_pci_card_exclusive_check(host->pcr, RTSX_SD_CARD); | ||
689 | if (err) { | ||
690 | cmd->error = err; | ||
691 | goto finish; | ||
692 | } | ||
693 | |||
687 | mutex_lock(&pcr->pcr_mutex); | 694 | mutex_lock(&pcr->pcr_mutex); |
688 | 695 | ||
689 | rtsx_pci_start_run(pcr); | 696 | rtsx_pci_start_run(pcr); |
@@ -901,6 +908,9 @@ static void sdmmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
901 | if (host->eject) | 908 | if (host->eject) |
902 | return; | 909 | return; |
903 | 910 | ||
911 | if (rtsx_pci_card_exclusive_check(host->pcr, RTSX_SD_CARD)) | ||
912 | return; | ||
913 | |||
904 | mutex_lock(&pcr->pcr_mutex); | 914 | mutex_lock(&pcr->pcr_mutex); |
905 | 915 | ||
906 | rtsx_pci_start_run(pcr); | 916 | rtsx_pci_start_run(pcr); |
@@ -1073,6 +1083,10 @@ static int sdmmc_switch_voltage(struct mmc_host *mmc, struct mmc_ios *ios) | |||
1073 | if (host->eject) | 1083 | if (host->eject) |
1074 | return -ENOMEDIUM; | 1084 | return -ENOMEDIUM; |
1075 | 1085 | ||
1086 | err = rtsx_pci_card_exclusive_check(host->pcr, RTSX_SD_CARD); | ||
1087 | if (err) | ||
1088 | return err; | ||
1089 | |||
1076 | mutex_lock(&pcr->pcr_mutex); | 1090 | mutex_lock(&pcr->pcr_mutex); |
1077 | 1091 | ||
1078 | rtsx_pci_start_run(pcr); | 1092 | rtsx_pci_start_run(pcr); |
@@ -1117,6 +1131,10 @@ static int sdmmc_execute_tuning(struct mmc_host *mmc, u32 opcode) | |||
1117 | if (host->eject) | 1131 | if (host->eject) |
1118 | return -ENOMEDIUM; | 1132 | return -ENOMEDIUM; |
1119 | 1133 | ||
1134 | err = rtsx_pci_card_exclusive_check(host->pcr, RTSX_SD_CARD); | ||
1135 | if (err) | ||
1136 | return err; | ||
1137 | |||
1120 | mutex_lock(&pcr->pcr_mutex); | 1138 | mutex_lock(&pcr->pcr_mutex); |
1121 | 1139 | ||
1122 | rtsx_pci_start_run(pcr); | 1140 | rtsx_pci_start_run(pcr); |
diff --git a/drivers/mmc/host/sdhci-s3c.c b/drivers/mmc/host/sdhci-s3c.c index b16dae00cfd4..7363efe72287 100644 --- a/drivers/mmc/host/sdhci-s3c.c +++ b/drivers/mmc/host/sdhci-s3c.c | |||
@@ -651,10 +651,9 @@ static int sdhci_s3c_probe(struct platform_device *pdev) | |||
651 | #endif | 651 | #endif |
652 | 652 | ||
653 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 653 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
654 | host->ioaddr = devm_request_and_ioremap(&pdev->dev, res); | 654 | host->ioaddr = devm_ioremap_resource(&pdev->dev, res); |
655 | if (!host->ioaddr) { | 655 | if (IS_ERR(host->ioaddr)) { |
656 | dev_err(dev, "failed to map registers\n"); | 656 | ret = PTR_ERR(host->ioaddr); |
657 | ret = -ENXIO; | ||
658 | goto err_req_regs; | 657 | goto err_req_regs; |
659 | } | 658 | } |
660 | 659 | ||