This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

DM8127: SD card remove event is missed.

Hello,

We have a DM8127 based product where we are using IPNC_RDK 3.5 which comes with Linux kernel 2.6.37_DM8127_IPNC_3.50.00. This product support the SD card interface to store misc data (files).

Problem Description: We have seen an instance, where the SD card was physically removed from the SD card slot but the kernel was not able to detect this and no udev event is generated. We don't see any MMC related activities in "dmesg" output.

Reproducibility: The insertion/removal event is detected most of the time but we have seen this problem twice till now so it is not so easy to reproduce.

SD card details: 32 GB Transcend, Class 10.

Setup / Design description: There is SD card detect GPIO connected to detect insert/remove events. The MMC driver is configured to detect events based on this GPIO and proper PIN_MUX is done:

static struct omap2_hsmmc_info mmc[] = {
        {
                .mmc            = 1,
               .caps              = MMC_CAP_4_BIT_DATA,
               .gpio_cd        = GPIO_TO_PIN(1, 6), /* Dedicated pins for CD and WP */
               .gpio_wp        = -EINVAL,                      /* Dedicated pins for WP */
               .ocr_mask      = MMC_VDD_33_34,
       },
       {}      /* Terminator */
};

Questions:

  1. Has anyone experienced such behavior?
  2. Is there any known issues with the MMC driver?
  3. Is there a possibility that the SD card detect interrupt can be missed by the driver which can lead to this behavior?

Any help will be highly appreciated. Please let me know if need any further details on the setup/test scenario.


--

Regards,

Krunal

  • I haven't found you an answer, but at least I'll document my examinations, since I did notice weird things:

    Since MMC has dedicated pins for card-detect and write-protect I would have expected those to be used, and indeed the driver uses irqs from the MMC peripheral itself for those purposes, but only if  mmc->version == MMC_CTRL_VERSION_2, otherwise it uses GPIO. This version field is documented as:

    arch/arm/plat-omap/include/plat/mmc.h
            MMC_CTRL_VERSION_1 = 0, /* OMAP class devicess */
            MMC_CTRL_VERSION_2      /* TI81XX class devicess */

    and seems to be used for this purpose only. This field and the considerable amount of logic associated with it was introduced by this commit, although you'd never guess from the commit message:

    commit ef6b8c97 (2011-07-04)
        Fixup platform hookup part for MMC driver on TI816x
    
    @@ -258,2 +262,5 @@ void __init omap2_hsmmc_init(struct omap2_hsmmc_info *contro
     
    +               if (cpu_is_ti816x())
    +                       mmc->version = MMC_CTRL_VERSION_2;
    +
                    if (c->name)
    

    (rest of diff omitted)

    814x support was introduced by replacing various occurrences of 816x by 81xx, including

    commit ca1b3a08 (2011-07-04)
        TI814X: MMC: This patch adds MMC support in TI814X
    
    @@ void __init omap2_hsmmc_init(struct omap2_hsmmc_info *contro
     
    -               if (cpu_is_ti816x())
    +               if (cpu_is_ti81xx())
                            mmc->version = MMC_CTRL_VERSION_2;

    (rest of diff omitted)

    Bugfixes:

    commit 605a4d1f (2011-07-05, authored 2011-05-27)
        This patch enables the interrupt status enable registers for card
        removal and insertion. Once an interrupt is obtained, this patch
        adds support for handling it in case of card removal. Once the card
        was removed, the SD bus power used to go off and therefore subsequent
        card insertions could not be detected completely in software. This
        patch handles this by enabling the SD bus power so that subsequent
        card insetions can happen properly in software.
    commit abf32ca6 (2011-07-12)
        This patch is a rectification of commit id 605a4d1 which enabled
        hot insertion/removal for mmc/sd cards in ti81xx.
        It was found that though the mmc/sd card removal and insertion was
        detected after the patch, the device was not unmounted on card
        removal.

    But a year later, worse problems were found, and the whole stuff was effectively removed, going back to GPIO:

    commit 55f040f3 (2012-07-17, authored 2012-07-03)
        The controller uses a status register for the card detect
        functionality. The implementation of this functionality caused
        a kernel hang in case the card was removed while I/O was
        in progress.
    
    @@ -261,6 +261,2 @@ void __init omap2_hsmmc_init(struct omap2_hsmmc_info *contro
                    }
    -
    -               if (cpu_is_ti81xx())
    -                       mmc->version = MMC_CTRL_VERSION_2;
    -
                    if (c->name)

    The next day it was re-added, but for the 816x only:

    commit 74970c4b (2012-07-18)
        Use the status register in case of ti816x platform
        for the card detect functionality.
    
    @@ -261,2 +261,6 @@ void __init omap2_hsmmc_init(struct omap2_hsmmc_info *contro
                    }
    +
    +               if (cpu_is_ti816x())
    +                       mmc->version = MMC_CTRL_VERSION_2;
    +
                    if (c->name)

    Note that nowhere is explained what the reason for this change was in the first place, why the original approach of using GPIO apparently isn't ok for the 816x.  It also seems to me this leaves the 816x with aforementioned kernel hang problem.

    Anyhow, the current situation seems to be that GPIO is used on the 814x, so I've tried to examine that closer.  I don't see anything obvious wrong with it: it requests an irq on either edge of card detect, which schedules a work item to have the card status reexamined by the mmc subsystem.  I'm however no linux kernel guru, so maybe I'm overlooking a race condition of some sort, but it looks robust.

    I've tried checking whether mainline linux mentions any card detect fixes, but the commits were simply too many and too invasive (the last common commit of mainline and ti81xx to omap_hsmmc.c was b432b4b3 dated 2010-11-17).

    Other options are the possibility that the problem might be a race condition in the GPIO driver, or that code running on one of the other cores is inappropriately meddling with GPIO.  I'll leave those options to explore by others, I've had enough confrontation with ancient crufty code for today... unpleasant reminder that we're stuck with a kernel dated Jan 2011.

  • Hi,


    Thanks for the detailed information. I tried this approach still see same issues sometime.

    Issue-1: With both polling & interrupt mode, even though the SD card is removed the device entries are still present (/dev/mmcblk*) and no udev event received for remove.

    Issue-2: With interrupt mode (default IPNC_3.5 kernel), sometimes multiple interrupts (cat /proc/interrupts | grep mmc) are seen for single insert/remove event.

    Any pointers?


    Regards,

    Krunal