Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit c1e97551 authored by Subhash Jadavani's avatar Subhash Jadavani Committed by Xiaonian Wang
Browse files

mmc: host: sdhci-msm: fix NULL pointer dereference



We are seeing the kernel panic due to NULL pointer dereference with
following call trace:
	sdhci_msm_set_clock+0x59c/0xa28
	sdhci_do_set_ios+0xf4/0x740
	sdhci_set_ios+0x28/0x3c
	mmc_set_ios+0xac/0x1ec
	__mmc_set_clock+0x2c/0x3c
	mmc_ungate_clock+0x20/0x28
	mmc_host_clk_hold+0x54/0xc4
	mmc_power_off+0x1c/0x70
	mmc_rescan+0x250/0x27c
	process_one_work+0x240/0x420
	worker_thread+0x268/0x390
	kthread+0xf8/0x100

This is happending when eMMC initialization is failing in HS400 mode.
sdhci_msm_set_clock() might be accessing the card pointer after it
was deallocated, this change adds the safety checks to avoid NULL
dereference.

Change-Id: I895b8b33cce4173100d58acf690e57b5f4e69081
Signed-off-by: default avatarSubhash Jadavani <subhashj@codeaurora.org>
parent 8c0c937d
Loading
Loading
Loading
Loading
+4 −3
Original line number Diff line number Diff line
@@ -2759,6 +2759,7 @@ static void sdhci_msm_set_clock(struct sdhci_host *host, unsigned int clock)
	int rc;
	struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
	struct sdhci_msm_host *msm_host = pltfm_host->priv;
	struct mmc_card *card = host->mmc->card;
	struct mmc_ios	curr_ios = host->mmc->ios;
	u32 sup_clock, ddr_clock, dll_lock;
	bool curr_pwrsave;
@@ -2782,7 +2783,7 @@ static void sdhci_msm_set_clock(struct sdhci_host *host, unsigned int clock)
	curr_pwrsave = !!(readl_relaxed(host->ioaddr + CORE_VENDOR_SPEC) &
			  CORE_CLK_PWRSAVE);
	if ((clock > 400000) &&
	    !curr_pwrsave && mmc_host_may_gate_card(host->mmc->card))
	    !curr_pwrsave && card && mmc_host_may_gate_card(card))
		writel_relaxed(readl_relaxed(host->ioaddr + CORE_VENDOR_SPEC)
				| CORE_CLK_PWRSAVE,
				host->ioaddr + CORE_VENDOR_SPEC);
@@ -2790,7 +2791,7 @@ static void sdhci_msm_set_clock(struct sdhci_host *host, unsigned int clock)
	 * Disable pwrsave for a newly added card if doesn't allow clock
	 * gating.
	 */
	else if (curr_pwrsave && !mmc_host_may_gate_card(host->mmc->card))
	else if (curr_pwrsave && card && !mmc_host_may_gate_card(card))
		writel_relaxed(readl_relaxed(host->ioaddr + CORE_VENDOR_SPEC)
				& ~CORE_CLK_PWRSAVE,
				host->ioaddr + CORE_VENDOR_SPEC);
@@ -2838,7 +2839,7 @@ static void sdhci_msm_set_clock(struct sdhci_host *host, unsigned int clock)
		 * register
		 */
		if ((msm_host->tuning_done ||
				(mmc_card_strobe(msm_host->mmc->card) &&
				(card && mmc_card_strobe(card) &&
				 msm_host->enhanced_strobe)) &&
				!msm_host->calibration_done) {
			/*