📄 tct.asm
字号:
;/* FUNCTION */
;/* */
;/* TCT_Schedule */
;/* */
;/* DESCRIPTION */
;/* */
;/* This function waits for a thread to become ready. Once a thread */
;/* is ready, this function initiates a transfer of control to that */
;/* thread. */
;/* */
;/* AUTHOR */
;/* */
;/* William E. Lamie, Accelerated Technology, Inc. */
;/* */
;/* CALLED BY */
;/* */
;/* INC_Initialize Main initialization routine */
;/* */
;/* CALLS */
;/* */
;/* TCT_Control_To_Thread Transfer control to a thread */
;/* */
;/* INPUTS */
;/* */
;/* TCD_Execute_Task Pointer to task to execute */
;/* */
;/* OUTPUTS */
;/* */
;/* None */
;/* */
;/* HISTORY */
;/* */
;/* NAME DATE REMARKS */
;/* */
;/* D. Foxall 02-07-1996 TMS320C30 version 1.0 */
;/* J. Trippi 03-11-1997 Modified for large memory model */
;/* */
;/*************************************************************************/
.global _TCT_Schedule
_TCT_Schedule:
;VOID TCT_Schedule(VOID)
;{
; /* register use: R0 - thread pointer
; R1 - interrupt level */
;
; /* It is assumed that interrupts are fully disabled at this point. */
; /* Determine if interrupts need to be enabled. */
;
;
.if NU_BIG
LDP @_TCD_Interrupt_Level ; Load Data Page Pointer
.endif
LDI @_TCD_Interrupt_Level,IE ; Pickup global interrupt level
RPTS 0 ; XIONGZHANGXUE
OR GIEMASK,ST ; Enable interrupts
;
; /* Wait until a thread (task or HISR) is available to execute. */
; do
; {
;
_TCT_Schedule_Loop:
;
; } while ((!TCD_Execute_HISR) && (!TCD_Execute_Task));
;
.if NU_BIG
LDP @_TCD_Execute_HISR ; Load Data Page Pointer
.endif
LDI @_TCD_Execute_HISR,R0 ; Pickup the HISR pointer
BNZ _TCT_Schedule_Thread ; If not NULL, found an HISR
.if NU_BIG
LDP @_TCD_Execute_Task ; Load Data Page Pointer
.endif
LDI @_TCD_Execute_Task,R0 ; Pickup the task pointer
BZ _TCT_Schedule_Loop ; Keep checking if task pointer is
; also NULL
_TCT_Schedule_Thread:
;
; /* Yes, either a task or an HISR is ready to execute. Lockout interrupts
; while the thread is transferred to. */
.if NU_BIG
LDP @_TCT_Disable_Interrupts ; Load Data Page Pointer
.endif
LDI @_TCT_Disable_Interrupts,IE ; Lockout interrupts
; NOP ; Interrupt lockout might not occur
; NOP ; for a few instructions
RPTS 0 ; XIONGZHANGXUE
OR GIEMASK,ST
;
; /* Transfer control to the thread by falling through to the following
; routine. R0 contains the thread pointer. */
;}
;
;
;/*************************************************************************/
;/* */
;/* FUNCTION */
;/* */
;/* TCT_Control_To_Thread */
;/* */
;/* DESCRIPTION */
;/* */
;/* This function transfers control to the specified thread. Each */
;/* time control is transferred to a thread, its scheduled counter */
;/* is incremented. Additionally, time-slicing for task threads is */
;/* enabled in this routine. The TCD_Current_Thread pointer is */
;/* setup by this function. */
;/* */
;/* AUTHOR */
;/* */
;/* William E. Lamie, Accelerated Technology, Inc. */
;/* */
;/* CALLED BY */
;/* */
;/* TCT_Schedule Indirectly called */
;/* TCT_Protect Protection task switch */
;/* */
;/* CALLS */
;/* */
;/* None */
;/* */
;/* INPUTS */
;/* */
;/* thread Thread control block pointer */
;/* */
;/* OUTPUTS */
;/* */
;/* None */
;/* */
;/* HISTORY */
;/* */
;/* NAME DATE REMARKS */
;/* */
;/* D. Foxall 02-07-1996 TMS320C30 version 1.0 */
;/* J. Trippi 03-11-1997 Modified for large memory model */
;/* M. Trippi 11-14-1997 Removed the code to SUBI and */
;/* ADDI to the SP since this */
;/* would case the saved DP to be */
;/* destroyed. */
;/* */
;/*************************************************************************/
.global _TCT_Control_To_Thread
_TCT_Control_To_Thread:
;VOID TCT_Control_To_Thread(TC_TCB *thread)
;{
; /* register use: R0, AR0 - thread pointer
; R1 - temporary values */
;
; /* At entry, R0 contains the pointer to the thread to be resumed.
; Interrupts have been locked out by preceding code. */
;
; /* Setup the current thread pointer. */
; TCD_Current_Thread = thread;
;
.if NU_BIG
LDP @_TCD_Current_Thread ; Load Data Page Pointer
.endif
LDI R0,AR0 ; Put thread pointer in AR0
STI R0,@_TCD_Current_Thread ; Setup the current thread ptr,
;
; /* Increment the thread scheduled counter. */
; thread -> tc_scheduled++;
;
LDI *+AR0(TCB_SCHEDULED),R1 ; Increment the scheduled count
ADDI 1,R1
STI R1,*+AR0(TCB_SCHEDULED)
;
; /* Check for time slice option. */
; if (thread -> tc_cur_time_slice)
LDI *+AR0(TCB_CURTIMESLC),R1 ; Pickup time slice value
BZ _TCT_No_TS_Start ; If 0, don't start time slice
;
; /* Start a time slice. */
; TMD_Time_Slice = thread -> tc_cur_time_slice;
; TMD_Time_Slice_State = TM_ACTIVE;
;
.if NU_BIG
LDP @_TMD_Time_Slice ; Load Data Page Pointer
.endif
STI R1,@_TMD_Time_Slice ; Otherwise, start time slice,
.if NU_BIG
LDP @_TMD_Time_Slice_State ; Load Data Page Pointer
.endif
LDI TM_ACTIVE,R1
STI R1,@_TMD_Time_Slice_State ; by setting up timer parameters
; }
_TCT_No_TS_Start:
;
; /* Pickup the stack pointer and resume the thread. */
; SP = thread -> tc_stack_pointer;
;
LDI *+AR0(TCB_STKPTR),SP ; Switch to thread's stack
;
; /* Pop off the saved information associated with the thread. Then
; determine which type of stack is present. A 1 on the top of the
; stack indicates an interrupt stack, while a 0 on the top of the
; stack indicates a solicited type of stack. */
;
POP R0 ; Pickup the top of the stack
BNZ _TCT_Interrupt_Stack ; If not 0, an interrupt stack
;
; /* A solicited stack. Restore minimum context registers */
POP AR7 ; Restore auxiliary registers
POP AR6
POP AR5
POP AR4
POPF R7 ; Restore the upper 32 bits of R7
POP R7 ; and the lower 32 bits
POPF R6 ; Restore the upper 32 bits of R6
POP R6 ; and the lower 32 bits
POPF R5 ; Restore the upper 32 bits of R5
POP R5 ; and the lower 32 bits
.if NU_BIG
LDP @_TCD_Interrupt_Level ; Load Data Page Pointer
.endif
POPF R4 ; Restore the upper 32 bits of R4
POP R4 ; and the lower 32 bits
;
; /* Determine if interrupts need to be enabled. */
;
LDI @_TCD_Interrupt_Level,IE ; Pickup global interrupt level
POP DP ; Restore data page pointer
POP AR3 ; Restore frame pointer
RETI ; Return, setting GIE bit in ST
;
_TCT_Interrupt_Stack:
; /* Restore all registers from the thread's stack */
;
RPTS 0
AND GIENOT,ST ; XIONGZHANGXUE
POP RC ; Restore repeat counter
POP RE ; Restore repeat end address
POP RS ; Restore repeat start address
POP IOF ; Restore I/O flag register
;
POP BK ; Restore block-size register
POP IR1 ; Restore index register 1
POP IR0 ; Restore index register 0
;
POP AR7
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -