📄 sys_support.s
字号:
*/
cmp r0, #0x00
beq undefined_interrupt
/*
* Enable the interrupt
*/
mrs r2, cpsr
and r2, r2, #~CPSR_IRQ_BIT /* Enable the interrupt */
msr cpsr,r2
/*
* Call Handler
*/
mov lr, pc
mov pc, r0
/*
* Disable the interrupt
*/
mrs r2, cpsr
and r2, r2, #CPSR_FIQ_BIT /* Inherit the FIQ bit */
orr r2, r2, #(CPSR_SVC|CPSR_IRQ_BIT)
msr cpsr,r2
/* Fix bug 2006.5.29 <Start> */
ldmfd sp!, {r0} /* Restore the MASK bit */
ldmfd sp!, {r1} /* Restore the enable register(IRQ0_ENABLEREG_L) */
str r0, [r1] /* Enable the interrupt */
/* Fix bug 2006.5.29 <End> */
ldmfd sp!, {r0} /* Restore the master bit */
ldmfd sp!, {r1} /* Restore the enable register(IRQ0_ENABLEREG_H) */
str r0, [r1] /* Enable the interrupt */
Handler_Proc_End:
/*
* Decrement the interrupt nested counts(interrupt_count)
*/
ldr r2, =interrupt_count
ldr r1, [r2]
sub r3, r1, #1
str r3, [r2]
cmp r3, #0x00
bne return_to_task_irq
/*
* Restore the task stack
*/
ldmfd sp!,{r0}
mov sp, r0
ldr r1, =reqflg /* Check reqflg */
ldr r0, [r1]
cmp r0, #0
beq return_to_task_irq
mov r0, #0
str r0, [r1] /* Clear reqflg */
b ret_int
return_to_task_irq:
/*
* Restore process
* There is no problem ,although interrupt is permited,because it is saved in the task context.
*/
ldmfd sp!,{r1} /* Restore the CPSR */
mrs r2, cpsr /* Inherit FIQ */
and r2, r2, #CPSR_FIQ_BIT
and r1, r1, #~CPSR_FIQ_BIT
orr r1, r1, r2
msr spsr, r1 /* Enable interupt */
ldmfd sp!,{r0-r3,ip,lr,pc}^ /* Restore task + enable interupt */
/*
* Call it when the undefined interupt occured, .
*/
undefined_interrupt:
b undef_interrupt
//******************************************************************************
// Routine to Disable Instruction Cache.
//******************************************************************************
.global disable_Icache
disable_Icache:
stmfd sp!, {a1, lr}
#if CACHE_I
mrc p15, 0, r0, c1, c0, 0
tst r0, #0x1000
ldrne r1, =R1_SBZ_DATA
bicne r0, r0, r1 // Clear SBZ bits.
ldrne r1, =R1_SBO_DATA
orrne r0, r0, r1 // Set SBO bits.
bicne r0, r0, #0x1000 // Clear I-Cache Control.
mcrne p15, 0, r0, c1, c0, 0
#endif
ldmfd sp!, {a1, lr}
bx lr
//******************************************************************************
// Routine to Disable Data Cache.
//******************************************************************************
.global disable_Dcache
disable_Dcache:
stmfd sp!, {a1, lr}
#if CACHE_D
mrc p15, 0, r0, c1, c0, 0
tst r0, #0x0004
ldrne r1, =R1_SBZ_DATA
bicne r0, r0, r1 // Clear SBZ bits.
ldrne r1, =R1_SBO_DATA
orrne r0, r0, r1 // Set SBO bits.
bicne r0, r0, #0x0004 // Clear D-Cache Control.
mcrne p15, 0, r0, c1, c0, 0
#endif
ldmfd sp!, {a1, lr}
bx lr
//******************************************************************************
// Routine to Enable Instruction Cache.
//******************************************************************************
.global enable_Icache
enable_Icache:
stmfd sp!, {a1, lr}
#if CACHE_I
mrc p15, 0, r0, c1, c0, 0
ldr r1, =R1_SBZ_DATA
bic r0, r0, r1 // Clear SBZ bits.
ldr r1, =R1_SBO_DATA
orr r0, r0, r1 // Set SBO bits.
orr r0, r0, #0x1000 // Set I-Cache Control.
mcr p15, 0, r0, c1, c0, 0
#endif
ldmfd sp!, {a1, lr}
bx lr
//******************************************************************************
// Routine to Enable Data Cache.
//******************************************************************************
.global enable_Dcache
enable_Dcache:
stmfd sp!, {a1, lr}
#if CACHE_D
mrc p15, 0, r0, c1, c0, 0
ldr r1, =R1_SBZ_DATA
bic r0, r0, r1 // Clear SBZ bits.
ldr r1, =R1_SBO_DATA
orr r0, r0, r1 // Set SBO bits.
orr r0, r0, #0x0004 // Set D-Cache Control.
mcr p15, 0, r0, c1, c0, 0
#endif
ldmfd sp!, {a1, lr}
bx lr
//******************************************************************************
// Routine to Flush (Invalidate) Instruction Cache.
//******************************************************************************
.global flush_Icache
flush_Icache:
stmfd sp!, {a1,a2,r4,r5,lr}
mov r4, r0 // Page start address.
mov r5, r1 // CACHE flush area Size
cmp r4, #0x0
beq Flush_ICache_ALL
cmp r5, #0x0
beq Flush_ICache_ALL
#if CACHE_I
stmfd sp!, {r4-r5}
add r5, r5, r4
bic r4, r4, #MVA_SBZ
add r5, r5, #CACHE_LNG
Flush_ICache_Line:
mcr p15, 0, r4, c7, c5, 1 // Invalidate ICache Single Entry.
add r4, r4, #CACHE_LNG
cmp r4, r5
blo Flush_ICache_Line
ldmfd sp!, {r4-r5}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
Flush_ICache_ALL:
#if CACHE_I
stmfd sp!, {r2}
mov r2, #0x0
mcr p15, 0, r2, c7, c5, 0 // Invalidate ALL I-Cache.
ldmfd sp!, {r2}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
//******************************************************************************
// Routine to Flush (Invalidate) Data Cache.
//******************************************************************************
.global flush_Dcache
flush_Dcache:
stmfd sp!, {a1,a2,r4,r5,lr}
mov r4, r0 // Page start address.
mov r5, r1 // CACHE flush area Size
cmp r4, #0x0
beq Flush_DCache_ALL
cmp r5, #0x0
beq Flush_DCache_ALL
#if CACHE_D
stmfd sp!, {r4-r5}
add r5, r5, r4
bic r4, r4, #MVA_SBZ
add r5, r5, #CACHE_LNG
Flush_DCache_Line:
mcr p15, 0, r4, c7, c14, 1 // Clean & flush DCache Single Entry.
add r4, r4, #CACHE_LNG
cmp r4, r5
blo Flush_DCache_Line
ldmfd sp!, {r4-r5}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
Flush_DCache_ALL:
#if CACHE_D
stmfd sp!, {r0-r2}
mov r1, #0x0 // Initialize index counter
Dflush_outer_loop:
mov r0, #0x0 // Initialize segment counter
Dflush_inner_loop:
orr r2, r1, r0 // Make segment and line address
mcr p15, 0, r2, c7, c14, 2 // Clean and Flush Data Cache entry
add r0, r0, #0x20
cmp r0, #0x100
bne Dflush_inner_loop
add r1, r1, #0x04000000
cmp r1, #0x0
bne Dflush_outer_loop
ldmfd sp!, {r0-r2}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
//******************************************************************************
// Routine to Clean Data Cache.
//******************************************************************************
.global clean_Dcache
clean_Dcache:
stmfd sp!, {a1,a2,r4,r5,lr}
mov r4, r0 // Page start address.
mov r5, r1 // CACHE area size to be Cleaned
cmp r4, #0x0
beq Flush_DCache_ALL
cmp r5, #0x0
beq Flush_DCache_ALL
#if CACHE_D
stmfd sp!, {r4-r5}
add r5, r5, r4
bic r4, r4, #MVA_SBZ
add r5, r5, #CACHE_LNG
Clean_DCache_Line:
mcr p15, 0, r4, c7, c10, 1 // CleanDCache Single Entry.
add r4, r4, #CACHE_LNG
cmp r4, r5
blo Clean_DCache_Line
ldmfd sp!, {r4-r5}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
Clean_DCache_ALL:
#if CACHE_D
stmfd sp!, {r0-r2}
mov r1, #0x0 // Initialize index counter
CleanD_outer_loop:
mov r0, #0x0 // Initialize segment counter
CleanD_inner_loop:
orr r2, r1, r0 // Make segment and line address
mcr p15, 0, r2, c7, c10, 2 // Clean Data Cache entry
add r0, r0, #0x20
cmp r0, #0x100
bne CleanD_inner_loop
add r1, r1, #0x04000000
cmp r1, #0x0
bne CleanD_outer_loop
ldmfd sp!, {r0-r2}
#endif
ldmfd sp!, {a1,a2,r4,r5,lr}
bx lr
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -