mmc: host: rk_sdmmc: clk_prepare/unprepare should be used in non-atomic context
authorlin tao <lt@mid-server3.(none)>
Tue, 24 Jun 2014 02:15:34 +0000 (10:15 +0800)
committerlin tao <lt@mid-server3.(none)>
Tue, 24 Jun 2014 02:18:00 +0000 (10:18 +0800)
drivers/mmc/host/rk_sdmmc.c

index f5f78969d38d274f60ec2b8ba01e5927211b21eb..6325d5d161dc31897a032436123910e53c1fd8de 100755 (executable)
@@ -1295,28 +1295,34 @@ static int dw_mci_get_ro(struct mmc_host *mmc)
 static int dw_mci_set_sdio_status(struct mmc_host *mmc, int val)
 {
         struct dw_mci_slot *slot = mmc_priv(mmc);
-        /*struct dw_mci_board *brd = slot->host->pdata;*/
-       struct dw_mci *host = slot->host;
+        struct dw_mci *host = slot->host;
+       /*struct dw_mci_board *brd = slot->host->pdata;*/
+
        if (!(mmc->restrict_caps & RESTRICT_CARD_TYPE_SDIO))
                 return 0;
                 
         spin_lock_bh(&host->lock);
-        if(val){
+
+        if(val)
                 set_bit(DW_MMC_CARD_PRESENT, &slot->flags);
+        else
+                clear_bit(DW_MMC_CARD_PRESENT, &slot->flags);
+
+        spin_unlock_bh(&host->lock);
+
+        if(test_bit(DW_MMC_CARD_PRESENT, &slot->flags)){
                 if(__clk_is_enabled(host->hclk_mmc) == false)
                         clk_prepare_enable(host->hclk_mmc);
                 if(__clk_is_enabled(host->clk_mmc) == false)
                         clk_prepare_enable(host->clk_mmc);
         }else{
-                clear_bit(DW_MMC_CARD_PRESENT, &slot->flags);
                 if(__clk_is_enabled(host->clk_mmc) == true)
                         clk_disable_unprepare(slot->host->clk_mmc);
                 if(__clk_is_enabled(host->hclk_mmc) == true)
                         clk_disable_unprepare(slot->host->hclk_mmc);
         }
-        spin_unlock_bh(&host->lock);
-        mmc_detect_change(slot->mmc, 20);    
 
+        mmc_detect_change(slot->mmc, 20);
         return 0;
 }