@@ -47,10 +47,21 @@ struct sdmmc_idma {
4747 bool use_bounce_buffer ;
4848};
4949
50+ struct sdmmc_dlyb ;
51+
52+ struct sdmmc_tuning_ops {
53+ int (* dlyb_enable )(struct sdmmc_dlyb * dlyb );
54+ void (* set_input_ck )(struct sdmmc_dlyb * dlyb );
55+ int (* tuning_prepare )(struct mmci_host * host );
56+ int (* set_cfg )(struct sdmmc_dlyb * dlyb , int unit __maybe_unused ,
57+ int phase , bool sampler __maybe_unused );
58+ };
59+
5060struct sdmmc_dlyb {
5161 void __iomem * base ;
5262 u32 unit ;
5363 u32 max ;
64+ struct sdmmc_tuning_ops * ops ;
5465};
5566
5667static int sdmmc_idma_validate_data (struct mmci_host * host ,
@@ -299,7 +310,7 @@ static void mmci_sdmmc_set_clkreg(struct mmci_host *host, unsigned int desired)
299310 mmci_write_clkreg (host , clk );
300311}
301312
302- static void sdmmc_dlyb_input_ck (struct sdmmc_dlyb * dlyb )
313+ static void sdmmc_dlyb_mp15_input_ck (struct sdmmc_dlyb * dlyb )
303314{
304315 if (!dlyb || !dlyb -> base )
305316 return ;
@@ -316,7 +327,8 @@ static void mmci_sdmmc_set_pwrreg(struct mmci_host *host, unsigned int pwr)
316327 /* adds OF options */
317328 pwr = host -> pwr_reg_add ;
318329
319- sdmmc_dlyb_input_ck (dlyb );
330+ if (dlyb && dlyb -> ops -> set_input_ck )
331+ dlyb -> ops -> set_input_ck (dlyb );
320332
321333 if (ios .power_mode == MMC_POWER_OFF ) {
322334 /* Only a reset could power-off sdmmc */
@@ -426,8 +438,15 @@ static bool sdmmc_busy_complete(struct mmci_host *host, u32 status, u32 err_msk)
426438 return true;
427439}
428440
429- static void sdmmc_dlyb_set_cfgr (struct sdmmc_dlyb * dlyb ,
430- int unit , int phase , bool sampler )
441+ static int sdmmc_dlyb_mp15_enable (struct sdmmc_dlyb * dlyb )
442+ {
443+ writel_relaxed (DLYB_CR_DEN , dlyb -> base + DLYB_CR );
444+
445+ return 0 ;
446+ }
447+
448+ static int sdmmc_dlyb_mp15_set_cfg (struct sdmmc_dlyb * dlyb ,
449+ int unit , int phase , bool sampler )
431450{
432451 u32 cfgr ;
433452
@@ -439,16 +458,18 @@ static void sdmmc_dlyb_set_cfgr(struct sdmmc_dlyb *dlyb,
439458
440459 if (!sampler )
441460 writel_relaxed (DLYB_CR_DEN , dlyb -> base + DLYB_CR );
461+
462+ return 0 ;
442463}
443464
444- static int sdmmc_dlyb_lng_tuning (struct mmci_host * host )
465+ static int sdmmc_dlyb_mp15_prepare (struct mmci_host * host )
445466{
446467 struct sdmmc_dlyb * dlyb = host -> variant_priv ;
447468 u32 cfgr ;
448469 int i , lng , ret ;
449470
450471 for (i = 0 ; i <= DLYB_CFGR_UNIT_MAX ; i ++ ) {
451- sdmmc_dlyb_set_cfgr (dlyb , i , DLYB_CFGR_SEL_MAX , true);
472+ dlyb -> ops -> set_cfg (dlyb , i , DLYB_CFGR_SEL_MAX , true);
452473
453474 ret = readl_relaxed_poll_timeout (dlyb -> base + DLYB_CFGR , cfgr ,
454475 (cfgr & DLYB_CFGR_LNGF ),
@@ -478,10 +499,14 @@ static int sdmmc_dlyb_phase_tuning(struct mmci_host *host, u32 opcode)
478499{
479500 struct sdmmc_dlyb * dlyb = host -> variant_priv ;
480501 int cur_len = 0 , max_len = 0 , end_of_len = 0 ;
481- int phase ;
502+ int phase , ret ;
482503
483504 for (phase = 0 ; phase <= dlyb -> max ; phase ++ ) {
484- sdmmc_dlyb_set_cfgr (dlyb , dlyb -> unit , phase , false);
505+ ret = dlyb -> ops -> set_cfg (dlyb , dlyb -> unit , phase , false);
506+ if (ret ) {
507+ dev_err (mmc_dev (host -> mmc ), "tuning config failed\n" );
508+ return ret ;
509+ }
485510
486511 if (mmc_send_tuning (host -> mmc , opcode , NULL )) {
487512 cur_len = 0 ;
@@ -499,10 +524,15 @@ static int sdmmc_dlyb_phase_tuning(struct mmci_host *host, u32 opcode)
499524 return - EINVAL ;
500525 }
501526
502- writel_relaxed (0 , dlyb -> base + DLYB_CR );
527+ if (dlyb -> ops -> set_input_ck )
528+ dlyb -> ops -> set_input_ck (dlyb );
503529
504530 phase = end_of_len - max_len / 2 ;
505- sdmmc_dlyb_set_cfgr (dlyb , dlyb -> unit , phase , false);
531+ ret = dlyb -> ops -> set_cfg (dlyb , dlyb -> unit , phase , false);
532+ if (ret ) {
533+ dev_err (mmc_dev (host -> mmc ), "tuning reconfig failed\n" );
534+ return ret ;
535+ }
506536
507537 dev_dbg (mmc_dev (host -> mmc ), "unit:%d max_dly:%d phase:%d\n" ,
508538 dlyb -> unit , dlyb -> max , phase );
@@ -515,6 +545,7 @@ static int sdmmc_execute_tuning(struct mmc_host *mmc, u32 opcode)
515545 struct mmci_host * host = mmc_priv (mmc );
516546 struct sdmmc_dlyb * dlyb = host -> variant_priv ;
517547 u32 clk ;
548+ int ret ;
518549
519550 if ((host -> mmc -> ios .timing != MMC_TIMING_UHS_SDR104 &&
520551 host -> mmc -> ios .timing != MMC_TIMING_MMC_HS200 ) ||
@@ -524,7 +555,9 @@ static int sdmmc_execute_tuning(struct mmc_host *mmc, u32 opcode)
524555 if (!dlyb || !dlyb -> base )
525556 return - EINVAL ;
526557
527- writel_relaxed (DLYB_CR_DEN , dlyb -> base + DLYB_CR );
558+ ret = dlyb -> ops -> dlyb_enable (dlyb );
559+ if (ret )
560+ return ret ;
528561
529562 /*
530563 * SDMMC_FBCK is selected when an external Delay Block is needed
@@ -535,8 +568,9 @@ static int sdmmc_execute_tuning(struct mmc_host *mmc, u32 opcode)
535568 clk |= MCI_STM32_CLK_SELFBCK ;
536569 mmci_write_clkreg (host , clk );
537570
538- if (sdmmc_dlyb_lng_tuning (host ))
539- return - EINVAL ;
571+ ret = dlyb -> ops -> tuning_prepare (host );
572+ if (ret )
573+ return ret ;
540574
541575 return sdmmc_dlyb_phase_tuning (host , opcode );
542576}
@@ -594,6 +628,13 @@ static struct mmci_host_ops sdmmc_variant_ops = {
594628 .post_sig_volt_switch = sdmmc_post_sig_volt_switch ,
595629};
596630
631+ static struct sdmmc_tuning_ops dlyb_tuning_mp15_ops = {
632+ .dlyb_enable = sdmmc_dlyb_mp15_enable ,
633+ .set_input_ck = sdmmc_dlyb_mp15_input_ck ,
634+ .tuning_prepare = sdmmc_dlyb_mp15_prepare ,
635+ .set_cfg = sdmmc_dlyb_mp15_set_cfg ,
636+ };
637+
597638void sdmmc_variant_init (struct mmci_host * host )
598639{
599640 struct device_node * np = host -> mmc -> parent -> of_node ;
@@ -612,6 +653,7 @@ void sdmmc_variant_init(struct mmci_host *host)
612653 return ;
613654
614655 dlyb -> base = base_dlyb ;
656+ dlyb -> ops = & dlyb_tuning_mp15_ops ;
615657 host -> variant_priv = dlyb ;
616658 host -> mmc_ops -> execute_tuning = sdmmc_execute_tuning ;
617659}
0 commit comments