, k q W+ Q7 h% u2 Q. t) JGuido Wischrop提供了下面的代码可以读取IDT的所有256项。! H$ a1 P" f' A% z4 e
5 P% N# d. @: \2 D# {4 RUCHAR *mBuffer; / [3 L2 A: `, p4 _3 @ULONG dummy; 2 V( r( Q7 f g4 j……! r/ ]" ~2 q$ D7 A. x5 }' l
_asm5 r3 O; j% Q% r! }3 \2 {
{2 S# G0 d0 R- l+ u; T9 M+ t
mov esi,mBuffer ' S6 `+ R/ t" J( d% L% G4 R8 Fsidt [esi] //load IDTR to *mBuffer 8 r6 L% y* H1 @7 f9 {& `movzx ecx,word ptr [esi] //load size of IDT to ECX 2 H- s9 U9 Y' P) r: wmov ebx,dword ptr [esi+2] //load Base Address of LDT to EBX+ r' H2 f% @/ `6 s
inc ecx " K8 ?) x- Q& G( dmov edi,mBuffer //mBuffer is the target* ~7 l' V; i' Q+ m+ O5 X8 v& V2 |. p
mov dummy,ecx //store size in dummy# @! R4 [3 M' c5 p2 Q7 a: \/ f
mov esi,ebx //store IDT Base Address to ESI' b$ T8 B- E5 T/ ~$ s! t0 F# v
shr ecx,2 + `; Q" ` e) ]% ?" o% {. Crep movsd //copy IDT to mBuffer 1 ]9 {9 v' _+ w& ^! E! d. e}0 h; t- h4 i" k- h( r' e, G
8 ]6 y% z4 R" i
这样我们就可以得到想要的IDT中的某一项,那么,我们是不是可以通过改写内存的方式直接替换相应的IDT表项呢?答案是肯定 的,有人声称这样能成功。我觉是没有太大的必要,因为通过标准的Kernel API调用也可以实现。- r( a3 k Y0 C; C( H
我们可以用Windriver生成代码来简单地体会一下挂硬件中断ISR的感觉。 7 g5 @! ~* ] L. S(1) Windriver---> Driver Wizard---->New Project----->ISA CARD% B" J1 L2 T: V% ?7 J# ]: \
(2) Interrupts---> New j8 M- A: v9 Q9 H( O# z
Interrupt Number = 14(或别的) & Edge Triggered & Shared ; |% M4 g% z- L(3) Listen to Interrupts : p) y; Q4 C" L- s+ S4 z8 d如果没有出现错误,则表明这个硬件中断可以挂我们的ISR。3 C. B' O. z! ^( u+ K
(4) Generate Code/ Z1 E6 ]3 V2 w2 k; L
(5) Build and Run ) |# }% Y% F9 N* o) z0 D(6) Enable Interrupt+ }; J3 C0 C3 B) F7 C5 E# ^ x4 _
(7) 切换到SoftIce中去(Ctrl + D),然后敲:intobj命令,可以看到如下的输入信息: & m9 p$ i8 l+ L" `4 X2 f:intobj0 j& U1 ^4 j6 ~' j2 N
Object Service Service Affinity. y( j- o6 r" G2 t* Z+ n+ j
Address Vector Address Context IRQL Mode Mask Symbol4 N k x3 j9 }1 e3 i/ {2 I8 S
FD349508 31 F7861900 FD4683E0 1A Edge 01 i8042prt!.text+1600 + L0 J6 L2 U" TFD348D88 3C F786798C FD35D020 0F Edge 01 i8042prt!PAGEMOUC+020C( _) `9 I7 ?. C/ j0 p0 `3 |1 K
FD189708 3D FC8F22C0 00000001 0E Edge 01 WINDRVR!.text+2040 0 r p, i6 z* {3 x3 L1 AFD48F788 3E FD10FE42 FD4BD030 0D Edge 01 atapi!.text+5AE2& F* t) J1 P1 @+ P7 U# W: V
FD34A888 3F FD057AA0 FD34E0DC 0C Level 01 NDIS!PAGENDSM( e+ _- E( ~# z6 Q
NTICE: Exit32 PID=70 MOD=ps2_diag 3 |; s6 b( @0 e+ `2 _- z: Q6 f8 C- q/ C g
从上面可以看到,0Eh(即14)号硬件中断被映射到了IDT的3Dh项。还不相信吗?好,让我们来测试一下。在SoftIce中敲入如下的指 令:genint 3d,看到什么了?呵呵,屏幕显示如下:# `" `, t8 H$ ]" o" a
+ G$ h$ \- O" ~; d5 e6 M' n% d9 k
7 O9 c" I: ^' H. b2 g ! w9 ?! A' F" F3 d9 g: r我们用:genint 3d这条指令模拟了一次硬件中断,结果表明我们的ISR确实是挂在了IDT的3Dh项处。在Softice中再运行几次genint 3d试试 看,屏幕上会输出什么样的结果呢?当然是Got Interrupt0 number 2,Got Interrupt0 number 3之类的信息啦。 1 i( Z# Y4 S3 l% u& F ?1 z9 w c. t0 U" m( [4 z m/ J一个问题马上被提出来了