1 /*******************************************************************************
2 Copyright (C) Marvell International Ltd. and its affiliates
4 This software file (the "File") is owned and distributed by Marvell
5 International Ltd. and/or its affiliates ("Marvell") under the following
6 alternative licensing terms. Once you have made an election to distribute the
7 File under one of the following license alternatives, please (i) delete this
8 introductory statement regarding license alternatives, (ii) delete the two
9 license alternatives that you have not elected to use and (iii) preserve the
10 Marvell copyright notice above.
12 ********************************************************************************
13 Marvell Commercial License Option
15 If you received this File from Marvell and you have entered into a commercial
16 license agreement (a "Commercial License") with Marvell, the File is licensed
17 to you under the terms of the applicable Commercial License.
19 ********************************************************************************
20 Marvell GPL License Option
22 If you received this File from Marvell, you may opt to use, redistribute and/or
23 modify this File in accordance with the terms and conditions of the General
24 Public License Version 2, June 1991 (the "GPL License"), a copy of which is
25 available along with the File in the license.txt file or by writing to the Free
26 Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 or
27 on the worldwide web at http://www.gnu.org/licenses/gpl.txt.
29 THE FILE IS DISTRIBUTED AS-IS, WITHOUT WARRANTY OF ANY KIND, AND THE IMPLIED
30 WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE ARE EXPRESSLY
31 DISCLAIMED. The GPL License provides additional details about this warranty
33 ********************************************************************************
34 Marvell BSD License Option
36 If you received this File from Marvell, you may opt to use, redistribute and/or
37 modify this File under the following licensing terms.
38 Redistribution and use in source and binary forms, with or without modification,
39 are permitted provided that the following conditions are met:
41 * Redistributions of source code must retain the above copyright notice,
42 this list of conditions and the following disclaimer.
44 * Redistributions in binary form must reproduce the above copyright
45 notice, this list of conditions and the following disclaimer in the
46 documentation and/or other materials provided with the distribution.
48 * Neither the name of Marvell nor the names of its contributors may be
49 used to endorse or promote products derived from this software without
50 specific prior written permission.
52 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
53 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
54 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
55 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
56 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
57 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
58 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
59 ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
60 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
61 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
63 *******************************************************************************/
65 /*******************************************************************************
69 * Memory full detection and best timing configuration is done in
70 * C code. C runtime environment requires a stack. This module API
71 * initialize DRAM interface chip select 0 for basic functionality for
73 * The module API assumes DRAM information is stored in I2C EEPROM reside
74 * in a given I2C address MV_BOARD_DIMM0_I2C_ADDR. The I2C EEPROM
75 * internal data structure is assumed to be orgenzied in common DRAM
76 * vendor SPD structure.
77 * NOTE: DFCDL values are assumed to be already initialized prior to
78 * this module API activity.
84 *******************************************************************************/
87 #define MV_ASMLANGUAGE
89 #include "mvSysHwConfig.h"
90 #include "mvDramIfRegs.h"
91 #include "mvDramIfConfig.h"
92 #include "mvCpuIfRegs.h"
93 #include "pex/mvPexRegs.h"
94 #include "pci/mvPciRegs.h"
95 #include "mvCtrlEnvSpec.h"
96 #include "mvCtrlEnvAsm.h"
97 #include "cpu/mvCpuArm.h"
104 .globl _mvDramIfConfig
108 /*******************************************************************************
109 * _mvDramIfConfig - Basic DRAM interface initialization.
112 * The function will initialize the following DRAM parameters using the
113 * values prepared by mvDramIfDetect routine. Values are located
114 * in predefined registers.
125 *******************************************************************************/
129 /* Save register on stack */
133 stmdb sp!, {r1, r2, r3, r4, r7, r11}
136 /* 1) Write to SDRAM coniguration register */
137 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG1)
139 ldr r1, =(INTER_REGS_BASE + SDRAM_CONFIG_REG)
142 /* 2) Write Dunit control low register */
143 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG3)
145 ldr r1, =(INTER_REGS_BASE + SDRAM_DUNIT_CTRL_REG)
148 /* 3) Write SDRAM address control register */
149 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG4)
151 ldr r1, =(INTER_REGS_BASE + SDRAM_ADDR_CTRL_REG)
154 /* 4) Write SDRAM bank 0 size register */
155 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG0)
157 ldr r1, =(INTER_REGS_BASE + SDRAM_SIZE_REG(0))
160 /* 5) Write SDRAM open pages control register */
161 ldr r1, =(INTER_REGS_BASE + SDRAM_OPEN_PAGE_CTRL_REG)
162 ldr r4, =SDRAM_OPEN_PAGES_CTRL_REG_DV
165 /* 6) Write SDRAM timing Low register */
166 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG5)
168 ldr r1, =(INTER_REGS_BASE + SDRAM_TIMING_CTRL_LOW_REG)
171 /* 7) Write SDRAM timing High register */
172 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG6)
174 ldr r1, =(INTER_REGS_BASE + SDRAM_TIMING_CTRL_HIGH_REG)
177 /* 8) Write SDRAM mode register */
178 /* The CPU must not attempt to change the SDRAM Mode register setting */
179 /* prior to DRAM controller completion of the DRAM initialization */
180 /* sequence. To guarantee this restriction, it is recommended that */
181 /* the CPU sets the SDRAM Operation register to NOP command, performs */
182 /* read polling until the register is back in Normal operation value, */
183 /* and then sets SDRAM Mode register to it
\92s new value. */
185 /* 8.1 write 'nop' to SDRAM operation */
186 mov r4, #0x5 /* 'NOP' command */
187 MV_REG_WRITE_ASM(r4, r1, SDRAM_OPERATION_REG)
189 /* 8.2 poll SDRAM operation. Make sure its back to normal operation */
192 cmp r4, #0 /* '0' = Normal SDRAM Mode */
195 /* 8.3 Now its safe to write new value to SDRAM Mode register */
196 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG2)
198 ldr r1, =(INTER_REGS_BASE + SDRAM_MODE_REG)
201 /* 8.4 Make the Dunit write the DRAM its new mode */
202 mov r4, #0x3 /* Mode Register Set command */
203 MV_REG_WRITE_ASM (r4, r1, SDRAM_OPERATION_REG)
205 /* 8.5 poll SDRAM operation. Make sure its back to normal operation */
208 cmp r4, #0 /* '0' = Normal SDRAM Mode */
212 /* Config DDR2 registers (Extended mode, ODTs and pad calibration) */
213 MV_REG_READ_ASM (r4, r1, SDRAM_CONFIG_REG)
214 tst r4, #SDRAM_DTYPE_DDR2
218 /* 9) Write SDRAM Extended mode register This operation should be */
219 /* done for each memory bank */
220 /* write 'nop' to SDRAM operation */
221 mov r4, #0x5 /* 'NOP' command */
222 MV_REG_WRITE_ASM (r4, r1, SDRAM_OPERATION_REG)
224 /* poll SDRAM operation. Make sure its back to normal operation */
227 cmp r4, #0 /* '0' = Normal SDRAM Mode */
230 /* Now its safe to write new value to SDRAM Extended Mode register */
231 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG10)
233 ldr r1, =(INTER_REGS_BASE + SDRAM_EXTENDED_MODE_REG)
236 /* Go over each of the Banks */
237 ldr r3, =0 /* r3 = DRAM bank Num */
240 /* Set the SDRAM Operation Control to each of the DRAM banks */
241 mov r2, r3 /* Do not swap the bank counter value */
242 MV_REG_WRITE_ASM (r2, r1, SDRAM_OPERATION_CTRL_REG)
244 /* Make the Dunit write the DRAM its new mode */
245 mov r4, #0x4 /* Extended Mode Register Set command */
246 MV_REG_WRITE_ASM (r4, r1, SDRAM_OPERATION_REG)
248 /* poll SDRAM operation. Make sure its back to normal operation */
251 cmp r4, #0 /* '0' = Normal SDRAM Mode */
255 cmp r3, #4 /* 4 = Number of banks */
259 /* Config DDR2 On Die Termination (ODT) registers */
260 /* Write SDRAM DDR2 ODT control low register */
261 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG7)
263 ldr r1, =(INTER_REGS_BASE + DDR2_SDRAM_ODT_CTRL_LOW_REG)
266 /* Write SDRAM DDR2 ODT control high register */
267 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG8)
269 ldr r1, =(INTER_REGS_BASE + DDR2_SDRAM_ODT_CTRL_HIGH_REG)
272 /* Write SDRAM DDR2 Dunit ODT control register */
273 ldr r1, =(INTER_REGS_BASE + DRAM_BUF_REG9)
275 ldr r1, =(INTER_REGS_BASE + DDR2_DUNIT_ODT_CONTROL_REG)
281 /* Implement Guideline (GL# MEM-2) P_CAL Automatic Calibration */
282 /* Does Not Work for Address/Control and Data Pads. */
283 /* Relevant for: 88F5181-A1/B0 and 88F5281-A0 */
286 MV_CTRL_MODEL_GET_ASM(r3, r1);
287 /* Read device revision */
288 MV_CTRL_REV_GET_ASM(r2, r1);
290 /* Continue if OrionN */
291 ldr r1, =MV_5180_DEV_ID
296 /* Continue if Orion1 and device revision B1 */
297 ldr r1, =MV_5181_DEV_ID
301 cmp r2, #MV_5181_B1_REV
307 ldr r1, =MV_5182_DEV_ID
312 ldr r1, =MV_5082_DEV_ID
317 ldr r1, =MV_8660_DEV_ID
325 /* DDR SDRAM Address/Control Pads Calibration */
326 MV_REG_READ_ASM (r3, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
328 /* Set Bit [31] to make the register writable */
329 orr r2, r3, #SDRAM_WR_EN
331 MV_REG_WRITE_ASM (r2, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
333 bic r3, r3, #SDRAM_WR_EN /* Make register read-only */
334 bic r3, r3, #SDRAM_TUNE_EN /* Disable auto calibration */
335 bic r3, r3, #SDRAM_DRVN_MASK /* Clear r1[5:0]<DrvN> */
336 bic r3, r3, #SDRAM_DRVP_MASK /* Clear r1[11:6]<DrvP> */
338 /* Get the final N locked value of driving strength [22:17] */
341 mov r1, r1, LSR #26 /* r1[5:0]<DrvN> = r3[22:17]<LockN> */
342 orr r1, r1, r1, LSL #6 /* r1[11:6]<DrvP> = r1[5:0]<DrvN> */
344 /* Write to both <DrvN> bits [5:0] and <DrvP> bits [11:6] */
347 MV_REG_WRITE_ASM (r3, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
350 /* DDR SDRAM Data Pads Calibration */
351 MV_REG_READ_ASM (r3, r1, SDRAM_DATA_PADS_CAL_REG)
353 /* Set Bit [31] to make the register writable */
354 orr r2, r3, #SDRAM_WR_EN
356 MV_REG_WRITE_ASM (r2, r1, SDRAM_DATA_PADS_CAL_REG)
358 bic r3, r3, #SDRAM_WR_EN /* Make register read-only */
359 bic r3, r3, #SDRAM_TUNE_EN /* Disable auto calibration */
360 bic r3, r3, #SDRAM_DRVN_MASK /* Clear r1[5:0]<DrvN> */
361 bic r3, r3, #SDRAM_DRVP_MASK /* Clear r1[11:6]<DrvP> */
363 /* Get the final N locked value of driving strength [22:17] */
367 orr r1, r1, r1, LSL #6 /* r1[5:0] = r3[22:17]<LockN> */
369 /* Write to both <DrvN> bits [5:0] and <DrvP> bits [11:6] */
372 MV_REG_WRITE_ASM (r3, r1, SDRAM_DATA_PADS_CAL_REG)
377 /* Implement Guideline (GL# MEM-3) Drive Strength Value */
378 /* Relevant for: 88F5181-A1/B0/B1, 88F5281-A0/B0/C/D, 88F5182, */
379 /* 88F5082, 88F5181L, 88F6082/L, 88F6183, 88F6183L */
381 /* Get SDRAM Config value */
382 MV_REG_READ_ASM (r2, r1, SDRAM_CONFIG_REG)
385 tst r2, #SDRAM_DTYPE_DDR2
389 ldr r4, =DDR2_ADDR_CTRL_PAD_STRENGTH_TYPICAL_DV
390 ldr r2, =DDR2_DATA_PAD_STRENGTH_TYPICAL_DV
393 ldr r4, =DDR1_ADDR_CTRL_PAD_STRENGTH_TYPICAL_DV
394 ldr r2, =DDR1_DATA_PAD_STRENGTH_TYPICAL_DV
397 /* DDR SDRAM Address/Control Pads Calibration */
398 MV_REG_READ_ASM (r3, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
400 orr r3, r3, #SDRAM_WR_EN /* Make register writeable */
402 MV_REG_WRITE_ASM (r3, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
405 bic r3, r3, #SDRAM_WR_EN /* Make register read-only */
406 bic r3, r3, #SDRAM_PRE_DRIVER_STRENGTH_MASK
407 orr r3, r4, r3 /* Set default value for DDR */
409 MV_REG_WRITE_ASM (r3, r1, SDRAM_ADDR_CTRL_PADS_CAL_REG)
412 /* DDR SDRAM Data Pads Calibration */
413 MV_REG_READ_ASM (r3, r1, SDRAM_DATA_PADS_CAL_REG)
415 orr r3, r3, #SDRAM_WR_EN /* Make register writeable */
417 MV_REG_WRITE_ASM (r3, r1, SDRAM_DATA_PADS_CAL_REG)
420 bic r3, r3, #SDRAM_WR_EN /* Make register read-only */
421 bic r3, r3, #SDRAM_PRE_DRIVER_STRENGTH_MASK
422 orr r3, r2, r3 /* Set default value for DDR */
424 MV_REG_WRITE_ASM (r3, r1, SDRAM_DATA_PADS_CAL_REG)
426 #if !defined(MV_88W8660) && !defined(MV_88F6183) && !defined(MV_88F6183L)
427 /* Implement Guideline (GL# MEM-4) DQS Reference Delay Tuning */
428 /* Relevant for: 88F5181-A1/B0/B1 and 88F5281-A0/B0/C/D, 88F5182 */
429 /* 88F5082, 88F5181L, 88F6082/L */
431 /* Calc the absolute address of the _cpuARMDDRCLK[] in the boot flash */
432 ldr r7, = _cpuARMDDRCLK
435 add r7, r7, #CFG_MONITOR_BASE
437 /* Get the "sample on reset" register for the DDR frequancy */
438 MV_REG_READ_ASM (r4, r1, MPP_SAMPLE_AT_RESET)
439 ldr r1, =MSAR_ARMDDRCLCK_MASK
441 #if 0 /* YOTAM TO BE FIX */
442 mov r1, r1, LSR #MSAR_ARMDDRCLCK_OFFS
446 MV_CTRL_MODEL_GET_ASM(r3, r2);
448 /* Continue if TC90 */
449 ldr r2, =MV_1281_DEV_ID
453 /* Continue if Orion2 */
454 ldr r2, =MV_5281_DEV_ID
456 #if 0 /* YOTAM TO BE FIX */
461 #if 0 /* YOTAM TO BE FIX */
462 tst r4, #MSAR_ARMDDRCLCK_H_MASK
466 ldr r4, =MV_CPU_ARM_CLK_ELM_SIZE
469 add r7, r7, #MV_CPU_ARM_CLK_DDR_OFF
473 /* Get SDRAM Config value */
474 MV_REG_READ_ASM (r2, r4, SDRAM_CONFIG_REG)
477 tst r2, #SDRAM_DTYPE_DDR2
481 ldr r2, =MV_5281_DEV_ID
484 MV_CTRL_REV_GET_ASM(r3, r2)
485 cmp r3, #MV_5281_D0_REV
486 beq orin2_d0_ddr2_ftdll_val
487 cmp r3, #MV_5281_D1_REV
488 beq orin2_d1_ddr2_ftdll_val
489 cmp r3, #MV_5281_D2_REV
490 beq orin2_d1_ddr2_ftdll_val
493 /* Set Orion 2 D1 ftdll values for DDR2 */
494 orin2_d1_ddr2_ftdll_val:
495 ldr r4, =FTDLL_DDR2_250MHZ_5281_D1
499 ldr r4, =FTDLL_DDR2_200MHZ_5281_D1
503 ldr r4, =FTDLL_DDR2_166MHZ_5281_D0
509 /* Set Orion 2 D0 ftdll values for DDR2 */
510 orin2_d0_ddr2_ftdll_val:
511 ldr r4, =FTDLL_DDR2_250MHZ_5281_D0
515 ldr r4, =FTDLL_DDR2_200MHZ_5281_D0
519 ldr r4, =FTDLL_DDR2_166MHZ_5281_D0
525 ldr r2, =MV_5182_DEV_ID
529 /* Set Orion nas ftdll values for DDR2 */
531 ldr r4, =FTDLL_DDR2_166MHZ_5182
536 /* default values for all other devices */
539 ldr r4, =FTDLL_DDR2_250MHZ
543 ldr r4, =FTDLL_DDR2_200MHZ
547 ldr r4, =FTDLL_DDR2_166MHZ
551 ldr r4, =FTDLL_DDR2_133MHZ
559 ldr r2, =MV_5281_DEV_ID
562 MV_CTRL_REV_GET_ASM(r3, r2)
563 cmp r3, #MV_5281_D0_REV
564 bge orin2_ddr1_ftdll_val
567 /* Set Orion 2 D0 and above ftdll values for DDR1 */
568 orin2_ddr1_ftdll_val:
569 ldr r4, =FTDLL_DDR1_200MHZ_5281_D0
573 ldr r4, =FTDLL_DDR1_166MHZ_5281_D0
579 ldr r2, =MV_5181_DEV_ID
582 MV_CTRL_REV_GET_ASM(r3, r2)
583 cmp r3, #MV_5181_B1_REV
584 bge orin1_ddr1_ftdll_val
587 /* Set Orion 1 ftdll values for DDR1 */
588 orin1_ddr1_ftdll_val:
589 ldr r4, =FTDLL_DDR1_166MHZ_5181_B1
595 ldr r4, =FTDLL_DDR1_133MHZ
600 ldr r4, =FTDLL_DDR1_166MHZ
605 ldr r4, =FTDLL_DDR1_200MHZ
614 MV_REG_WRITE_ASM (r4, r1, SDRAM_FTDLL_CONFIG_REG)
617 MV_REG_WRITE_ASM (r4, r1, SDRAM_FTDLL_CONFIG_REG)
619 #endif /* !defined(MV_88W8660) && !defined(MV_88F6183) && !defined(MV_88F6183L) */
623 /* Restore the registers we used to save the DDR detect values */
625 ldr r4, =DRAM_BUF_REG0_DV
626 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG0)
628 ldr r4, =DRAM_BUF_REG1_DV
629 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG1)
631 ldr r4, =DRAM_BUF_REG2_DV
632 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG2)
634 ldr r4, =DRAM_BUF_REG3_DV
635 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG3)
637 ldr r4, =DRAM_BUF_REG4_DV
638 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG4)
640 ldr r4, =DRAM_BUF_REG5_DV
641 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG5)
643 ldr r4, =DRAM_BUF_REG6_DV
644 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG6)
646 ldr r4, =DRAM_BUF_REG7_DV
647 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG7)
649 ldr r4, =DRAM_BUF_REG8_DV
650 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG8)
652 ldr r4, =DRAM_BUF_REG9_DV
653 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG9)
655 ldr r4, =DRAM_BUF_REG10_DV
656 MV_REG_WRITE_ASM (r4, r1, DRAM_BUF_REG10)
659 /* Restore registers */
660 /* Save register on stack */
664 ldmia sp!, {r1, r2, r3, r4, r7, r11}