On 17 November 2011 11:06, Subhash Jadavani <subhashj@xxxxxxxxxxxxxx> wrote: > Hi Girish, > >> -----Original Message----- >> From: linux-mmc-owner@xxxxxxxxxxxxxxx [mailto:linux-mmc- >> owner@xxxxxxxxxxxxxxx] On Behalf Of Sahitya Tummala >> Sent: Tuesday, November 08, 2011 2:10 PM >> To: Girish K S >> Cc: linux-mmc@xxxxxxxxxxxxxxx; cjb@xxxxxxxxxx; patches@xxxxxxxxxx; >> linux-samsung-soc@xxxxxxxxxxxxxxx >> Subject: Re: [PATCH RESEND V4] mmc: core: HS200 mode support for eMMC >> 4.5 >> >> Hi Girish, >> >> On 10/26/2011 10:29 AM, Girish K S wrote: >> > This patch adds the support of the HS200 bus speed for eMMC 4.5 >> devices. >> > The eMMC 4.5 devices have support for 200MHz bus speed.The mmc core >> and >> > host modules have been touched to add support for this module. >> > >> > It is necessary to know the card type in the sdhci.c file to add >> support >> > for eMMC tuning function. So card.h file is included to import the >> card >> > data structure. >> > >> > cc: Chris Ball<cjb@xxxxxxxxxx> >> > Signed-off-by: Girish K S<girish.shivananjappa@xxxxxxxxxx> >> > --- >> > Changes in v4: >> > Rebased onto chris-mmc/mmc-next branch. This patch is >> successfully >> > applied on commit with id >> de022ed3fdc14808299b2fa66dbb1ed5ab921912. >> > Changes in v3: >> > In the previous commits of chris-mmc/mmc-next branch, the patch >> with >> > commit id (c0f22a2c92e357e7cb3988b0b13034d70b7461f9) defines >> caps2 for >> > more capabilities. This patch version deletes the member >> ext_caps(created >> > in my earlier patch) from struct mmc_host and reuses already >> accepted >> > caps2 member. >> > Changes in v2: >> > Rebased to latest chris-mmc/mmc-next branch. Resolved indentation >> > problems identified in review. This patch has to be applied >> before >> > the patch released for modifying the printk messages. >> > Changes in v1: >> > Case statements in switch that produce same result have >> > been combined to reduce repeated assignments. >> > patch recreated after rebase to chris balls mmc-next branch. >> > >> > drivers/mmc/core/bus.c | 3 +- >> > drivers/mmc/core/mmc.c | 92 >> ++++++++++++++++++++++++++++++++++++++++---- >> > drivers/mmc/host/sdhci.c | 36 +++++++++++++++--- >> > include/linux/mmc/card.h | 3 + >> > include/linux/mmc/host.h | 6 +++ >> > include/linux/mmc/mmc.h | 8 +++- >> > include/linux/mmc/sdhci.h | 1 + >> > 7 files changed, 132 insertions(+), 17 deletions(-) >> > >> > diff --git a/drivers/mmc/core/bus.c b/drivers/mmc/core/bus.c >> > index 46b6e84..2f82f6b 100644 >> > --- a/drivers/mmc/core/bus.c >> > +++ b/drivers/mmc/core/bus.c >> > @@ -301,10 +301,11 @@ int mmc_add_card(struct mmc_card *card) >> > mmc_card_ddr_mode(card) ? "DDR " : "", >> > type); >> > } else { >> > - printk(KERN_INFO "%s: new %s%s%s card at address %04x\n", >> > + pr_info("%s: new %s%s%s%s card at address %04x\n", >> > mmc_hostname(card->host), >> > mmc_sd_card_uhs(card) ? "ultra high speed " : >> > (mmc_card_highspeed(card) ? "high speed " : ""), >> > + (mmc_card_hs200(card) ? "HS200 " : ""), >> > mmc_card_ddr_mode(card) ? "DDR " : "", >> > type, card->rca); >> > } >> > diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c >> > index 3627044..4db248c 100644 >> > --- a/drivers/mmc/core/mmc.c >> > +++ b/drivers/mmc/core/mmc.c >> > @@ -285,6 +285,39 @@ static int mmc_read_ext_csd(struct mmc_card >> *card, u8 *ext_csd) >> > } >> > card->ext_csd.raw_card_type = ext_csd[EXT_CSD_CARD_TYPE]; >> > switch (ext_csd[EXT_CSD_CARD_TYPE]& EXT_CSD_CARD_TYPE_MASK) { >> > + case EXT_CSD_CARD_TYPE_SDR_200 | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_200 | EXT_CSD_CARD_TYPE_DDR_1_8V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_200 | EXT_CSD_CARD_TYPE_DDR_1_2V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_200 | EXT_CSD_CARD_TYPE_DDR_52 | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + card->ext_csd.hs_max_dtr = 200000000; >> > + card->ext_csd.card_type = EXT_CSD_CARD_TYPE_SDR_200; >> > + break; >> > + case EXT_CSD_CARD_TYPE_SDR_1_2V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_2V | EXT_CSD_CARD_TYPE_DDR_1_8V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_2V | EXT_CSD_CARD_TYPE_DDR_1_2V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_2V | EXT_CSD_CARD_TYPE_DDR_52 | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + card->ext_csd.hs_max_dtr = 200000000; >> > + card->ext_csd.card_type = EXT_CSD_CARD_TYPE_SDR_1_2V; >> > + break; >> > + case EXT_CSD_CARD_TYPE_SDR_1_8V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_8V | EXT_CSD_CARD_TYPE_DDR_1_8V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_8V | EXT_CSD_CARD_TYPE_DDR_1_2V | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + case EXT_CSD_CARD_TYPE_SDR_1_8V | EXT_CSD_CARD_TYPE_DDR_52 | >> > + EXT_CSD_CARD_TYPE_52 | EXT_CSD_CARD_TYPE_26: >> > + card->ext_csd.hs_max_dtr = 200000000; >> > + card->ext_csd.card_type = EXT_CSD_CARD_TYPE_SDR_1_8V; >> > + break; >> > case EXT_CSD_CARD_TYPE_DDR_52 | EXT_CSD_CARD_TYPE_52 | >> > EXT_CSD_CARD_TYPE_26: >> > card->ext_csd.hs_max_dtr = 52000000; >> > @@ -699,6 +732,7 @@ static int mmc_init_card(struct mmc_host *host, >> u32 ocr, >> > { >> > struct mmc_card *card; >> > int err, ddr = 0; >> > + int hs_sdr = 0; >> > u32 cid[4]; >> > unsigned int max_dtr; >> > u32 rocr; >> > @@ -890,11 +924,15 @@ static int mmc_init_card(struct mmc_host *host, >> u32 ocr, >> > /* >> > * Activate high speed (if supported) >> > */ >> > - if ((card->ext_csd.hs_max_dtr != 0)&& >> > - (host->caps& MMC_CAP_MMC_HIGHSPEED)) { >> > - err = mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, >> > - EXT_CSD_HS_TIMING, 1, >> > - card->ext_csd.generic_cmd6_time); >> > + if (card->ext_csd.hs_max_dtr != 0) { >> > + if ((card->ext_csd.hs_max_dtr> 52000000)&& >> > + (host->caps2& MMC_CAP2_HIGHSPEED_200)) >> > + err = mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, >> > + EXT_CSD_HS_TIMING, 2, 0); >> > + else if (host->caps& MMC_CAP_MMC_HIGHSPEED) >> > + err = mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, >> > + EXT_CSD_HS_TIMING, 1, 0); >> > + >> > if (err&& err != -EBADMSG) >> > goto free_card; >> > >> > @@ -903,7 +941,10 @@ static int mmc_init_card(struct mmc_host *host, >> u32 ocr, >> > mmc_hostname(card->host)); >> > err = 0; >> > } else { >> > - mmc_card_set_highspeed(card); >> > + if (card->ext_csd.hs_max_dtr> 52000000) >> > + mmc_card_set_hs200(card); >> > + else >> > + mmc_card_set_highspeed(card); >> > mmc_set_timing(card->host, MMC_TIMING_MMC_HS); >> > } >> > } >> > @@ -929,7 +970,7 @@ static int mmc_init_card(struct mmc_host *host, >> u32 ocr, >> > */ >> > max_dtr = (unsigned int)-1; >> > >> > - if (mmc_card_highspeed(card)) { >> > + if (mmc_card_highspeed(card) || mmc_card_hs200(card)) { >> > if (max_dtr> card->ext_csd.hs_max_dtr) >> > max_dtr = card->ext_csd.hs_max_dtr; >> > } else if (max_dtr> card->csd.max_dtr) { >> > @@ -955,6 +996,22 @@ static int mmc_init_card(struct mmc_host *host, >> u32 ocr, >> > } >> > >> > /* >> > + * Indicate HS200 SDR mode (if supported). >> > + */ >> > + if (mmc_card_hs200(card)) { >> > + if ((card->ext_csd.card_type& EXT_CSD_CARD_TYPE_SDR_1_8V) >> > + && ((host->caps2& (MMC_CAP2_HS200_1_8V_SDR | >> > + MMC_CAP2_HS200)) >> > + == (MMC_CAP2_HS200_1_8V_SDR | > MMC_CAP2_HS200))) >> > + hs_sdr = MMC_1_8V_SDR_MODE; >> > + else if ((card->ext_csd.card_type& >> EXT_CSD_CARD_TYPE_SDR_1_2V) >> > + && ((host->caps2& (MMC_CAP2_HS200_1_2V_SDR | >> > + MMC_CAP2_HS200)) >> > + == (MMC_CAP2_HS200_1_2V_SDR | > MMC_CAP2_HS200))) >> > + hs_sdr = MMC_1_2V_SDR_MODE; >> > + } >> > + >> > + /* >> > * Activate wide bus and DDR (if supported). >> > */ >> > if ((card->csd.mmca_vsn>= CSD_SPEC_VER_4)&& >> > @@ -994,16 +1051,24 @@ static int mmc_init_card(struct mmc_host >> *host, u32 ocr, >> > if (!err) { >> > mmc_set_bus_width(card->host, bus_width); >> > >> > + if ((host->caps2& MMC_CAP2_HS200)&& >> > + card->host->ops->execute_tuning) >> > + err = card->host->ops-> \ >> > + execute_tuning(card->host); >> > + >> > /* >> > * If controller can't handle bus width > test, >> > * compare ext_csd previously read in 1 bit >> mode >> > * against ext_csd at new bus width >> > */ >> > - if (!(host->caps& MMC_CAP_BUS_WIDTH_TEST)) >> > + if (!(host->caps& MMC_CAP_BUS_WIDTH_TEST)&& >> > + !err) >> > err = mmc_compare_ext_csds(card, >> > bus_width); >> > - else >> > + else if (!err) >> > err = mmc_bus_test(card, bus_width); >> > + else >> > + pr_warning("tuning execution > failed\n"); >> > if (!err) >> > break; >> > } >> > @@ -1052,6 +1117,15 @@ static int mmc_init_card(struct mmc_host >> *host, u32 ocr, >> > mmc_card_set_ddr_mode(card); >> > mmc_set_timing(card->host, MMC_TIMING_UHS_DDR50); >> > mmc_set_bus_width(card->host, bus_width); >> > + } else if (hs_sdr) { >> > + if (hs_sdr == EXT_CSD_CARD_TYPE_SDR_1_2V) { >> > + err = mmc_set_signal_voltage(host, >> > + MMC_SIGNAL_VOLTAGE_120, 0); >> > + if (err) >> > + goto err; >> > + } >> > + mmc_set_timing(card->host, MMC_TIMING_MMC_HS); >> Can you define a new timing mode for HS200 instead of using the same >> high speed >> timing mode MMC_TIMING_MMC_HS? The host driver might need to configure >> it's controller with a different timing mode for HS200 cards. >> > + mmc_set_bus_width(card->host, bus_width); >> > } >> > } > Any comment on using the new timing mode for HS200? > Will look into it tomorrow and let you know > Regards, > Subhash > >> Thanks, >> Sahitya. >> >> -- >> Sent by a consultant of the Qualcomm Innovation Center, Inc. >> The Qualcomm Innovation Center, Inc. is a member of the Code Aurora >> Forum. >> >> >> -- >> 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 > > -- To unsubscribe from this list: send the line "unsubscribe linux-samsung-soc" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html