mmc: Handle switch error status bit in MMC card status
authorAndrew Gabbasov <andrew_gabbasov@mentor.com>
Thu, 3 Apr 2014 09:34:32 +0000 (04:34 -0500)
committerPantelis Antoniou <panto@antoniou-consulting.com>
Fri, 23 May 2014 08:34:33 +0000 (11:34 +0300)
MMC switch command for unsupported feature (e.g. bus width) sets a switch
error bit in card status. This bit should be checked, and, if it's set,
no access with new controller settings should be performed.

Acked-by: Pantelis Antoniou <panto@antoniou-consulting.com>
Signed-off-by: Andrew Gabbasov <andrew_gabbasov@mentor.com>
drivers/mmc/mmc.c
include/mmc.h

index 0c9ae5d9cdb421755e32af59321bdbc3a9776bd7..bb9014dc064296daacd7c548a427dcacac6420c4 100644 (file)
@@ -150,6 +150,8 @@ int mmc_send_status(struct mmc *mmc, int timeout)
 #endif
                return TIMEOUT;
        }
+       if (cmd.response[0] & MMC_STATUS_SWITCH_ERROR)
+               return SWITCH_ERR;
 
        return 0;
 }
@@ -501,7 +503,7 @@ static int mmc_change_freq(struct mmc *mmc)
        err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, 1);
 
        if (err)
-               return err;
+               return err == SWITCH_ERR ? 0 : err;
 
        /* Now check to see that it worked */
        err = mmc_send_ext_csd(mmc, ext_csd);
index bc11f45a6fca691bcc8ecb873af5a0bbafb76def..9143efe6684d04efdecf1385cc8e2b0d77152f2e 100644 (file)
@@ -54,6 +54,7 @@
 #define COMM_ERR               -18 /* Communications Error */
 #define TIMEOUT                        -19
 #define IN_PROGRESS            -20 /* operation is in progress */
+#define SWITCH_ERR             -21 /* Card reports failure to switch mode */
 
 #define MMC_CMD_GO_IDLE_STATE          0
 #define MMC_CMD_SEND_OP_COND           1
 #define SECURE_ERASE           0x80000000
 
 #define MMC_STATUS_MASK                (~0x0206BF7F)
+#define MMC_STATUS_SWITCH_ERROR        (1 << 7)
 #define MMC_STATUS_RDY_FOR_DATA (1 << 8)
 #define MMC_STATUS_CURR_STATE  (0xf << 9)
 #define MMC_STATUS_ERROR       (1 << 19)