2 * Startup Code for MIPS32 CPU-core
4 * Copyright (c) 2003 Wolfgang Denk <wd@denx.de>
6 * See file CREDITS for list of people who contributed to this
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License as
11 * published by the Free Software Foundation; either version 2 of
12 * the License, or (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
28 #include <asm/regdef.h>
29 #include <asm/mipsregs.h>
30 #include <asm/addrspace.h>
31 #include <ar7240_soc.h>
33 .globl hornet_ddr_init
37 #define set_mem(_mem, _val) \
41 //============================================
42 // init DDR1 parameter before rel_start
43 //===========================================
45 // 0x18000000 (DDR_CONFIG, p. 54)
46 // CFG_DDR_CONFIG_VAL = 0x7fbc8cd0 (ap121.h)
47 li t8, CFG_DDR_CONFIG_VAL;
48 set_mem(0xB8000000, t8);
50 // 0x18000004 (DDR_CONFIG2, p. 55)
51 // CFG_DDR_CONFIG2_VAL = 0x99d0e6a8 (ap121.h)
52 li t8, CFG_DDR_CONFIG2_VAL;
53 set_mem(0xB8000004, t8);
56 * WR720N v3 (CH version) has wrong bootstrap configuration,
57 * so the memory type cannot be recognized automatically
59 #if !defined(CONFIG_FOR_TPLINK_WR720N_V3)
61 // TODO: what about SDRAM?
62 // 0x180600AC (BOOT_STRAP, p. 81)
63 li t8, 0xB80600AC // load BOOT_STRAP reg address
64 lw t9, 0(t8) // and its value
65 li t8, 0x2000 // 0x2000 -> BIT13 is set
67 beq t9, zero, ddr1_config // jump if we have DDR1
71 // 0x1800008C (DDR_DDR2_CONFIG, p. 58)
73 set_mem(0xB800008C, t8);
76 // 0x18000010 (DDR_CONTROL, p. 56)
78 set_mem(0xB8000010, t8);
80 // Disable High Temperature Self-Refresh Rate
81 // 0x18000090 (DDR_EMR2, p. 58)
83 set_mem(0xB8000090, t8);
85 // Extended Mode Register 2 Set (EMR2S)
86 // 0x18000010 (DDR_CONTROL, p. 56)
88 set_mem(0xB8000010, t8);
90 // 0x18000094 (DDR_EMR3, p. 58)
92 set_mem(0xB8000094, t8);
94 // Extended Mode Register 3 Set (EMR3S)
95 // 0x18000010 (DDR_CONTROL, p. 56)
97 set_mem(0xB8000010, t8);
100 // 0x1800000C (DDR_EXTENDED_MODE_REGISTER, p. 55)
102 set_mem(0xB800000C, t8);
104 // Extended Mode Register Set (EMRS)
105 // 0x18000010 (DDR_CONTROL, p. 56)
107 set_mem(0xB8000010, t8);
110 // 0x18000008 (DDR_MODE_REGISTER, p. 55)
112 set_mem(0xB8000008, t8);
114 // Mode Register Set (MRS)
115 // 0x18000010 (DDR_CONTROL, p. 56)
117 set_mem(0xB8000010, t8);
120 // 0x18000010 (DDR_CONTROL, p. 56)
122 set_mem(0xB8000010, t8);
125 // 0x18000010 (DDR_CONTROL, p. 56)
127 set_mem(0xB8000010, t8);
130 // 0x18000010 (DDR_CONTROL, p. 56)
132 set_mem(0xB8000010, t8);
134 // Write recovery (WR) 6 clock, CAS Latency 3, Burst Length 8
135 // 0x18000008 (DDR_MODE_REGISTER, p. 55)
137 set_mem(0xB8000008, t8);
139 // Mode Register Set (MRS)
140 // 0x18000010 (DDR_CONTROL, p. 56)
142 set_mem(0xB8000010, t8);
144 // E7,E8,E9 equal to 1(Enable OCD defaults), Enable DLL, Reduced Drive Strength
145 // 0x1800000C (DDR_EXTENDED_MODE_REGISTER, p. 55)
147 set_mem(0xB800000C, t8);
149 // Extended Mode Register Set (EMRS)
150 // 0x18000010 (DDR_CONTROL, p. 56)
152 set_mem(0xB8000010, t8);
154 // E7,E8,E9 equal to 0(OCD exit), Enable DLL, Reduced Drive Strength
155 // 0x1800000C (DDR_EXTENDED_MODE_REGISTER, p. 55)
157 set_mem(0xB800000C, t8);
159 // Extended Mode Register Set (EMRS)
160 // 0x18000010 (DDR_CONTROL, p. 56)
162 set_mem(0xB8000010, t8);
164 // Refresh control. Bit 14 is enable. Bits<13:0> Refresh time
165 // 0x18000014 (DDR_REFRESH, p. 56)
166 li t8, CFG_DDR_REFRESH_VAL;
167 set_mem(0xB8000014, t8);
169 // DQS 0 Tap Control (needs tuning)
170 // 0x1800001C (TAP_CONTROL_0, p. 56)
171 li t8, CFG_DDR_TAP0_VAL;
172 set_mem(0xB800001C, t8);
174 // DQS 1 Tap Control (needs tuning)
175 // 0x18000020 (TAP_CONTROL_1, p. 57)
176 li t8, CFG_DDR_TAP1_VAL;
177 set_mem(0xB8000020, t8);
180 // 0x18000018 (DDR_RD_DATA_THIS_CYCLE, p. 56)
182 set_mem(0xB8000018, t8);
186 #endif /* !defined(CONFIG_FOR_TPLINK_WR720N_V3) */
190 // 0x18000010 (DDR_CONTROL, p. 56)
192 set_mem(0xB8000010, t8);
194 // 0x18000008 (DDR_MODE_REGISTER, p. 55)
195 li t8, CFG_DDR_MODE_VAL_INIT;
196 set_mem(0xB8000008, t8);
198 // Write Mode Word in DDR
199 // 0x18000010 (DDR_CONTROL, p. 56)
201 set_mem(0xB8000010, t8);
203 // Enable DLL, High drive strength from DDR
204 // 0x1800000C (DDR_EXTENDED_MODE_REGISTER, p. 55)
206 set_mem(0xB800000C, t8);
208 // Write Extended Mode Word of DDR
209 // 0x18000010 (DDR_CONTROL, p. 56)
211 set_mem(0xB8000010, t8);
214 // 0x18000010 (DDR_CONTROL, p. 56)
216 set_mem(0xB8000010, t8);
218 // DLL out of reset, CAS Latency 3
219 // 0x18000008 (DDR_MODE_REGISTER, p. 55)
220 li t8, CFG_DDR_MODE_VAL;
221 set_mem(0xB8000008, t8);
224 // 0x18000010 (DDR_CONTROL, p. 56)
226 set_mem(0xB8000010, t8);
228 // Refresh control. Bit 14 is enable. Bits<13:0> Refresh time
229 // 0x18000014 (DDR_REFRESH, p. 56)
230 li t8, CFG_DDR_REFRESH_VAL;
231 set_mem(0xB8000014, t8);
233 // DQS 0 Tap Control (needs tuning)
234 // 0x1800001C (TAP_CONTROL_0, p. 56)
235 li t8, CFG_DDR_TAP0_VAL;
236 set_mem(0xB800001C, t8);
238 // DQS 1 Tap Control (needs tuning)
239 // 0x18000020 (TAP_CONTROL_1, p. 57)
240 li t8, CFG_DDR_TAP1_VAL;
241 set_mem(0xB8000020, t8);
244 // 0x18000018 (DDR_RD_DATA_THIS_CYCLE, p. 56)
246 set_mem(0xB8000018, t8);
252 * void hornet_ddr_tap_init(void)
254 * This "function" is used to find the tap settings for the DDR
256 .globl hornet_ddr_tap_init
257 .ent hornet_ddr_tap_init
258 hornet_ddr_tap_init: /* { */
393 bne t0, t1, write_loop_start
395 ###### ddr init over #########
398 li a1, 0x80002000 ### Start address of the pattern 200
399 li a2, 0x80003000 ### End Address of the pattern 220
400 li t0, 0xb800001c ## Tap settings addr
401 lw a3, 0x0(t0) ## loading default tap value
405 li t1, 0x1 ## $t1=1 indicates increasing tap value, 0 = decreasing
409 #li t7, 0x200 ## No. of times read has to happen for 1 tap setting
410 li t8, 0xb8000000 #### Loading Tap Setting
415 #if 0 /* Hornet doesn't have DQS2, DQS3*/
422 ###### t0 stores current tap setting under test
423 ###### t1 indicates increment or decrement of tap
440 bne t5, t6, tap_fail # jump to fail if not equal
445 addiu t2, t2, 0x4 #incrementing addr
450 bne t3, t4, tap_addr_loop # compare new addr if end addr not reached
453 addiu t7, t7, -1 # read passed for all locations once hence decrement t7
455 bnez t7, pat_read # t7 = 0 represents passing of all locations for given tap
459 bnez t1, tap_incr # increment tap if t1 = 1
463 bnez t0, tap_decr ## $t0=0 implies tap=0 works
464 nop ## so low limit=0, else decrement tap value
466 li t8, 0x80500000 ## assigning lower limit = 0
468 add t9, t9, t0 ##adding lower limit to upper limit (used to calc mid value)
476 tap_decr: # decrement t0 by 1 and move to loading this new tap
486 xori v1, t0, 0x20 # limiting upper limit to 0x20
496 bnez t1, up_limit # t1=0 means lower limit detected @ fail else upper limit
502 li t8, 0x80500000 # storing lower limit
505 add t9, t9, t0 # storing lower limit# adding lower limit and upper limit
516 li t1, 0x0 ## changing to decreasing tap mode
517 li t8, 0x80500000 ## storing upper limit
524 ori t0, a3, 0x0 # loading default tap value
530 tap_calc: ## calculating mid value of the tap, storing DQS0, DQS1 in 0x80500008, 0x8050000c resp.
547 li t8, 0xb8000000 #### Loading Tap Setting
562 .end hornet_ddr_tap_init