mmc: Explicitly enable mmc card clocks before programing crypto key

Command queue driver has customized changes to work on msm-4.14 where
pm_runtime_get_sync() enables the host clocks but customized code releases
the clock after 100ms of inactivity to save power.
With new FBE V2 the crypto keys are programmed in submit_bio() context
where pm_runtime_get_sync() is called by KSM driver but crypto clock need
to be kept on before programming the crypto key to ensure crypto registers
are accesible.
So export and call the mmc clock APIs to hold the mmc and crypto clocks
while programming crypto keys.

Test: repeated power on/off test.

Change-Id: I6cae7febdfac053f4477ab34f4265b9f4f24606c
Signed-off-by: Neeraj Soni <neersoni@codeaurora.org>
tirimbino
Neeraj Soni 4 years ago committed by Gerrit - the friendly Code Review server
parent c70886c604
commit 7c22fbacd4
  1. 2
      drivers/mmc/core/host.c
  2. 29
      drivers/mmc/host/cmdq_hci-crypto-qti.c

@ -199,6 +199,7 @@ void mmc_host_clk_hold(struct mmc_host *host)
spin_unlock_irqrestore(&host->clk_lock, flags);
mutex_unlock(&host->clk_gate_mutex);
}
EXPORT_SYMBOL(mmc_host_clk_hold);
/**
* mmc_host_may_gate_card - check if this card may be gated
@ -248,6 +249,7 @@ void mmc_host_clk_release(struct mmc_host *host)
msecs_to_jiffies(host->clkgate_delay));
spin_unlock_irqrestore(&host->clk_lock, flags);
}
EXPORT_SYMBOL(mmc_host_clk_release);
/**
* mmc_host_clk_rate - get current clock frequency setting

@ -19,7 +19,6 @@
#include "sdhci-msm.h"
#include "cmdq_hci-crypto-qti.h"
#include <linux/crypto-qti-common.h>
#include <linux/pm_runtime.h>
#include <linux/atomic.h>
#if IS_ENABLED(CONFIG_CRYPTO_DEV_QCOM_ICE)
#include <crypto/ice.h>
@ -30,6 +29,8 @@
#define MINIMUM_DUN_SIZE 512
#define MAXIMUM_DUN_SIZE 65536
static struct mmc_host *mmc_host;
static struct cmdq_host_crypto_variant_ops cmdq_crypto_qti_variant_ops = {
.host_init_crypto = cmdq_crypto_qti_init_crypto,
.enable = cmdq_crypto_qti_enable,
@ -121,11 +122,15 @@ static int cmdq_crypto_qti_keyslot_program(struct keyslot_manager *ksm,
return -EINVAL;
}
mmc_host_clk_hold(mmc_host);
err = crypto_qti_keyslot_program(host->crypto_vops->priv, key,
slot, data_unit_mask, crypto_alg_id);
if (err)
pr_err("%s: failed with error %d\n", __func__, err);
mmc_host_clk_release(mmc_host);
return err;
}
@ -137,19 +142,21 @@ static int cmdq_crypto_qti_keyslot_evict(struct keyslot_manager *ksm,
int val = 0;
struct cmdq_host *host = keyslot_manager_private(ksm);
pm_runtime_get_sync(&host->mmc->card->dev);
if (!cmdq_is_crypto_enabled(host) ||
!cmdq_keyslot_valid(host, slot)) {
pm_runtime_put_sync(&host->mmc->card->dev);
return -EINVAL;
}
mmc_host_clk_hold(mmc_host);
err = crypto_qti_keyslot_evict(host->crypto_vops->priv, slot);
if (err)
if (err) {
pr_err("%s: failed with error %d\n", __func__, err);
mmc_host_clk_release(mmc_host);
return err;
}
mmc_host_clk_release(mmc_host);
pm_runtime_put_sync(&host->mmc->card->dev);
val = atomic_read(&keycache) & ~(1 << slot);
atomic_set(&keycache, val);
@ -237,6 +244,11 @@ int cmdq_host_init_crypto_qti_spec(struct cmdq_host *host,
* descriptor would be used to pass crypto specific informaton.
*/
host->caps |= CMDQ_TASK_DESC_SZ_128;
mmc_host = host->mmc;
if (!mmc_host) {
err = -ENODEV;
goto out;
}
return 0;
out:
@ -319,6 +331,11 @@ int cmdq_host_init_crypto_qti_spec(struct cmdq_host *host,
* descriptor would be used to pass crypto specific informaton.
*/
host->caps |= CMDQ_TASK_DESC_SZ_128;
mmc_host = host->mmc;
if (!mmc_host) {
err = -ENODEV;
goto out;
}
return 0;

Loading…
Cancel
Save