这个SideKick是个好东东。
pVM1%n:# 7 lSR 下面的程序不是我写的。
?pWda<& {:#c1d2@8 用汇编编写DOS下的内存驻留程序(1)
rZ&li/Z " {X0& WfHa hC4
M}(XM %]1te*_ P%;lHC #i JS/~6'uB 绪言
mQ9y{}t=4 E`Br# "/Bl #O{cplh, 0.1 内存驻留与中断
ZH<qidpR ;ojJXH~$} p=V1M-
内存驻留程序英文叫Terminate and Stay Resident Program,缩写为TSR.这些程序加载进内存,执行完后,就驻留在内存里,当满足条件时,调到前台来执行。
55ft,a B
OD!0CR5 ?<rZ9$ 内存驻留程序的常用形式有:
M8IU[Pz4 M/,lP biZ=TI2P,L >诸如Borland 的SideKick弹出式实用程序
#qARcxbK| < lUpvr XQ2YUe]DJ >日历系统
hW9U%-D 7m %[$X` C`-CfZZ >网络服务器
MEu{'[C shEAr*u :`>tCYy; >通讯程序
T7|=
`~ FNs$k=*8 2%|n}V[ >本地的DOS扩展(如CCDOS,UCDOS等中文系统都属于这个范畴)
Y$#6%`*#>n .7M.bpmqE Tb!FO"o >一些可恶的人利用TSR技术制作很多可恶的病毒程序,几乎所有的病毒程序都是TSR程序.
T*g}^TEh *zMt/d*<& ;oO_5[,M 就象多任务系统调度一个进程有一个调度程序一样,在PC中从前台程序进入到一个TSR,也要有一个调度者,只是PC操作系统的调度不称为调度程序,而只称为触发机制.触发机制调度TSR执行在PC机上党称为激活一个TSR.触发机制主要有以下几种:
$rJgBN >S8
n8U BSL+Gjj~} >硬件中断:党用的是键盘中断INT 9H,时钟中断INT 8H,通讯中断INT 14H,磁盘中断INT 13H等等.
2.^CIJc
/([a%,DI 7{]L{ j- >软件中断:党用的是键盘中断INT 16H,时钟中断INT 1CH,DOS中断INT 21H,等等.
r?w>x` \}\#
fg fCZ"0P3( >以上各种的结合.
~Kl"V%> ~~O4!|t [E+J=L.l 从以上的触发机制可以看出,TSR和PC机的中断系统有着密切的关系.每种激活方式实际上都是与中断有关的.常用特殊的击键序列的识别码是通过截获INT 9H和INT 16H来实现.实际上不管TSR程序的哪一个环节,都与中断有着密切的关系.因此在具体进行TSR和程序设计之前,先介绍PC中断系统.在此只作简单说明.
:9e4(7~ona A]1dR\p l](!2a=[ 在PC机内存的最低端(0000H开始)的1K字节中,存放着256个指针即常说的中为向量或中断矢量(Interrupt vertor),每个中断向量都指向一个子程序,该程序称为中断处理程序(Interrup handler).一个中断向量由四个字节组成,有一个字是中断处理程序的偏移量值,后一个字是中断处理程序的段值.256中断向量一起称为中断向量表.
noLr185 @NL37C W*?qOq
{ 手式计算中断向量的首址,可通过以下的公式来求得:
mmG]|Cl@ A
H=%6oT2 )3O#T$h X号中断向量的首址=0000H:X*4
Vvp{y RN}joKV z "z 当产生一个中断时,处理器都按顺序执行以下步骤:
~'|^|*}~Dj C^c<s [email protected]D21 >在堆栈上压入处理器的标志(相当于指令PUSHF).
_pzYmQ \qTp#sF +_25E.>ml >在堆栈上压入当前CS和IP值(相当于指令PUSH CS和PUSH IP).
^*+j7A.n JDW/Mc1bh {c~w
Ms# >关闭中断(CLI)
mwMu1# ?]aVRmL s IBP$9 >从中断向量加载的CS和IP,执行中断处理程序.
WJI}~/z;C ?2R!n"m-d DMTc{ 当执行完中断处理程序后,一般用IRET返回,它的作用是:
lANi$
:aE ^=a:{["@! |
O 9 b >从堆栈上取出保存的IP和CS(相当于指令POP CS和PUSH CS).
pMY7{z Z78i7k } R;fe v
1mE >同时恢复中断前的处理器标志(相当于指令POPF).
CpK:u!
Dn w
n|;Li JpZ_cb`<E' 中断有多种分类,由触发的原因和实现的性质来分,可分为硬件中断和软件中断,从操作系统分层实现来说,可以分成BIOS中断,BOS中断和用户中断.
(zxL!ZR< Y]^*mc0fE :S}ZF$
$j% 一方面,BIOS和DOS通过中断系统向用户提供一个操作系统功能界面.也就是说用户(一般来说是前台程序)的功能主要是通过调用DOS和BIOS的中断服务来实现的,具体来说就是通过INT指令来实现的.另一方面,BIOS和DOS由中断系统所构成,BIOS对硬件成为高层的功能,并通过中断的形式向用户提供.
q(csZ\e= 6pt|Crvu !1K.HdK 如果在当前程序执行的同时,能将一块代码放在内存,把中断向量指向代码中的子程序,那么在当前程序执行中产生中断时,就有可能执行不属于当前程序和操作系统的代码,产生的中断可能是当前程序产生的软件中断,也可能是由硬件产生的硬件中断.这就是单任务的PC操作系统可能执行多于一个进程的简单说明.
';}:*nZ//_ <FAbImE} @$Yk#N;&( 在PC中断系统中有几个中断具有周期性,即INT 8H,INT 1CH和INT 28H.它们或者周期性被执行用于时间计时,或者周期性产生用于等待.它们是在实现TSR时进行轮询触发的基础.键盘中断(INT 9H和INT 16H)当用户击键时发生,利用它们是进行热键处理的基础.串行口通讯也是触发的一个重要机制.此外众多的软件中断也是触发的媒介.
K4o']{:U {:=W)
37U O9m sPb: 0 d+b<J, 0.2 DOS的可重入性分析
-x:7K\=$SX I[b{*g2Zw neE
Zw#(Z 一个多任务操作系统之所以能使多个进行并存,是因为操作系统的大部分代码是可以了重的,对于临界资源有相应的PV操作,使得当调度一个新的进程时,能完整地保存前一个里程的现场,当再一次调度被挂起的进程时能象没有被中断一样继续执行.
e
z_c; "kC6G% atW^^4: 对于PC机来说,代码的重入性比较弱,对临界资源没有PC操作.当我们用中断程序启动用户的TSR时,如果只保存标志和寄存器,以及当前进程一些信息,那么只保存了当前程序的一部分现场,DOS的临界资源不会自动保存.在进行TSR设计时,一定要了解PC操作系统的重入性和临界资源.
}gFa9M< rCsC}2O yE
.st9m 重入性总是体现在代码上,所谓可重入代码的指这样的代码,即该代码被执行时还没有从中退出,由于某种原因又一次或者多次进入相同的代码,该代码每次的执行结果都是正确的,就说该代码是可重入的.相反,如果结果不正确,那么就就该代码是不可重入的.下面是一个可重入的子程序的例子:
-[&Z{1A4x4 @' %XdH ;#+I"Ow Add proc near
?* r ,1cpV|mAr SL`; `// cmp DS:word ptr [si],0
`z.sWF|f!O _00}O+GLM4 X"mPRnE330 je DonotAddTheValue
)A6=P%;}>I !vVW8hbp ,L<x=Dg add ax,DS:word ptr [si]
.t9`e=% CIsX$W 2Dt^W.! DonotAddTheValue:
j}K3YfH \}%_FnP0ZU ^uphpABpD ret
4^k8|#c LE~vSm^# /reGT!u Add endp
1r*yYm' y+= s/c oB>#P-V 上面的例子不管在其中任何一处再一次执行该子程序,执行结果不变.为了说明,只举多种可能性中的一种.
q(WGvl^r /x]^Cqe #xq3)B mov ds,0100h ;ds=0100h
.gNziDO
F_i
"v5# L@jpid95 mov si,0010h ;si=0010h
G$)tp^%]
_|4QrZ$n( e>6W ^ ) mov ax,0001h ;ax,=0001h
}'86hnW 9V~hz (^ Jr%F#/ call Add
6xY6EC OoRg:"9{# d>T8V(Bb cmp 0100h:word ptr [0010h],0 ;Call Add subroutine
mKyF<1,m <%W&xk J_j4Zb% K push ds ;Interrupted
tk:nth SUIu.4Mz ^ UhqV"[7k push si
/?0|hi<_$ Z0O0Q =e\Y M,yxPHlN push ax
;8f)p9vE =v!Z8zk=W +uj;00
D mov ds,0200h ;ds=0200h
XD?]+ XiV
K4sD8 -e?n4YO*\ mov si,0200h ;si=0020h
DZLEx{cm 9i
lJ HRQfT>"/ mov ax,0003h ;ax=0003h
lqgR4 ! +2k{yl b|may/xWH call Add
TKbfZw Hwtoa, __1Hx?f cmp 0200h:word ptr [0020h],0 ;0200:0020h=0004h
Yt{Z+.;9OI C-@M|K9A' {X<_Y< jne
{5HQ=& XbeT x PMX'vA` add ax,0200h:word ptr [0020h] ;ax=0007h
"pcr-?L #Ye0*` fZS'e{V ret ;Return
b$pCp`/MT .wTb/x ew~uOG+ pop ax ;ax=0001h
1}SON4U PR AP~P&^ T,Q7 YI pop si ;si=0010h
7q 5 \]J[ qF-Fc q T~SkFZ pop ds ;ds=0100h
?' mP`9I 'vZy-qHrV (Rp5g}b iret ;Return to Add subroutine
f_;tFP
B <lU(9)
L;& +W$uHQq jne
{zc*yV\ F9tWJJUsr <Wj/A/ add ax,0100h:word ptr [0100h] ;ax= 0001h
|Q@( <'8= #6mw CA| Im};wJ& ;0100h:0010h= 0002h
=Lb(N61 G(o6/ j~=<O<P ;----------------------------------------
0r[a$p>` *lu*h&Y