diff options
Diffstat (limited to 'drivers/mmc/host/atmel-mci.c')
-rw-r--r-- | drivers/mmc/host/atmel-mci.c | 21 |
1 files changed, 17 insertions, 4 deletions
diff --git a/drivers/mmc/host/atmel-mci.c b/drivers/mmc/host/atmel-mci.c index cf6a100bb38f..5e10d3663ab5 100644 --- a/drivers/mmc/host/atmel-mci.c +++ b/drivers/mmc/host/atmel-mci.c | |||
@@ -177,6 +177,7 @@ struct atmel_mci { | |||
177 | * available. | 177 | * available. |
178 | * @wp_pin: GPIO pin used for card write protect sending, or negative | 178 | * @wp_pin: GPIO pin used for card write protect sending, or negative |
179 | * if not available. | 179 | * if not available. |
180 | * @detect_is_active_high: The state of the detect pin when it is active. | ||
180 | * @detect_timer: Timer used for debouncing @detect_pin interrupts. | 181 | * @detect_timer: Timer used for debouncing @detect_pin interrupts. |
181 | */ | 182 | */ |
182 | struct atmel_mci_slot { | 183 | struct atmel_mci_slot { |
@@ -196,6 +197,7 @@ struct atmel_mci_slot { | |||
196 | 197 | ||
197 | int detect_pin; | 198 | int detect_pin; |
198 | int wp_pin; | 199 | int wp_pin; |
200 | bool detect_is_active_high; | ||
199 | 201 | ||
200 | struct timer_list detect_timer; | 202 | struct timer_list detect_timer; |
201 | }; | 203 | }; |
@@ -574,6 +576,7 @@ atmci_submit_data_dma(struct atmel_mci *host, struct mmc_data *data) | |||
574 | struct scatterlist *sg; | 576 | struct scatterlist *sg; |
575 | unsigned int i; | 577 | unsigned int i; |
576 | enum dma_data_direction direction; | 578 | enum dma_data_direction direction; |
579 | unsigned int sglen; | ||
577 | 580 | ||
578 | /* | 581 | /* |
579 | * We don't do DMA on "complex" transfers, i.e. with | 582 | * We don't do DMA on "complex" transfers, i.e. with |
@@ -603,11 +606,14 @@ atmci_submit_data_dma(struct atmel_mci *host, struct mmc_data *data) | |||
603 | else | 606 | else |
604 | direction = DMA_TO_DEVICE; | 607 | direction = DMA_TO_DEVICE; |
605 | 608 | ||
609 | sglen = dma_map_sg(&host->pdev->dev, data->sg, data->sg_len, direction); | ||
610 | if (sglen != data->sg_len) | ||
611 | goto unmap_exit; | ||
606 | desc = chan->device->device_prep_slave_sg(chan, | 612 | desc = chan->device->device_prep_slave_sg(chan, |
607 | data->sg, data->sg_len, direction, | 613 | data->sg, data->sg_len, direction, |
608 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); | 614 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); |
609 | if (!desc) | 615 | if (!desc) |
610 | return -ENOMEM; | 616 | goto unmap_exit; |
611 | 617 | ||
612 | host->dma.data_desc = desc; | 618 | host->dma.data_desc = desc; |
613 | desc->callback = atmci_dma_complete; | 619 | desc->callback = atmci_dma_complete; |
@@ -618,6 +624,9 @@ atmci_submit_data_dma(struct atmel_mci *host, struct mmc_data *data) | |||
618 | chan->device->device_issue_pending(chan); | 624 | chan->device->device_issue_pending(chan); |
619 | 625 | ||
620 | return 0; | 626 | return 0; |
627 | unmap_exit: | ||
628 | dma_unmap_sg(&host->pdev->dev, data->sg, sglen, direction); | ||
629 | return -ENOMEM; | ||
621 | } | 630 | } |
622 | 631 | ||
623 | #else /* CONFIG_MMC_ATMELMCI_DMA */ | 632 | #else /* CONFIG_MMC_ATMELMCI_DMA */ |
@@ -924,7 +933,8 @@ static int atmci_get_cd(struct mmc_host *mmc) | |||
924 | struct atmel_mci_slot *slot = mmc_priv(mmc); | 933 | struct atmel_mci_slot *slot = mmc_priv(mmc); |
925 | 934 | ||
926 | if (gpio_is_valid(slot->detect_pin)) { | 935 | if (gpio_is_valid(slot->detect_pin)) { |
927 | present = !gpio_get_value(slot->detect_pin); | 936 | present = !(gpio_get_value(slot->detect_pin) ^ |
937 | slot->detect_is_active_high); | ||
928 | dev_dbg(&mmc->class_dev, "card is %spresent\n", | 938 | dev_dbg(&mmc->class_dev, "card is %spresent\n", |
929 | present ? "" : "not "); | 939 | present ? "" : "not "); |
930 | } | 940 | } |
@@ -1028,7 +1038,8 @@ static void atmci_detect_change(unsigned long data) | |||
1028 | return; | 1038 | return; |
1029 | 1039 | ||
1030 | enable_irq(gpio_to_irq(slot->detect_pin)); | 1040 | enable_irq(gpio_to_irq(slot->detect_pin)); |
1031 | present = !gpio_get_value(slot->detect_pin); | 1041 | present = !(gpio_get_value(slot->detect_pin) ^ |
1042 | slot->detect_is_active_high); | ||
1032 | present_old = test_bit(ATMCI_CARD_PRESENT, &slot->flags); | 1043 | present_old = test_bit(ATMCI_CARD_PRESENT, &slot->flags); |
1033 | 1044 | ||
1034 | dev_vdbg(&slot->mmc->class_dev, "detect change: %d (was %d)\n", | 1045 | dev_vdbg(&slot->mmc->class_dev, "detect change: %d (was %d)\n", |
@@ -1456,6 +1467,7 @@ static int __init atmci_init_slot(struct atmel_mci *host, | |||
1456 | slot->host = host; | 1467 | slot->host = host; |
1457 | slot->detect_pin = slot_data->detect_pin; | 1468 | slot->detect_pin = slot_data->detect_pin; |
1458 | slot->wp_pin = slot_data->wp_pin; | 1469 | slot->wp_pin = slot_data->wp_pin; |
1470 | slot->detect_is_active_high = slot_data->detect_is_active_high; | ||
1459 | slot->sdc_reg = sdc_reg; | 1471 | slot->sdc_reg = sdc_reg; |
1460 | 1472 | ||
1461 | mmc->ops = &atmci_ops; | 1473 | mmc->ops = &atmci_ops; |
@@ -1477,7 +1489,8 @@ static int __init atmci_init_slot(struct atmel_mci *host, | |||
1477 | if (gpio_request(slot->detect_pin, "mmc_detect")) { | 1489 | if (gpio_request(slot->detect_pin, "mmc_detect")) { |
1478 | dev_dbg(&mmc->class_dev, "no detect pin available\n"); | 1490 | dev_dbg(&mmc->class_dev, "no detect pin available\n"); |
1479 | slot->detect_pin = -EBUSY; | 1491 | slot->detect_pin = -EBUSY; |
1480 | } else if (gpio_get_value(slot->detect_pin)) { | 1492 | } else if (gpio_get_value(slot->detect_pin) ^ |
1493 | slot->detect_is_active_high) { | ||
1481 | clear_bit(ATMCI_CARD_PRESENT, &slot->flags); | 1494 | clear_bit(ATMCI_CARD_PRESENT, &slot->flags); |
1482 | } | 1495 | } |
1483 | } | 1496 | } |