Commit 4265900e authored by Saugata Das's avatar Saugata Das Committed by Chris Ball

mmc: MMC-4.5 Data Tag Support

MMC-4.5 data tag feature will be used to store the file system meta-data
in the tagged region of eMMC. This will improve the write and subsequent
read transfer time for the meta data.
Signed-off-by: default avatarSaugata Das <saugata.das@linaro.org>
Tested-by: default avatarVenkatraman S <svenkatr@ti.com>
Signed-off-by: default avatarChris Ball <cjb@laptop.org>
parent e2a0883e
...@@ -1080,6 +1080,7 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq, ...@@ -1080,6 +1080,7 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq,
struct mmc_blk_request *brq = &mqrq->brq; struct mmc_blk_request *brq = &mqrq->brq;
struct request *req = mqrq->req; struct request *req = mqrq->req;
struct mmc_blk_data *md = mq->data; struct mmc_blk_data *md = mq->data;
bool do_data_tag;
/* /*
* Reliable writes are used to implement Forced Unit Access and * Reliable writes are used to implement Forced Unit Access and
...@@ -1155,6 +1156,16 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq, ...@@ -1155,6 +1156,16 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq,
if (do_rel_wr) if (do_rel_wr)
mmc_apply_rel_rw(brq, card, req); mmc_apply_rel_rw(brq, card, req);
/*
* Data tag is used only during writing meta data to speed
* up write and any subsequent read of this meta data
*/
do_data_tag = (card->ext_csd.data_tag_unit_size) &&
(req->cmd_flags & REQ_META) &&
(rq_data_dir(req) == WRITE) &&
((brq->data.blocks * brq->data.blksz) >=
card->ext_csd.data_tag_unit_size);
/* /*
* Pre-defined multi-block transfers are preferable to * Pre-defined multi-block transfers are preferable to
* open ended-ones (and necessary for reliable writes). * open ended-ones (and necessary for reliable writes).
...@@ -1173,13 +1184,13 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq, ...@@ -1173,13 +1184,13 @@ static void mmc_blk_rw_rq_prep(struct mmc_queue_req *mqrq,
* We'll avoid using CMD23-bounded multiblock writes for * We'll avoid using CMD23-bounded multiblock writes for
* these, while retaining features like reliable writes. * these, while retaining features like reliable writes.
*/ */
if ((md->flags & MMC_BLK_CMD23) && mmc_op_multi(brq->cmd.opcode) &&
if ((md->flags & MMC_BLK_CMD23) && (do_rel_wr || !(card->quirks & MMC_QUIRK_BLK_NO_CMD23) ||
mmc_op_multi(brq->cmd.opcode) && do_data_tag)) {
(do_rel_wr || !(card->quirks & MMC_QUIRK_BLK_NO_CMD23))) {
brq->sbc.opcode = MMC_SET_BLOCK_COUNT; brq->sbc.opcode = MMC_SET_BLOCK_COUNT;
brq->sbc.arg = brq->data.blocks | brq->sbc.arg = brq->data.blocks |
(do_rel_wr ? (1 << 31) : 0); (do_rel_wr ? (1 << 31) : 0) |
(do_data_tag ? (1 << 29) : 0);
brq->sbc.flags = MMC_RSP_R1 | MMC_CMD_AC; brq->sbc.flags = MMC_RSP_R1 | MMC_CMD_AC;
brq->mrq.sbc = &brq->sbc; brq->mrq.sbc = &brq->sbc;
} }
......
...@@ -519,6 +519,20 @@ static int mmc_read_ext_csd(struct mmc_card *card, u8 *ext_csd) ...@@ -519,6 +519,20 @@ static int mmc_read_ext_csd(struct mmc_card *card, u8 *ext_csd)
ext_csd[EXT_CSD_CACHE_SIZE + 1] << 8 | ext_csd[EXT_CSD_CACHE_SIZE + 1] << 8 |
ext_csd[EXT_CSD_CACHE_SIZE + 2] << 16 | ext_csd[EXT_CSD_CACHE_SIZE + 2] << 16 |
ext_csd[EXT_CSD_CACHE_SIZE + 3] << 24; ext_csd[EXT_CSD_CACHE_SIZE + 3] << 24;
if (ext_csd[EXT_CSD_DATA_SECTOR_SIZE] == 1)
card->ext_csd.data_sector_size = 4096;
else
card->ext_csd.data_sector_size = 512;
if ((ext_csd[EXT_CSD_DATA_TAG_SUPPORT] & 1) &&
(ext_csd[EXT_CSD_TAG_UNIT_SIZE] <= 8)) {
card->ext_csd.data_tag_unit_size =
((unsigned int) 1 << ext_csd[EXT_CSD_TAG_UNIT_SIZE]) *
(card->ext_csd.data_sector_size);
} else {
card->ext_csd.data_tag_unit_size = 0;
}
} }
out: out:
......
...@@ -71,6 +71,8 @@ struct mmc_ext_csd { ...@@ -71,6 +71,8 @@ struct mmc_ext_csd {
bool hpi_en; /* HPI enablebit */ bool hpi_en; /* HPI enablebit */
bool hpi; /* HPI support bit */ bool hpi; /* HPI support bit */
unsigned int hpi_cmd; /* cmd used as HPI */ unsigned int hpi_cmd; /* cmd used as HPI */
unsigned int data_sector_size; /* 512 bytes or 4KB */
unsigned int data_tag_unit_size; /* DATA TAG UNIT size */
unsigned int boot_ro_lock; /* ro lock support */ unsigned int boot_ro_lock; /* ro lock support */
bool boot_ro_lockable; bool boot_ro_lockable;
u8 raw_partition_support; /* 160 */ u8 raw_partition_support; /* 160 */
......
...@@ -274,6 +274,7 @@ struct _mmc_csd { ...@@ -274,6 +274,7 @@ struct _mmc_csd {
#define EXT_CSD_FLUSH_CACHE 32 /* W */ #define EXT_CSD_FLUSH_CACHE 32 /* W */
#define EXT_CSD_CACHE_CTRL 33 /* R/W */ #define EXT_CSD_CACHE_CTRL 33 /* R/W */
#define EXT_CSD_POWER_OFF_NOTIFICATION 34 /* R/W */ #define EXT_CSD_POWER_OFF_NOTIFICATION 34 /* R/W */
#define EXT_CSD_DATA_SECTOR_SIZE 61 /* R */
#define EXT_CSD_GP_SIZE_MULT 143 /* R/W */ #define EXT_CSD_GP_SIZE_MULT 143 /* R/W */
#define EXT_CSD_PARTITION_ATTRIBUTE 156 /* R/W */ #define EXT_CSD_PARTITION_ATTRIBUTE 156 /* R/W */
#define EXT_CSD_PARTITION_SUPPORT 160 /* RO */ #define EXT_CSD_PARTITION_SUPPORT 160 /* RO */
...@@ -315,6 +316,8 @@ struct _mmc_csd { ...@@ -315,6 +316,8 @@ struct _mmc_csd {
#define EXT_CSD_POWER_OFF_LONG_TIME 247 /* RO */ #define EXT_CSD_POWER_OFF_LONG_TIME 247 /* RO */
#define EXT_CSD_GENERIC_CMD6_TIME 248 /* RO */ #define EXT_CSD_GENERIC_CMD6_TIME 248 /* RO */
#define EXT_CSD_CACHE_SIZE 249 /* RO, 4 bytes */ #define EXT_CSD_CACHE_SIZE 249 /* RO, 4 bytes */
#define EXT_CSD_TAG_UNIT_SIZE 498 /* RO */
#define EXT_CSD_DATA_TAG_SUPPORT 499 /* RO */
#define EXT_CSD_HPI_FEATURES 503 /* RO */ #define EXT_CSD_HPI_FEATURES 503 /* RO */
/* /*
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment