📄 fwbvd1.s
字号:
VDONE
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;
; Now that we have copied ourselves into RAM, jump to RAM's 'CodeInRAM' Label and start there
;
add r2, pc, #CodeInRAM-(.+8) ; Calc. PC-relative address of 'CodeInRAM'
ldr r1, =(EBOOT_PARTITION_PHY_BASE + EbootOffset) ; Load Phy Adx of where we started our copy above
add r1, r1, r2 ; Calc. Phy Adx of 'CodeInRAM' tag
IF Interworking :LOR: Thumbing
bx r1
ELSE
mov pc, r1
ENDIF
nop
nop
nop
CodeInRAM
IF BSP_MAINSTONE = "1"
ldr r1, =FPGA_REGS_BASE_PHYSICAL
mov r0, pc ; display PHYSICAL PC on 7-segs
setHexLED r1, r0 ; We are in SDRAM
ENDIF
BUILDTTB
; *****************************************************************
; *****************************************************************
; *****************************************************************
; *****************************************************************
; *****************************************************************
; Fill in first-level Section descriptors to create 1MB mapped regions
; from the contents of the MemoryMap array. (OEMAddressTable[])
;
; (r9) = TTB
; (r11) = ptr to MemoryMap array
;
;
; We split the mappings: [8000 0000 --> 9FFF FFFF] = Cacheable, Bufferable
; [A000 0000 --> BFFF FFFF] = NonCacheable, nonBufferable
;
;;;;; **************************************
; All code below is EBOOT-specific
; (i.e. NOT used by winCE itself)
; **************************************
;
; Set TTB
;
ldr r9, =EBOOT_PARTITION_PHY_BASE ; (r9) = physical address of 1st level table (EBOOT partition base) 0xA000 0000
ldr r0, =0xFFFFC000
and r9, r9, r0 ; mask off TTB[31:0] (must be 0's)
mcr p15, 0, r9, c2, c0, 0 ; set TTB
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; ~~~~~~~~~~ MAP CACHEABLE. BUFFERABLE SECTION DESCRIPTORS ~~~~~~~~~~~~~~~~
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
mov r0, #0x0E ; (r0) = Section (1MB) Descriptor; C=B=1. Write-Back, Read-Allocate
orr r0, r0, #0x400 ; set AP
20 mov r1, r11 ; (r1) = ptr to MemoryMap array
;
; Start Crunching through the OEMAddressTable[]
;
; r2 temporarily holds OEMAddressTable[VA]
; r3 temporarily holds OEMAddressTable[PHY]
; r4 temporarily holds OEMAddressTable[#MB]
;
25
ldr r2, [r1], #4 ; (r2) = virtual, Cached address to map Bank at
ldr r3, [r1], #4 ; (r3) = physical address to map from
ldr r4, [r1], #4 ; (r4) = num MB to map
cmp r4, #0 ; End of table?
beq %F29
;****************************************************************************************************************************************************************
; (r2) holds the &descriptor
; (r0) holds the actual section descriptor
;
; Create Descriptor Address
;
ldr r6, =0xFFF00000
and r2, r2, r6 ; only VA[31:20] are valid
orr r2, r9, r2, LSR #18 ; build the descriptor address: r2 = (TTB[31:14} | VA[31:20] >> 18)
; Create the Descriptor
;
ldr r6, =0xFFF00000
and r3, r3, r6 ; only PA[31:20] are valid for the descriptor; rest will be static
orr r0, r3, r0 ; build the descriptor: r0 = (PA[31:20] | the rest of the descriptor)
; Store the descriptor at the proper (phy) address
;
28 str r0, [r2], #4
add r0, r0, #0x00100000 ; (r0) = THE Section descriptor for the next 1MB mapping (just add 1MB)
sub r4, r4, #1 ; Decrement number of MB left
cmp r4, #0
bne %B28 ; Map next MB
bic r0, r0, #0xF0000000 ; Clear Section Base Address Field
bic r0, r0, #0x0FF00000 ; Clear Section Base Address Field
b %B25 ; Get and process next table element
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;
; Next, go through the above loop construct again.
; This time, we will map C=B=0 space (i.e. uncached, nonbuffered)
;
29
tst r0, #8 ; Test for 'C' bit set (means we just used above loop structure to map Cacheable,Bufferable space)
bic r0, r0, #0x0C ; clear cachable & bufferable bits in Descriptor (clear C&B bits)
add r9, r9, #0x0800 ; (r9) = ptr to 1st PTE for "unmapped uncached space" (0x2000 0000 + V_U_Adx)
bne %B20 ; go setup Descriptors for uncached space (map C=B=0 space)
ACTIVATEMMU
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; The 1st Level Section Descriptors are setup. Initialize the MMU and turn it on.
;
mov r1, #1
mcr p15, 0, r1, c3, c0, 0 ; setup access to domain 0
mcr p15, 0, r0, c8, c7, 0 ; flush I+D TLBs
mcr p15, 0, r1, c7, c10, 4 ; drain write and fill buffers
mov r1, #0x78 ; bits [6:3] must be written as 1's
orr r1, r1, #0x1 ; Enable: MMU
orr r1, r1, #0x1000 ; Enable icache
orr r1, r1, #0x0800 ; Enable BTB
orr r1, r1, #0x4 ; Enable Data Cache
ldr r2, =VirtualStart ; RVA
cmp r2, #0 ; make sure no stall on "mov pc,r2" below
IF BSP_MAINSTONE = "1"
ldr r5, =FPGA_REGS_BASE_PHYSICAL
ldr r8, =0x000c0de9
setHexLED r5, r8
ENDIF
;
; *Flip the MMU ON*
;
mcr p15, 0, r1, c1, c0, 0 ; MMU ON: All mem accesses now ~Virtual~
IF Interworking :LOR: Thumbing
bx r2
ELSE
mov pc, r2
ENDIF
nop
nop
nop
; **********************************
; MMU & caches now enabled.
;
; (r9) = physcial=virtual (direct mapped) address of 1st level page table
ALIGN
VirtualStart
IF BSP_MAINSTONE = "1"
ldr r1, =FPGA_REGS_BASE_U_VIRTUAL
mov r0, pc
setHexLED r1, r0
ENDIF
;
; Set up a SVC mode stack
;
ldr sp, =EBOOT_PARTITION_VIR_C_BASE ; cached, virtual ram. Set Stack Pointer
add sp, sp, #StackOffset ; Space reserved for stack in the BOOT.BIB file
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; Now that we have set up the MMU descriptors, are executing virtually, and
; have set up a stack, it is time to launch EBOOT.
;
; ldr r1, =FFUART_BASE_U_VIRTUAL
; add r2, pc, #MainLabel-(.+8)
; PrintStr r1, r2, r3
IF :DEF: ETHBOOT
bl main ; **Jump to Main.c::main(), never to return.**
nop
nop
nop
HANG
b HANG
ENDIF ; // if :DEF: ETHBOOT
; *********************************************************************************
; SubRoutines
; *********************************************************************************
; void Launch(unsigned long pFunc)
;
; Routine Description:
;
; This function launches the program at pFunc. The expectation is that
; the launched program never returns. We disable the MMU right
; before we jump to [r0].
;
; Arguments:
;
; pFunc (r0) - Supplies the Virtual, Cached address of the program to launch.
;
; Return Value:
;
; None; the launched program never returns.
;
; Called From:
;
; Main.c::main()
;
; PreConditions:
;
; It is assumed that the MMU and Caches are ON upon entry
;
LEAF_ENTRY Launch
ldr r2, =PhysicalStart ; *This is the Relative Virtual Address (RVA). It is simply an offset.
;
; First, we need to find the Offset that will get us from Virtual->Physical for
; the EBOOT Partition
;
ldr r3, =(EBOOT_PARTITION_PHY_BASE - SDRAM_VIR_C_EBOOT_PARTITION)
;
; Next, we add the above found Offset to PhysicalStart's RVA.
; (R2 now points to the Physical address of PhysicalStart (below).)
;
add r2, r2, r3
;
; Now, we calculate the Offset that will get us from Virtual->Physical for
; the WinCE Partition
;
ldr r3, =(SDRAM_PHY_WINCE_PARTITION - SDRAM_VIR_C_WINCE_PARTITION)
;
; ...then add the above Offset to the Virtual/Cached Address passed to us in R0
;
add r0, r0, r3 ; r0 = (Virtual Address of Program to Launch) + Virtual->Physical Offset
mov r3, r0 ; bman
; Support soft reset with Eboot running as boot code.
ldr r4, =(RESET_LAUNCH_ADDR_PHYSICAL) ; get pointer to SLEEPDATA
;
; Next, we disable the MMU, I&D Caches.
;
mov r1, #0x0078
mcr p15, 0, r1, c1, c0, 0
mov r1, #0 ; Clear out soft reset indicator register to avoid aliasing in launched program
str r3, [r4] ; Store launch address for soft reset use
IF Interworking :LOR: Thumbing
bx r2
ELSE
mov pc, r2
ENDIF
nop ; These NOPs are used to flush the Pipeline
nop
nop
nop
PhysicalStart
mcr p15, 0, r2, c8, c7, 0 ; Flush the I&D TLBs
ldr r0, =OEMAddressTable
; Jump to program we are launching!! No return.
;
IF Interworking :LOR: Thumbing
bx r3
ELSE
mov pc, r3
ENDIF
; ----------------------
; void Launch2(unsigned long pFunc)
;
; Routine Description:
;
; This function launches the program at pFunc. The expectation is that
; the launched program never returns. We disable the MMU right
; before we jump to [r0].
;
; Arguments:
;
; pFunc (r0) - Supplies the Physical Address of the program to launch.
;
; Return Value:
;
; None; the launched program never returns.
;
; Called From:
;
; Main.c::main()
;
; PreConditions:
;
; It is assumed that the MMU and Caches are ON upon entry
;
LEAF_ENTRY Launch2
ldr r2, =PhysicalStart2 ; *This is the Relative Virtual Address (RVA). It is simply an offset.
;
; First, we need to find the Offset that will get us from Virtual->Phyiscal for
; the EBOOT Partition
;
ldr r3, =(EBOOT_PARTITION_PHY_BASE - SDRAM_VIR_C_EBOOT_PARTITION)
;
; Next, we add the above found Offset to PhysicalStart's RVA.
; (R2 now points to the Physical address of PhysicalStart (below).)
;
add r2, r2, r3
;
; Now, we calculate the Offset that will get us from Virtual->Physical for
; the WinCE Partition
;
ldr r3, =(SDRAM_PHY_WINCE_PARTITION - SDRAM_VIR_C_WINCE_PARTITION)
;
; ...then add the above Offset to the Virtual/Cached Address passed to us in R0
;
;add r0, r0, r3 ; r0 = (Virtual Address of Program to Launch) + Virtual->Physical Offset
; Support soft reset with Eboot running as boot code.
ldr r4, =(RESET_LAUNCH_ADDR_PHYSICAL) ; get pointer to SLEEPDATA
;cjw Does this count for Soft Reset???
;
; Next, we disable the MMU, I&D Caches and the Write Buffer.
;
mov r1, #0x0078
mcr p15, 0, r1, c1, c0, 0
str r0, [r4] ; Store launch address for soft reset use
mov r1, #0 ; Clear out soft reset indicator register to avoid aliasing in launched program
mov pc, r2 ; Jump to PhysicalStart
nop ; These NOPs are used to flush the Pipeline
nop
nop
nop
PhysicalStart2
mov r2, #0
mcr p15, 0, r2, c8, c7, 0 ; Flush the I&D TLBs
mov pc, r0 ; Jump to program we are launching!! No return.
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -