📄 ktimer5.asm
字号:
;*
;* COW : Character Oriented Windows
;*
;* ktimer5.asm : DOS 5 kernel timer (for ticks)
include kernel.inc
IFNDEF DOS5
.error -- only DOS 5
ENDIF
sBegin DATA
assumes DS,DGROUP
externDP pwndAlarm ;* != NULL if alarm set
externD semaMessage ;* message semaphore
labelD dmsKick ;* time to sleep
staticW OFF_dmsKick,-1
staticW SEG_dmsKick,-1
sEnd DATA
sBegin BSS
assumes DS,DGROUP
staticD semaTimer, 0 ;* timer semaphore
staticW idThread, 0 ;* id of timer thread
staticB fTimerLive, 0 ;* TRUE => timer alive
;* * stack
DB 64 DUP (?)
labelB wStackMax
sEnd BSS
;*****************************************************************************
;* * DOS 5 calls
externFP <DosCreateThread, DosSemClear, DosSemSetWait, DosSemClear, DosExit>
;*****************************************************************************
sBegin KERNEL
assumes CS,KERNEL
assumes SS,NOTHING
assumes DS,NOTHING ;* interrupt handler may be called from anywhere
;********* TimerThread **********
;* entry : semaEvent and semaTimer valid
;* * THREAD for processing timer
;* exit : n/a (dies when killed)
labelFP TimerThread
assumes DS,DATA
;* * when timer semaphore gets cleared, clear the message semaphore
;* * (this thread is necessary since we want 1 semaphore for all
;* * input events).
test fTimerLive,-1
jz TimerDies
PushArg <ds, <dataOffset semaTimer>> ;* hsemaTimer
PushArg <SEG_dmsKick, OFF_dmsKick> ;* wait time
cCall DosSemSetWait
;* * timer has elapsed, clear message semaphore
PushArg <ds, <dataOffset semaMessage>>
cCall DosSemClear
jmp TimerThread ;* forever
TimerDies:
xor ax,ax
cCall DosExit, <ax, ax> ;* kill this thread
;* * NOTREACHED
;********** KickTimer **********
;* entry : dms = time in ms to kick timer
;* *
cPrivate KickTimer, <>
parmD dms
cBegin KickTimer
mov ax,OFF_dms
mov dx,SEG_dms
mov OFF_dmsKick,ax
mov SEG_dmsKick,dx
;* * now kick the timer to install the new time
PushArg <ds, <dataOffset semaTimer>> ;* hsemaTimer
cCall DosSemClear
cEnd KickTimer
sEnd KERNEL
;*****************************************************************************
sBegin INIT
assumes CS,INIT
assumes DS,DGROUP
assumes SS,DGROUP
;********** InitSysTimer **********
;* entry : n/a
;* * Called to initialize the timer routine
;* exit : ax != 0 => ok
cProc FInitSysTimer,<FAR,PUBLIC,ATOMIC>
cBegin FInitSysTimer
;* * create the timer thread
mov ax,-1
mov OFF_dmsKick,ax
mov SEG_dmsKick,ax ;* longest time to sleep
mov fTimerLive,al
IFNDEF COW_SWAPPED
mov dx,cs
ELSE
mov dx,SEG kernelBase
ENDIF
mov ax,kernelOffset TimerThread
PushArg <dx, ax>
PushArg <ds, <dataOffset idThread>>
PushArg <ss, <dataOffset wStackMax>>
cCall DosCreateThread
or ax,ax
jnz init_timer_error
ExitTrueUnless init_timer_error
cEnd FInitSysTimer
sEnd INIT
;*****************************************************************************
sBegin EXIT
assumes CS,EXIT
assumes SS,DATA
assumes DS,DATA
;********** EndSysTimer **********
;* entry : n/a
;* * Unhook the timer interrupt
;* exit : n/a
cProc EndSysTimer,<FAR,PUBLIC,ATOMIC>
cBegin EndSysTimer
;* * kill thread
mov fTimerLive,0
;* * kick the thread (timer semaphore) so the thread dies
PushArg <ds, <dataOffset semaTimer>> ;* hsemaTimer
cCall DosSemClear
cEnd EndSysTimer
sEnd EXIT
;*****************************************************************************
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -