/* Copyright (c) 2013-2015, The Linux Foundation. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met:
 *     * Redistributions of source code must retain the above copyright
 *       notice, this list of conditions and the following disclaimer.
 *     * Redistributions in binary form must reproduce the above
 *       copyright notice, this list of conditions and the following
 *       disclaimer in the documentation and/or other materials provided
 *       with the distribution.
 *     * Neither the name of The Linux Foundation nor the names of its
 *       contributors may be used to endorse or promote products derived
 *       from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#include <string.h>
#include <stdlib.h>
#include <debug.h>
#include <reg.h>
#include <mmc_sdhci.h>
#include <sdhci.h>
#include <sdhci_msm.h>
#include <partition_parser.h>
#include <platform/iomap.h>
#include <platform/timer.h>
#include <platform.h>

extern void clock_init_mmc(uint32_t);
extern void clock_config_mmc(uint32_t, uint32_t);

/* data access time unit in ns */
static const uint32_t taac_unit[] =
{
	1, 10, 100, 1000, 10000, 100000, 1000000, 10000000
};

/* data access time value x 10 */
static const uint32_t taac_value[] =
{
	0, 10, 12, 13, 15, 20, 25, 30, 35, 40, 45, 50, 55, 60, 70, 80
};

/* data transfer rate in kbit/s */
static const uint32_t xfer_rate_unit[] =
{
	100, 1000, 10000, 100000, 0, 0, 0, 0
};

/* data transfer rate value x 10*/
static const uint32_t xfer_rate_value[] =
{
	0, 10, 12, 13, 15, 20, 26, 30, 35, 40, 45, 52, 55, 60, 70, 80
};

/*
 * Function: mmc decode and save csd
 * Arg     : Card structure & raw csd
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Decodes CSD response received from the card.
 *           Note that we have defined only few of the CSD elements
 *           in csd structure. We'll only decode those values.
 */
static uint32_t mmc_decode_and_save_csd(struct mmc_card *card)
{
	uint32_t mmc_sizeof = 0;
	uint32_t mmc_unit = 0;
	uint32_t mmc_value = 0;
	uint32_t mmc_temp = 0;
	uint32_t *raw_csd = card->raw_csd;

	struct mmc_csd mmc_csd;

	mmc_sizeof = sizeof(uint32_t) * 8;

	mmc_csd.cmmc_structure = UNPACK_BITS(raw_csd, 126, 2, mmc_sizeof);

	if (MMC_CARD_SD(card)) {
		/* Parse CSD according to SD card spec. */

		/* CSD register is little bit differnet for CSD version 2.0 High
		 * Capacity and CSD version 1.0/2.0 Standard memory cards.
		 * In Version 2.0 some of the fields have fixed values and it's
		 * not necessary for host to refer these fields in CSD sent by
		 * card
		 */

		if (mmc_csd.cmmc_structure == 1) {
			/* CSD Version 2.0 */
			mmc_csd.card_cmd_class = UNPACK_BITS(raw_csd, 84, 12, mmc_sizeof);
			/* Fixed value is 9 = 2^9 = 512 */
			mmc_csd.write_blk_len = 512;
			/* Fixed value is 9 = 512 */
			mmc_csd.read_blk_len = 512;
			/* Fixed value: 010b */
			mmc_csd.r2w_factor = 0x2;
			/* Not there in version 2.0 */
			mmc_csd.c_size_mult = 0;
			mmc_csd.c_size  = UNPACK_BITS(raw_csd, 48, 22, mmc_sizeof);
			mmc_csd.nsac_clk_cycle = UNPACK_BITS(raw_csd, 104, 8, mmc_sizeof)
									 * 100;

			mmc_unit = UNPACK_BITS(raw_csd, 112, 3, mmc_sizeof);
			mmc_value = UNPACK_BITS(raw_csd, 115, 4, mmc_sizeof);
			mmc_csd.taac_ns = (taac_value[mmc_value] * taac_unit[mmc_unit])
							   / 10;

			mmc_csd.erase_blk_len = 1;
			mmc_csd.read_blk_misalign = 0;
			mmc_csd.write_blk_misalign = 0;
			mmc_csd.read_blk_partial = 0;
			mmc_csd.write_blk_partial = 0;

			mmc_unit = UNPACK_BITS(raw_csd, 96, 3, mmc_sizeof);
			mmc_value = UNPACK_BITS(raw_csd, 99, 4, mmc_sizeof);
			mmc_csd.tran_speed = (xfer_rate_value[mmc_value] *
								 xfer_rate_unit[mmc_unit]) / 10;

			mmc_csd.wp_grp_size = 0x0;
			mmc_csd.wp_grp_enable = 0x0;
			mmc_csd.perm_wp = UNPACK_BITS(raw_csd, 13, 1, mmc_sizeof);
			mmc_csd.temp_wp = UNPACK_BITS(raw_csd, 12, 1, mmc_sizeof);

			/* Calculate the card capcity */
			card->capacity = (unsigned long long) (1 + mmc_csd.c_size) * 512 * 1024;
		} else {
			/* CSD Version 1.0 */
			mmc_csd.card_cmd_class = UNPACK_BITS(raw_csd, 84, 12, mmc_sizeof);

			mmc_temp = UNPACK_BITS(raw_csd, 22, 4, mmc_sizeof);
			mmc_csd.write_blk_len = (mmc_temp > 8 && mmc_temp < 12) ?
									(1 << mmc_temp) : 512;

			mmc_temp = UNPACK_BITS(raw_csd, 80, 4, mmc_sizeof);
			mmc_csd.read_blk_len = (mmc_temp > 8 && mmc_temp < 12) ?
								   (1 << mmc_temp) : 512;

			mmc_unit = UNPACK_BITS(raw_csd, 112, 3, mmc_sizeof);
			mmc_value = UNPACK_BITS(raw_csd, 115, 4, mmc_sizeof);
			mmc_csd.taac_ns = (taac_value[mmc_value] * taac_unit[mmc_unit])
							  / 10;

			mmc_unit = UNPACK_BITS(raw_csd, 96, 3, mmc_sizeof);
			mmc_value = UNPACK_BITS(raw_csd, 99, 4, mmc_sizeof);
			mmc_csd.tran_speed = (xfer_rate_value[mmc_value] *
								 xfer_rate_unit[mmc_unit]) / 10;

			mmc_csd.nsac_clk_cycle = UNPACK_BITS(raw_csd, 104, 8, mmc_sizeof)
									 * 100;

			mmc_csd.r2w_factor = UNPACK_BITS(raw_csd, 26, 3, mmc_sizeof);
			mmc_csd.sector_size = UNPACK_BITS(raw_csd, 39, 7, mmc_sizeof) + 1;

			mmc_csd.erase_blk_len = UNPACK_BITS(raw_csd, 46, 1, mmc_sizeof);
			mmc_csd.read_blk_misalign = UNPACK_BITS(raw_csd, 77, 1, mmc_sizeof);
			mmc_csd.write_blk_misalign = UNPACK_BITS(raw_csd, 78, 1, mmc_sizeof);
			mmc_csd.read_blk_partial = UNPACK_BITS(raw_csd, 79, 1, mmc_sizeof);
			mmc_csd.write_blk_partial = UNPACK_BITS(raw_csd, 21, 1, mmc_sizeof);

			mmc_csd.c_size_mult = UNPACK_BITS(raw_csd, 47, 3, mmc_sizeof);
			mmc_csd.c_size = UNPACK_BITS(raw_csd, 62, 12, mmc_sizeof);
			mmc_csd.wp_grp_size = UNPACK_BITS(raw_csd, 32, 7, mmc_sizeof);
			mmc_csd.wp_grp_enable = UNPACK_BITS(raw_csd, 31, 1, mmc_sizeof);
			mmc_csd.perm_wp = UNPACK_BITS(raw_csd, 13, 1, mmc_sizeof);
			mmc_csd.temp_wp = UNPACK_BITS(raw_csd, 12, 1, mmc_sizeof);

			/* Calculate the card capacity */
			mmc_temp = (1 << (mmc_csd.c_size_mult + 2)) * (mmc_csd.c_size + 1);
			card->capacity = (unsigned long long)mmc_temp * mmc_csd.read_blk_len;
		}
	} else {
		/* Parse CSD according to MMC card spec. */
		mmc_csd.spec_vers = UNPACK_BITS(raw_csd, 122, 4, mmc_sizeof);
		mmc_csd.card_cmd_class = UNPACK_BITS(raw_csd, 84, 12, mmc_sizeof);
		mmc_csd.write_blk_len = 1 << UNPACK_BITS(raw_csd, 22, 4, mmc_sizeof);
		mmc_csd.read_blk_len =  1 << UNPACK_BITS(raw_csd, 80, 4, mmc_sizeof);
		mmc_csd.r2w_factor = UNPACK_BITS(raw_csd, 26, 3, mmc_sizeof);
		mmc_csd.c_size_mult = UNPACK_BITS(raw_csd, 47, 3, mmc_sizeof);
		mmc_csd.c_size = UNPACK_BITS(raw_csd, 62, 12, mmc_sizeof);
		mmc_csd.nsac_clk_cycle = UNPACK_BITS(raw_csd, 104, 8, mmc_sizeof) * 100;

		mmc_unit = UNPACK_BITS(raw_csd, 112, 3, mmc_sizeof);
		mmc_value = UNPACK_BITS(raw_csd, 115, 4, mmc_sizeof);
		mmc_csd.taac_ns = (taac_value[mmc_value] * taac_unit[mmc_unit]) / 10;

		mmc_csd.read_blk_misalign = UNPACK_BITS(raw_csd, 77, 1, mmc_sizeof);
		mmc_csd.write_blk_misalign = UNPACK_BITS(raw_csd, 78, 1, mmc_sizeof);
		mmc_csd.read_blk_partial = UNPACK_BITS(raw_csd, 79, 1, mmc_sizeof);
		mmc_csd.write_blk_partial = UNPACK_BITS(raw_csd, 21, 1, mmc_sizeof);

		/* Ignore -- no use of this value. */
		mmc_csd.tran_speed = 0x00;

		mmc_csd.erase_grp_size = UNPACK_BITS(raw_csd, 42, 5, mmc_sizeof);
		mmc_csd.erase_grp_mult = UNPACK_BITS(raw_csd, 37, 5, mmc_sizeof);
		mmc_csd.wp_grp_size = UNPACK_BITS(raw_csd, 32, 5, mmc_sizeof);
		mmc_csd.wp_grp_enable = UNPACK_BITS(raw_csd, 31, 1, mmc_sizeof);
		mmc_csd.perm_wp = UNPACK_BITS(raw_csd, 13, 1, mmc_sizeof);
		mmc_csd.temp_wp = UNPACK_BITS(raw_csd, 12, 1, mmc_sizeof);

		/* Calculate the card capcity */
		if (mmc_csd.c_size != 0xFFF) {
			/* For cards less than or equal to 2GB */
			mmc_temp = (1 << (mmc_csd.c_size_mult + 2)) * (mmc_csd.c_size + 1);
			card->capacity = (unsigned long long) mmc_temp * mmc_csd.read_blk_len;
		} else {
			/* For cards greater than 2GB, Ext CSD register's SEC_COUNT
			 * is used to calculate the size.
			 */
			uint64_t sec_count;

			sec_count = (card->ext_csd[MMC_SEC_COUNT4] << MMC_SEC_COUNT4_SHIFT)
						| (card->ext_csd[MMC_SEC_COUNT3] << MMC_SEC_COUNT3_SHIFT)
						| (card->ext_csd[MMC_SEC_COUNT2] << MMC_SEC_COUNT2_SHIFT)
						| card->ext_csd[MMC_SEC_COUNT1];
			card->capacity = sec_count * MMC_BLK_SZ;
		}
	}

	/* save the information in card structure */
	memcpy((struct mmc_csd *)&card->csd,(struct mmc_csd *)&mmc_csd,
			sizeof(struct mmc_csd));

	if (MMC_CARD_MMC(card)) {

		/* Calculate the wp grp size */
		if (card->ext_csd[MMC_ERASE_GRP_DEF])
			card->wp_grp_size = MMC_HC_ERASE_MULT * card->ext_csd[MMC_HC_ERASE_GRP_SIZE] / MMC_BLK_SZ;
		else
			card->wp_grp_size = (card->csd.wp_grp_size + 1) * (card->csd.erase_grp_size + 1) \
						  * (card->csd.erase_grp_mult + 1);

		card->rpmb_size = RPMB_PART_MIN_SIZE * card->ext_csd[RPMB_SIZE_MULT];
		card->rel_wr_count = card->ext_csd[REL_WR_SEC_C];
	}
	else {
		card->wp_grp_size = (card->csd.wp_grp_size + 1) * (card->csd.erase_grp_size + 1) \
						* (card->csd.erase_grp_mult + 1);
	}

	dprintf(SPEW, "Decoded CSD fields:\n");
	dprintf(SPEW, "cmmc_structure: %u\n", mmc_csd.cmmc_structure);
	dprintf(SPEW, "card_cmd_class: %x\n", mmc_csd.card_cmd_class);
	dprintf(SPEW, "write_blk_len: %u\n", mmc_csd.write_blk_len);
	dprintf(SPEW, "read_blk_len: %u\n", mmc_csd.read_blk_len);
	dprintf(SPEW, "r2w_factor: %u\n", mmc_csd.r2w_factor);
	dprintf(SPEW, "sector_size: %u\n", mmc_csd.sector_size);
	dprintf(SPEW, "c_size_mult:%u\n", mmc_csd.c_size_mult);
	dprintf(SPEW, "c_size: %u\n", mmc_csd.c_size);
	dprintf(SPEW, "nsac_clk_cycle: %u\n", mmc_csd.nsac_clk_cycle);
	dprintf(SPEW, "taac_ns: %u\n", mmc_csd.taac_ns);
	dprintf(SPEW, "tran_speed: %u kbps\n", mmc_csd.tran_speed);
	dprintf(SPEW, "erase_blk_len: %u\n", mmc_csd.erase_blk_len);
	dprintf(SPEW, "read_blk_misalign: %u\n", mmc_csd.read_blk_misalign);
	dprintf(SPEW, "write_blk_misalign: %u\n", mmc_csd.write_blk_misalign);
	dprintf(SPEW, "read_blk_partial: %u\n", mmc_csd.read_blk_partial);
	dprintf(SPEW, "write_blk_partial: %u\n", mmc_csd.write_blk_partial);
	dprintf(SPEW, "wp_grp_size: %u\n", card->wp_grp_size);
	dprintf(SPEW, "Card Capacity: %llu Bytes\n", card->capacity);

	return 0;
}

/*
 * Function: mmc decode & save cid
 * Arg     : card structure & raw cid
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Decode CID sent by the card.
 */
static uint32_t mmc_decode_and_save_cid(struct mmc_card *card,
										uint32_t *raw_cid)
{
	struct mmc_cid mmc_cid;
	uint32_t mmc_sizeof = 0;
	int i = 0;

	if (!raw_cid) {
		return 1;
	}

	mmc_sizeof = sizeof(uint32_t) * 8;

	if (MMC_CARD_SD(card)) {
		mmc_cid.mid = UNPACK_BITS(raw_cid, 120, 8, mmc_sizeof);
		mmc_cid.oid = UNPACK_BITS(raw_cid, 104, 16, mmc_sizeof);

		for (i = 0; i < 5; i++) {
			mmc_cid.pnm[i] = (uint8_t)UNPACK_BITS(raw_cid,
								    (104 - 8 * (i + 1)),
								    8,
								    mmc_sizeof);
		}
		mmc_cid.pnm[5] = 0;
		mmc_cid.pnm[6] = 0;

		mmc_cid.prv = UNPACK_BITS(raw_cid, 56, 8, mmc_sizeof);
		mmc_cid.psn = UNPACK_BITS(raw_cid, 24, 32, mmc_sizeof);
		mmc_cid.month = UNPACK_BITS(raw_cid, 8, 4, mmc_sizeof);
		mmc_cid.year = UNPACK_BITS(raw_cid, 12, 8, mmc_sizeof);
		mmc_cid.year += 2000;
	} else {
		mmc_cid.mid = UNPACK_BITS(raw_cid, 120, 8, mmc_sizeof);
		mmc_cid.oid = UNPACK_BITS(raw_cid, 104, 16, mmc_sizeof);

		for (i = 0; i < 6; i++) {
			mmc_cid.pnm[i] = (uint8_t)UNPACK_BITS(raw_cid, (104 - 8 * (i + 1)),
												  8, mmc_sizeof);
		}
		mmc_cid.pnm[6] = 0;

		mmc_cid.prv = UNPACK_BITS(raw_cid, 48, 8, mmc_sizeof);
		mmc_cid.psn = UNPACK_BITS(raw_cid, 16, 32, mmc_sizeof);
		mmc_cid.month = UNPACK_BITS(raw_cid, 8, 4, mmc_sizeof);
		mmc_cid.year = UNPACK_BITS(raw_cid, 12, 4, mmc_sizeof);
		mmc_cid.year += 1997;
	}

	/* save it in card database */
	memcpy((struct mmc_cid *)&card->cid,
	       (struct mmc_cid *)&mmc_cid, sizeof(struct mmc_cid));

	dprintf(SPEW, "Decoded CID fields:\n");
	dprintf(SPEW, "Manufacturer ID: %x\n", mmc_cid.mid);
	dprintf(SPEW, "OEM ID: 0x%x\n", mmc_cid.oid);
	dprintf(SPEW, "Product Name: %s\n", mmc_cid.pnm);
	dprintf(SPEW, "Product revision: %d.%d\n", (mmc_cid.prv >> 4),
											   (mmc_cid.prv & 0xF));
	dprintf(SPEW, "Product serial number: %X\n", mmc_cid.psn);
	dprintf(SPEW, "Manufacturing date: %d %d\n", mmc_cid.month, mmc_cid.year);

	return 0;
}

/*
 * Function: mmc reset cards
 * Arg     : host structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Reset all the cards to idle condition (CMD 0)
 */
static uint8_t mmc_reset_card(struct sdhci_host *host)
{
	struct mmc_command cmd;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	cmd.cmd_index = CMD0_GO_IDLE_STATE;
	cmd.argument = 0;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_NONE;

	/* send command */
	return sdhci_send_command(host, &cmd);
}

/*
 * Function: mmc operations command
 * Arg     : host & card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Send CMD1 to know whether the card supports host VDD profile or not.
 */
static uint32_t mmc_send_op_cond(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_resp = 0;
	uint32_t mmc_ret = 0;
	uint32_t mmc_retry = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD1 format:
	 * [31] Busy bit
	 * [30:29] Access mode
	 * [28:24] reserved
	 * [23:15] 2.7-3.6
	 * [14:8]  2.0-2.6
	 * [7]     1.7-1.95
	 * [6:0]   reserved
	 */

	cmd.cmd_index = CMD1_SEND_OP_COND;
	cmd.argument = card->ocr;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R3;

	do {
		mmc_ret = sdhci_send_command(host, &cmd);
		if (mmc_ret)
			return mmc_ret;

		/* Command returned success, now it's time to examine response */
		mmc_resp = cmd.resp[0];

		/* Check the response for busy status */
		if (!(mmc_resp & MMC_OCR_BUSY)) {
			mmc_retry++;
			mdelay(1);
			continue;
		} else
			break;
	} while (mmc_retry < MMC_MAX_COMMAND_RETRY);

	/* If we reached here after max retries, we failed to get OCR */
	if (mmc_retry == MMC_MAX_COMMAND_RETRY && !(mmc_resp & MMC_OCR_BUSY)) {
		dprintf(CRITICAL, "Card has busy status set. Init did not complete\n");
		return 1;
	}

	/* Response contains card's ocr. Update card's information */
	card->ocr = mmc_resp;

	if (mmc_resp & MMC_OCR_SEC_MODE)
		card->type = MMC_TYPE_MMCHC;
	else
		card->type = MMC_TYPE_STD_MMC;

	return 0;
}

/*
 * Function: mmc send cid
 * Arg     : host & card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Request any card to send its uniquie card identification
 *           (CID) number (CMD2).
 */
static uint32_t mmc_all_send_cid(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD2 Format:
	 * [31:0] stuff bits
	 */
	cmd.cmd_index = CMD2_ALL_SEND_CID;
	cmd.argument = 0;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R2;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret) {
		return mmc_ret;
	}

	/* Response contains card's 128 bits CID register */
	mmc_ret = mmc_decode_and_save_cid(card, cmd.resp);
	if (mmc_ret) {
		return mmc_ret;
	}

	return 0;
}

/*
 * Function: mmc send relative address
 * Arg     : host & card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Ask card to send it's relative card address (RCA).
 *           This RCA number is shorter than CID and is used by
 *           the host to address the card in future (CMD3)
 */
static uint32_t mmc_send_relative_address(struct sdhci_host *host,
										  struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD3 Format:
	 * [31:0] stuff bits
	 */
	if (MMC_CARD_SD(card)) {
		cmd.cmd_index = CMD3_SEND_RELATIVE_ADDR;
		cmd.argument = 0;
		cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
		cmd.resp_type = SDHCI_CMD_RESP_R6;

		/* send command */
		mmc_ret = sdhci_send_command(host, &cmd);
		if (mmc_ret)
			return mmc_ret;

		/* For sD, card will send RCA. Store it */
		card->rca = (cmd.resp[0] >> 16);
	} else {
		cmd.cmd_index = CMD3_SEND_RELATIVE_ADDR;
		cmd.argument = (MMC_RCA << 16);
		card->rca = (cmd.argument >> 16);
		cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
		cmd.resp_type = SDHCI_CMD_RESP_R6;

		/* send command */
		mmc_ret = sdhci_send_command(host, &cmd);
		if (mmc_ret)
			return mmc_ret;
	}

	return 0;
}

/*
 * Function: mmc send csd
 * Arg     : host, card structure & o/p arg to store csd
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Requests card to send it's CSD register's contents. (CMD9)
 */
static uint32_t mmc_send_csd(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_arg = 0;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD9 Format:
	 * [31:16] RCA
	 * [15:0] stuff bits
	 */
	mmc_arg |= card->rca << 16;

	cmd.cmd_index = CMD9_SEND_CSD;
	cmd.argument = mmc_arg;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R2;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret)
		return mmc_ret;

	/* response contains the card csd */
	memcpy(card->raw_csd, cmd.resp, sizeof(cmd.resp));

	return 0;
}

/*
 * Function: mmc select card
 * Arg     : host, card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Selects a card by sending CMD7 to the card with its RCA.
 *           If RCA field is set as 0 ( or any other address ),
 *           the card will be de-selected. (CMD7)
 */
static uint32_t mmc_select_card(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_arg = 0;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD7 Format:
	 * [31:16] RCA
	 * [15:0] stuff bits
	 */
	mmc_arg |= card->rca << 16;

	cmd.cmd_index = CMD7_SELECT_DESELECT_CARD;
	cmd.argument = mmc_arg;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;

	/* If we are deselecting card, we do not get response */
	if (card->rca) {
		if (MMC_CARD_SD(card))
			cmd.resp_type = SDHCI_CMD_RESP_R1B;
		else
			cmd.resp_type = SDHCI_CMD_RESP_R1;
	} else
		cmd.resp_type = SDHCI_CMD_RESP_NONE;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret)
		return mmc_ret;

	return 0;
}

/*
 * Function: mmc set block len
 * Arg     : host, card structure & block length
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Send command to set block length.
 */
static uint32_t mmc_set_block_len(struct sdhci_host *host,
								  struct mmc_card *card,
								  uint32_t block_len)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD16 Format:
	 * [31:0] block length
	 */

	cmd.cmd_index = CMD16_SET_BLOCKLEN;
	cmd.argument = block_len;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret)
		return mmc_ret;

	/*
	 * If blocklength is larger than 512 bytes,
	 * the card sets BLOCK_LEN_ERROR bit.
	 */
	if (cmd.resp[0] & MMC_R1_BLOCK_LEN_ERR) {
		dprintf(CRITICAL, "The block length is not supported by the card\n");
		return 1;
	}

	return 0;
}

/*
 * Function: mmc get card status
 * Arg     : host, card structure & o/p argument card status
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Get the current status of the card
 */
static uint32_t mmc_get_card_status(struct sdhci_host *host,
									struct mmc_card *card, uint32_t *status)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD13 Format:
	 * [31:16] RCA
	 * [15:0] stuff bits
	 */
	cmd.cmd_index = CMD13_SEND_STATUS;
	cmd.argument = card->rca << 16;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret)
		return mmc_ret;

	/* Checking ADDR_OUT_OF_RANGE error in CMD13 response */
	if ((cmd.resp[0] >> 31) & 0x01)
		return 1;

	*status = cmd.resp[0];
	return 0;
}

/*
 * Function: mmc get ext csd
 * Arg     : host, card structure & array to hold ext attributes
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Send ext csd command & get the card attributes
 */
static uint32_t mmc_get_ext_csd(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	card->ext_csd = memalign(CACHE_LINE, ROUNDUP(512, CACHE_LINE));

	ASSERT(card->ext_csd);

	memset(card->ext_csd, 0, sizeof(card->ext_csd));

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD8 */
	cmd.cmd_index = CMD8_SEND_EXT_CSD;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.data.data_ptr = card->ext_csd;
	cmd.data.num_blocks = 1;
	cmd.data_present = 0x1;
	cmd.trans_mode = SDHCI_MMC_READ;

	/* send command */
	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret)
		return mmc_ret;

	return mmc_ret;
}

/*
 * Function: mmc switch command
 * Arg     : Host, card structure, access mode, index & value to be set
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Send switch command to the card to set the ext attribute @ index
 */
static uint32_t mmc_switch_cmd(struct sdhci_host *host, struct mmc_card *card,
							   uint32_t access, uint32_t index, uint32_t value)
{

	struct mmc_command cmd;
	uint32_t mmc_ret = 0;
	uint32_t mmc_status;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD6 Format:
	 * [31:26] set to 0
	 * [25:24] access
	 * [23:16] index
	 * [15:8] value
	 * [7:3] set to 0
	 * [2:0] cmd set
	 */
	cmd.cmd_index = CMD6_SWITCH_FUNC;
	cmd.argument |= (access << 24);
	cmd.argument |= (index << 16);
	cmd.argument |= (value << 8);
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1B;

	mmc_ret = sdhci_send_command(host, &cmd);
	if (mmc_ret) {
		dprintf(CRITICAL, "CMD6 send failed\n");
		return mmc_ret;
	}

	/* Check if the card completed the switch command processing */
	mmc_ret = mmc_get_card_status(host, card, &mmc_status);
	if (mmc_ret) {
		dprintf(CRITICAL, "Get card status failed\n");
		return mmc_ret;
	}

	if (MMC_CARD_STATUS(mmc_status) != MMC_TRAN_STATE) {
		dprintf(CRITICAL, "Switch cmd failed. Card not in tran state %x\n", mmc_status);
		mmc_ret = 1;
	}

	if (mmc_status & MMC_SWITCH_FUNC_ERR_FLAG) {
		dprintf(CRITICAL, "Switch cmd failed. Switch Error.\n");
		mmc_ret = 1;
	}

	return mmc_ret;
}

bool mmc_set_drv_type(struct sdhci_host *host, struct mmc_card *card, uint8_t drv_type)
{
	uint32_t ret = 0;
	bool drv_type_changed = false;

	uint32_t value = ((drv_type << 4) | MMC_HS200_TIMING);

	if (MMC_CARD_MMC(card)) {
		if (card->ext_csd[MMC_EXT_MMC_DRV_STRENGTH] & (1 << drv_type))
			ret = mmc_switch_cmd(host, card, MMC_ACCESS_WRITE, MMC_EXT_MMC_HS_TIMING, value);
		if (!ret)
			drv_type_changed = true;
	}
	return drv_type_changed;
}
/*
 * Function: mmc set bus width
 * Arg     : Host, card structure & width
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Send switch command to set bus width
 */
static uint32_t mmc_set_bus_width(struct sdhci_host *host,
								  struct mmc_card *card,
								  uint32_t width)
{
	uint32_t mmc_ret = 0;

	mmc_ret = mmc_switch_cmd(host, card, MMC_ACCESS_WRITE,
							 MMC_EXT_MMC_BUS_WIDTH, width);

	if (mmc_ret) {
		dprintf(CRITICAL, "Switch cmd failed\n");
		return mmc_ret;
	}

	return 0;
}


/*
 * Function: mmc card supports hs400 mode
 * Arg     : None
 * Return  : 1 if hs400 mode is supported, 0 otherwise
 * Flow    : Check the ext csd attributes of the card
 */
static uint8_t mmc_card_supports_hs400_mode(struct mmc_card *card)
{
	if (MMC_CARD_MMC(card)) {
		if (card->ext_csd[MMC_DEVICE_TYPE] & MMC_HS_HS400_MODE)
			return 1;
		else
			return 0;
	}
	else
		return 0;
}

/*
 * Function: mmc card supports hs200 mode
 * Arg     : None
 * Return  : 1 if HS200 mode is supported, 0 otherwise
 * Flow    : Check the ext csd attributes of the card
 */
static uint8_t mmc_card_supports_hs200_mode(struct mmc_card *card)
{
	if (MMC_CARD_MMC(card)) {
		if (card->ext_csd[MMC_DEVICE_TYPE] & MMC_HS_HS200_MODE)
			return 1;
		else
			return 0;
	}
	else
		return 0;
}

/*
 * Function: mmc card supports ddr mode
 * Arg     : None
 * Return  : 1 if DDR mode is supported, 0 otherwise
 * Flow    : Check the ext csd attributes of the card
 */
static uint8_t mmc_card_supports_ddr_mode(struct mmc_card *card)
{
	if (MMC_CARD_MMC(card)) {
		if (card->ext_csd[MMC_DEVICE_TYPE] & MMC_HS_DDR_MODE)
			return 1;
		else
			return 0;
	}
	else
		return 0;
}

/*
 * Function : Enable HS200 mode
 * Arg      : Host, card structure and bus width
 * Return   : 0 on Success, 1 on Failure
 * Flow     :
 *           - Set the bus width to 4/8 bit SDR as supported by the target & host
 *           - Set the HS_TIMING on ext_csd 185 for the card
 */
static uint32_t mmc_set_hs200_mode(struct sdhci_host *host,
								   struct mmc_card *card, uint32_t width)
{
	uint32_t mmc_ret = 0;

	DBG("\n Enabling HS200 Mode Start\n");

	/* Set 4/8 bit SDR bus width */
	mmc_ret = mmc_set_bus_width(host, card, width);
	if (mmc_ret) {
		dprintf(CRITICAL, "Failure to set wide bus for Card(RCA:%x)\n",
						  card->rca);
		return mmc_ret;
	}

	/* Setting HS200 in HS_TIMING using EXT_CSD (CMD6) */
	mmc_ret = mmc_switch_cmd(host, card, MMC_ACCESS_WRITE, MMC_EXT_MMC_HS_TIMING, MMC_HS200_TIMING);

	if (mmc_ret) {
		dprintf(CRITICAL, "Switch cmd returned failure %d\n", __LINE__);
		return mmc_ret;
	}

	/* Enable SDR104 mode in controller */
	sdhci_set_uhs_mode(host, SDHCI_SDR104_MODE);

	/* Run the clock @ 400 Mhz */
	if (host->caps.hs400_support && mmc_card_supports_hs400_mode(card))
	{
		/* Save the timing value, before changing the clock */
		MMC_SAVE_TIMING(host, MMC_HS400_TIMING);
		/*
		* Set the MCI_CLK divider before changing the sdcc core
		* core clk to ensure card receives no more than 200 MHZ
		* clock frequency
		*/
		sdhci_msm_set_mci_clk(host);
		clock_config_mmc(host->msm_host->slot, SDHCI_CLK_400MHZ);
	}

	/* Execute Tuning for hs200 mode */
	if ((mmc_ret = sdhci_msm_execute_tuning(host, card, width)))
		dprintf(CRITICAL, "Tuning for hs200 failed\n");

	/* Once the tuning is executed revert back the clock to 200MHZ
	 * and disable the MCI_CLK divider so that we can use SDHC clock
	 * divider to supply clock to the card
	 */
	if (host->timing == MMC_HS400_TIMING)
	{
		MMC_SAVE_TIMING(host, MMC_HS200_TIMING);
		sdhci_msm_set_mci_clk(host);
		clock_config_mmc(host->msm_host->slot, MMC_CLK_192MHZ);
	}
	else
	{
		/* Save the timing value, before changing the clock */
		MMC_SAVE_TIMING(host, MMC_HS200_TIMING);
	}


	DBG("\n Enabling HS200 Mode Done\n");

	return mmc_ret;
}

/*
 * Function: mmc set ddr mode
 * Arg     : Host & card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Set bus width for ddr mode & set controller in DDR mode
*/
static uint8_t mmc_set_ddr_mode(struct sdhci_host *host, struct mmc_card *card)
{
	uint8_t mmc_ret = 0;

	DBG("\n Enabling DDR Mode Start\n");

	/* Set width for 8 bit DDR mode by default */
	mmc_ret = mmc_set_bus_width(host, card, DATA_DDR_BUS_WIDTH_8BIT);

	if (mmc_ret) {
		dprintf(CRITICAL, "Failure to set DDR mode for Card(RCA:%x)\n",
						  card->rca);
		return mmc_ret;
	}

	/* Save the timing value, before changing the clock */
	MMC_SAVE_TIMING(host, SDHCI_DDR50_MODE);

	/* Set the DDR mode in controller */
	sdhci_set_uhs_mode(host, SDHCI_DDR50_MODE);

	DBG("\n Enabling DDR Mode Done\n");

	return 0;
}

/*
 * Function: mmc set high speed interface
 * Arg     : Host & card structure
 * Return  : None
 * Flow    : Sets the sdcc clock & clock divider in the host controller
 *           Adjust the interface speed to optimal speed
 */
static uint32_t mmc_set_hs_interface(struct sdhci_host *host,
									 struct mmc_card *card)
{
	uint32_t mmc_ret = 0;

	/* Setting HS_TIMING in EXT_CSD (CMD6) */
	mmc_ret = mmc_switch_cmd(host, card, MMC_ACCESS_WRITE,
							 MMC_EXT_MMC_HS_TIMING, MMC_HS_TIMING);

	if (mmc_ret) {
		dprintf(CRITICAL, "Switch cmd returned failure %d\n", __LINE__);
		return mmc_ret;
	}

	/* Save the timing value, before changing the clock */
	MMC_SAVE_TIMING(host, SDHCI_SDR25_MODE);

	/* Set the SDR25 mode in controller */
	sdhci_set_uhs_mode(host, SDHCI_SDR25_MODE);

	return 0;
}

/*
 * Function : Enable HS400 mode
 * Arg      : Host, card structure and bus width
 * Return   : 0 on Success, 1 on Failure
 * Flow     :
 *           - Set the bus width to 8 bit DDR
 *           - Set the HS_TIMING on ext_csd 185 for the card
 */
uint32_t mmc_set_hs400_mode(struct sdhci_host *host,
								   struct mmc_card *card, uint32_t width)
{
	uint32_t mmc_ret = 0;

	/*
	 * Emmc 5.0 spec does not allow changing to hs400 mode directly
	 * Need to follow the sequence to change to hs400 mode
	 * 1. Enable HS200 mode, perform tuning
	 * 2. Change to high speed mode
	 * 3. Enable DDR mode
	 * 4. Enable HS400 mode & execute tuning
	 */

	DBG("\n Enabling HS400 Mode Start\n");
	/* HS400 mode is supported only in DDR 8-bit */
	if (width != DATA_BUS_WIDTH_8BIT)
	{
		dprintf(CRITICAL, "Bus width is not 8-bit, cannot switch to hs400: %u\n", width);
		return 1;
	}

	/* 1.Enable HS200 mode */
	mmc_ret = mmc_set_hs200_mode(host, card, width);

	if (mmc_ret)
	{
		dprintf(CRITICAL, "Failure Setting HS200 mode %s\t%d\n",__func__, __LINE__);
		return mmc_ret;
	}

	/* 2. Enable High speed mode */
	/* This is needed to set the clock to a low value &
	 * so that we can switch to hs_timing --> 0x1 */
	/* Save the timing value, before changing the clock */
	MMC_SAVE_TIMING(host, SDHCI_SDR12_MODE);
	sdhci_set_uhs_mode(host, SDHCI_SDR12_MODE);

	/* 3. Set HS_TIMING to 0x1 */
	mmc_ret = mmc_set_hs_interface(host, card);
	if (mmc_ret)
	{
		dprintf(CRITICAL, "Error adjusting interface speed!:%s\t%d\n", __func__, __LINE__);
		return mmc_ret;
	}

	/*4. Enable DDR mode */
	mmc_ret = mmc_set_ddr_mode(host, card);
	if (mmc_ret)
	{
		dprintf(CRITICAL, "Failure setting DDR mode:%s\t%d\n", __func__, __LINE__);
		return mmc_ret;
	}

	/*5. Set hs400 timing */
	mmc_ret = mmc_switch_cmd(host, card, MMC_ACCESS_WRITE, MMC_EXT_MMC_HS_TIMING, MMC_HS400_TIMING);

	if (mmc_ret)
	{
		dprintf(CRITICAL, "Switch cmd returned failure %s\t%d\n",__func__,  __LINE__);
		return mmc_ret;
	}

	/* 6. Enable SDR104 mode in controller */
	/* Save the timing value, before changing the clock */
	MMC_SAVE_TIMING(host, MMC_HS400_TIMING);
	sdhci_set_uhs_mode(host, SDHCI_SDR104_MODE);
	/*
	* Enable HS400 mode
	*/
	sdhci_msm_set_mci_clk(host);
	/* Set the clock back to 400 MHZ */
	clock_config_mmc(host->msm_host->slot, SDHCI_CLK_400MHZ);

	/* 7. Execute Tuning for hs400 mode */
	if ((mmc_ret = sdhci_msm_execute_tuning(host, card, width)))
		dprintf(CRITICAL, "Tuning for hs400 failed\n");

	DBG("\n Enabling HS400 Mode Done\n");

	return mmc_ret;
}

/*
 * Function: mmc_host_init
 * Arg     : mmc device structure
 * Return  : 0 on success, 1 on Failure
 * Flow    : Initialize the host contoller
 *           Set the clock rate to 400 KHZ for init
 */
static uint8_t mmc_host_init(struct mmc_device *dev)
{
	uint8_t mmc_ret = 0;

	struct sdhci_host *host;
	struct mmc_config_data *cfg;
	struct sdhci_msm_data *data;

	event_t sdhc_event;

	host = &dev->host;
	cfg = &dev->config;

	event_init(&sdhc_event, false, EVENT_FLAG_AUTOUNSIGNAL);

	host->base = cfg->sdhc_base;
	host->sdhc_event = &sdhc_event;
	host->caps.hs200_support = cfg->hs200_support;
	host->caps.hs400_support = cfg->hs400_support;

	data = (struct sdhci_msm_data *) malloc(sizeof(struct sdhci_msm_data));
	ASSERT(data);

	data->sdhc_event = &sdhc_event;
	data->pwrctl_base = cfg->pwrctl_base;
	data->pwr_irq = cfg->pwr_irq;
	data->slot = cfg->slot;
	data->use_io_switch = cfg->use_io_switch;

	host->msm_host = data;

	/* Initialize any clocks needed for SDC controller */
	clock_init_mmc(cfg->slot);

	clock_config_mmc(cfg->slot, cfg->max_clk_rate);

	/* Configure the CDC clocks needed for emmc storage
	 * we use slot '1' for emmc
	 */
	if (cfg->slot == 1)
		clock_config_cdc(cfg->slot);

	/*
	 * MSM specific sdhc init
	 */
	sdhci_msm_init(host, data);

	/*
	 * Initialize the controller, read the host capabilities
	 * set power on mode
	 */
	sdhci_init(host);

	/* Setup initial freq to 400KHz */
	mmc_ret = sdhci_clk_supply(host, SDHCI_CLK_400KHZ);

	return mmc_ret;
}

/*
 * Function: mmc identify card
 * Arg     : host & card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Performs card identification process:
 *           1. Get card's unique identification number (CID)
 *           2. Get(for sd)/set (for mmc) relative card address (RCA)
 *           3. Select the card to put it in TRAN state
 */
static uint32_t mmc_identify_card(struct sdhci_host *host, struct mmc_card *card)
{
	uint32_t mmc_return = 0;

	/* Ask card to send its unique card identification (CID) number (CMD2) */
	mmc_return = mmc_all_send_cid(host, card);
	if (mmc_return) {
		dprintf(CRITICAL,"Failure getting card's CID number!\n");
		return mmc_return;
	}

	/* Ask card to send a relative card address (RCA) (CMD3) */
	mmc_return = mmc_send_relative_address(host, card);
	if (mmc_return) {
		dprintf(CRITICAL, "Failure getting card's RCA!\n");
		return mmc_return;
	}

	/* Get card's CSD register (CMD9) */
	mmc_return = mmc_send_csd(host, card);
	if (mmc_return) {
		dprintf(CRITICAL,"Failure getting card's CSD information!\n");
		return mmc_return;
	}

	/* Select the card (CMD7) */
	mmc_return = mmc_select_card(host, card);
	if (mmc_return) {
		dprintf(CRITICAL, "Failure selecting the Card with RCA: %x\n",card->rca);
		return mmc_return;
	}

	/* Set the card status as active */
	card->status = MMC_STATUS_ACTIVE;

	return 0;
}

/*
 * Function: mmc_reset_card_and_send_op
 * Arg     : Host & Card structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Routine to initialize MMC card. It resets a card to idle state,
 *           verify operating voltage and set the card in ready state.
 */
static uint32_t mmc_reset_card_and_send_op(struct sdhci_host *host, struct mmc_card *card)
{
	uint32_t mmc_return = 0;

	/* 1. Card Reset - CMD0 */
	mmc_return = mmc_reset_card(host);
	if (mmc_return) {
		dprintf(CRITICAL, "Failure resetting MMC cards!\n");
		return mmc_return;
	}

	/* 2. Card Initialization process */

	/*
	 * Send CMD1 to identify and reject cards that do not match host's VDD range
	 * profile. Cards sends its OCR register in response.
	 */

	mmc_return = mmc_send_op_cond(host, card);

	/* OCR is not received, init could not complete */
	if (mmc_return) {
		dprintf(CRITICAL, "Failure getting OCR response from MMC Card\n");
		return mmc_return;
	}

	return 0;
}

static uint32_t mmc_send_app_cmd(struct sdhci_host *host, struct mmc_card *card)
{
	struct mmc_command cmd = {0};

	cmd.cmd_index = CMD55_APP_CMD;
	cmd.argument = (card->rca << 16);
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	if (sdhci_send_command(host, &cmd))
	{
		dprintf(CRITICAL, "Failed Sending CMD55\n");
		return 1;
	}
	return 0;
}

uint32_t mmc_sd_card_init(struct sdhci_host *host, struct mmc_card *card)
{
	uint8_t i;
	struct mmc_command cmd;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* Use the SD card RCA 0x0 during init */
	card->rca = SD_CARD_RCA;

	/* Send CMD8 for voltage check*/
	for (i = 0 ;i < SD_CMD8_MAX_RETRY; i++)
	{
		cmd.cmd_index = CMD8_SEND_IF_COND;
		cmd.argument = MMC_SD_HC_VOLT_SUPPLIED;
		cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
		cmd.resp_type = SDHCI_CMD_RESP_R7;

		if (sdhci_send_command(host, &cmd))
		{
			dprintf(CRITICAL, "The response for CMD8 does not match the supplied value\n");
			return 1;
		}
		else
		{
			/* If the command response echos the voltage back */
			if (cmd.resp[0] == MMC_SD_HC_VOLT_SUPPLIED)
				break;
		}
		/* As per SDCC the spec try for max three times with
		 * 1 ms delay
		 */
		mdelay(1);
	}

	if (i == SD_CMD8_MAX_RETRY && (cmd.resp[0] != MMC_SD_HC_VOLT_SUPPLIED))
	{
		dprintf(CRITICAL, "Error: CMD8 response timed out\n");
		return 1;
	}

	/* Send ACMD41 for OCR */
	for (i = 0; i < SD_ACMD41_MAX_RETRY; i++)
	{
		/* Send APP_CMD before ACMD41*/
		if (mmc_send_app_cmd(host, card))
		{
			dprintf(CRITICAL, "Failed sending App command\n");
			return 1;
		}

		/* APP_CMD is successful, send ACMD41 now */
		cmd.cmd_index = ACMD41_SEND_OP_COND;
		cmd.argument = MMC_SD_OCR | MMC_SD_HC_HCS;
		cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
		cmd.resp_type = SDHCI_CMD_RESP_R3;

		if (sdhci_send_command(host, &cmd))
		{
			dprintf(CRITICAL, "Failure sending ACMD41\n");
			return 1;
		}
		else
		{
			if (cmd.resp[0] & MMC_SD_DEV_READY)
			{
				if (cmd.resp[0] & (1 << 30))
					card->type = MMC_CARD_TYPE_SDHC;
				else
					card->type = MMC_CARD_TYPE_STD_SD;

				break;
			}
		}
		/*
		 * As per SDCC spec try for max 1 second
		 */
		mdelay(50);
	}

	if (i == SD_ACMD41_MAX_RETRY && !(cmd.resp[0] & MMC_SD_DEV_READY))
	{
		dprintf(CRITICAL, "Error: ACMD41 response timed out\n");
		return 1;
	}

	return 0;
}

/*
 * Function to read SD card information from SD status
 */
static uint32_t mmc_sd_get_card_ssr(struct sdhci_host *host, struct mmc_card *card)
{
	BUF_DMA_ALIGN(raw_sd_status, 64);
	struct mmc_command cmd = {0};
	uint32_t sd_status[16];
	uint32_t *status = sd_status;
	uint32_t au_size;
	int i;
	int j;

	if (mmc_send_app_cmd(host, card))
	{
		dprintf(CRITICAL, "Failed sending App command\n");
		return 1;
	}

	cmd.cmd_index = ACMD13_SEND_SD_STATUS;
	cmd.argument = 0x0;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.trans_mode = SDHCI_MMC_READ;
	cmd.data_present = 0x1;
	cmd.data.data_ptr = raw_sd_status;
	cmd.data.num_blocks = 0x1;
	cmd.data.blk_sz = 0x40;

	/* send command */
	if (sdhci_send_command(host, &cmd))
		return 1;

	memcpy(sd_status, raw_sd_status, sizeof(sd_status));

	for (i = 15, j = 0; i >=0 ; i--, j++)
		sd_status[i] = swap_endian32(sd_status[j]);

	au_size = UNPACK_BITS(status, MMC_SD_AU_SIZE_BIT, MMC_SD_AU_SIZE_LEN, 32);
	/* Card AU size in sectors */
	card->ssr.au_size = 1 << (au_size + 4);
	card->ssr.num_aus = UNPACK_BITS(status, MMC_SD_ERASE_SIZE_BIT, MMC_SD_ERASE_SIZE_LEN, 32);

	return 0;
}

/*
 * Function to read the SD CARD configuration register
 */
static uint32_t mmc_sd_get_card_scr(struct sdhci_host *host, struct mmc_card *card)
{
	BUF_DMA_ALIGN(scr_resp, 8);
	struct mmc_command cmd = {0};
	uint32_t raw_scr[2];

	/* Now read the SCR register */
	/* Send APP_CMD before ACMD51*/
	if (mmc_send_app_cmd(host, card))
	{
		dprintf(CRITICAL, "Failed sending App command\n");
		return 1;
	}

	cmd.cmd_index = ACMD51_READ_CARD_SCR;
	cmd.argument = 0x0;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.trans_mode = SDHCI_MMC_READ;
	cmd.data_present = 0x1;
	cmd.data.data_ptr = scr_resp;
	cmd.data.num_blocks = 0x1;
	cmd.data.blk_sz = 0x8;

	/* send command */
	if (sdhci_send_command(host, &cmd))
		return 1;

	memcpy(raw_scr, scr_resp, sizeof(raw_scr));

	card->raw_scr[0] = swap_endian32(raw_scr[0]);
	card->raw_scr[1] = swap_endian32(raw_scr[1]);

	/*
	 * Parse & Populate the SCR data as per sdcc spec
	 */
	card->scr.bus_widths = (card->raw_scr[0] & SD_SCR_BUS_WIDTH_MASK) >> SD_SCR_BUS_WIDTH;
	card->scr.cmd23_support = (card->raw_scr[0] & SD_SCR_CMD23_SUPPORT);
	card->scr.sd_spec = (card->raw_scr[0] & SD_SCR_SD_SPEC_MASK) >> SD_SCR_SD_SPEC;
	card->scr.sd3_spec = (card->raw_scr[0] & SD_SCR_SD_SPEC3_MASK) >> SD_SCR_SD_SPEC3;

	return 0;
}

/*
 * Function: mmc_set_sd_bus_width
 * Arg     : host, device structure & width
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Set the bus width for the card
 */
uint32_t mmc_sd_set_bus_width(struct sdhci_host *host, struct mmc_card *card, uint8_t width)
{
	struct mmc_command cmd = {0};

	/* Send APP_CMD before ACMD6*/
	if (mmc_send_app_cmd(host, card))
	{
		dprintf(CRITICAL, "Failed sending App command\n");
		return 1;
	}

	cmd.cmd_index = ACMD6_SET_BUS_WIDTH;
	cmd.argument = (width == DATA_BUS_WIDTH_4BIT) ? (1<<1) : 0;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	/* send command */
	if (sdhci_send_command(host, &cmd))
		return 1;

	return 0;
}

uint32_t mmc_sd_set_hs(struct sdhci_host *host, struct mmc_card *card)
{
       struct mmc_command cmd = {0};
       BUF_DMA_ALIGN(switch_resp, 64);

       cmd.cmd_index = CMD6_SWITCH_FUNC;
       cmd.argument = MMC_SD_SWITCH_HS;
       cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
       cmd.resp_type = SDHCI_CMD_RESP_R1;
       cmd.trans_mode = SDHCI_MMC_READ;
       cmd.data_present = 0x1;
       cmd.data.data_ptr = switch_resp;
       cmd.data.num_blocks = 0x1;
       cmd.data.blk_sz = 0x40;

       /* send command */
       if (sdhci_send_command(host, &cmd))
             return 1;

	/* Set the SDR25 mode in controller*/
	sdhci_set_uhs_mode(host, SDHCI_SDR25_MODE);

	return 0;
}

/*
 * Function: mmc_init_card
 * Arg     : mmc device structure
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Performs initialization and identification of eMMC cards connected
 *           to the host.
 */

static uint32_t mmc_card_init(struct mmc_device *dev)
{
	uint32_t mmc_return = 0;
	uint8_t bus_width = 0;

	struct sdhci_host *host;
	struct mmc_card *card;
	struct mmc_config_data *cfg;

	host = &dev->host;
	card = &dev->card;
	cfg  = &dev->config;

	/* Initialize MMC card structure */
	card->status = MMC_STATUS_INACTIVE;

	/* TODO: Get the OCR params from target */
	card->ocr = MMC_OCR_27_36 | MMC_OCR_SEC_MODE;

	/* Initialize the internal MMC */
	mmc_return = mmc_reset_card_and_send_op(host, card);
	if (mmc_return)
	{
		dprintf(CRITICAL, "MMC card failed to respond, try for SD card\n");
		/* Reset the card & get the OCR */
		mmc_return = mmc_sd_card_init(host, card);
		if (mmc_return)
		{
			dprintf(CRITICAL, "Failed to initialize SD card\n");
			return mmc_return;
		}
	}

	/* Identify (CMD2, CMD3 & CMD9) and select the card (CMD7) */
	mmc_return = mmc_identify_card(host, card);
	if (mmc_return)
		return mmc_return;

	/* set interface speed */
	if (MMC_CARD_SD(card))
	{
		mmc_return = mmc_sd_set_hs(host, card);
		if (mmc_return)
		{
			dprintf(CRITICAL, "Failed to set HS for SD card\n");
			return mmc_return;
		}
	}
	else
	{
		mmc_return = mmc_set_hs_interface(host, card);
		if (mmc_return) {
			dprintf(CRITICAL, "Error adjusting interface speed!\n");
			return mmc_return;
		}
	}

	/* Now get the extended CSD for the card */
	if (MMC_CARD_MMC(card))
	{
			/* For MMC cards, also get the extended csd */
			mmc_return = mmc_get_ext_csd(host, card);

			if (mmc_return) {
				dprintf(CRITICAL, "Failure getting card's ExtCSD information!\n");
				return mmc_return;
			}
	}
	else
	{
		/*Read SCR for sd card */
		if (mmc_sd_get_card_scr(host, card))
		{
			dprintf(CRITICAL, "Failure getting card's SCR register\n");
			return 1;
		}
		/* Read SSR for the SD card */
		if (mmc_sd_get_card_ssr(host, card))
		{
			dprintf(CRITICAL, "Failed to get SSR from the card\n");
			return 1;
		}
	}

	/* Decode and save the CSD register */
	mmc_return = mmc_decode_and_save_csd(card);
	if (mmc_return) {
		dprintf(CRITICAL, "Failure decoding card's CSD information!\n");
		return mmc_return;
	}


	if (MMC_CARD_MMC(card))
	{
		/* Set the bus width based on host, target capbilities */
		if (cfg->bus_width == DATA_BUS_WIDTH_8BIT && host->caps.bus_width_8bit)
				bus_width = DATA_BUS_WIDTH_8BIT;
		/*
		 * Host contoller by default supports 4 bit & 1 bit mode.
		 * No need to check for host support here
		 */
		else if (cfg->bus_width == DATA_BUS_WIDTH_4BIT)
				bus_width = DATA_BUS_WIDTH_4BIT;
		else
				bus_width = DATA_BUS_WIDTH_1BIT;

		/* Set 4/8 bit SDR bus width in controller */
		mmc_return = sdhci_set_bus_width(host, bus_width);

		if (mmc_return) {
			dprintf(CRITICAL, "Failed to set bus width for host controller\n");
			return 1;
		}

		/* Enable high speed mode in the follwing order:
		 * 1. HS400 mode if supported by host & card
		 * 1. HS200 mode if supported by host & card
		 * 2. DDR mode host, if supported by host & card
		 * 3. Use normal speed mode with supported bus width
		 */
		if (host->caps.hs400_support && mmc_card_supports_hs400_mode(card))
		{
			dprintf(INFO, "SDHC Running in HS400 mode\n");
			mmc_return = mmc_set_hs400_mode(host, card, bus_width);
			if (mmc_return)
			{
				dprintf(CRITICAL, "Failure to set HS400 mode for Card(RCA:%x)\n",
								  card->rca);
				return mmc_return;
			}
		}
#if USE_TARGET_HS200_CAPS
		else if (host->caps.hs200_support && host->caps.sdr104_support && mmc_card_supports_hs200_mode(card))
#else
		else if (host->caps.sdr104_support && mmc_card_supports_hs200_mode(card))
#endif
		{
			dprintf(INFO, "SDHC Running in HS200 mode\n");
			mmc_return = mmc_set_hs200_mode(host, card, bus_width);

			if (mmc_return) {
				dprintf(CRITICAL, "Failure to set HS200 mode for Card(RCA:%x)\n",
								  card->rca);
				return mmc_return;
			}
		} else if (host->caps.ddr_support && mmc_card_supports_ddr_mode(card)) {
			dprintf(INFO, "SDHC Running in DDR mode\n");
			mmc_return = mmc_set_ddr_mode(host, card);

			if (mmc_return) {
				dprintf(CRITICAL, "Failure to set DDR mode for Card(RCA:%x)\n",
								  card->rca);
				return mmc_return;
			}
		} else {
			dprintf(INFO, "SDHC Running in High Speed mode\n");
			/* Set HS_TIMING mode */
			mmc_return = mmc_set_hs_interface(host, card);
			if (mmc_return) {
				dprintf(CRITICAL, "Failure to enalbe HS mode for Card(RCA:%x)\n",
								  card->rca);
				return mmc_return;
			}
			/* Set wide bus mode */
			mmc_return = mmc_set_bus_width(host, card, bus_width);
			if (mmc_return) {
				dprintf(CRITICAL, "Failure to set wide bus for Card(RCA:%x)\n",
								  card->rca);
				return mmc_return;
			}
		}
	}
	else
	{
		/* Check the supported bus width for the card from SCR register */
		if (card->scr.bus_widths & SD_SCR_WIDTH_4BIT)
			bus_width = DATA_BUS_WIDTH_4BIT;
		else
			bus_width = DATA_BUS_WIDTH_1BIT;

		mmc_return = mmc_sd_set_bus_width(host, card, bus_width);
		if (mmc_return)
		{
			dprintf(CRITICAL, "Failed to set bus width for the card\n");
			return mmc_return;
		}

		/* Set bit SDR bus width in controller */
		mmc_return = sdhci_set_bus_width(host, bus_width);
		if (mmc_return)
		{
			dprintf(CRITICAL, "Failed to set bus width for host controller\n");
			return mmc_return;
		}
	}


	card->block_size = MMC_BLK_SZ;

	if (MMC_CARD_MMC(card)) {
		/* Enable RST_n_FUNCTION */
		if (!card->ext_csd[MMC_EXT_CSD_RST_N_FUNC])
		{
			mmc_return = mmc_switch_cmd(host, card, MMC_SET_BIT, MMC_EXT_CSD_RST_N_FUNC, RST_N_FUNC_ENABLE);

			if (mmc_return)
			{
				dprintf(CRITICAL, "Failed to enable RST_n_FUNCTION\n");
				return mmc_return;
			}
		}

	}
	return mmc_return;
}

/*
 * Function: mmc display csd
 * Arg     : None
 * Return  : None
 * Flow    : Displays the csd information
 */
static void mmc_display_csd(struct mmc_card *card)
{
	dprintf(SPEW, "erase_grpsize: %d\n", card->csd.erase_grp_size);
	dprintf(SPEW, "erase_grpmult: %d\n", card->csd.erase_grp_mult);
	dprintf(SPEW, "wp_grpsize: %d\n", card->csd.wp_grp_size);
	dprintf(SPEW, "wp_grpen: %d\n", card->csd.wp_grp_enable);
	dprintf(SPEW, "perm_wp: %d\n", card->csd.perm_wp);
	dprintf(SPEW, "temp_wp: %d\n", card->csd.temp_wp);
}

/*
 * Function: mmc_init
 * Arg     : MMC configuration data
 * Return  : Pointer to mmc device
 * Flow    : Entry point to MMC boot process
 *           Initialize the sd host controller
 *           Initialize the mmc card
 *           Set the clock & high speed mode
 */
struct mmc_device *mmc_init(struct mmc_config_data *data)
{
	uint8_t mmc_ret = 0;
	struct mmc_device *dev;

	dev = (struct mmc_device *) malloc (sizeof(struct mmc_device));

	if (!dev) {
		dprintf(CRITICAL, "Error allocating mmc device\n");
		return NULL;
	}

	ASSERT(data);

	memcpy((void*)&dev->config, (void*)data, sizeof(struct mmc_config_data));

	memset((struct mmc_card *)&dev->card, 0, sizeof(struct mmc_card));

	/* Initialize the host & clock */
	dprintf(SPEW, " Initializing MMC host data structure and clock!\n");

	mmc_ret = mmc_host_init(dev);
	if (mmc_ret) {
		dprintf(CRITICAL, "Error Initializing MMC host : %u\n", mmc_ret);
		return NULL;
	}

	/* Initialize and identify cards connected to host */
	mmc_ret = mmc_card_init(dev);
	if (mmc_ret) {
		dprintf(CRITICAL, "Failed detecting MMC/SDC @ slot%d\n",
						  dev->config.slot);
		return NULL;
	}

	dprintf(INFO, "Done initialization of the card\n");

	mmc_display_csd(&dev->card);

	return dev;
}

static uint32_t mmc_parse_response(uint32_t resp)
{
	/* Trying to write beyond card capacity */
	if (resp & MMC_R1_ADDR_OUT_OF_RANGE) {
		dprintf(CRITICAL, "Attempting to read or write beyond the Device capacity\n");
		return 1;
	}

	/* Misaligned address not matching block length */
	if (resp & MMC_R1_ADDR_ERR) {
		dprintf(CRITICAL, "The misaligned address did not match the block length used\n");
		return 1;
	}

	/* Invalid block length */
	if (resp & MMC_R1_BLOCK_LEN_ERR) {
		dprintf(CRITICAL, "The transferred bytes does not match the block length\n");
		return 1;
	}

	/* Tried to program write protected block */
	if (resp & MMC_R1_WP_VIOLATION) {
		dprintf(CRITICAL, "Attempt to program a write protected block\n");
		return 1;
	}

	/* card controller error */
	if (resp & MMC_R1_CC_ERROR) {
		dprintf(CRITICAL, "Device error occurred, which is not related to the host command\n");
		return 1;
	}

	/* Generic error */
	if (resp & MMC_R1_GENERIC_ERR) {
		dprintf(CRITICAL, "A generic Device error\n");
		return 1;
	}

	/* Finally check for card in TRAN state */
	if (MMC_CARD_STATUS(resp) != MMC_TRAN_STATE) {
		dprintf(CRITICAL, "MMC card is not in TRAN state\n");
		return 1;
	}

	return 0;
}

static uint32_t mmc_stop_command(struct mmc_device *dev)
{
	struct mmc_command cmd;
	uint32_t mmc_ret = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	cmd.cmd_index = CMD12_STOP_TRANSMISSION;
	cmd.argument = (dev->card.rca << 16);
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	mmc_ret = sdhci_send_command(&dev->host, &cmd);
	if(mmc_ret)
	{
		dprintf(CRITICAL, "Failed to send stop command\n");
		return mmc_ret;
	}

	/* Response contains 32 bit Card status.
	 * Parse the errors & provide relevant information */

	return mmc_parse_response(cmd.resp[0]);
}

/*
 * Function: mmc sdhci read
 * Arg     : mmc device structure, block address, number of blocks & destination
 * Return  : 0 on Success, non zero on success
 * Flow    : Fill in the command structure & send the command
 */
uint32_t mmc_sdhci_read(struct mmc_device *dev, void *dest,
						uint64_t blk_addr, uint32_t num_blocks)
{
	uint32_t mmc_ret = 0;
	struct mmc_command cmd;
	struct mmc_card *card = &dev->card;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD17/18 Format:
	 * [31:0] Data Address
	 */
	if (num_blocks == 1)
		cmd.cmd_index = CMD17_READ_SINGLE_BLOCK;
	else
		cmd.cmd_index = CMD18_READ_MULTIPLE_BLOCK;

	/*
	 * Standard emmc cards use byte mode addressing
	 * convert the block address to byte address before
	 * sending the command
	 */
	if (card->type == MMC_TYPE_STD_MMC)
		cmd.argument = blk_addr * card->block_size;
	else
		cmd.argument = blk_addr;

	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.trans_mode = SDHCI_MMC_READ;
	cmd.data_present = 0x1;

	/* Use CMD23 If card supports CMD23:
	 * For SD card use the value read from SCR register
	 * For emmc by default use CMD23.
	 * Also as per SDCC spec always use CMD23 to stop
	 * multiblock read/write if UHS (Ultra High Speed) is
	 * enabled
	 */
	if (MMC_CARD_SD(card))
		cmd.cmd23_support = dev->card.scr.cmd23_support;
	else
		cmd.cmd23_support = 0x1;

	cmd.data.data_ptr = dest;
	cmd.data.num_blocks = num_blocks;

	/* send command */
	mmc_ret = sdhci_send_command(&dev->host, &cmd);

	/* For multi block read failures send stop command */
	if (mmc_ret && num_blocks > 1)
	{
		return mmc_stop_command(dev);
	}

	/*
	 * Response contains 32 bit Card status.
	 * Parse the errors & provide relevant information
	 */
	return mmc_parse_response(cmd.resp[0]);
}

/*
 * Function: mmc sdhci write
 * Arg     : mmc device structure, block address, number of blocks & source
 * Return  : 0 on Success, non zero on success
 * Flow    : Fill in the command structure & send the command
 */
uint32_t mmc_sdhci_write(struct mmc_device *dev, void *src,
						 uint64_t blk_addr, uint32_t num_blocks)
{
	uint32_t mmc_ret = 0;
	struct mmc_command cmd;
	struct mmc_card *card = &dev->card;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* CMD24/25 Format:
	 * [31:0] Data Address
	 */

	if (num_blocks == 1)
		cmd.cmd_index = CMD24_WRITE_SINGLE_BLOCK;
	else
		cmd.cmd_index = CMD25_WRITE_MULTIPLE_BLOCK;

	/*
	 * Standard emmc cards use byte mode addressing
	 * convert the block address to byte address before
	 * sending the command
	 */
	if (card->type == MMC_TYPE_STD_MMC)
		cmd.argument = blk_addr * card->block_size;
	else
		cmd.argument = blk_addr;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.trans_mode = SDHCI_MMC_WRITE;

	/* Use CMD23 If card supports CMD23:
	 * For SD card use the value read from SCR register
	 * For emmc by default use CMD23.
	 * Also as per SDCC spec always use CMD23 to stop
	 * multiblock read/write if UHS (Ultra High Speed) is
	 * enabled
	 */
	if (MMC_CARD_SD(card))
		cmd.cmd23_support = dev->card.scr.cmd23_support;
	else
		cmd.cmd23_support = 0x1;

	cmd.data_present = 0x1;
	cmd.data.data_ptr = src;
	cmd.data.num_blocks = num_blocks;

	/* send command */
	mmc_ret = sdhci_send_command(&dev->host, &cmd);

	/* For multi block write failures send stop command */
	if (mmc_ret && num_blocks > 1)
	{
		return mmc_stop_command(dev);
	}

	/*
	 * Response contains 32 bit Card status.
	 * Parse the errors & provide relevant information
	 */
	return mmc_parse_response(cmd.resp[0]);
}

/*
 * Send the erase group start address using CMD35
 */
static uint32_t mmc_send_erase_grp_start(struct mmc_device *dev, uint32_t erase_start)
{
	struct mmc_command cmd;
	struct mmc_card *card = &dev->card;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	if (MMC_CARD_MMC(card))
		cmd.cmd_index = CMD35_ERASE_GROUP_START;
	else
		cmd.cmd_index = CMD32_ERASE_WR_BLK_START;

	/*
	 * Standard emmc cards use byte mode addressing
	 * convert the block address to byte address before
	 * sending the command
	 */
	if (card->type == MMC_TYPE_STD_MMC)
		cmd.argument = erase_start * card->block_size;
	else
		cmd.argument = erase_start;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	/* send command */
	if (sdhci_send_command(&dev->host, &cmd))
		return 1;

	/*
	 * CMD35 on failure returns address out of range error
	 */
	if (MMC_ADDR_OUT_OF_RANGE(cmd.resp[0]))
	{
		dprintf(CRITICAL, "Address for CMD35 is out of range\n");
		return 1;
	}

	return 0;
}

/*
 * Send the erase group end address using CMD36
 */
static uint32_t mmc_send_erase_grp_end(struct mmc_device *dev, uint32_t erase_end)
{
	struct mmc_command cmd;
	struct mmc_card *card = &dev->card;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	if (MMC_CARD_MMC(card))
		cmd.cmd_index = CMD36_ERASE_GROUP_END;
	else
		cmd.cmd_index = CMD33_ERASE_WR_BLK_END;

	/*
	 * Standard emmc cards use byte mode addressing
	 * convert the block address to byte address before
	 * sending the command
	 */
	if (card->type == MMC_TYPE_STD_MMC)
		cmd.argument = erase_end * card->block_size;
	else
		cmd.argument = erase_end;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	/* send command */
	if (sdhci_send_command(&dev->host, &cmd))
		return 1;

	/*
	 * CMD3 on failure returns address out of range error
	 */
	if (MMC_ADDR_OUT_OF_RANGE(cmd.resp[0]))
	{
		dprintf(CRITICAL, "Address for CMD36 is out of range\n");
		return 1;
	}

	return 0;
}

/*
 * Send the erase CMD38, to erase the selected erase groups
 */
static uint32_t mmc_send_erase(struct mmc_device *dev, uint64_t erase_timeout)
{
	struct mmc_command cmd;
	uint32_t status;
	uint32_t retry = 0;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	cmd.cmd_index = CMD38_ERASE;
	cmd.argument = 0x00000000;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1B;
	cmd.cmd_timeout = erase_timeout;

	/* send command */
	if (sdhci_send_command(&dev->host, &cmd))
		return 1;

	do
	{
		if (mmc_get_card_status(&dev->host, &dev->card, &status))
		{
			dprintf(CRITICAL, "Failed to get card status after erase\n");
			return 1;
		}
		/* Check if the response of erase command has eras skip status set */
		if (status & MMC_R1_WP_ERASE_SKIP)
			dprintf(CRITICAL, "Write Protect set for the region, only partial space was erased\n");

		retry++;
		udelay(1000);
		if (retry == MMC_MAX_CARD_STAT_RETRY)
		{
			dprintf(CRITICAL, "Card status check timed out after sending erase command\n");
			return 1;
		}
	} while(!(status & MMC_READY_FOR_DATA) || (MMC_CARD_STATUS(status) == MMC_PROG_STATE));


	return 0;
}


/*
 * Function: mmc sdhci erase
 * Arg     : mmc device structure, block address and length
 * Return  : 0 on Success, non zero on failure
 * Flow    : Fill in the command structure & send the command
 */
uint32_t mmc_sdhci_erase(struct mmc_device *dev, uint32_t blk_addr, uint64_t len)
{
	uint32_t erase_unit_sz = 0;
	uint32_t erase_start;
	uint32_t erase_end;
	uint32_t blk_end;
	uint32_t num_erase_grps;
	uint64_t erase_timeout = 0;
	struct mmc_card *card;


	card = &dev->card;

	/*
	 * Calculate the erase unit size,
	 * 1. Based on emmc 4.5 spec for emmc card
	 * 2. Use SD Card Status info for SD cards
	 */
	if (MMC_CARD_MMC(card))
	{
		/*
		 * Calculate the erase unit size as per the emmc specification v4.5
		 */
		if (dev->card.ext_csd[MMC_ERASE_GRP_DEF])
			erase_unit_sz = (MMC_HC_ERASE_MULT * dev->card.ext_csd[MMC_HC_ERASE_GRP_SIZE]) / MMC_BLK_SZ;
		else
			erase_unit_sz = (dev->card.csd.erase_grp_size + 1) * (dev->card.csd.erase_grp_mult + 1);
	}
	else
		erase_unit_sz = dev->card.ssr.au_size * dev->card.ssr.num_aus;


	/* Convert length in blocks */
	len = len / MMC_BLK_SZ;

	if (len < erase_unit_sz)
	{
		dprintf(CRITICAL, "Requested length is less than min erase group size\n");
		return 1;
	}

	/* Calculate erase groups based on the length in blocks */
	num_erase_grps = len / erase_unit_sz;

	/* Start address of the erase range */
	erase_start = blk_addr;

	/* Last address of the erase range */
	erase_end = blk_addr + ((num_erase_grps - 1) * erase_unit_sz);

	/* Boundary check for overlap */
	blk_end = blk_addr + len;

	if (erase_end > blk_end)
	{
		dprintf(CRITICAL, "The erase group overlaps the max requested for erase\n");
		erase_end -= erase_unit_sz;
	}

	/* Send CMD35 for erase group start */
	if (mmc_send_erase_grp_start(dev, erase_start))
	{
		dprintf(CRITICAL, "Failed to send erase grp start address\n");
		return 1;
	}

	/* Send CMD36 for erase group end */
	if (mmc_send_erase_grp_end(dev, erase_end))
	{
		dprintf(CRITICAL, "Failed to send erase grp end address\n");
		return 1;
	}

	/*
	 * As per emmc 4.5 spec section 7.4.27, calculate the erase timeout
	 * erase_timeout = 300ms * ERASE_TIMEOUT_MULT * num_erase_grps
	 */
	if (MMC_CARD_MMC(card))
		erase_timeout = (300 * 1000 * card->ext_csd[MMC_ERASE_TIMEOUT_MULT] * num_erase_grps);
	else
		erase_timeout = (300 * 1000 * num_erase_grps);

	/* Send CMD38 to perform erase */
	if (mmc_send_erase(dev, erase_timeout))
	{
		dprintf(CRITICAL, "Failed to erase the specified partition\n");
		return 1;
	}

	return 0;
}

/*
 * Function: mmc get wp status
 * Arg     : mmc device structure, block address and buffer for getting wp status
 * Return  : 0 on Success, 1 on Failure
 * Flow    : Get the WP group status by sending CMD31
 */
uint32_t mmc_get_wp_status(struct mmc_device *dev, uint32_t addr, uint8_t *wp_status)
{
	struct mmc_command cmd;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	cmd.cmd_index = CMD31_SEND_WRITE_PROT_TYPE;
	cmd.argument = addr;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;
	cmd.trans_mode = SDHCI_MMC_READ;
	cmd.data_present = 0x1;
	cmd.data.data_ptr = wp_status;
	cmd.data.num_blocks = 0x1;
	cmd.data.blk_sz = 0x8;

	if (sdhci_send_command(&dev->host, &cmd))
	{
		dprintf(CRITICAL, "Failed to get status of write protect bits\n");
		return 1;
	}

	return 0;
}

/*
 * Function: mmc set/clear WP on user area
 * Arg     : mmc device structure, block address,len, & flag to set or clear
 * Return  : 0 on success, 1 on failure
 * Flow    : Function to set/clear power on write protect on user area
 */

uint32_t mmc_set_clr_power_on_wp_user(struct mmc_device *dev, uint32_t addr, uint64_t len, uint8_t set_clr)
{
	struct mmc_command cmd;
	struct mmc_card *card = &dev->card;
	uint32_t wp_grp_size;
	uint32_t status;
	uint32_t num_wp_grps;
	uint32_t ret;
	uint32_t retry = 0;
	uint32_t i;

	memset((struct mmc_command *)&cmd, 0, sizeof(struct mmc_command));

	/* Convert len into blocks */
	len = len / MMC_BLK_SZ;
	wp_grp_size = dev->card.wp_grp_size;

	/* Disable PERM WP */
	ret = mmc_switch_cmd(&dev->host, &dev->card, MMC_SET_BIT, MMC_USR_WP, MMC_US_PERM_WP_DIS);

	if (ret)
	{
		dprintf(CRITICAL, "Failed to Disable PERM WP\n");
		return ret;
	}

	/* Read the default values for user WP */
	ret = mmc_get_ext_csd(&dev->host, &dev->card);

	if (ret)
	{
		dprintf(CRITICAL, "Failed to read ext csd for the card\n");
		return ret;
	}

	/* Check if user power on WP is disabled or perm WP is enabled */
	if ((dev->card.ext_csd[MMC_USR_WP] & MMC_US_PWR_WP_DIS)
		|| (dev->card.ext_csd[MMC_USR_WP] & MMC_US_PERM_WP_EN))
	{
		dprintf(CRITICAL, "Power on protection is disabled, cannot be set\n");
		return 1;
	}

	if (len < wp_grp_size)
	{
		dprintf(CRITICAL, "Length is less than min WP size, WP was not set\n");
		return 1;
	}

	/* Set power on USER WP */
	ret = mmc_switch_cmd(&dev->host, &dev->card, MMC_SET_BIT, MMC_USR_WP, MMC_US_PWR_WP_EN);

	if (ret)
	{
		dprintf(CRITICAL, "Failed to set power on WP for user\n");
		return ret;
	}

	num_wp_grps = ROUNDUP(len, wp_grp_size) / wp_grp_size;

	if (set_clr)
		cmd.cmd_index = CMD28_SET_WRITE_PROTECT;
	else
		cmd.cmd_index = CMD29_CLEAR_WRITE_PROTECT;

	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1B;

	for(i = 0; i < num_wp_grps; i++)
	{
		/*
		* Standard emmc cards use byte mode addressing
		* convert the block address to byte address before
		* sending the command
		*/
		if (card->type == MMC_TYPE_STD_MMC)
			cmd.argument = (addr + (i * wp_grp_size)) * card->block_size;
		else
			cmd.argument = addr + (i * wp_grp_size);

		if (sdhci_send_command(&dev->host, &cmd))
			return 1;

		/* CMD28/CMD29 On failure returns address out of range error */
		if (MMC_ADDR_OUT_OF_RANGE(cmd.resp[0]))
		{
			dprintf(CRITICAL, "Address for CMD28/29 is out of range\n");
			return 1;
		}

		/* Check the card status */
		do
		{
			if (mmc_get_card_status(&dev->host, &dev->card, &status))
			{
				dprintf(CRITICAL, "Failed to get card status afterapplying write protect\n");
				return 1;
			}

		/* Time out for WP command */
		retry++;
		udelay(1000);
		if (retry == MMC_MAX_CARD_STAT_RETRY)
		{
			dprintf(CRITICAL, "Card status timed out after sending write protect command\n");
			return 1;
		}
		} while (!(status & MMC_READY_FOR_DATA) || (MMC_CARD_STATUS(status) == MMC_PROG_STATE));

	}

	return 0;
}

/* Function to put the mmc card to sleep */
void mmc_put_card_to_sleep(struct mmc_device *dev)
{
	struct mmc_command cmd = {0};
	struct mmc_card *card = &dev->card;

	cmd.cmd_index = CMD7_SELECT_DESELECT_CARD;
	cmd.argument = 0x00000000;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_NONE;

	/* send command */
	if(sdhci_send_command(&dev->host, &cmd))
	{
		dprintf(CRITICAL, "card deselect error: %s\n", __func__);
		return;
	}

	cmd.cmd_index = CMD5_SLEEP_AWAKE;
	cmd.argument = (card->rca << MMC_CARD_RCA_BIT) | MMC_CARD_SLEEP;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1B;

	/* send command */
	if(sdhci_send_command(&dev->host, &cmd))
		dprintf(CRITICAL, "card sleep error: %s\n", __func__);
}

/*
 * Switch the partition access type to rpmb or default
 */
static uint32_t mmc_sdhci_switch_part(struct mmc_device *dev, uint32_t type)
{
	uint32_t part_access;
	uint32_t ret;

	/* Clear the partition access */
	part_access = dev->card.ext_csd[MMC_PARTITION_CONFIG] & ~PARTITION_ACCESS_MASK;
	part_access |= type;

	ret = mmc_switch_cmd(&dev->host, &dev->card, MMC_ACCESS_WRITE, MMC_PARTITION_CONFIG, part_access);

	if (ret)
	{
		dprintf(CRITICAL, "Failed to switch partition to type: %u\n", type);
		return 1;
	}

	dev->card.ext_csd[MMC_PARTITION_CONFIG] = part_access;
	return 0;
}

static uint32_t mmc_sdhci_set_blk_cnt(struct mmc_device *dev, uint32_t blk_cnt, uint32_t rel_write)
{
	struct mmc_command cmd = {0};

	cmd.cmd_index = CMD23_SET_BLOCK_COUNT;
	cmd.argument = blk_cnt & 0x0000ffff;
	cmd.argument |= rel_write;
	cmd.cmd_type = SDHCI_CMD_TYPE_NORMAL;
	cmd.resp_type = SDHCI_CMD_RESP_R1;

	if (sdhci_send_command(&dev->host, &cmd))
	{
		dprintf(CRITICAL, "Set block count failed: %s\n", __func__);
		return 1;
	}

	return 0;
}

uint32_t mmc_sdhci_rpmb_send(struct mmc_device *dev, struct mmc_command *cmd)
{
	int i;
	uint32_t retry = 5;
	uint32_t status;
	uint32_t rel_write = 0;
	uint32_t ret = 1;

	ASSERT(cmd);

	/* 1. Set the partition type to rpmb */
	if (mmc_sdhci_switch_part(dev, PART_ACCESS_RPMB))
		return 1;

	for (i = 0; i < MAX_RPMB_CMDS; i++)
	{
		if (!cmd[i].cmd_index)
			break;

		if (cmd[i].write_flag == true)
			rel_write = BIT(31);
		else
			rel_write = 0;

		/* 2. Set the block count using cmd23 */
		if (mmc_sdhci_set_blk_cnt(dev, cmd[i].data.num_blocks, rel_write))
			goto err;

		/* 3. Send the command */
		if (sdhci_send_command(&dev->host, &cmd[i]))
			goto err;
		do
		{
			/* 4. Poll for card status to ensure rpmb operation completeness */
			if (mmc_get_card_status(&dev->host, &dev->card, &status))
			{
				dprintf(CRITICAL, "Failed to get card status after rpmb operations\n");
				goto err;
			}

			retry--;
			udelay(500);
			if (!retry)
			{
				dprintf(CRITICAL, "Card status check timed out after rpmb operations\n");
				goto err;
			}
		} while(!(status & MMC_READY_FOR_DATA) || (MMC_CARD_STATUS(status) == MMC_PROG_STATE));
	}

	/* If we reach here, that means success */
	ret = 0;

err:
	/* 5. Switch the partition back to default type */
	if (mmc_sdhci_switch_part(dev, PART_ACCESS_DEFAULT))
		ret = 1;

	return ret;
}
