⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 fw_arm.s

📁 ARM9基于WINDOWSCE的BSP源代码
💻 S
字号:
;
;   The content of this file or document is CONFIDENTIAL and PROPRIETARY
;   to Jade Technologies Co., Ltd.  It is subjected to the terms of a
;   License Agreement between Licensee and Jade Technologies Co., Ltd.
;   restricting among other things, the use, reproduction, distribution
;   and transfer.  Each of the embodiments, including this information 
;   and any derivative work shall retain this copyright notice.
; 
;   Copyright (c) 2004 - 2005 Jade Technologies Co., Ltd. 
;   All rights reserved.
; ----------------------------------------------------------------
; File:     fw_arm.s,v
; Revision: 1.0
; ----------------------------------------------------------------
; $
;
;
; Module Name:
;
;    fw_arm.s
;
; Abstract:
;
;    This module implements the code necessary to initialize the HW and
;    Kernel interface routines.
;


;
; This one source file is used to provide Startup code both for the
; Ethernet Boot Loader, and for the WinCE kernel. The default is to
; build for the WinCE kernel
;

    IF :LNOT: :DEF: EBOOT
        GBLL    EBOOT
EBOOT   SETL    {FALSE}
    ENDIF
    IF :LNOT: :DEF: EXEFLASH
        GBLL    EXEFLASH
EXEFLASH SETL    {FALSE}
    ENDIF

        OPT     2       ; disable listing in fw_arm.lst
        INCLUDE kxarm.h
        INCLUDE armmacros.inc
        INCLUDE sizes.inc
        INCLUDE bits.inc
        INCLUDE platform.inc
        INCLUDE cpumodes.inc
        INCLUDE target.inc
        INCLUDE sp810.inc
;zq add
	INCLUDE mpmcinit.inc

        OPT     1       ; enable listing in fw_arm.lst

        IMPORT  ARMInitSerial
        IMPORT  ARMPutHex
        IMPORT  ARMWriteString


    IF EBOOT
        IMPORT  EbootMain
    ELSE
        IMPORT  KernelStart
    ENDIF

    IF EBOOT :LOR: :LNOT:EXEFLASH
        IMPORT  EverythingRelocate
    ENDIF

    IF :DEF: EXAMPLE_MEMCONFIG
        IMPORT  ARMConfigMemory
    ENDIF

CP15ControlInit EQU     0xc0001078              ; Async. Bus mode
                                                ; I-Cache enabled
                                                ; Little-Endian
                                                ; MMU Disabled

        STARTUPTEXT
        LEAF_ENTRY StartUp

        ; There are two ways into StartUp: from the bootmonitor/reset or from
        ; wake up. In either case, the processor should be in a privileged mode
        ; (e.g. SVC) with the MMU disabled. If the MMU might be active, there
        ; needs to be code to ensure that the executable is still at the next
        ; address when the MMU is turned off.
        ;
      
        ; disable all interrupts, set SVC mode
        mov     r0, #(SVC32Mode :OR: NoINTS)
        msr     cpsr_c, r0
      
;**************************************   
;zq add
	IF EBOOT
	;remap
;	MOV r0, #PHYS_SC_BASE				; r0 -> System Controller
;   	MOV r1, #2
;     	STR r1, [r0, #BOOTMAPCLR]			;REMAPSTATIC=0
;	MOV r1, #1
;    	STR r1, [r0, #MAPMOVE]				;remaped to SDRAM	
     
	;sdram init
;	BL 	mpmcinit
	ENDIF	
;**************************************  
        ;
        ; Here is a good place to do any speed (CPU, memory etc) setup
        ; We do not do any here as the boot monitor is used to do this for now
        ;
				;zq we use 32k ref_clk
        ; Set all the timers to 1MHz
        ldr     r0, =PHYS_SC_BASE
        ldr     r1, [r0, #ARM_SCCtrl]
        orr     r1, r1, #(SCCtrlTimer0EnSel :OR: SCCtrlTimer1EnSel :OR: SCCtrlTimer2EnSel :OR: SCCtrlTimer3EnSel)
        str     r1, [r0, #ARM_SCCtrl]

ContinueSetup

        ; Only used temporarily, but setup a stack for use by 'C' routines;
        ; Use only the first 32KB of the area. Remember this is a full descending
        ; based stack.
        ldr     sp, =TEMP_STACK_BASE
        

    IF :DEF: EXAMPLE_MEMCONFIG
        BL  ARMConfigMemory
    ENDIF

        ; Now reset all CP15 features
        ldr                     r0, =CP15ControlInit
        WRMMU_STATE             r0

        mov                     r0, #0x0
        WRMMU_FlushTB           r0              ; flush TLBs
        WRCACHE_FlushIDC        r0              ; flush caches

        ; Example code to support remapping to flash after a reset
    IF :DEF: EXAMPLE_FLASHREMAP
        ; Make sure we're running from the physical memory address and
        ; not an address mapped to 0 (the normal reset state).
        GOTO_ROM        r0, r1
    ENDIF

        DISABLE_INTS    r0, r1                  ; Ints -> IRQ; LEDs

    IF EBOOT :LOR: :LNOT:EXEFLASH
        ;
        ; Relocate code from Flash to RAM if necessary. This step is required
        ; for EBOOT as it's code runs from physical, not virtual, addresses. It 
        ; is optional for Win CE, though running from RAM increases performance
        ;
        ; Returns with r0 = linked address for Startup, -1 if currently
        ; executing in the correct place
        ;

        ; NOTE: Since the eboot/nk image is built to execute from RAM but we're 
        ; currently executing out of flash, make sure this call is a relative 
        ; branch.  Once the code is relocated to RAM, absolute address references 
        ; are fine.
        ;
        ; The branch with link instruction will do a relative branch and since we
        ; don't care about Thumb/ARM mode switching, it works fine here.
        ;
        bl       EverythingRelocate

        ; branch to final execution address if necessary
        cmp     r0, #-1
        addne   r0, r0, #(RealStartup - StartUp)
        movne   pc, r0

    ENDIF

RealStartup

        ; init the debug serial port and say "hello".
        bl      ARMInitSerial
        adr     r0, HelloMsg
        bl      ARMWriteString

        adr     r0, StackMsg
        bl      ARMWriteString
        mov     r0, sp
        bl      ARMPutHex

        adr     r0, EndMsg
        bl      ARMWriteString

    IF EBOOT
        CALL    EbootMain
    ELSE
        ; (r0) = physical address of OEMMemoryMap
        adr     r0, OEMAddressTable

        bl      KernelStart
    ENDIF

        ; control should never return to this routine; if it does, output
        ; some debug & spin
        adr     r0, ByeMsg
        bl      ARMWriteString

spin    b       spin

    IF EBOOT
HelloMsg        DCB     13, 10, "Z228 Ethernet Boot Loader", 13, 10, 0
ByeMsg          DCB     13, 10, "ARMVPB_Eboot returned!", 13, 10, 0
    ELSE
HelloMsg        DCB     13, 10, "WindowsCE on Z228", 13, 10, 0
ByeMsg          DCB     13, 10, "KernelStart returned!", 13, 10, 0
    ENDIF

StackMsg        DCB     "  Stack Pointer: ", 0
EndMsg          DCB     13, 10, 0

        ENTRY_END   StartUp
        ALIGN   4

    IF :LNOT: EBOOT
        INCLUDE mapx20t.inc
    ENDIF
    
    
;****************************************************************
mpmcinit     PROC

		mov  r2, lr
		
; prepare to initialize MPMC
  	LDR     r6, =MPMC_Base

; Set AHB Timeouts  // use default values
; -----------------------------------------------------------------------------


; Set Clocking scheme	//0x111
; -----------------------------------------------------------------------------
        MOV     r0, #0xFF
        ADD     r0, r0, #0x12
        STR     r0, [r6, #MPMCDynamicReadConfig - MPMC_Base]

; Set SDRAM Initialisation Value (I) to NOP (MPMCDynamicControl [8:7] to 2'b11)
; -----------------------------------------------------------------------------

        ADD     r7, r6, #1
        ADD     r7, r7, #0xFF           ; MPMC_Base_Plus_256
        
        
	MOV	r0, #0x0
        ADD     r0, r0,#0xFF
        ADD     r0,r0,  #0x84           ; 0x183 

        STR     r0, [r6, #MPMCDynamicControl - MPMC_Base]

; Set SDRAM Initialisation Value (I) to PALL (MPMCDynamicControl [8:7] to 2'b10)
; -----------------------------------------------------------------------------

        SUB    r0, r0, #0x80           ; 0x103
        STR     r0, [r6, #MPMCDynamicControl - MPMC_Base]


; Write a small value (1) into the refresh register (MPMCDynamicRefresh)
; -----------------------------------------------------------------------------

; 0x1 (x16) = 16 cycles between refreshes

        MOV     r0, #1
        STR     r0, [r6, #MPMCDynamicRefresh - MPMC_Base]

; Perform refresh cycles
; -----------------------------------------------------------------------------

        MOV     r0, #0x30   ; Set required number of loop cycles to allow enough refreshes
w       SUB    	r0,  r0, #1
		CMP		r0, #1
        BNE     w

; Write operational value into refresh reg (MPMCDynamicRefresh)
; -----------------------------------------------------------------------------
;default : CPU CLOCK = 133MHz; HCLK = 66MHz 
; For 15.625us refresh rate, with 66MHz clock = (15.625 * 66)/16 = 60    freq = 100  , 15.625 *100/16 = 99

        MOV     r0, #0x3C
        STR     r0, [r6, #MPMCDynamicRefresh - MPMC_Base]

; Program RAS/CAS latency (MPMCDynamicRASCAS[0,1,2,3])
; -----------------------------------------------------------------------------

; MPMCDynamicRASCASn [10:7] -> CAS latency in half cycle increments
; MPMCDynamicRASCASn  [3:0] -> RAS latency in one cycle increments
; 32'h0000 0202 => RAS = 2 cycles, CAS = 2 cycles                                     ;CAS = 2 RAS= 3, 0203
; 32'h0000 0182 => RAS = 2 cycles, CAS = 1.5 cycles

        MOV     r0, #0xFF
        ADD    r0, r0, #0x84           ; 0x183
        ADD     r0,r0, #0x80           ; 0x203
        STR     r0, [r7, #MPMCDynamicRasCas0 - MPMC_Base_Plus_256]
        STR     r0, [r7, #MPMCDynamicRasCas1 - MPMC_Base_Plus_256]

; Write operational value into Config reg (MpmcDynamicConfig n)
; -----------------------------------------------------------------------------

; For RBC : 32'h 0000 4880                                                              ;4680
; For BRC : 32'h 0000 5880

        MOV     r0, #0x8D		
        MOV r0,r0, lsl #7		;0x4680		             
        STR     r0, [r7, #MPMCDynamicConfig0 - MPMC_Base_Plus_256]
        STR     r0, [r7, #MPMCDynamicConfig1 - MPMC_Base_Plus_256]

; Set DynamicRP Register								rp = 15ns/clk #02
; -----------------------------------------------------------------------------
        MOV     r0, #0x2                                                                
        STR     r0, [r6, #MPMCDynamictRP - MPMC_Base]

; Set DynamicRAS Register								tRAS = 37ns /CLK = 5 
; -----------------------------------------------------------------------------
        MOV     r0, #0x5                                                                
        STR     r0, [r6, #MPMCDynamictRAS - MPMC_Base]

; Set DynamicSREX Register								tXSR = 67 /clk = 9 
; -----------------------------------------------------------------------------
        MOV     r0, #0x9                                                                
        STR     r0, [r6, #MPMCDynamictSREX - MPMC_Base]

; Set DynamicWR Register								tWR =  ( clk+ 7) /clk = 2
; -----------------------------------------------------------------------------
	MOV     r1, #0x2
        STR     r1, [r6, #MPMCDynamictWR - MPMC_Base]  
                                         
; Set DynamicRC Register								tRC = 60 /clk = 8
; -----------------------------------------------------------------------------
	MOV     r0, #0x8  
        STR     r0, [r6, #MPMCDynamictRC - MPMC_Base]          
                                 
; Set DynamicRFC Register								tREC = 66/clk = 9
; ----------------------------------------------------------------------------- 
	MOV     r0, #0x9 
        STR     r0, [r6, #MPMCDynamictRFC - MPMC_Base] 
                                         
; Set DynamicXSR Register								tXSR = 67 /clk = 9 
; -----------------------------------------------------------------------------
        STR     r0, [r6, #MPMCDynamictXSR - MPMC_Base]                                  

; Set DynamicRRD Register								tRRD = 14 /clk =2
; -----------------------------------------------------------------------------
        MOV     r0, #2                                                                    
        STR     r0, [r6, #MPMCDynamictRRD - MPMC_Base]

; Set DynamicMRD Register								tMRD = 2clk
; -----------------------------------------------------------------------------                                                             
        STR     r0, [r6, #MPMCDynamictMRD - MPMC_Base]

; Set DynamicCDLR Register								tCDL = 1 clk
; -----------------------------------------------------------------------------
		MOV     r1, #1  
        STR     r0, [r6, #MPMCDynamictCDLR - MPMC_Base]                                


; Set SDRAM Initialisation Value (I) to MODE (MPMCDynamicControl [8:7] to 2'b01)
; -----------------------------------------------------------------------------
        MOV     r0, #0x83
        STR     r0, [r6, #MPMCDynamicControl - MPMC_Base]

; Program the Mode Registers. SDRAM Addr[5] = 1'b1, all others 0
; -----------------------------------------------------------------------------

; SDRAM Addr[11:0] = 12'h020
; For RBC : SDRAM Addr[11:0] translates to HADDR [25:13] = 0x40000                    RBC = 0x40000
; For BRC : SDRAM Addr[11:0] translates to HADDR [23:11] = 0x10000
; To program the register, do a read from the memory base addr + the value above

        LDR     r5, =SDRAM4ModeRegAddr			;0x00040000
        LDR     r0, [r5]

        LDR     r5, =SDRAM5ModeRegAddr			;0x08040000
        LDR     r0, [r5]

; Set SDRAM Initialisation Value (I) to PALL
; -----------------------------------------------------------------------------

;        MOV     r0, #0x83
;        ADD     r0, r0, #0x80
;        STR     r0, [r6, #MPMCDynamicControl - MPMC_Base]


; Set SDRAM Initialisation Value (I) to NORMAL (MPMCDynamicControl [8:7] to 2'b00)
; -----------------------------------------------------------------------------

        MOV     r0, #3
        STR     r0, [r6, #MPMCDynamicControl - MPMC_Base]


; Mpmc Dynamic Memory Config complete
; -----------------------------------------------------------------------------



       	mov pc, r2
   
   
   	ENDP


        END

; EOF fw_arm.s

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -