1*b28c29d0SBiju Das /* 2*b28c29d0SBiju Das * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved. 3*b28c29d0SBiju Das * 4*b28c29d0SBiju Das * SPDX-License-Identifier: BSD-3-Clause 5*b28c29d0SBiju Das */ 6*b28c29d0SBiju Das 7*b28c29d0SBiju Das #include <common/debug.h> 8*b28c29d0SBiju Das #include <lib/mmio.h> 9*b28c29d0SBiju Das 10*b28c29d0SBiju Das #include "emmc_config.h" 11*b28c29d0SBiju Das #include "emmc_def.h" 12*b28c29d0SBiju Das #include "emmc_hal.h" 13*b28c29d0SBiju Das #include "emmc_registers.h" 14*b28c29d0SBiju Das #include "emmc_std.h" 15*b28c29d0SBiju Das #include "micro_delay.h" 16*b28c29d0SBiju Das #include "rcar_def.h" 17*b28c29d0SBiju Das 18*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode); 19*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_card_init(void); 20*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_high_speed(void); 21*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_bus_width(uint32_t width); 22*b28c29d0SBiju Das static uint32_t emmc_set_timeout_register_value(uint32_t freq); 23*b28c29d0SBiju Das static void set_sd_clk(uint32_t clkDiv); 24*b28c29d0SBiju Das static uint32_t emmc_calc_tran_speed(uint32_t *freq); 25*b28c29d0SBiju Das static void emmc_get_partition_access(void); 26*b28c29d0SBiju Das static void emmc_set_bootpartition(void); 27*b28c29d0SBiju Das 28*b28c29d0SBiju Das static void emmc_set_bootpartition(void) 29*b28c29d0SBiju Das { 30*b28c29d0SBiju Das uint32_t reg; 31*b28c29d0SBiju Das 32*b28c29d0SBiju Das reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK); 33*b28c29d0SBiju Das if (reg == PRR_PRODUCT_M3_CUT10) { 34*b28c29d0SBiju Das mmc_drv_obj.boot_partition_en = 35*b28c29d0SBiju Das (EMMC_PARTITION_ID) ((mmc_drv_obj.ext_csd_data[179] & 36*b28c29d0SBiju Das EMMC_BOOT_PARTITION_EN_MASK) >> 37*b28c29d0SBiju Das EMMC_BOOT_PARTITION_EN_SHIFT); 38*b28c29d0SBiju Das } else if ((reg == PRR_PRODUCT_H3_CUT20) 39*b28c29d0SBiju Das || (reg == PRR_PRODUCT_M3_CUT11)) { 40*b28c29d0SBiju Das mmc_drv_obj.boot_partition_en = mmc_drv_obj.partition_access; 41*b28c29d0SBiju Das } else { 42*b28c29d0SBiju Das if ((mmio_read_32(MFISBTSTSR) & MFISBTSTSR_BOOT_PARTITION) != 43*b28c29d0SBiju Das 0U) { 44*b28c29d0SBiju Das mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_2; 45*b28c29d0SBiju Das } else { 46*b28c29d0SBiju Das mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_1; 47*b28c29d0SBiju Das } 48*b28c29d0SBiju Das } 49*b28c29d0SBiju Das } 50*b28c29d0SBiju Das 51*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_card_init(void) 52*b28c29d0SBiju Das { 53*b28c29d0SBiju Das int32_t retry; 54*b28c29d0SBiju Das uint32_t freq = MMC_400KHZ; /* 390KHz */ 55*b28c29d0SBiju Das EMMC_ERROR_CODE result; 56*b28c29d0SBiju Das uint32_t result_calc; 57*b28c29d0SBiju Das 58*b28c29d0SBiju Das /* state check */ 59*b28c29d0SBiju Das if ((mmc_drv_obj.initialize != TRUE) 60*b28c29d0SBiju Das || (mmc_drv_obj.card_power_enable != TRUE) 61*b28c29d0SBiju Das || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) 62*b28c29d0SBiju Das ) { 63*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_STATE); 64*b28c29d0SBiju Das return EMMC_ERR_STATE; 65*b28c29d0SBiju Das } 66*b28c29d0SBiju Das 67*b28c29d0SBiju Das /* clock on (force change) */ 68*b28c29d0SBiju Das mmc_drv_obj.current_freq = 0; 69*b28c29d0SBiju Das mmc_drv_obj.max_freq = MMC_20MHZ; 70*b28c29d0SBiju Das result = emmc_set_request_mmc_clock(&freq); 71*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 72*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 73*b28c29d0SBiju Das return EMMC_ERR; 74*b28c29d0SBiju Das } 75*b28c29d0SBiju Das 76*b28c29d0SBiju Das rcar_micro_delay(1000U); /* wait 1ms */ 77*b28c29d0SBiju Das 78*b28c29d0SBiju Das /* Get current access partition */ 79*b28c29d0SBiju Das emmc_get_partition_access(); 80*b28c29d0SBiju Das 81*b28c29d0SBiju Das /* CMD0, arg=0x00000000 */ 82*b28c29d0SBiju Das result = emmc_send_idle_cmd(0x00000000); 83*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 84*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 85*b28c29d0SBiju Das return result; 86*b28c29d0SBiju Das } 87*b28c29d0SBiju Das 88*b28c29d0SBiju Das rcar_micro_delay(200U); /* wait 74clock 390kHz(189.74us) */ 89*b28c29d0SBiju Das 90*b28c29d0SBiju Das /* CMD1 */ 91*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD1_SEND_OP_COND, EMMC_HOST_OCR_VALUE); 92*b28c29d0SBiju Das for (retry = 300; retry > 0; retry--) { 93*b28c29d0SBiju Das result = 94*b28c29d0SBiju Das emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 95*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 96*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 97*b28c29d0SBiju Das return result; 98*b28c29d0SBiju Das } 99*b28c29d0SBiju Das 100*b28c29d0SBiju Das if ((mmc_drv_obj.r3_ocr & EMMC_OCR_STATUS_BIT) != 0) { 101*b28c29d0SBiju Das break; /* card is ready. exit loop */ 102*b28c29d0SBiju Das } 103*b28c29d0SBiju Das rcar_micro_delay(1000U); /* wait 1ms */ 104*b28c29d0SBiju Das } 105*b28c29d0SBiju Das 106*b28c29d0SBiju Das if (retry == 0) { 107*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_TIMEOUT); 108*b28c29d0SBiju Das return EMMC_ERR_TIMEOUT; 109*b28c29d0SBiju Das } 110*b28c29d0SBiju Das 111*b28c29d0SBiju Das switch (mmc_drv_obj.r3_ocr & EMMC_OCR_ACCESS_MODE_MASK) { 112*b28c29d0SBiju Das case EMMC_OCR_ACCESS_MODE_SECT: 113*b28c29d0SBiju Das mmc_drv_obj.access_mode = TRUE; /* sector mode */ 114*b28c29d0SBiju Das break; 115*b28c29d0SBiju Das default: 116*b28c29d0SBiju Das /* unknown value */ 117*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR); 118*b28c29d0SBiju Das return EMMC_ERR; 119*b28c29d0SBiju Das } 120*b28c29d0SBiju Das 121*b28c29d0SBiju Das /* CMD2 */ 122*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD2_ALL_SEND_CID_MMC, 0x00000000); 123*b28c29d0SBiju Das mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.cid_data[0]); /* use CID special buffer */ 124*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 125*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 126*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 127*b28c29d0SBiju Das return result; 128*b28c29d0SBiju Das } 129*b28c29d0SBiju Das 130*b28c29d0SBiju Das /* CMD3 */ 131*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD3_SET_RELATIVE_ADDR, EMMC_RCA << 16); 132*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 133*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 134*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 135*b28c29d0SBiju Das return result; 136*b28c29d0SBiju Das } 137*b28c29d0SBiju Das 138*b28c29d0SBiju Das /* CMD9 (CSD) */ 139*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD9_SEND_CSD, EMMC_RCA << 16); 140*b28c29d0SBiju Das mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.csd_data[0]); /* use CSD special buffer */ 141*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 142*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 143*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 144*b28c29d0SBiju Das return result; 145*b28c29d0SBiju Das } 146*b28c29d0SBiju Das 147*b28c29d0SBiju Das /* card version check */ 148*b28c29d0SBiju Das if (EMMC_CSD_SPEC_VARS() < 4) { 149*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, 150*b28c29d0SBiju Das EMMC_ERR_ILLEGAL_CARD); 151*b28c29d0SBiju Das return EMMC_ERR_ILLEGAL_CARD; 152*b28c29d0SBiju Das } 153*b28c29d0SBiju Das 154*b28c29d0SBiju Das /* CMD7 (select card) */ 155*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD7_SELECT_CARD, EMMC_RCA << 16); 156*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 157*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 158*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 159*b28c29d0SBiju Das return result; 160*b28c29d0SBiju Das } 161*b28c29d0SBiju Das 162*b28c29d0SBiju Das mmc_drv_obj.selected = TRUE; 163*b28c29d0SBiju Das 164*b28c29d0SBiju Das /* 165*b28c29d0SBiju Das * card speed check 166*b28c29d0SBiju Das * Card spec is calculated from TRAN_SPEED(CSD) 167*b28c29d0SBiju Das */ 168*b28c29d0SBiju Das result_calc = emmc_calc_tran_speed(&freq); 169*b28c29d0SBiju Das if (result_calc == 0) { 170*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, 171*b28c29d0SBiju Das EMMC_ERR_ILLEGAL_CARD); 172*b28c29d0SBiju Das return EMMC_ERR_ILLEGAL_CARD; 173*b28c29d0SBiju Das } 174*b28c29d0SBiju Das mmc_drv_obj.max_freq = freq; /* max frequency (card spec) */ 175*b28c29d0SBiju Das 176*b28c29d0SBiju Das result = emmc_set_request_mmc_clock(&freq); 177*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 178*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 179*b28c29d0SBiju Das return EMMC_ERR; 180*b28c29d0SBiju Das } 181*b28c29d0SBiju Das 182*b28c29d0SBiju Das /* set read/write timeout */ 183*b28c29d0SBiju Das mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq); 184*b28c29d0SBiju Das SETR_32(SD_OPTION, 185*b28c29d0SBiju Das ((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) | 186*b28c29d0SBiju Das mmc_drv_obj.data_timeout)); 187*b28c29d0SBiju Das 188*b28c29d0SBiju Das /* SET_BLOCKLEN(512byte) */ 189*b28c29d0SBiju Das /* CMD16 */ 190*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD16_SET_BLOCKLEN, EMMC_BLOCK_LENGTH); 191*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 192*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 193*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 194*b28c29d0SBiju Das return result; 195*b28c29d0SBiju Das } 196*b28c29d0SBiju Das 197*b28c29d0SBiju Das /* Transfer Data Length */ 198*b28c29d0SBiju Das SETR_32(SD_SIZE, EMMC_BLOCK_LENGTH); 199*b28c29d0SBiju Das 200*b28c29d0SBiju Das /* CMD8 (EXT_CSD) */ 201*b28c29d0SBiju Das emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000, 202*b28c29d0SBiju Das (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]), 203*b28c29d0SBiju Das EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ, 204*b28c29d0SBiju Das HAL_MEMCARD_NOT_DMA); 205*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 206*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 207*b28c29d0SBiju Das /* 208*b28c29d0SBiju Das * CMD12 is not send. 209*b28c29d0SBiju Das * If BUS initialization is failed, user must be execute Bus initialization again. 210*b28c29d0SBiju Das * Bus initialization is start CMD0(soft reset command). 211*b28c29d0SBiju Das */ 212*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 213*b28c29d0SBiju Das return result; 214*b28c29d0SBiju Das } 215*b28c29d0SBiju Das 216*b28c29d0SBiju Das /* Set boot partition */ 217*b28c29d0SBiju Das emmc_set_bootpartition(); 218*b28c29d0SBiju Das 219*b28c29d0SBiju Das return EMMC_SUCCESS; 220*b28c29d0SBiju Das } 221*b28c29d0SBiju Das 222*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_high_speed(void) 223*b28c29d0SBiju Das { 224*b28c29d0SBiju Das uint32_t freq; /* High speed mode clock frequency */ 225*b28c29d0SBiju Das EMMC_ERROR_CODE result; 226*b28c29d0SBiju Das uint8_t cardType; 227*b28c29d0SBiju Das 228*b28c29d0SBiju Das /* state check */ 229*b28c29d0SBiju Das if (mmc_drv_obj.selected != TRUE) { 230*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_HIGH_SPEED, EMMC_ERR_STATE); 231*b28c29d0SBiju Das return EMMC_ERR_STATE; 232*b28c29d0SBiju Das } 233*b28c29d0SBiju Das 234*b28c29d0SBiju Das /* max frequency */ 235*b28c29d0SBiju Das cardType = (uint8_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_CARD_TYPE]; 236*b28c29d0SBiju Das if ((cardType & EMMC_EXT_CSD_CARD_TYPE_52MHZ) != 0) 237*b28c29d0SBiju Das freq = MMC_52MHZ; 238*b28c29d0SBiju Das else if ((cardType & EMMC_EXT_CSD_CARD_TYPE_26MHZ) != 0) 239*b28c29d0SBiju Das freq = MMC_26MHZ; 240*b28c29d0SBiju Das else 241*b28c29d0SBiju Das freq = MMC_20MHZ; 242*b28c29d0SBiju Das 243*b28c29d0SBiju Das /* Hi-Speed-mode selection */ 244*b28c29d0SBiju Das if ((freq == MMC_52MHZ) || (freq == MMC_26MHZ)) { 245*b28c29d0SBiju Das /* CMD6 */ 246*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD6_SWITCH, EMMC_SWITCH_HS_TIMING); 247*b28c29d0SBiju Das result = 248*b28c29d0SBiju Das emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 249*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 250*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED); 251*b28c29d0SBiju Das return result; 252*b28c29d0SBiju Das } 253*b28c29d0SBiju Das 254*b28c29d0SBiju Das mmc_drv_obj.hs_timing = TIMING_HIGH_SPEED; /* High-Speed */ 255*b28c29d0SBiju Das } 256*b28c29d0SBiju Das 257*b28c29d0SBiju Das /* set mmc clock */ 258*b28c29d0SBiju Das mmc_drv_obj.max_freq = freq; 259*b28c29d0SBiju Das result = emmc_set_request_mmc_clock(&freq); 260*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 261*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED); 262*b28c29d0SBiju Das return EMMC_ERR; 263*b28c29d0SBiju Das } 264*b28c29d0SBiju Das 265*b28c29d0SBiju Das /* set read/write timeout */ 266*b28c29d0SBiju Das mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq); 267*b28c29d0SBiju Das SETR_32(SD_OPTION, 268*b28c29d0SBiju Das ((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) | 269*b28c29d0SBiju Das mmc_drv_obj.data_timeout)); 270*b28c29d0SBiju Das 271*b28c29d0SBiju Das /* CMD13 */ 272*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16); 273*b28c29d0SBiju Das result = 274*b28c29d0SBiju Das emmc_exec_cmd(EMMC_R1_ERROR_MASK_WITHOUT_CRC, mmc_drv_obj.response); 275*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 276*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED); 277*b28c29d0SBiju Das return result; 278*b28c29d0SBiju Das } 279*b28c29d0SBiju Das 280*b28c29d0SBiju Das return EMMC_SUCCESS; 281*b28c29d0SBiju Das } 282*b28c29d0SBiju Das 283*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode) 284*b28c29d0SBiju Das { 285*b28c29d0SBiju Das uint32_t value; 286*b28c29d0SBiju Das 287*b28c29d0SBiju Das /* busy check */ 288*b28c29d0SBiju Das if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) { 289*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, 290*b28c29d0SBiju Das EMMC_ERR_CARD_BUSY); 291*b28c29d0SBiju Das return EMMC_ERR; 292*b28c29d0SBiju Das } 293*b28c29d0SBiju Das 294*b28c29d0SBiju Das if (mode == TRUE) { 295*b28c29d0SBiju Das /* clock ON */ 296*b28c29d0SBiju Das value = 297*b28c29d0SBiju Das ((GETR_32(SD_CLK_CTRL) | MMC_SD_CLK_START) & 298*b28c29d0SBiju Das SD_CLK_WRITE_MASK); 299*b28c29d0SBiju Das SETR_32(SD_CLK_CTRL, value); /* on */ 300*b28c29d0SBiju Das mmc_drv_obj.clock_enable = TRUE; 301*b28c29d0SBiju Das } else { 302*b28c29d0SBiju Das /* clock OFF */ 303*b28c29d0SBiju Das value = 304*b28c29d0SBiju Das ((GETR_32(SD_CLK_CTRL) & MMC_SD_CLK_STOP) & 305*b28c29d0SBiju Das SD_CLK_WRITE_MASK); 306*b28c29d0SBiju Das SETR_32(SD_CLK_CTRL, value); /* off */ 307*b28c29d0SBiju Das mmc_drv_obj.clock_enable = FALSE; 308*b28c29d0SBiju Das } 309*b28c29d0SBiju Das 310*b28c29d0SBiju Das return EMMC_SUCCESS; 311*b28c29d0SBiju Das } 312*b28c29d0SBiju Das 313*b28c29d0SBiju Das static EMMC_ERROR_CODE emmc_bus_width(uint32_t width) 314*b28c29d0SBiju Das { 315*b28c29d0SBiju Das EMMC_ERROR_CODE result = EMMC_ERR; 316*b28c29d0SBiju Das 317*b28c29d0SBiju Das /* parameter check */ 318*b28c29d0SBiju Das if ((width != 8) && (width != 4) && (width != 1)) { 319*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_PARAM); 320*b28c29d0SBiju Das return EMMC_ERR_PARAM; 321*b28c29d0SBiju Das } 322*b28c29d0SBiju Das 323*b28c29d0SBiju Das /* state check */ 324*b28c29d0SBiju Das if (mmc_drv_obj.selected != TRUE) { 325*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_STATE); 326*b28c29d0SBiju Das return EMMC_ERR_STATE; 327*b28c29d0SBiju Das } 328*b28c29d0SBiju Das 329*b28c29d0SBiju Das /* 2 = 8bit, 1 = 4bit, 0 =1bit */ 330*b28c29d0SBiju Das mmc_drv_obj.bus_width = (HAL_MEMCARD_DATA_WIDTH) (width >> 2); 331*b28c29d0SBiju Das 332*b28c29d0SBiju Das /* CMD6 */ 333*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD6_SWITCH, 334*b28c29d0SBiju Das (EMMC_SWITCH_BUS_WIDTH_1 | 335*b28c29d0SBiju Das (mmc_drv_obj.bus_width << 8))); 336*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 337*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 338*b28c29d0SBiju Das /* occurred error */ 339*b28c29d0SBiju Das mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT; 340*b28c29d0SBiju Das goto EXIT; 341*b28c29d0SBiju Das } 342*b28c29d0SBiju Das 343*b28c29d0SBiju Das switch (mmc_drv_obj.bus_width) { 344*b28c29d0SBiju Das case HAL_MEMCARD_DATA_WIDTH_1_BIT: 345*b28c29d0SBiju Das SETR_32(SD_OPTION, 346*b28c29d0SBiju Das ((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT15)); 347*b28c29d0SBiju Das break; 348*b28c29d0SBiju Das case HAL_MEMCARD_DATA_WIDTH_4_BIT: 349*b28c29d0SBiju Das SETR_32(SD_OPTION, (GETR_32(SD_OPTION) & ~(BIT15 | BIT13))); 350*b28c29d0SBiju Das break; 351*b28c29d0SBiju Das case HAL_MEMCARD_DATA_WIDTH_8_BIT: 352*b28c29d0SBiju Das SETR_32(SD_OPTION, 353*b28c29d0SBiju Das ((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT13)); 354*b28c29d0SBiju Das break; 355*b28c29d0SBiju Das default: 356*b28c29d0SBiju Das goto EXIT; 357*b28c29d0SBiju Das } 358*b28c29d0SBiju Das 359*b28c29d0SBiju Das /* CMD13 */ 360*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16); 361*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 362*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 363*b28c29d0SBiju Das goto EXIT; 364*b28c29d0SBiju Das } 365*b28c29d0SBiju Das 366*b28c29d0SBiju Das /* CMD8 (EXT_CSD) */ 367*b28c29d0SBiju Das emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000, 368*b28c29d0SBiju Das (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]), 369*b28c29d0SBiju Das EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ, 370*b28c29d0SBiju Das HAL_MEMCARD_NOT_DMA); 371*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 372*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 373*b28c29d0SBiju Das goto EXIT; 374*b28c29d0SBiju Das } 375*b28c29d0SBiju Das 376*b28c29d0SBiju Das return EMMC_SUCCESS; 377*b28c29d0SBiju Das 378*b28c29d0SBiju Das EXIT: 379*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, result); 380*b28c29d0SBiju Das ERROR("BL2: emmc bus_width error end\n"); 381*b28c29d0SBiju Das return result; 382*b28c29d0SBiju Das } 383*b28c29d0SBiju Das 384*b28c29d0SBiju Das EMMC_ERROR_CODE emmc_select_partition(EMMC_PARTITION_ID id) 385*b28c29d0SBiju Das { 386*b28c29d0SBiju Das EMMC_ERROR_CODE result; 387*b28c29d0SBiju Das uint32_t arg; 388*b28c29d0SBiju Das uint32_t partition_config; 389*b28c29d0SBiju Das 390*b28c29d0SBiju Das /* state check */ 391*b28c29d0SBiju Das if (mmc_drv_obj.mount != TRUE) { 392*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_STATE); 393*b28c29d0SBiju Das return EMMC_ERR_STATE; 394*b28c29d0SBiju Das } 395*b28c29d0SBiju Das 396*b28c29d0SBiju Das /* id = PARTITION_ACCESS(Bit[2:0]) */ 397*b28c29d0SBiju Das if ((id & ~PARTITION_ID_MASK) != 0) { 398*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_PARAM); 399*b28c29d0SBiju Das return EMMC_ERR_PARAM; 400*b28c29d0SBiju Das } 401*b28c29d0SBiju Das 402*b28c29d0SBiju Das /* EXT_CSD[179] value */ 403*b28c29d0SBiju Das partition_config = 404*b28c29d0SBiju Das (uint32_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_PARTITION_CONFIG]; 405*b28c29d0SBiju Das if ((partition_config & PARTITION_ID_MASK) == id) { 406*b28c29d0SBiju Das result = EMMC_SUCCESS; 407*b28c29d0SBiju Das } else { 408*b28c29d0SBiju Das 409*b28c29d0SBiju Das partition_config = 410*b28c29d0SBiju Das (uint32_t) ((partition_config & ~PARTITION_ID_MASK) | id); 411*b28c29d0SBiju Das arg = EMMC_SWITCH_PARTITION_CONFIG | (partition_config << 8); 412*b28c29d0SBiju Das 413*b28c29d0SBiju Das result = emmc_set_ext_csd(arg); 414*b28c29d0SBiju Das } 415*b28c29d0SBiju Das 416*b28c29d0SBiju Das return result; 417*b28c29d0SBiju Das } 418*b28c29d0SBiju Das 419*b28c29d0SBiju Das static void set_sd_clk(uint32_t clkDiv) 420*b28c29d0SBiju Das { 421*b28c29d0SBiju Das uint32_t dataL; 422*b28c29d0SBiju Das 423*b28c29d0SBiju Das dataL = (GETR_32(SD_CLK_CTRL) & (~SD_CLK_CTRL_CLKDIV_MASK)); 424*b28c29d0SBiju Das 425*b28c29d0SBiju Das switch (clkDiv) { 426*b28c29d0SBiju Das case 1: 427*b28c29d0SBiju Das dataL |= 0x000000FFU; 428*b28c29d0SBiju Das break; /* 1/1 */ 429*b28c29d0SBiju Das case 2: 430*b28c29d0SBiju Das dataL |= 0x00000000U; 431*b28c29d0SBiju Das break; /* 1/2 */ 432*b28c29d0SBiju Das case 4: 433*b28c29d0SBiju Das dataL |= 0x00000001U; 434*b28c29d0SBiju Das break; /* 1/4 */ 435*b28c29d0SBiju Das case 8: 436*b28c29d0SBiju Das dataL |= 0x00000002U; 437*b28c29d0SBiju Das break; /* 1/8 */ 438*b28c29d0SBiju Das case 16: 439*b28c29d0SBiju Das dataL |= 0x00000004U; 440*b28c29d0SBiju Das break; /* 1/16 */ 441*b28c29d0SBiju Das case 32: 442*b28c29d0SBiju Das dataL |= 0x00000008U; 443*b28c29d0SBiju Das break; /* 1/32 */ 444*b28c29d0SBiju Das case 64: 445*b28c29d0SBiju Das dataL |= 0x00000010U; 446*b28c29d0SBiju Das break; /* 1/64 */ 447*b28c29d0SBiju Das case 128: 448*b28c29d0SBiju Das dataL |= 0x00000020U; 449*b28c29d0SBiju Das break; /* 1/128 */ 450*b28c29d0SBiju Das case 256: 451*b28c29d0SBiju Das dataL |= 0x00000040U; 452*b28c29d0SBiju Das break; /* 1/256 */ 453*b28c29d0SBiju Das case 512: 454*b28c29d0SBiju Das dataL |= 0x00000080U; 455*b28c29d0SBiju Das break; /* 1/512 */ 456*b28c29d0SBiju Das } 457*b28c29d0SBiju Das 458*b28c29d0SBiju Das SETR_32(SD_CLK_CTRL, dataL); 459*b28c29d0SBiju Das mmc_drv_obj.current_freq = (uint32_t) clkDiv; 460*b28c29d0SBiju Das } 461*b28c29d0SBiju Das 462*b28c29d0SBiju Das static void emmc_get_partition_access(void) 463*b28c29d0SBiju Das { 464*b28c29d0SBiju Das uint32_t reg; 465*b28c29d0SBiju Das EMMC_ERROR_CODE result; 466*b28c29d0SBiju Das 467*b28c29d0SBiju Das reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK); 468*b28c29d0SBiju Das if ((reg == PRR_PRODUCT_H3_CUT20) || (reg == PRR_PRODUCT_M3_CUT11)) { 469*b28c29d0SBiju Das SETR_32(SD_OPTION, 0x000060EEU); /* 8 bits width */ 470*b28c29d0SBiju Das /* CMD8 (EXT_CSD) */ 471*b28c29d0SBiju Das emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000U, 472*b28c29d0SBiju Das (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]), 473*b28c29d0SBiju Das EMMC_MAX_EXT_CSD_LENGTH, 474*b28c29d0SBiju Das HAL_MEMCARD_READ, HAL_MEMCARD_NOT_DMA); 475*b28c29d0SBiju Das mmc_drv_obj.get_partition_access_flag = TRUE; 476*b28c29d0SBiju Das result = 477*b28c29d0SBiju Das emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 478*b28c29d0SBiju Das mmc_drv_obj.get_partition_access_flag = FALSE; 479*b28c29d0SBiju Das if (result == EMMC_SUCCESS) { 480*b28c29d0SBiju Das mmc_drv_obj.partition_access = 481*b28c29d0SBiju Das (EMMC_PARTITION_ID) (mmc_drv_obj.ext_csd_data[179] 482*b28c29d0SBiju Das & PARTITION_ID_MASK); 483*b28c29d0SBiju Das } else if (result == EMMC_ERR_CMD_TIMEOUT) { 484*b28c29d0SBiju Das mmc_drv_obj.partition_access = PARTITION_ID_BOOT_1; 485*b28c29d0SBiju Das } else { 486*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_GET_PERTITION_ACCESS, 487*b28c29d0SBiju Das result); 488*b28c29d0SBiju Das panic(); 489*b28c29d0SBiju Das } 490*b28c29d0SBiju Das SETR_32(SD_OPTION, 0x0000C0EEU); /* Initialize */ 491*b28c29d0SBiju Das } 492*b28c29d0SBiju Das } 493*b28c29d0SBiju Das 494*b28c29d0SBiju Das static uint32_t emmc_calc_tran_speed(uint32_t *freq) 495*b28c29d0SBiju Das { 496*b28c29d0SBiju Das const uint32_t unit[8] = { 10000U, 100000U, 1000000U, 10000000U, 497*b28c29d0SBiju Das 0U, 0U, 0U, 0U }; /* frequency unit (1/10) */ 498*b28c29d0SBiju Das const uint32_t mult[16] = { 0U, 10U, 12U, 13U, 15U, 20U, 26U, 30U, 35U, 499*b28c29d0SBiju Das 40U, 45U, 52U, 55U, 60U, 70U, 80U }; 500*b28c29d0SBiju Das uint32_t tran_speed = EMMC_CSD_TRAN_SPEED(); 501*b28c29d0SBiju Das uint32_t max_freq; 502*b28c29d0SBiju Das uint32_t result; 503*b28c29d0SBiju Das 504*b28c29d0SBiju Das /* 505*b28c29d0SBiju Das * tran_speed = 0x32 506*b28c29d0SBiju Das * unit[tran_speed&0x7] = uint[0x2] = 1000000 507*b28c29d0SBiju Das * mult[(tran_speed&0x78)>>3] = mult[0x30>>3] = mult[6] = 26 508*b28c29d0SBiju Das * 1000000 * 26 = 26000000 (26MHz) 509*b28c29d0SBiju Das */ 510*b28c29d0SBiju Das 511*b28c29d0SBiju Das result = 1; 512*b28c29d0SBiju Das max_freq = 513*b28c29d0SBiju Das unit[tran_speed & EMMC_TRANSPEED_FREQ_UNIT_MASK] * 514*b28c29d0SBiju Das mult[(tran_speed & EMMC_TRANSPEED_MULT_MASK) >> 515*b28c29d0SBiju Das EMMC_TRANSPEED_MULT_SHIFT]; 516*b28c29d0SBiju Das 517*b28c29d0SBiju Das if (max_freq == 0) { 518*b28c29d0SBiju Das result = 0; 519*b28c29d0SBiju Das } else if (max_freq >= MMC_FREQ_52MHZ) { 520*b28c29d0SBiju Das *freq = MMC_52MHZ; 521*b28c29d0SBiju Das } else if (max_freq >= MMC_FREQ_26MHZ) { 522*b28c29d0SBiju Das *freq = MMC_26MHZ; 523*b28c29d0SBiju Das } else if (max_freq >= MMC_FREQ_20MHZ) { 524*b28c29d0SBiju Das *freq = MMC_20MHZ; 525*b28c29d0SBiju Das } else { 526*b28c29d0SBiju Das *freq = MMC_400KHZ; 527*b28c29d0SBiju Das } 528*b28c29d0SBiju Das 529*b28c29d0SBiju Das return result; 530*b28c29d0SBiju Das } 531*b28c29d0SBiju Das 532*b28c29d0SBiju Das static uint32_t emmc_set_timeout_register_value(uint32_t freq) 533*b28c29d0SBiju Das { 534*b28c29d0SBiju Das uint32_t timeout_cnt; /* SD_OPTION - Timeout Counter */ 535*b28c29d0SBiju Das 536*b28c29d0SBiju Das switch (freq) { 537*b28c29d0SBiju Das case 1U: 538*b28c29d0SBiju Das timeout_cnt = 0xE0U; 539*b28c29d0SBiju Das break; /* SDCLK * 2^27 */ 540*b28c29d0SBiju Das case 2U: 541*b28c29d0SBiju Das timeout_cnt = 0xE0U; 542*b28c29d0SBiju Das break; /* SDCLK * 2^27 */ 543*b28c29d0SBiju Das case 4U: 544*b28c29d0SBiju Das timeout_cnt = 0xD0U; 545*b28c29d0SBiju Das break; /* SDCLK * 2^26 */ 546*b28c29d0SBiju Das case 8U: 547*b28c29d0SBiju Das timeout_cnt = 0xC0U; 548*b28c29d0SBiju Das break; /* SDCLK * 2^25 */ 549*b28c29d0SBiju Das case 16U: 550*b28c29d0SBiju Das timeout_cnt = 0xB0U; 551*b28c29d0SBiju Das break; /* SDCLK * 2^24 */ 552*b28c29d0SBiju Das case 32U: 553*b28c29d0SBiju Das timeout_cnt = 0xA0U; 554*b28c29d0SBiju Das break; /* SDCLK * 2^23 */ 555*b28c29d0SBiju Das case 64U: 556*b28c29d0SBiju Das timeout_cnt = 0x90U; 557*b28c29d0SBiju Das break; /* SDCLK * 2^22 */ 558*b28c29d0SBiju Das case 128U: 559*b28c29d0SBiju Das timeout_cnt = 0x80U; 560*b28c29d0SBiju Das break; /* SDCLK * 2^21 */ 561*b28c29d0SBiju Das case 256U: 562*b28c29d0SBiju Das timeout_cnt = 0x70U; 563*b28c29d0SBiju Das break; /* SDCLK * 2^20 */ 564*b28c29d0SBiju Das case 512U: 565*b28c29d0SBiju Das timeout_cnt = 0x70U; 566*b28c29d0SBiju Das break; /* SDCLK * 2^20 */ 567*b28c29d0SBiju Das default: 568*b28c29d0SBiju Das timeout_cnt = 0xE0U; 569*b28c29d0SBiju Das break; /* SDCLK * 2^27 */ 570*b28c29d0SBiju Das } 571*b28c29d0SBiju Das 572*b28c29d0SBiju Das return timeout_cnt; 573*b28c29d0SBiju Das } 574*b28c29d0SBiju Das 575*b28c29d0SBiju Das EMMC_ERROR_CODE emmc_set_ext_csd(uint32_t arg) 576*b28c29d0SBiju Das { 577*b28c29d0SBiju Das EMMC_ERROR_CODE result; 578*b28c29d0SBiju Das 579*b28c29d0SBiju Das /* CMD6 */ 580*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD6_SWITCH, arg); 581*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 582*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 583*b28c29d0SBiju Das return result; 584*b28c29d0SBiju Das } 585*b28c29d0SBiju Das 586*b28c29d0SBiju Das /* CMD13 */ 587*b28c29d0SBiju Das emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16); 588*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 589*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 590*b28c29d0SBiju Das return result; 591*b28c29d0SBiju Das } 592*b28c29d0SBiju Das 593*b28c29d0SBiju Das /* CMD8 (EXT_CSD) */ 594*b28c29d0SBiju Das emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000, 595*b28c29d0SBiju Das (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]), 596*b28c29d0SBiju Das EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ, 597*b28c29d0SBiju Das HAL_MEMCARD_NOT_DMA); 598*b28c29d0SBiju Das result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response); 599*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 600*b28c29d0SBiju Das return result; 601*b28c29d0SBiju Das } 602*b28c29d0SBiju Das return EMMC_SUCCESS; 603*b28c29d0SBiju Das } 604*b28c29d0SBiju Das 605*b28c29d0SBiju Das EMMC_ERROR_CODE emmc_set_request_mmc_clock(uint32_t *freq) 606*b28c29d0SBiju Das { 607*b28c29d0SBiju Das /* parameter check */ 608*b28c29d0SBiju Das if (freq == NULL) { 609*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_PARAM); 610*b28c29d0SBiju Das return EMMC_ERR_PARAM; 611*b28c29d0SBiju Das } 612*b28c29d0SBiju Das 613*b28c29d0SBiju Das /* state check */ 614*b28c29d0SBiju Das if ((mmc_drv_obj.initialize != TRUE) 615*b28c29d0SBiju Das || (mmc_drv_obj.card_power_enable != TRUE)) { 616*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_STATE); 617*b28c29d0SBiju Das return EMMC_ERR_STATE; 618*b28c29d0SBiju Das } 619*b28c29d0SBiju Das 620*b28c29d0SBiju Das /* clock is already running in the desired frequency. */ 621*b28c29d0SBiju Das if ((mmc_drv_obj.clock_enable == TRUE) 622*b28c29d0SBiju Das && (mmc_drv_obj.current_freq == *freq)) { 623*b28c29d0SBiju Das return EMMC_SUCCESS; 624*b28c29d0SBiju Das } 625*b28c29d0SBiju Das 626*b28c29d0SBiju Das /* busy check */ 627*b28c29d0SBiju Das if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) { 628*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, 629*b28c29d0SBiju Das EMMC_ERR_CARD_BUSY); 630*b28c29d0SBiju Das return EMMC_ERR; 631*b28c29d0SBiju Das } 632*b28c29d0SBiju Das 633*b28c29d0SBiju Das set_sd_clk(*freq); 634*b28c29d0SBiju Das mmc_drv_obj.clock_enable = FALSE; 635*b28c29d0SBiju Das 636*b28c29d0SBiju Das return emmc_clock_ctrl(TRUE); /* clock on */ 637*b28c29d0SBiju Das } 638*b28c29d0SBiju Das 639*b28c29d0SBiju Das EMMC_ERROR_CODE rcar_emmc_mount(void) 640*b28c29d0SBiju Das { 641*b28c29d0SBiju Das EMMC_ERROR_CODE result; 642*b28c29d0SBiju Das 643*b28c29d0SBiju Das /* state check */ 644*b28c29d0SBiju Das if ((mmc_drv_obj.initialize != TRUE) 645*b28c29d0SBiju Das || (mmc_drv_obj.card_power_enable != TRUE) 646*b28c29d0SBiju Das || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) 647*b28c29d0SBiju Das ) { 648*b28c29d0SBiju Das emmc_write_error_info(EMMC_FUNCNO_MOUNT, EMMC_ERR_STATE); 649*b28c29d0SBiju Das return EMMC_ERR_STATE; 650*b28c29d0SBiju Das } 651*b28c29d0SBiju Das 652*b28c29d0SBiju Das /* initialize card (IDLE state --> Transfer state) */ 653*b28c29d0SBiju Das result = emmc_card_init(); 654*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 655*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT); 656*b28c29d0SBiju Das if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) { 657*b28c29d0SBiju Das /* nothing to do. */ 658*b28c29d0SBiju Das } 659*b28c29d0SBiju Das return result; 660*b28c29d0SBiju Das } 661*b28c29d0SBiju Das 662*b28c29d0SBiju Das /* Switching high speed mode */ 663*b28c29d0SBiju Das result = emmc_high_speed(); 664*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 665*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED); 666*b28c29d0SBiju Das if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) { 667*b28c29d0SBiju Das /* nothing to do. */ 668*b28c29d0SBiju Das } 669*b28c29d0SBiju Das return result; 670*b28c29d0SBiju Das } 671*b28c29d0SBiju Das 672*b28c29d0SBiju Das /* Changing the data bus width */ 673*b28c29d0SBiju Das result = emmc_bus_width(8); 674*b28c29d0SBiju Das if (result != EMMC_SUCCESS) { 675*b28c29d0SBiju Das emmc_write_error_info_func_no(EMMC_FUNCNO_BUS_WIDTH); 676*b28c29d0SBiju Das if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) { 677*b28c29d0SBiju Das /* nothing to do. */ 678*b28c29d0SBiju Das } 679*b28c29d0SBiju Das return result; 680*b28c29d0SBiju Das } 681*b28c29d0SBiju Das 682*b28c29d0SBiju Das /* mount complete */ 683*b28c29d0SBiju Das mmc_drv_obj.mount = TRUE; 684*b28c29d0SBiju Das 685*b28c29d0SBiju Das return EMMC_SUCCESS; 686*b28c29d0SBiju Das } 687