ddr4_init.c 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Copyright 2018 NXP
  4. */
  5. #include <common.h>
  6. #include <errno.h>
  7. #include <asm/io.h>
  8. #include <asm/arch/ddr.h>
  9. #include <asm/arch/clock.h>
  10. #include <asm/arch/imx8m_ddr.h>
  11. #include <asm/arch/sys_proto.h>
  12. void ddr4_cfg_umctl2(struct dram_cfg_param *ddrc_cfg, int num)
  13. {
  14. int i = 0;
  15. for (i = 0; i < num; i++) {
  16. reg32_write(ddrc_cfg->reg, ddrc_cfg->val);
  17. ddrc_cfg++;
  18. }
  19. }
  20. void ddr_init(struct dram_timing_info *dram_timing)
  21. {
  22. volatile unsigned int tmp_t;
  23. /*
  24. * assert [0]ddr1_preset_n, [1]ddr1_core_reset_n,
  25. * [2]ddr1_phy_reset, [3]ddr1_phy_pwrokin_n,
  26. * [4]src_system_rst_b!
  27. */
  28. reg32_write(SRC_DDRC_RCR_ADDR, 0x8F00003F);
  29. /* deassert [4]src_system_rst_b! */
  30. reg32_write(SRC_DDRC_RCR_ADDR, 0x8F00000F);
  31. /*
  32. * change the clock source of dram_apb_clk_root
  33. * to source 4 --800MHz/4
  34. */
  35. clock_set_target_val(DRAM_APB_CLK_ROOT, CLK_ROOT_ON |
  36. CLK_ROOT_SOURCE_SEL(4) |
  37. CLK_ROOT_PRE_DIV(CLK_ROOT_PRE_DIV4));
  38. dram_pll_init(DRAM_PLL_OUT_600M);
  39. reg32_write(0x303A00EC, 0x0000ffff); /* PGC_CPU_MAPPING */
  40. reg32setbit(0x303A00F8, 5); /* PU_PGC_SW_PUP_REQ */
  41. /* release [0]ddr1_preset_n, [3]ddr1_phy_pwrokin_n */
  42. reg32_write(SRC_DDRC_RCR_ADDR, 0x8F000006);
  43. reg32_write(DDRC_DBG1(0), 0x00000001);
  44. reg32_write(DDRC_PWRCTL(0), 0x00000001);
  45. while (0 != (0x7 & reg32_read(DDRC_STAT(0))))
  46. ;
  47. /* config the uMCTL2's registers */
  48. ddr4_cfg_umctl2(dram_timing->ddrc_cfg, dram_timing->ddrc_cfg_num);
  49. reg32_write(DDRC_RFSHCTL3(0), 0x00000001);
  50. /* RESET: <ctn> DEASSERTED */
  51. /* RESET: <a Port 0 DEASSERTED(0) */
  52. reg32_write(SRC_DDRC_RCR_ADDR, 0x8F000004);
  53. reg32_write(SRC_DDRC_RCR_ADDR, 0x8F000000);
  54. reg32_write(DDRC_DBG1(0), 0x00000000);
  55. reg32_write(DDRC_PWRCTL(0), 0x00000aa);
  56. reg32_write(DDRC_SWCTL(0), 0x00000000);
  57. reg32_write(DDRC_DFIMISC(0), 0x00000000);
  58. /* config the DDR PHY's registers */
  59. ddr_cfg_phy(dram_timing);
  60. do {
  61. tmp_t = reg32_read(IP2APB_DDRPHY_IPS_BASE_ADDR(0) +
  62. 4 * 0x00020097);
  63. } while (tmp_t != 0);
  64. reg32_write(DDRC_DFIMISC(0), 0x00000020);
  65. /* wait DFISTAT.dfi_init_complete to 1 */
  66. while (0 == (0x1 & reg32_read(DDRC_DFISTAT(0))))
  67. ;
  68. /* clear DFIMISC.dfi_init_complete_en */
  69. reg32_write(DDRC_DFIMISC(0), 0x00000000);
  70. /* set DFIMISC.dfi_init_complete_en again */
  71. reg32_write(DDRC_DFIMISC(0), 0x00000001);
  72. reg32_write(DDRC_PWRCTL(0), 0x0000088);
  73. /*
  74. * set SWCTL.sw_done to enable quasi-dynamic register
  75. * programming outside reset.
  76. */
  77. reg32_write(DDRC_SWCTL(0), 0x00000001);
  78. /* wait SWSTAT.sw_done_ack to 1 */
  79. while (0 == (0x1 & reg32_read(DDRC_SWSTAT(0))))
  80. ;
  81. /* wait STAT to normal state */
  82. while (0x1 != (0x7 & reg32_read(DDRC_STAT(0))))
  83. ;
  84. reg32_write(DDRC_PWRCTL(0), 0x0000088);
  85. reg32_write(DDRC_PCTRL_0(0), 0x00000001);
  86. /* dis_auto-refresh is set to 0 */
  87. reg32_write(DDRC_RFSHCTL3(0), 0x00000000);
  88. /* save the dram timing config into memory */
  89. dram_config_save(dram_timing, CONFIG_SAVED_DRAM_TIMING_BASE);
  90. }