RE: [PATCH 1/2] mmc: sdhci: update timeout clock setting if SDCLK is used

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi, Kevin

My host also has this quirk(SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK), I had sent a patch use the same way as yours to calculate the max_discard_to and host->timeout_clk. But I place the code in host->ops->set_clock which in my sdhci-esdhci.h. also my host has quirk SDHCI_QUIRK_NONSTANDARD_CLOCK, just return in the beginning.

So if you can place this code in the beginning of the function, it will also work for my host, and one of my patch will no need to be merge. Also it will work for other host with the same quirk.

if (host->ops->set_clock) {
	host->ops->set_clock(host, clock);
	if (host->quirks & SDHCI_QUIRK_NONSTANDARD_CLOCK)
		return;
}

BTW, I have a card: MMC + PLUS 256MB Kingston. Its max_dtr was 26MHz so after calculate the real-clock, we can get the working clock 25MHz, but it will encounter timeout when cmd25 send. All other cmds work fine.
One method I found was to reduce its clock to 16MHz, it work with no issue for all cmds. Did you met this issue before? 


Regards
Haijun.


> -----Original Message-----
> From: Kevin Liu [mailto:kliu5@xxxxxxxxxxx]
> Sent: Sunday, January 06, 2013 5:32 PM
> To: linux-mmc@xxxxxxxxxxxxxxx; Chris Ball; Andy Shevchenko; Mark Brown;
> Adrian Hunter
> Cc: Philip Rakity; Aaron Lu; Shawn Guo; Ulf Hansson; Johan Rudholm;
> Daniel Drake; Guennadi Liakhovetski; Huang Changming-R66093; Alexander
> Stein; Girish K S; Zhang Haijun-B42677; Viresh Kumar; Heiko Stuebner;
> Thomas Abraham; Chander Kashyap; Jaehoon Chung; Sebastian Hesselbarth;
> Zhangfei Gao; Haojian Zhuang; Chao Xie; keyuan.liu@xxxxxxxxx; Kevin Liu
> Subject: [PATCH 1/2] mmc: sdhci: update timeout clock setting if SDCLK is
> used
> 
> 1. If SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK is selected, getting timeout
> through register or callback function is useless. So skip current
> redundant code.
> 2. If SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK is selected, host uses SDCLK
> instead of TMCLK for data timeouts. So host->timeout_clk and mmc-
> >max_discard_to should be updated accordingly when SDCLK changed.
> 3. If callback function get_timeout_clock is used, the timeout clock will
> be returned directly and no need to multiply by the timeout clock unit
> read from register.
> 
> Signed-off-by: Kevin Liu <kliu5@xxxxxxxxxxx>
> ---
>  drivers/mmc/host/sdhci.c |   38 +++++++++++++++++++++-----------------
>  1 file changed, 21 insertions(+), 17 deletions(-)
> 
> diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c index
> 04af0fd..c13415c 100644
> --- a/drivers/mmc/host/sdhci.c
> +++ b/drivers/mmc/host/sdhci.c
> @@ -1159,8 +1159,14 @@ static void sdhci_set_clock(struct sdhci_host
> *host, unsigned int clock)
>  		div >>= 1;
>  	}
> 
> -	if (real_div)
> +	if (real_div) {
>  		host->mmc->actual_clock = (host->max_clk * clk_mul) /
> real_div;
> +		if (host->quirks & SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK) {
> +			host->timeout_clk = host->mmc->actual_clock / 1000;
> +			host->mmc->max_discard_to =
> +				(1 << 27) / host->timeout_clk;
> +		}
> +	}
> 
>  	clk |= (div & SDHCI_DIV_MASK) << SDHCI_DIVIDER_SHIFT;
>  	clk |= ((div & SDHCI_DIV_HI_MASK) >> SDHCI_DIV_MASK_LEN) @@ -
> 2828,23 +2834,21 @@ int sdhci_add_host(struct sdhci_host *host)
>  	} else
>  		mmc->f_min = host->max_clk / SDHCI_MAX_DIV_SPEC_200;
> 
> -	host->timeout_clk =
> -		(caps[0] & SDHCI_TIMEOUT_CLK_MASK) >> SDHCI_TIMEOUT_CLK_SHIFT;
> -	if (host->timeout_clk == 0) {
> -		if (host->ops->get_timeout_clock) {
> -			host->timeout_clk = host->ops->get_timeout_clock(host);
> -		} else if (!(host->quirks &
> -				SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK)) {
> -			pr_err("%s: Hardware doesn't specify timeout clock "
> -			       "frequency.\n", mmc_hostname(mmc));
> -			return -ENODEV;
> -		}
> +	if (!(host->quirks & SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK)) {
> +		host->timeout_clk = (caps[0] & SDHCI_TIMEOUT_CLK_MASK) >>
> +					SDHCI_TIMEOUT_CLK_SHIFT;
> +		if (host->timeout_clk == 0) {
> +			if (host->ops->get_timeout_clock) {
> +				host->timeout_clk =
> +					host->ops->get_timeout_clock(host);
> +			} else {
> +				pr_err("%s: Hardware doesn't specify timeout "
> +					"clock frequency.\n", mmc_hostname(mmc));
> +				return -ENODEV;
> +			}
> +		} else if (caps[0] & SDHCI_TIMEOUT_CLK_UNIT)
> +			host->timeout_clk *= 1000;
>  	}
> -	if (caps[0] & SDHCI_TIMEOUT_CLK_UNIT)
> -		host->timeout_clk *= 1000;
> -
> -	if (host->quirks & SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK)
> -		host->timeout_clk = mmc->f_max / 1000;
> 
>  	mmc->max_discard_to = (1 << 27) / host->timeout_clk;
> 
> --
> 1.7.9.5
> 


--
To unsubscribe from this list: send the line "unsubscribe linux-mmc" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [Linux USB Devel]     [Linux Media]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux