1 // SPDX-License-Identifier: GPL-2.0-or-later
4 * Copyright 2022 Toradex
6 * Generated code from MX8M_DDR_tool
8 * Align with uboot version:
9 * imx_v2019.04_5.4.x and above version
10 * For imx_v2018.03_4.14.78_1.0.0_ga ~ imx_v2018.04_4.19.35_1.1.0_ga:
11 * please replace #include <asm/arch/ddr.h> with #include <asm/arch/imx8m_ddr.h>
14 #include <linux/kernel.h>
15 #include <asm/arch/ddr.h>
16 #include "lpddr4_timing.h"
18 struct dram_cfg_param ddr_ddrc_cfg_single_rank_patch[] = {
19 { 0x3d400000, 0xa1080020},
24 struct dram_cfg_param ddr_fsp0_cfg_single_rank_patch[] = {
29 struct dram_cfg_param ddr_fsp1_cfg_single_rank_patch[] = {
34 struct dram_cfg_param ddr_fsp2_cfg_single_rank_patch[] = {
39 struct dram_cfg_param ddr_fsp0_2d_cfg_single_rank_patch[] = {
44 struct dram_cfg_param ddr_ddrc_cfg[] = {
45 /** Initialize DDRC registers **/
48 { 0x3d400000, 0xa3080020 },
49 { 0x3d400020, 0x1303 },
50 { 0x3d400024, 0x1e84800 },
51 { 0x3d400064, 0x7a017c },
52 { 0x3d400070, 0x7027f90 },
53 { 0x3d400074, 0x790 },
54 { 0x3d4000d0, 0xc00307a3 },
55 { 0x3d4000d4, 0xc50000 },
56 { 0x3d4000dc, 0xf4003f },
57 { 0x3d4000e0, 0x330000 },
58 { 0x3d4000e8, 0x660048 },
59 { 0x3d4000ec, 0x160048 },
60 { 0x3d400100, 0x2028222a },
61 { 0x3d400104, 0x8083f },
62 { 0x3d40010c, 0xe0e000 },
63 { 0x3d400110, 0x12040a12 },
64 { 0x3d400114, 0x2050f0f },
65 { 0x3d400118, 0x1010009 },
66 { 0x3d40011c, 0x502 },
67 { 0x3d400130, 0x20800 },
68 { 0x3d400134, 0xe100002 },
69 { 0x3d400138, 0x184 },
70 { 0x3d400144, 0xc80064 },
71 { 0x3d400180, 0x3e8001e },
72 { 0x3d400184, 0x3207a12 },
74 { 0x3d400190, 0x49f820e },
75 { 0x3d400194, 0x80303 },
76 { 0x3d4001b4, 0x1f0e },
77 { 0x3d4001a0, 0xe0400018 },
78 { 0x3d4001a4, 0xdf00e4 },
79 { 0x3d4001a8, 0x80000000 },
83 { 0x3d4000f4, 0x799 },
84 { 0x3d400108, 0x9121b1c },
88 { 0x3d400210, 0x1f1f },
89 { 0x3d400204, 0x80808 },
90 { 0x3d400214, 0x7070707 },
91 { 0x3d400218, 0x7070707 },
92 { 0x3d40021c, 0xf08 },
93 { 0x3d400250, 0x1705 },
95 { 0x3d40025c, 0x4000030 },
96 { 0x3d400264, 0x900093e7 },
97 { 0x3d40026c, 0x2005574 },
98 { 0x3d400400, 0x111 },
99 { 0x3d400404, 0x72ff },
100 { 0x3d400408, 0x72ff },
101 { 0x3d400494, 0x2100e07 },
102 { 0x3d400498, 0x620096 },
103 { 0x3d40049c, 0x1100e07 },
104 { 0x3d4004a0, 0xc8012c },
105 { 0x3d402020, 0x1001 },
106 { 0x3d402024, 0x30d400 },
107 { 0x3d402050, 0x20d000 },
108 { 0x3d402064, 0xc0026 },
109 { 0x3d4020dc, 0x840000 },
110 { 0x3d4020e0, 0x330000 },
111 { 0x3d4020e8, 0x660048 },
112 { 0x3d4020ec, 0x160048 },
113 { 0x3d402100, 0xa040305 },
114 { 0x3d402104, 0x30407 },
115 { 0x3d402108, 0x203060b },
116 { 0x3d40210c, 0x505000 },
117 { 0x3d402110, 0x2040202 },
118 { 0x3d402114, 0x2030202 },
119 { 0x3d402118, 0x1010004 },
120 { 0x3d40211c, 0x302 },
121 { 0x3d402130, 0x20300 },
122 { 0x3d402134, 0xa100002 },
123 { 0x3d402138, 0x27 },
124 { 0x3d402144, 0x14000a },
125 { 0x3d402180, 0x640004 },
126 { 0x3d402190, 0x3818200 },
127 { 0x3d402194, 0x80303 },
128 { 0x3d4021b4, 0x100 },
129 { 0x3d4020f4, 0x599 },
130 { 0x3d403020, 0x1001 },
131 { 0x3d403024, 0xc3500 },
132 { 0x3d403050, 0x20d000 },
133 { 0x3d403064, 0x3000a },
134 { 0x3d4030dc, 0x840000 },
135 { 0x3d4030e0, 0x330000 },
136 { 0x3d4030e8, 0x660048 },
137 { 0x3d4030ec, 0x160048 },
138 { 0x3d403100, 0xa010102 },
139 { 0x3d403104, 0x30404 },
140 { 0x3d403108, 0x203060b },
141 { 0x3d40310c, 0x505000 },
142 { 0x3d403110, 0x2040202 },
143 { 0x3d403114, 0x2030202 },
144 { 0x3d403118, 0x1010004 },
145 { 0x3d40311c, 0x302 },
146 { 0x3d403130, 0x20300 },
147 { 0x3d403134, 0xa100002 },
149 { 0x3d403144, 0x50003 },
150 { 0x3d403180, 0x190004 },
151 { 0x3d403190, 0x3818200 },
152 { 0x3d403194, 0x80303 },
153 { 0x3d4031b4, 0x100 },
154 { 0x3d4030f4, 0x599 },
158 /* PHY Initialize Configuration */
159 struct dram_cfg_param ddr_ddrphy_cfg[] = {
367 /* ddr phy trained csr */
368 struct dram_cfg_param ddr_ddrphy_trained_csr[] = {
1090 /* P0 message block parameter for training firmware */
1091 struct dram_cfg_param ddr_fsp0_cfg[] = {
1095 { 0x54005, 0x2228 },
1097 { 0x54008, 0x131f },
1102 { 0x54019, 0x3ff4 },
1104 { 0x5401b, 0x4866 },
1105 { 0x5401c, 0x4800 },
1107 { 0x5401f, 0x3ff4 },
1109 { 0x54021, 0x4866 },
1110 { 0x54022, 0x4800 },
1112 { 0x5402b, 0x1000 },
1114 { 0x54032, 0xf400 },
1115 { 0x54033, 0x333f },
1116 { 0x54034, 0x6600 },
1119 { 0x54037, 0x1600 },
1120 { 0x54038, 0xf400 },
1121 { 0x54039, 0x333f },
1122 { 0x5403a, 0x6600 },
1125 { 0x5403d, 0x1600 },
1129 /* P1 message block parameter for training firmware */
1130 struct dram_cfg_param ddr_fsp1_cfg[] = {
1135 { 0x54005, 0x2228 },
1137 { 0x54008, 0x121f },
1144 { 0x5401b, 0x4866 },
1145 { 0x5401c, 0x4800 },
1149 { 0x54021, 0x4866 },
1150 { 0x54022, 0x4800 },
1152 { 0x5402b, 0x1000 },
1154 { 0x54032, 0x8400 },
1155 { 0x54033, 0x3300 },
1156 { 0x54034, 0x6600 },
1159 { 0x54037, 0x1600 },
1160 { 0x54038, 0x8400 },
1161 { 0x54039, 0x3300 },
1162 { 0x5403a, 0x6600 },
1165 { 0x5403d, 0x1600 },
1169 /* P2 message block parameter for training firmware */
1170 struct dram_cfg_param ddr_fsp2_cfg[] = {
1175 { 0x54005, 0x2228 },
1177 { 0x54008, 0x121f },
1184 { 0x5401b, 0x4866 },
1185 { 0x5401c, 0x4800 },
1189 { 0x54021, 0x4866 },
1190 { 0x54022, 0x4800 },
1192 { 0x5402b, 0x1000 },
1194 { 0x54032, 0x8400 },
1195 { 0x54033, 0x3300 },
1196 { 0x54034, 0x6600 },
1199 { 0x54037, 0x1600 },
1200 { 0x54038, 0x8400 },
1201 { 0x54039, 0x3300 },
1202 { 0x5403a, 0x6600 },
1205 { 0x5403d, 0x1600 },
1209 /* P0 2D message block parameter for training firmware */
1210 struct dram_cfg_param ddr_fsp0_2d_cfg[] = {
1214 { 0x54005, 0x2228 },
1220 { 0x54010, 0x1f7f },
1222 { 0x54019, 0x3ff4 },
1224 { 0x5401b, 0x4866 },
1225 { 0x5401c, 0x4800 },
1227 { 0x5401f, 0x3ff4 },
1229 { 0x54021, 0x4866 },
1230 { 0x54022, 0x4800 },
1232 { 0x5402b, 0x1000 },
1234 { 0x54032, 0xf400 },
1235 { 0x54033, 0x333f },
1236 { 0x54034, 0x6600 },
1239 { 0x54037, 0x1600 },
1240 { 0x54038, 0xf400 },
1241 { 0x54039, 0x333f },
1242 { 0x5403a, 0x6600 },
1245 { 0x5403d, 0x1600 },
1249 /* DRAM PHY init engine image */
1250 struct dram_cfg_param ddr_phy_pie[] = {
1309 { 0x9005c, 0x40c0 },
1315 { 0x90062, 0x4040 },
1385 { 0x40001, 0x4008 },
1389 { 0x40002, 0x4040 },
1399 { 0x40044, 0x1740 },
1407 { 0x40046, 0x2001 },
1411 { 0x40047, 0x2800 },
1419 { 0x40049, 0x1400 },
1429 { 0x4000c, 0x4028 },
1441 { 0x4000f, 0x4040 },
1445 { 0x40010, 0x2604 },
1452 { 0x40071, 0x2002 },
1457 { 0x40013, 0x2604 },
1464 { 0x40074, 0x2002 },
1465 { 0x40015, 0x4040 },
1471 { 0x40056, 0x1200 },
1475 { 0x40057, 0x1300 },
1479 { 0x40058, 0x1200 },
1483 { 0x40059, 0x1300 },
1485 { 0x4001a, 0x4808 },
1526 { 0x900c9, 0x8568 },
1535 { 0x900d2, 0x8558 },
1540 { 0x900d7, 0x1ff8 },
1541 { 0x900d8, 0x85a8 },
1550 { 0x900e1, 0x8310 },
1553 { 0x900e4, 0xa310 },
1565 { 0x900f0, 0x8310 },
1568 { 0x900f3, 0xa310 },
1570 { 0x900f5, 0x1ff8 },
1571 { 0x900f6, 0x85a8 },
1583 { 0x90102, 0x8b10 },
1586 { 0x90105, 0xab10 },
1598 { 0x90111, 0x8b10 },
1601 { 0x90114, 0xab10 },
1616 { 0x90123, 0x8080 },
1631 { 0x90132, 0x8080 },
1637 { 0x90138, 0x8568 },
1646 { 0x90141, 0x8558 },
1658 { 0x9014d, 0x8558 },
1673 { 0x9015c, 0x8140 },
1676 { 0x9015f, 0x8138 },
1700 { 0x90177, 0x8140 },
1746 { 0x9000f, 0x6110 },
1747 { 0x90010, 0x2152 },
1748 { 0x90011, 0xdfbd },
1749 { 0x90012, 0x2060 },
1750 { 0x90013, 0x6152 },
1776 { 0x10002, 0x6209 },
1790 { 0x11002, 0x6209 },
1804 { 0x12002, 0x6209 },
1818 { 0x13002, 0x6209 },
1834 struct dram_fsp_msg ddr_dram_fsp_msg[] = {
1838 .fw_type = FW_1D_IMAGE,
1839 .fsp_cfg = ddr_fsp0_cfg,
1840 .fsp_cfg_num = ARRAY_SIZE(ddr_fsp0_cfg),
1845 .fw_type = FW_1D_IMAGE,
1846 .fsp_cfg = ddr_fsp1_cfg,
1847 .fsp_cfg_num = ARRAY_SIZE(ddr_fsp1_cfg),
1852 .fw_type = FW_1D_IMAGE,
1853 .fsp_cfg = ddr_fsp2_cfg,
1854 .fsp_cfg_num = ARRAY_SIZE(ddr_fsp2_cfg),
1859 .fw_type = FW_2D_IMAGE,
1860 .fsp_cfg = ddr_fsp0_2d_cfg,
1861 .fsp_cfg_num = ARRAY_SIZE(ddr_fsp0_2d_cfg),
1865 /* ddr timing config params */
1866 struct dram_timing_info dram_timing = {
1867 .ddrc_cfg = ddr_ddrc_cfg,
1868 .ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg),
1869 .ddrphy_cfg = ddr_ddrphy_cfg,
1870 .ddrphy_cfg_num = ARRAY_SIZE(ddr_ddrphy_cfg),
1871 .fsp_msg = ddr_dram_fsp_msg,
1872 .fsp_msg_num = ARRAY_SIZE(ddr_dram_fsp_msg),
1873 .ddrphy_trained_csr = ddr_ddrphy_trained_csr,
1874 .ddrphy_trained_csr_num = ARRAY_SIZE(ddr_ddrphy_trained_csr),
1875 .ddrphy_pie = ddr_phy_pie,
1876 .ddrphy_pie_num = ARRAY_SIZE(ddr_phy_pie),
1877 .fsp_table = { 4000, 400, 100, },
1880 static void apply_cfg_patch(struct dram_cfg_param *cfg, int cfg_sz,
1881 struct dram_cfg_param *patch, int patch_sz)
1885 for (i = 0; i < cfg_sz; i++)
1886 for (j = 0; j < patch_sz; j++)
1887 if (cfg[i].reg == patch[j].reg)
1888 cfg[i].val = patch[j].val;
1891 void lpddr4_single_rank_training_patch(void)
1893 apply_cfg_patch(ddr_ddrc_cfg, ARRAY_SIZE(ddr_ddrc_cfg),
1894 ddr_ddrc_cfg_single_rank_patch,
1895 ARRAY_SIZE(ddr_ddrc_cfg_single_rank_patch));
1897 apply_cfg_patch(ddr_fsp0_cfg, ARRAY_SIZE(ddr_fsp0_cfg),
1898 ddr_fsp0_cfg_single_rank_patch,
1899 ARRAY_SIZE(ddr_fsp0_cfg_single_rank_patch));
1901 apply_cfg_patch(ddr_fsp1_cfg, ARRAY_SIZE(ddr_fsp1_cfg),
1902 ddr_fsp1_cfg_single_rank_patch,
1903 ARRAY_SIZE(ddr_fsp1_cfg_single_rank_patch));
1905 apply_cfg_patch(ddr_fsp2_cfg, ARRAY_SIZE(ddr_fsp2_cfg),
1906 ddr_fsp2_cfg_single_rank_patch,
1907 ARRAY_SIZE(ddr_fsp2_cfg_single_rank_patch));
1909 apply_cfg_patch(ddr_fsp0_2d_cfg, ARRAY_SIZE(ddr_fsp0_2d_cfg),
1910 ddr_fsp0_2d_cfg_single_rank_patch,
1911 ARRAY_SIZE(ddr_fsp0_2d_cfg_single_rank_patch));