接上一篇,这一篇写得是内存初始化。本人对ddr初始化,不是特别懂。只是勉强翻译注释。如有错误,希望高手能不吝赐教。废话不多说,贴上这该死的代码。
/*
* armboot - Memory Initialize Code for S5PV210/ARM-Cortex CPU-core
*
* Copyright (c) 2009 Samsung Electronics
*
*
* See file CREDITS for list of people who contributed to this
* project.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of
* the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston,
* MA 02111-1307 USA
*
* Base codes by scsuh (sc.suh)
* Modified By JhoonKim ([email protected]), aESOP Embedded Forum(http://www.aesop.or.kr)
* 10.08.15 - To Supported for SEC K4T1G164QX DDR2 Memory for aESOP S5PV210
*/
#include
#include
.globl mem_ctrl_asm_init //全局变量
mem_ctrl_asm_init:
#ifndef CONFIG_EVT1 //由于定义过,所以再次不用分析
ldr r0, =ASYNC_MSYS_DMC0_BASE //0xF1E00000
ldr r1, =0x0
str r1, [r0, #0x0]
/* This register is removed at EVT1 of C110. */
ldr r1, =0x0
str r1, [r0, #0xC]
#endif
#ifdef CONFIG_MCP_SINGLE
/* DMC0 Drive Strength (Setting 2X) 设置内存访问信号的强度*/
/*DRAM Driver Strength 数值越大,则内存访问信号的强度也越大。内存对工作频率是比较敏感的,当工作频率高于
内存的标称频率时, 将该选项的数值调高, 可以提高电脑在超频状态下的稳定性*/
ldr r0, =ELFIN_GPIO_BASE //0xE0200000
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_0DRV_SR_OFFSET] //0xE020_03CC
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_1DRV_SR_OFFSET] //0xE020_03EC
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_2DRV_SR_OFFSET] //0xE020_040C
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_3DRV_SR_OFFSET] //0xE020_042C
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_4DRV_SR_OFFSET] //0xE020_044C
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_5DRV_SR_OFFSET] //0xE020_046C
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_6DRV_SR_OFFSET] //0xE020_048C
ldr r1, =0x0000AAAA
str r1, [r0, #MP1_7DRV_SR_OFFSET] //0xE020_04AC
ldr r1, =0x00002AAA
str r1, [r0, #MP1_8DRV_SR_OFFSET] //0xE020_04CC
/* DMC1 Drive Strength (Setting 2X) */
ldr r0, =ELFIN_GPIO_BASE //0xE0200000 形同上面,就不细细的写了
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_0DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_1DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_2DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_3DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_4DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_5DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_6DRV_SR_OFFSET]
ldr r1, =0x0000AAAA
str r1, [r0, #MP2_7DRV_SR_OFFSET]
ldr r1, =0x00002AAA
str r1, [r0, #MP2_8DRV_SR_OFFSET]
/* DMC0 initialization at single Type 初始化PHY DLL */
/* 凡是使用 DDR 类型的 DRAM,都需要使用 DLL(Delay Locked Loop 延时锁定回路提供一个数据滤波信号)技术,当数据有效时,
存储控制器可使用这个数据滤波信号来精确定位数据。*/
ldr r0, =APB_DMC_0_BASE //0xF000_0000
ldr r1, =0x00101000 @PhyControl0 DLL parameter setting, manual 0x00101000
/*
bit[15:8] DLL Lock Start Point Initial DLL lock start point. This is the number of delay cells and is the start point where "DLL"
start tracing to lock. CalculatesInitial delay time by multiplying the unit delay of delay cell and this value. This value should
be 0x10
bit [23:16] DLL Delay Increment Increase the amount of start point 这个值应该设置为0x10
*/
str r1, [r0, #DMC_PHYCONTROL0] //PHY Control0 Register(0xF000_0018)
ldr r1, =0x00000086 @PhyControl1 DLL parameter setting, LPDDR/LPDDR2 Case
str r1, [r0, #DMC_PHYCONTROL1] //0xF000_001C PHY Control1 Register
ldr r1, =0x00101002 @PhyControl0 DLL on
str r1, [r0, #DMC_PHYCONTROL0] //0xF000_0018
ldr r1, =0x00101003 @PhyControl0 DLL start
str r1, [r0, #DMC_PHYCONTROL0] //0xF000_0018
find_lock_val:
ldr r1, [r0, #DMC_PHYSTATUS] @Load Phystatus register value 0xF000_0040
and r2, r1, #0x7
cmp r2, #0x7 @Loop until DLL is locked
bne find_lock_val
and r1, #0x3fc0
mov r2, r1, LSL #18
orr r2, r2, #0x100000
orr r2 ,r2, #0x1000
orr r1, r2, #0x3 @Force Value locking
str r1, [r0, #DMC_PHYCONTROL0] //0xF000_0018
#if 0 /* Memory margin test 10.01.05 */
orr r1, r2, #0x1 @DLL off
str r1, [r0, #DMC_PHYCONTROL0]
#endif
/* setting DDR2 */
ldr r1, =0x0FFF2010 @ConControl auto refresh off
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =DMC0_MEMCONTROL @MemControl BL=4, 1 chip, DDR2 type, dynamic self refresh, force precharge, dynamic power down off
str r1, [r0, #DMC_MEMCONTROL]
ldr r1, =DMC0_MEMCONFIG_0 @MemConfig0 256MB config, 8 banks,Mapping Method[12:15]0:linear, 1:linterleaved, 2:Mixed
str r1, [r0, #DMC_MEMCONFIG0]
ldr r1, =DMC0_MEMCONFIG_1 @MemConfig1
str r1, [r0, #DMC_MEMCONFIG1]
ldr r1, =0xFF000000 @PrechConfig
str r1, [r0, #DMC_PRECHCONFIG]
ldr r1, =DMC0_TIMINGA_REF @TimingAref 7.8us*133MHz=1038(0x40E), 100MHz=780(0x30C), 20MHz=156(0x9C), 10MHz=78(0x4E)
str r1, [r0, #DMC_TIMINGAREF]
ldr r1, =DMC0_TIMING_ROW @TimingRow for @200MHz
str r1, [r0, #DMC_TIMINGROW]
ldr r1, =DMC0_TIMING_DATA @TimingData CL=4
str r1, [r0, #DMC_TIMINGDATA]
ldr r1, =DMC0_TIMING_PWR @TimingPower
str r1, [r0, #DMC_TIMINGPOWER]
ldr r1, =0x07000000 @DirectCmd chip0 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @DirectCmd chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00020000 @DirectCmd chip0 EMRS2
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00030000 @DirectCmd chip0 EMRS3
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010400 @DirectCmd chip0 EMRS1 (MEM DLL on, DQS# disable)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000542 @DirectCmd chip0 MRS (MEM DLL reset) CL=4, BL=4
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @DirectCmd chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @DirectCmd chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @DirectCmd chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000442 @DirectCmd chip0 MRS (MEM DLL unreset)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010780 @DirectCmd chip0 EMRS1 (OCD default)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010400 @DirectCmd chip0 EMRS1 (OCD exit)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x07100000 @DirectCmd chip1 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @DirectCmd chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00120000 @DirectCmd chip1 EMRS2
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00130000 @DirectCmd chip1 EMRS3
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110400 @DirectCmd chip1 EMRS1 (MEM DLL on, DQS# disable)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100542 @DirectCmd chip1 MRS (MEM DLL reset) CL=4, BL=4
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @DirectCmd chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @DirectCmd chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @DirectCmd chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100442 @DirectCmd chip1 MRS (MEM DLL unreset)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110780 @DirectCmd chip1 EMRS1 (OCD default)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110400 @DirectCmd chip1 EMRS1 (OCD exit)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x0FF02030 @ConControl auto refresh on
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0xFFFF00FF @PwrdnConfig
str r1, [r0, #DMC_PWRDNCONFIG]
ldr r1, =0x00202400 @MemControl BL=4, 1 chip, DDR2 type, dynamic self refresh, force precharge, dynamic power down off
str r1, [r0, #DMC_MEMCONTROL]
/* DMC1 initialization */
ldr r0, =APB_DMC_1_BASE
ldr r1, =0x00101000 @Phycontrol0 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00000086 @Phycontrol1 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL1]
ldr r1, =0x00101002 @PhyControl0 DLL on
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00101003 @PhyControl0 DLL start
str r1, [r0, #DMC_PHYCONTROL0]
find_lock_val1:
ldr r1, [r0, #DMC_PHYSTATUS] @Load Phystatus register value
and r2, r1, #0x7
cmp r2, #0x7 @Loop until DLL is locked
bne find_lock_val1
and r1, #0x3fc0
mov r2, r1, LSL #18
orr r2, r2, #0x100000
orr r2, r2, #0x1000
orr r1, r2, #0x3 @Force Value locking
str r1, [r0, #DMC_PHYCONTROL0]
#if 0 /* Memory margin test 10.01.05 */
orr r1, r2, #0x1 @DLL off
str r1, [r0, #DMC_PHYCONTROL0]
#endif
/* settinf fot DDR2 */
ldr r0, =APB_DMC_1_BASE
ldr r1, =0x0FFF2010 @auto refresh off
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =DMC1_MEMCONTROL @MemControl BL=4, 2 chip, DDR2 type, dynamic self refresh, force precharge, dynamic power down off
str r1, [r0, #DMC_MEMCONTROL]
ldr r1, =DMC1_MEMCONFIG_0 @MemConfig0 512MB config, 8 banks,Mapping Method[12:15]0:linear, 1:linterleaved, 2:Mixed
str r1, [r0, #DMC_MEMCONFIG0]
ldr r1, =DMC1_MEMCONFIG_1 @MemConfig1
str r1, [r0, #DMC_MEMCONFIG1]
ldr r1, =0xFF000000
str r1, [r0, #DMC_PRECHCONFIG]
ldr r1, =DMC1_TIMINGA_REF @TimingAref 7.8us*133MHz=1038(0x40E), 100MHz=780(0x30C), 20MHz=156(0x9C), 10MHz=78(0x4
str r1, [r0, #DMC_TIMINGAREF]
ldr r1, =DMC1_TIMING_ROW @TimingRow for @200MHz
str r1, [r0, #DMC_TIMINGROW]
ldr r1, =DMC1_TIMING_DATA @TimingData CL=3
str r1, [r0, #DMC_TIMINGDATA]
ldr r1, =DMC1_TIMING_PWR @TimingPower
str r1, [r0, #DMC_TIMINGPOWER]
ldr r1, =0x07000000 @DirectCmd chip0 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @DirectCmd chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00020000 @DirectCmd chip0 EMRS2
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00030000 @DirectCmd chip0 EMRS3
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010400 @DirectCmd chip0 EMRS1 (MEM DLL on, DQS# disable)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000542 @DirectCmd chip0 MRS (MEM DLL reset) CL=4, BL=4
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @DirectCmd chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @DirectCmd chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @DirectCmd chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000442 @DirectCmd chip0 MRS (MEM DLL unreset)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010780 @DirectCmd chip0 EMRS1 (OCD default)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00010400 @DirectCmd chip0 EMRS1 (OCD exit)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x07100000 @DirectCmd chip1 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @DirectCmd chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00120000 @DirectCmd chip1 EMRS2
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00130000 @DirectCmd chip1 EMRS3
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110440 @DirectCmd chip1 EMRS1 (MEM DLL on, DQS# disable)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100542 @DirectCmd chip1 MRS (MEM DLL reset) CL=4, BL=4
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @DirectCmd chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @DirectCmd chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @DirectCmd chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100442 @DirectCmd chip1 MRS (MEM DLL unreset)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110780 @DirectCmd chip1 EMRS1 (OCD default)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00110400 @DirectCmd chip1 EMRS1 (OCD exit)
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x0FF02030 @ConControl auto refresh on
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0xFFFF00FF @PwrdnConfig
str r1, [r0, #DMC_PWRDNCONFIG]
ldr r1, =DMC1_MEMCONTROL @MemControl BL=4, 2 chip, DDR2 type, dynamic self refresh, force precharge, dynamic power down off
str r1, [r0, #DMC_MEMCONTROL]
#else /* CONFIG_MCP_SINGLE */
/* DMC0 initialization */
ldr r0, =APB_DMC_0_BASE
ldr r1, =0x00101000 @Phycontrol0 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00000084 @Phycontrol1 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL1]
ldr r1, =0x00101002 @Phycontrol2 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00101003 @Dll on
str r1, [r0, #DMC_PHYCONTROL0]
find_lock_val:
ldr r1, [r0, #DMC_PHYSTATUS] @Load Phystatus register value
and r2, r1, #0x7
cmp r2, #0x7 @Loop until DLL is locked
bne find_lock_val
and r1, #0x3fc0
mov r2, r1, LSL #18
orr r2, r2, #0x100000
orr r2, r2, #0x1000
orr r1, r2, #0x3 @Force Value locking
str r1, [r0, #DMC_PHYCONTROL0]
#if 1 /* DRAM margin test 10.01.06 */
orr r1, r2, #0x1 @DLL off
str r1, [r0, #DMC_PHYCONTROL0]
#endif
ldr r1, =0x0fff1010 @auto refresh off
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0x00212100
str r1, [r0, #DMC_MEMCONTROL]
ldr r1, =DMC0_MEMCONFIG_0
str r1, [r0, #DMC_MEMCONFIG0]
ldr r1, =DMC0_MEMCONFIG_1
str r1, [r0, #DMC_MEMCONFIG1]
ldr r1, =0xff000000
str r1, [r0, #DMC_PRECHCONFIG]
ldr r1, =DMC0_TIMINGA_REF
str r1, [r0, #DMC_TIMINGAREF]
ldr r1, =DMC0_TIMING_ROW @TimingRow @133MHz
str r1, [r0, #DMC_TIMINGROW]
ldr r1, =DMC0_TIMING_DATA
str r1, [r0, #DMC_TIMINGDATA]
ldr r1, =DMC0_TIMING_PWR @Timing Power
str r1, [r0, #DMC_TIMINGPOWER]
ldr r1, =0x07000000 @chip0 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000032 @chip0 MRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x07100000 @chip1 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100032 @chip1 MRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x0FFF20B0 @ConControl auto refresh on
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0xFFFF00FF @PwrdnConfig
str r1, [r0, #DMC_PWRDNCONFIG]
ldr r1, =0x00212113 @MemControl
str r1, [r0, #DMC_MEMCONTROL]
/* DMC1 initialization */
ldr r0, =APB_DMC_1_BASE
ldr r1, =0x00101000 @Phycontrol0 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00000084 @Phycontrol1 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL1]
ldr r1, =0x00101002 @Phycontrol2 DLL parameter setting
str r1, [r0, #DMC_PHYCONTROL0]
ldr r1, =0x00101003 @Dll on
str r1, [r0, #DMC_PHYCONTROL0]
find_lock_val1:
ldr r1, [r0, #DMC_PHYSTATUS] @Load Phystatus register value
and r2, r1, #0x7
cmp r2, #0x7 @Loop until DLL is locked
bne find_lock_val1
and r1, #0x3fc0
mov r2, r1, LSL #18
orr r2, r2, #0x100000
orr r2, r2, #0x1000
orr r1, r2, #0x3 @Force Value locking
str r1, [r0, #DMC_PHYCONTROL0]
#if 1 /* Memory margin test 10.01.05 */
orr r1, r2, #0x1 @DLL off
str r1, [r0, #DMC_PHYCONTROL0]
#endif
ldr r0, =APB_DMC_1_BASE
ldr r1, =0x0FFF1010 @auto refresh off
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0x00212100
str r1, [r0, #DMC_MEMCONTROL]
ldr r1, =DMC1_MEMCONFIG_0
str r1, [r0, #DMC_MEMCONFIG0]
ldr r1, =DMC1_MEMCONFIG_1
str r1, [r0, #DMC_MEMCONFIG1]
ldr r1, =0xff000000
str r1, [r0, #DMC_PRECHCONFIG]
ldr r1, =DMC1_TIMINGA_REF
str r1, [r0, #DMC_TIMINGAREF]
ldr r1, =DMC1_TIMING_ROW @TimingRow @133MHz
str r1, [r0, #DMC_TIMINGROW]
ldr r1, =DMC1_TIMING_DATA
str r1, [r0, #DMC_TIMINGDATA]
ldr r1, =DMC1_TIMING_PWR @Timing Power
str r1, [r0, #DMC_TIMINGPOWER]
ldr r1, =0x07000000 @chip0 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01000000 @chip0 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05000000 @chip0 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00000032 @chip0 MRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00020020 @chip0 EMRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x07100000 @chip1 Deselect
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x01100000 @chip1 PALL
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x05100000 @chip1 REFA
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00100032 @chip1 MRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x00120020 @chip0 EMRS
str r1, [r0, #DMC_DIRECTCMD]
ldr r1, =0x0FFF10B0 @ConControl auto refresh on
str r1, [r0, #DMC_CONCONTROL]
ldr r1, =0xFFFF00FF @PwrdnConfig
str r1, [r0, #DMC_PWRDNCONFIG]
ldr r1, =0x00212113 @MemControl
str r1, [r0, #DMC_MEMCONTROL]
#endif /* CONFIG_MCP_AC / CONFIG_MCP_H / CONFIG_MCP_B / CONFIG_MCP_D */
mov pc, lr
/* Below code is for ARM926EJS and ARM1026EJS */
.globl cleanDCache
cleanDCache:
mrc p15, 0, pc, c7, c10, 3 /* test/clean D-Cache */
bne cleanDCache
mov pc, lr
.globl cleanFlushDCache
cleanFlushDCache:
mrc p15, 0, pc, c7, c14, 3 /* test/cleanflush D-Cache */
bne cleanFlushDCache
mov pc, lr
.globl cleanFlushCache
cleanFlushCache:
mrc p15, 0, pc, c7, c14, 3 /* test/cleanflush D-Cache */
bne cleanFlushCache
mcr p15, 0, r0, c7, c5, 0 /* flush I-Cache */
mov pc, lr
.ltorg
/*
* v7_flush_dcache_all()
*
* Flush the whole D-cache.
*
* Corrupted registers: r0-r5, r7, r9-r11
*
* - mm - mm_struct describing address space
*/
.align 5
.global v7_flush_dcache_all
v7_flush_dcache_all:
ldr r0, =0xffffffff
mrc p15, 1, r0, c0, c0, 1 @ Read CLIDR
ands r3, r0, #0x7000000
mov r3, r3, LSR #23 @ Cache level value (naturally aligned)
beq Finished
mov r10, #0
Loop1:
add r2, r10, r10, LSR #1 @ Work out 3xcachelevel
mov r1, r0, LSR r2 @ bottom 3 bits are the Ctype for this level
and r1, r1, #7 @ get those 3 bits alone
cmp r1, #2
blt Skip @ no cache or only instruction cache at this level
mcr p15, 2, r10, c0, c0, 0 @ write the Cache Size selection register
mov r1, #0
mcr p15, 0, r1, c7, c5, 4 @ PrefetchFlush to sync the change to the CacheSizeID reg
mrc p15, 1, r1, c0, c0, 0 @ reads current Cache Size ID register
and r2, r1, #0x7 @ extract the line length field
add r2, r2, #4 @ add 4 for the line length offset (log2 16 bytes)
ldr r4, =0x3FF
ands r4, r4, r1, LSR #3 @ R4 is the max number on the way size (right aligned)
clz r5, r4 @ R5 is the bit position of the way size increment
ldr r7, =0x00007FFF
ands r7, r7, r1, LSR #13 @ R7 is the max number of the index size (right aligned)
Loop2:
mov r9, r4 @ R9 working copy of the max way size (right aligned)
Loop3:
orr r11, r10, r9, LSL r5 @ factor in the way number and cache number into R11
orr r11, r11, r7, LSL r2 @ factor in the index number
mcr p15, 0, r11, c7, c6, 2 @ invalidate by set/way
subs r9, r9, #1 @ decrement the way number
bge Loop3
subs r7, r7, #1 @ decrement the index
bge Loop2
Skip:
add r10, r10, #2 @ increment the cache number
cmp r3, r10
bgt Loop1
Finished:
mov pc, lr
.align 5
.global disable_l2cache
disable_l2cache:
mrc p15, 0, r0, c1, c0, 1
bic r0, r0, #(1<<1)
mcr p15, 0, r0, c1, c0, 1
mov pc, lr
.align 5
.global enable_l2cache
enable_l2cache:
mrc p15, 0, r0, c1, c0, 1
orr r0, r0, #(1<<1)
mcr p15, 0, r0, c1, c0, 1
mov pc, lr
.align 5
.global set_l2cache_auxctrl
set_l2cache_auxctrl:
mov r0, #0x0
mcr p15, 1, r0, c9, c0, 2
mov pc, lr
.align 5
.global set_l2cache_auxctrl_cycle
set_l2cache_auxctrl_cycle:
mrc p15, 1, r0, c9, c0, 2
bic r0, r0, #(0x1<<29)
bic r0, r0, #(0x1<<21)
bic r0, r0, #(0x7<<6)
bic r0, r0, #(0x7<<0)
mcr p15, 1, r0, c9, c0, 2
mov pc,lr
.align 5
CoInvalidateDCacheIndex:
;/* r0 = index */
mcr p15, 0, r0, c7, c6, 2
mov pc,lr
如果你觉得写得还行,转载时请保留作者信息。作者:捷宇 邮箱:[email protected] 博客:http://blog.csdn.net/jayyuz