According to the JEDEC Standard, eMMC v4.4 cards can supoort secure erase.
the first bit in ext_csd[EXT_CSD_SEC_FEATURE_SUPPORT] - EXT_CSD_SEC_ER_EN
is used to check if secure erase supoort by the device.

Signed-off-by: dennis <dennislaplaci...@gmail.com>
---
 drivers/mmc/Kconfig     |  8 ++++++++
 drivers/mmc/mmc.c       |  4 ++++
 drivers/mmc/mmc_write.c | 16 +++++++++++++---
 include/mmc.h           |  5 ++++-
 4 files changed, 29 insertions(+), 4 deletions(-)

diff --git a/drivers/mmc/Kconfig b/drivers/mmc/Kconfig
index 14d7913986..6105cbe960 100644
--- a/drivers/mmc/Kconfig
+++ b/drivers/mmc/Kconfig
@@ -18,6 +18,14 @@ config MMC_WRITE
        help
          Enable write access to MMC and SD Cards
 
+config MMC_SECURE_ERASE
+       bool "Enable secure erase for eMMC"
+       depends on MMC_WRITE
+       default n
+       help
+         This option replace the default erase with secure erase in eMMC v4.4
+         and above cards.
+
 config MMC_BROKEN_CD
        bool "Poll for broken card detection case"
        help
diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c
index a6394bcf30..56b17070e7 100644
--- a/drivers/mmc/mmc.c
+++ b/drivers/mmc/mmc.c
@@ -2272,6 +2272,10 @@ static int mmc_startup_v4(struct mmc *mmc)
                if ((capacity >> 20) > 2 * 1024)
                        mmc->capacity_user = capacity;
        }
+#if CONFIG_IS_ENABLED(MMC_SECURE_ERASE)
+       if (mmc->version >= MMC_VERSION_4_4 && IS_MMC(mmc))
+               mmc->sec_feature_support = ext_csd[EXT_CSD_SEC_FEATURE_SUPPORT];
+#endif
 
        if (mmc->version >= MMC_VERSION_4_5)
                mmc->gen_cmd6_time = ext_csd[EXT_CSD_GENERIC_CMD6_TIME];
diff --git a/drivers/mmc/mmc_write.c b/drivers/mmc/mmc_write.c
index 6a4453ca02..0b720ccf7e 100644
--- a/drivers/mmc/mmc_write.c
+++ b/drivers/mmc/mmc_write.c
@@ -15,7 +15,7 @@
 #include <linux/math64.h>
 #include "mmc_private.h"
 
-static ulong mmc_erase_t(struct mmc *mmc, ulong start, lbaint_t blkcnt)
+static ulong mmc_erase_t(struct mmc *mmc, ulong start, lbaint_t blkcnt, uint 
arg)
 {
        struct mmc_cmd cmd;
        ulong end;
@@ -52,7 +52,7 @@ static ulong mmc_erase_t(struct mmc *mmc, ulong start, 
lbaint_t blkcnt)
                goto err_out;
 
        cmd.cmdidx = MMC_CMD_ERASE;
-       cmd.cmdarg = MMC_ERASE_ARG;
+       cmd.cmdarg = arg;
        cmd.resp_type = MMC_RSP_R1b;
 
        err = mmc_send_cmd(mmc, &cmd, NULL);
@@ -81,6 +81,7 @@ ulong mmc_berase(struct blk_desc *block_dev, lbaint_t start, 
lbaint_t blkcnt)
        struct mmc *mmc = find_mmc_device(dev_num);
        lbaint_t blk = 0, blk_r = 0;
        int timeout_ms = 1000;
+       uint arg = MMC_ERASE_ARG;
 
        if (!mmc)
                return -1;
@@ -105,6 +106,15 @@ ulong mmc_berase(struct blk_desc *block_dev, lbaint_t 
start, lbaint_t blkcnt)
                       ((start + blkcnt + mmc->erase_grp_size)
                       & ~(mmc->erase_grp_size - 1)) - 1);
 
+#if CONFIG_IS_ENABLED(MMC_SECURE_ERASE)
+       if (!(mmc->sec_feature_support & EXT_CSD_SEC_ER_EN)) {
+               printf("secure erase not supported on device\n"
+                      "perform insecure erase\n");
+       } else {
+               arg = MMC_SECURE_ERASE_ARG;
+       }
+#endif
+
        while (blk < blkcnt) {
                if (IS_SD(mmc) && mmc->ssr.au) {
                        blk_r = ((blkcnt - blk) > mmc->ssr.au) ?
@@ -113,7 +123,7 @@ ulong mmc_berase(struct blk_desc *block_dev, lbaint_t 
start, lbaint_t blkcnt)
                        blk_r = ((blkcnt - blk) > mmc->erase_grp_size) ?
                                mmc->erase_grp_size : (blkcnt - blk);
                }
-               err = mmc_erase_t(mmc, start + blk, blk_r);
+               err = mmc_erase_t(mmc, start + blk, blk_r, arg);
                if (err)
                        break;
 
diff --git a/include/mmc.h b/include/mmc.h
index 1d377e0281..bfdc712bdd 100644
--- a/include/mmc.h
+++ b/include/mmc.h
@@ -80,7 +80,6 @@ struct bd_info;
 #define MMC_MODE_1BIT          BIT(28)
 #define MMC_MODE_SPI           BIT(27)
 
-
 #define SD_DATA_4BIT   0x00040000
 
 #define IS_SD(x)       ((x)->version & SD_VERSION_SD)
@@ -240,6 +239,7 @@ static inline bool mmc_is_tuning_cmd(uint cmdidx)
 #define EXT_CSD_HC_WP_GRP_SIZE         221     /* RO */
 #define EXT_CSD_HC_ERASE_GRP_SIZE      224     /* RO */
 #define EXT_CSD_BOOT_MULT              226     /* RO */
+#define EXT_CSD_SEC_FEATURE_SUPPORT 231 /* RO */
 #define EXT_CSD_GENERIC_CMD6_TIME       248     /* RO */
 #define EXT_CSD_BKOPS_SUPPORT          502     /* RO */
 
@@ -247,6 +247,8 @@ static inline bool mmc_is_tuning_cmd(uint cmdidx)
  * EXT_CSD field definitions
  */
 
+#define EXT_CSD_SEC_ER_EN   BIT(0)
+
 #define EXT_CSD_CMD_SET_NORMAL         (1 << 0)
 #define EXT_CSD_CMD_SET_SECURE         (1 << 1)
 #define EXT_CSD_CMD_SET_CPSECURE       (1 << 2)
@@ -690,6 +692,7 @@ struct mmc {
        uint tran_speed;
        uint legacy_speed; /* speed for the legacy mode provided by the card */
        uint read_bl_len;
+       u8 sec_feature_support;
 #if CONFIG_IS_ENABLED(MMC_WRITE)
        uint write_bl_len;
        uint erase_grp_size;    /* in 512-byte sectors */
-- 
2.17.1

Reply via email to