* [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200()
@ 2019-02-13 9:06 Chaotian Jing
2019-02-13 12:08 ` Ulf Hansson
0 siblings, 1 reply; 5+ messages in thread
From: Chaotian Jing @ 2019-02-13 9:06 UTC (permalink / raw)
To: Ulf Hansson
Cc: Matthias Brugger, Shawn Lin, Simon Horman, Chaotian Jing,
Kyle Roeschley, Hongjie Fang, Harish Jenny K N, linux-mmc,
linux-kernel, linux-arm-kernel, linux-mediatek, srv_heupstream,
Adrian Hunter
mmc_hs400_to_hs200() begins with the card and host in HS400 mode.
Therefore, any commands sent to the card should use HS400 timing.
reduce clock frequency to 50Mhz but without host timming change
may cause CMD6 response CRC error. because host still running at
hs400 mode, and it's hard to find a suitable setting for all eMMC
cards when clock frequency reduced to 50Mhz but card & host still
in hs400 mode.
this patch refers to mmc_select_hs400(), make the reduce clock frequency
after card timing change.
Signed-off-by: Chaotian Jing <chaotian.jing@mediatek.com>
Fixes: ef3d232245ab ("mmc: mmc: Relax checking for switch errors after HS200 switch")
---
drivers/mmc/core/mmc.c | 29 +++++++++++++++++++++++------
1 file changed, 23 insertions(+), 6 deletions(-)
diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c
index 09c688f..00adc2d 100644
--- a/drivers/mmc/core/mmc.c
+++ b/drivers/mmc/core/mmc.c
@@ -1239,20 +1239,37 @@ int mmc_hs400_to_hs200(struct mmc_card *card)
int err;
u8 val;
- /* Reduce frequency to HS */
- max_dtr = card->ext_csd.hs_max_dtr;
- mmc_set_clock(host, max_dtr);
-
/* Switch HS400 to HS DDR */
val = EXT_CSD_TIMING_HS;
err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING,
val, card->ext_csd.generic_cmd6_time, 0,
true, false, true);
- if (err)
- goto out_err;
+ /*
+ * as we are on the way to do re-tune, so if the CMD6 got response CRC
+ * error, do not treat it as error.
+ */
+ if (err) {
+ if (err == -EILSEQ) {
+ /*
+ * card will busy after sending out response and host
+ * driver may not wait busy de-assert when get
+ * response CRC error. so just wait enough time to
+ * ensure card leave busy state.
+ */
+ mmc_delay(card->ext_csd.generic_cmd6_time);
+ pr_debug("%s: %s switch to HS got CRC error\n",
+ mmc_hostname(host), __func__);
+ } else {
+ goto out_err;
+ }
+ }
mmc_set_timing(host, MMC_TIMING_MMC_DDR52);
+ /* Reduce frequency to HS */
+ max_dtr = card->ext_csd.hs_max_dtr;
+ mmc_set_clock(host, max_dtr);
+
err = mmc_switch_status(card);
if (err)
goto out_err;
--
1.8.1.1.dirty
^ permalink raw reply related [flat|nested] 5+ messages in thread* Re: [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() 2019-02-13 9:06 [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() Chaotian Jing @ 2019-02-13 12:08 ` Ulf Hansson 2019-02-14 2:14 ` Chaotian Jing 0 siblings, 1 reply; 5+ messages in thread From: Ulf Hansson @ 2019-02-13 12:08 UTC (permalink / raw) To: Chaotian Jing Cc: Matthias Brugger, Shawn Lin, Simon Horman, Kyle Roeschley, Hongjie Fang, Harish Jenny K N, linux-mmc@vger.kernel.org, Linux Kernel Mailing List, Linux ARM, linux-mediatek, srv_heupstream, Adrian Hunter On Wed, 13 Feb 2019 at 10:07, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > mmc_hs400_to_hs200() begins with the card and host in HS400 mode. > Therefore, any commands sent to the card should use HS400 timing. > reduce clock frequency to 50Mhz but without host timming change > may cause CMD6 response CRC error. because host still running at > hs400 mode, and it's hard to find a suitable setting for all eMMC > cards when clock frequency reduced to 50Mhz but card & host still > in hs400 mode. > this patch refers to mmc_select_hs400(), make the reduce clock frequency > after card timing change. > > Signed-off-by: Chaotian Jing <chaotian.jing@mediatek.com> > Fixes: ef3d232245ab ("mmc: mmc: Relax checking for switch errors after HS200 switch") > --- > drivers/mmc/core/mmc.c | 29 +++++++++++++++++++++++------ > 1 file changed, 23 insertions(+), 6 deletions(-) > > diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c > index 09c688f..00adc2d 100644 > --- a/drivers/mmc/core/mmc.c > +++ b/drivers/mmc/core/mmc.c > @@ -1239,20 +1239,37 @@ int mmc_hs400_to_hs200(struct mmc_card *card) > int err; > u8 val; > > - /* Reduce frequency to HS */ > - max_dtr = card->ext_csd.hs_max_dtr; > - mmc_set_clock(host, max_dtr); > - > /* Switch HS400 to HS DDR */ > val = EXT_CSD_TIMING_HS; > err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, > val, card->ext_csd.generic_cmd6_time, 0, > true, false, true); > - if (err) > - goto out_err; > + /* > + * as we are on the way to do re-tune, so if the CMD6 got response CRC > + * error, do not treat it as error. > + */ > + if (err) { > + if (err == -EILSEQ) { > + /* > + * card will busy after sending out response and host > + * driver may not wait busy de-assert when get > + * response CRC error. so just wait enough time to > + * ensure card leave busy state. > + */ > + mmc_delay(card->ext_csd.generic_cmd6_time); > + pr_debug("%s: %s switch to HS got CRC error\n", > + mmc_hostname(host), __func__); > + } else { > + goto out_err; > + } > + } > > mmc_set_timing(host, MMC_TIMING_MMC_DDR52); > > + /* Reduce frequency to HS */ > + max_dtr = card->ext_csd.hs_max_dtr; > + mmc_set_clock(host, max_dtr); > + What Adrian suggested was to not to move this part, but instead, only allow CRC errors from the CMD6 as above. I guess it didn't work for you? > err = mmc_switch_status(card); > if (err) > goto out_err; > -- > 1.8.1.1.dirty > Kind regards Uffe ^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() 2019-02-13 12:08 ` Ulf Hansson @ 2019-02-14 2:14 ` Chaotian Jing 2019-02-14 8:14 ` Ulf Hansson 0 siblings, 1 reply; 5+ messages in thread From: Chaotian Jing @ 2019-02-14 2:14 UTC (permalink / raw) To: Ulf Hansson Cc: Matthias Brugger, Shawn Lin, Simon Horman, Kyle Roeschley, Hongjie Fang, Harish Jenny K N, linux-mmc@vger.kernel.org, Linux Kernel Mailing List, Linux ARM, linux-mediatek, srv_heupstream, Adrian Hunter On Wed, 2019-02-13 at 13:08 +0100, Ulf Hansson wrote: > On Wed, 13 Feb 2019 at 10:07, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > > > mmc_hs400_to_hs200() begins with the card and host in HS400 mode. > > Therefore, any commands sent to the card should use HS400 timing. > > reduce clock frequency to 50Mhz but without host timming change > > may cause CMD6 response CRC error. because host still running at > > hs400 mode, and it's hard to find a suitable setting for all eMMC > > cards when clock frequency reduced to 50Mhz but card & host still > > in hs400 mode. > > this patch refers to mmc_select_hs400(), make the reduce clock frequency > > after card timing change. > > > > Signed-off-by: Chaotian Jing <chaotian.jing@mediatek.com> > > Fixes: ef3d232245ab ("mmc: mmc: Relax checking for switch errors after HS200 switch") > > --- > > drivers/mmc/core/mmc.c | 29 +++++++++++++++++++++++------ > > 1 file changed, 23 insertions(+), 6 deletions(-) > > > > diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c > > index 09c688f..00adc2d 100644 > > --- a/drivers/mmc/core/mmc.c > > +++ b/drivers/mmc/core/mmc.c > > @@ -1239,20 +1239,37 @@ int mmc_hs400_to_hs200(struct mmc_card *card) > > int err; > > u8 val; > > > > - /* Reduce frequency to HS */ > > - max_dtr = card->ext_csd.hs_max_dtr; > > - mmc_set_clock(host, max_dtr); > > - > > /* Switch HS400 to HS DDR */ > > val = EXT_CSD_TIMING_HS; > > err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, > > val, card->ext_csd.generic_cmd6_time, 0, > > true, false, true); > > - if (err) > > - goto out_err; > > + /* > > + * as we are on the way to do re-tune, so if the CMD6 got response CRC > > + * error, do not treat it as error. > > + */ > > + if (err) { > > + if (err == -EILSEQ) { > > + /* > > + * card will busy after sending out response and host > > + * driver may not wait busy de-assert when get > > + * response CRC error. so just wait enough time to > > + * ensure card leave busy state. > > + */ > > + mmc_delay(card->ext_csd.generic_cmd6_time); > > + pr_debug("%s: %s switch to HS got CRC error\n", > > + mmc_hostname(host), __func__); > > + } else { > > + goto out_err; > > + } > > + } > > > > mmc_set_timing(host, MMC_TIMING_MMC_DDR52); > > > > + /* Reduce frequency to HS */ > > + max_dtr = card->ext_csd.hs_max_dtr; > > + mmc_set_clock(host, max_dtr); > > + > > What Adrian suggested was to not to move this part, but instead, only > allow CRC errors from the CMD6 as above. > > I guess it didn't work for you? > It should work for me. another issue is CMD6 will be sent 3 times at max err = mmc_wait_for_cmd(host, &cmd, MMC_CMD_RETRIES); if the first CMD6 got response CRC error, then Host driver must wait busy signal de-assert before send the next CMD6. So that it really make sense to issue CMD6(R1B) for 3 times ? if host driver did not handle the first CMD6 response CRC error and send second CMD6 directly, then this CMD6 will get timeout due to card still in busy state. > > err = mmc_switch_status(card); > > if (err) > > goto out_err; > > -- > > 1.8.1.1.dirty > > > > Kind regards > Uffe ^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() 2019-02-14 2:14 ` Chaotian Jing @ 2019-02-14 8:14 ` Ulf Hansson 2019-02-14 8:40 ` Chaotian Jing 0 siblings, 1 reply; 5+ messages in thread From: Ulf Hansson @ 2019-02-14 8:14 UTC (permalink / raw) To: Chaotian Jing Cc: Matthias Brugger, Shawn Lin, Simon Horman, Kyle Roeschley, Hongjie Fang, Harish Jenny K N, linux-mmc@vger.kernel.org, Linux Kernel Mailing List, Linux ARM, linux-mediatek, srv_heupstream, Adrian Hunter On Thu, 14 Feb 2019 at 03:14, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > On Wed, 2019-02-13 at 13:08 +0100, Ulf Hansson wrote: > > On Wed, 13 Feb 2019 at 10:07, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > > > > > mmc_hs400_to_hs200() begins with the card and host in HS400 mode. > > > Therefore, any commands sent to the card should use HS400 timing. > > > reduce clock frequency to 50Mhz but without host timming change > > > may cause CMD6 response CRC error. because host still running at > > > hs400 mode, and it's hard to find a suitable setting for all eMMC > > > cards when clock frequency reduced to 50Mhz but card & host still > > > in hs400 mode. > > > this patch refers to mmc_select_hs400(), make the reduce clock frequency > > > after card timing change. > > > > > > Signed-off-by: Chaotian Jing <chaotian.jing@mediatek.com> > > > Fixes: ef3d232245ab ("mmc: mmc: Relax checking for switch errors after HS200 switch") > > > --- > > > drivers/mmc/core/mmc.c | 29 +++++++++++++++++++++++------ > > > 1 file changed, 23 insertions(+), 6 deletions(-) > > > > > > diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c > > > index 09c688f..00adc2d 100644 > > > --- a/drivers/mmc/core/mmc.c > > > +++ b/drivers/mmc/core/mmc.c > > > @@ -1239,20 +1239,37 @@ int mmc_hs400_to_hs200(struct mmc_card *card) > > > int err; > > > u8 val; > > > > > > - /* Reduce frequency to HS */ > > > - max_dtr = card->ext_csd.hs_max_dtr; > > > - mmc_set_clock(host, max_dtr); > > > - > > > /* Switch HS400 to HS DDR */ > > > val = EXT_CSD_TIMING_HS; > > > err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, > > > val, card->ext_csd.generic_cmd6_time, 0, > > > true, false, true); > > > - if (err) > > > - goto out_err; > > > + /* > > > + * as we are on the way to do re-tune, so if the CMD6 got response CRC > > > + * error, do not treat it as error. > > > + */ > > > + if (err) { > > > + if (err == -EILSEQ) { > > > + /* > > > + * card will busy after sending out response and host > > > + * driver may not wait busy de-assert when get > > > + * response CRC error. so just wait enough time to > > > + * ensure card leave busy state. > > > + */ > > > + mmc_delay(card->ext_csd.generic_cmd6_time); > > > + pr_debug("%s: %s switch to HS got CRC error\n", > > > + mmc_hostname(host), __func__); > > > + } else { > > > + goto out_err; > > > + } > > > + } > > > > > > mmc_set_timing(host, MMC_TIMING_MMC_DDR52); > > > > > > + /* Reduce frequency to HS */ > > > + max_dtr = card->ext_csd.hs_max_dtr; > > > + mmc_set_clock(host, max_dtr); > > > + > > > > What Adrian suggested was to not to move this part, but instead, only > > allow CRC errors from the CMD6 as above. > > > > I guess it didn't work for you? > > > It should work for me. another issue is CMD6 will be sent 3 times at max Alright, let's give it a try then. > err = mmc_wait_for_cmd(host, &cmd, MMC_CMD_RETRIES); Yeah, that one have I thought about earlier as well. > > if the first CMD6 got response CRC error, then Host driver must wait > busy signal de-assert before send the next CMD6. > > So that it really make sense to issue CMD6(R1B) for 3 times ? if host > driver did not handle the first CMD6 response CRC error and send second > CMD6 directly, then this CMD6 will get timeout due to card still in busy > state. I fully agree with you, I don't think it makes sense to retry - not even for any CMD6, because of the busy signalling the card may raise afterwards. Perhaps we should start with a simple oneliner patch, giving zero instead of MMC_CMD_RETRIES to mmc_wait_for_cmd() and see how that plays. Then on top we can add the special error handling of the CRC errors, along the lines of what you suggest. Does it make sense? [...] Kind regards Uffe ^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() 2019-02-14 8:14 ` Ulf Hansson @ 2019-02-14 8:40 ` Chaotian Jing 0 siblings, 0 replies; 5+ messages in thread From: Chaotian Jing @ 2019-02-14 8:40 UTC (permalink / raw) To: Ulf Hansson Cc: Matthias Brugger, Shawn Lin, Simon Horman, Kyle Roeschley, Hongjie Fang, Harish Jenny K N, linux-mmc@vger.kernel.org, Linux Kernel Mailing List, Linux ARM, linux-mediatek, srv_heupstream, Adrian Hunter On Thu, 2019-02-14 at 09:14 +0100, Ulf Hansson wrote: > On Thu, 14 Feb 2019 at 03:14, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > > > On Wed, 2019-02-13 at 13:08 +0100, Ulf Hansson wrote: > > > On Wed, 13 Feb 2019 at 10:07, Chaotian Jing <chaotian.jing@mediatek.com> wrote: > > > > > > > > mmc_hs400_to_hs200() begins with the card and host in HS400 mode. > > > > Therefore, any commands sent to the card should use HS400 timing. > > > > reduce clock frequency to 50Mhz but without host timming change > > > > may cause CMD6 response CRC error. because host still running at > > > > hs400 mode, and it's hard to find a suitable setting for all eMMC > > > > cards when clock frequency reduced to 50Mhz but card & host still > > > > in hs400 mode. > > > > this patch refers to mmc_select_hs400(), make the reduce clock frequency > > > > after card timing change. > > > > > > > > Signed-off-by: Chaotian Jing <chaotian.jing@mediatek.com> > > > > Fixes: ef3d232245ab ("mmc: mmc: Relax checking for switch errors after HS200 switch") > > > > --- > > > > drivers/mmc/core/mmc.c | 29 +++++++++++++++++++++++------ > > > > 1 file changed, 23 insertions(+), 6 deletions(-) > > > > > > > > diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c > > > > index 09c688f..00adc2d 100644 > > > > --- a/drivers/mmc/core/mmc.c > > > > +++ b/drivers/mmc/core/mmc.c > > > > @@ -1239,20 +1239,37 @@ int mmc_hs400_to_hs200(struct mmc_card *card) > > > > int err; > > > > u8 val; > > > > > > > > - /* Reduce frequency to HS */ > > > > - max_dtr = card->ext_csd.hs_max_dtr; > > > > - mmc_set_clock(host, max_dtr); > > > > - > > > > /* Switch HS400 to HS DDR */ > > > > val = EXT_CSD_TIMING_HS; > > > > err = __mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, > > > > val, card->ext_csd.generic_cmd6_time, 0, > > > > true, false, true); > > > > - if (err) > > > > - goto out_err; > > > > + /* > > > > + * as we are on the way to do re-tune, so if the CMD6 got response CRC > > > > + * error, do not treat it as error. > > > > + */ > > > > + if (err) { > > > > + if (err == -EILSEQ) { > > > > + /* > > > > + * card will busy after sending out response and host > > > > + * driver may not wait busy de-assert when get > > > > + * response CRC error. so just wait enough time to > > > > + * ensure card leave busy state. > > > > + */ > > > > + mmc_delay(card->ext_csd.generic_cmd6_time); > > > > + pr_debug("%s: %s switch to HS got CRC error\n", > > > > + mmc_hostname(host), __func__); > > > > + } else { > > > > + goto out_err; > > > > + } > > > > + } > > > > > > > > mmc_set_timing(host, MMC_TIMING_MMC_DDR52); > > > > > > > > + /* Reduce frequency to HS */ > > > > + max_dtr = card->ext_csd.hs_max_dtr; > > > > + mmc_set_clock(host, max_dtr); > > > > + > > > > > > What Adrian suggested was to not to move this part, but instead, only > > > allow CRC errors from the CMD6 as above. > > > > > > I guess it didn't work for you? > > > > > It should work for me. another issue is CMD6 will be sent 3 times at max > > Alright, let's give it a try then. > > > err = mmc_wait_for_cmd(host, &cmd, MMC_CMD_RETRIES); > > Yeah, that one have I thought about earlier as well. > > > > > if the first CMD6 got response CRC error, then Host driver must wait > > busy signal de-assert before send the next CMD6. > > > > So that it really make sense to issue CMD6(R1B) for 3 times ? if host > > driver did not handle the first CMD6 response CRC error and send second > > CMD6 directly, then this CMD6 will get timeout due to card still in busy > > state. > > I fully agree with you, I don't think it makes sense to retry - not > even for any CMD6, because of the busy signalling the card may raise > afterwards. > > Perhaps we should start with a simple oneliner patch, giving zero > instead of MMC_CMD_RETRIES to mmc_wait_for_cmd() and see how that > plays. > > Then on top we can add the special error handling of the CRC errors, > along the lines of what you suggest. > > Does it make sense? > Sure, I will upload a new patch to change the retry time from 3 to 0 along with this patch. > [...] > > Kind regards > Uffe ^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2019-02-14 8:40 UTC | newest] Thread overview: 5+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2019-02-13 9:06 [PATCH v1] mmc: mmc: Fix HS setting in mmc_hs400_to_hs200() Chaotian Jing 2019-02-13 12:08 ` Ulf Hansson 2019-02-14 2:14 ` Chaotian Jing 2019-02-14 8:14 ` Ulf Hansson 2019-02-14 8:40 ` Chaotian Jing
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox