Esempio n. 1
0
/*********************************************************************
* Method	 :  
* Description:  
* Parameters :  
*	            
* Returns    :  
* Note       :
*********************************************************************/
s32 sdxc_request_done(struct awsmc_host* smc_host)
{
    struct mmc_request* req = smc_host->mrq;
    u32 temp;
    s32 ret = 0;
    
    if (smc_host->int_sum & SDXC_IntErrBit)
    {
        awsmc_dbg_err("smc %d err, cmd %d, %s%s%s%s%s%s%s%s%s%s !!\n", 
            smc_host->pdev->id, req->cmd->opcode,
    		smc_host->int_sum & SDXC_RespErr     ? " RE"     : "",
    		smc_host->int_sum & SDXC_RespCRCErr  ? " RCE"    : "",
    		smc_host->int_sum & SDXC_DataCRCErr  ? " DCE"    : "",
    		smc_host->int_sum & SDXC_RespTimeout ? " RTO"    : "",
    		smc_host->int_sum & SDXC_DataTimeout ? " DTO"    : "",
    		smc_host->int_sum & SDXC_DataStarve  ? " DS"     : "",
    		smc_host->int_sum & SDXC_FIFORunErr  ? " FE"     : "",
    		smc_host->int_sum & SDXC_HardWLocked ? " HL"     : "",
    		smc_host->int_sum & SDXC_StartBitErr ? " SBE"    : "",
    		smc_host->int_sum & SDXC_EndBitErr   ? " EBE"    : ""
    		);
        
        if (req->data)
        {
            awsmc_dbg_err("In data %s operation\n", req->data->flags & MMC_DATA_WRITE ? "write" : "read");
        }
    	ret = -1;
        goto _out_;
    }
    
    if (req->cmd)
    {
        if (req->cmd->flags & MMC_RSP_136)
    	{
    		req->cmd->resp[0] = sdc_read(SDXC_REG_RESP3);
    		req->cmd->resp[1] = sdc_read(SDXC_REG_RESP2);
    		req->cmd->resp[2] = sdc_read(SDXC_REG_RESP1);
    		req->cmd->resp[3] = sdc_read(SDXC_REG_RESP0);
    	}
    	else
    	{
    		req->cmd->resp[0] = sdc_read(SDXC_REG_RESP0);
    	}
    }
    
_out_:
    if (req->data)
    {
        if (!(req->data->flags & MMC_DATA_WRITE) && (sdc_read(SDXC_REG_STAS) & SDXC_DataFSMBusy))
        {
            printk("data fsm busy\n");
        }
        if (smc_host->dodma)
        {
    		smc_host->dma_done = 0;
            sdc_write(SDXC_REG_IDST, 0x337);
            sdc_write(SDXC_REG_IDIE, 0);
            sdxc_idma_off(smc_host);
            sdxc_dma_disable(smc_host);
        }
        
        sdxc_fifo_reset(smc_host);
    }
    
    temp = sdc_read(SDXC_REG_STAS);
    if ((temp & SDXC_DataFSMBusy) || (smc_host->int_sum & (SDXC_RespErr | SDXC_HardWLocked | SDXC_RespTimeout)))
    {
        awsmc_dbg("sdc %d abnormal status: %s %s\n", smc_host->pdev->id,
                                                  temp & SDXC_DataFSMBusy ? "DataFSMBusy" : "",
                                                  smc_host->int_sum & SDXC_HardWLocked ? "HardWLocked" : "");
        sdxc_reset(smc_host);
        sdxc_program_clk(smc_host);
    }
    
    sdc_write(SDXC_REG_RINTR, 0xffff);
    sdxc_clear_imask(smc_host);
    //re-enable card detect debounce
    if (smc_host->cd_gpio == CARD_DETECT_BY_DATA3)
    {
        sdxc_cd_debounce_on(smc_host);
    }

    awsmc_dbg("smc %d done, resp %08x %08x %08x %08x\n", smc_host->pdev->id, req->cmd->resp[0], req->cmd->resp[1], req->cmd->resp[2], req->cmd->resp[3]);
    
	if (req->data && req->data->stop && (smc_host->int_sum & SDXC_IntErrBit))
	{
		awsmc_msg("found data error, need to send stop command !!\n");
		sdxc_send_manual_stop(smc_host, req);
	}
    
    if ((smc_host->pdev->id==3) && req->data && (req->data->flags & MMC_DATA_WRITE) && !(smc_host->int_sum & SDXC_IntErrBit))
    {
        u32 ready = 0;
//        u32 i = 0;
        do {
//            awsmc_msg("smc %d check ready %d \r", smc_host->pdev->id, i++);
            ready = sdxc_check_r1_ready(smc_host);
        } while (!ready);
//        awsmc_msg("\n");
    }
    return ret;
}
Esempio n. 2
0
int sunximmc_check_r1_ready(struct mmc_host *mmc)
{
    struct sunxi_mmc_host *smc_host = mmc_priv(mmc);
    return sdxc_check_r1_ready(smc_host);
}