nt!KiDeferredReadyThread函数分析之插入DispatcherReadyListHead列表的一个例子
1: kd> p
eax=00000000 ebx=0000000e ecx=00000003 edx=0000000e esi=89555268 edi=80a059f8
eip=80a41fbc esp=f75f6814 ebp=f75f6834 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
nt!KiDeferredReadyThread+0x394:
80a41fbc a1806eb180 mov eax,dword ptr [nt!_KiIdleSummary (80b16e80)] ds:0023:80b16e80=00000000
1: kd> p
eax=00000000 ebx=0000000e ecx=00000003 edx=0000000e esi=89555268 edi=80a059f8
eip=80a421d6 esp=f75f6814 ebp=f75f6834 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
nt!KiDeferredReadyThread+0x5ae:
80a421d6 0f85effdffff jne nt!KiDeferredReadyThread+0x3a3 (80a41fcb) [br=0]
1: kd> dv IdleSet
IdleSet = 0
1: kd> p
eax=00000000 ebx=0000000e ecx=00000003 edx=0000000e esi=89555268 edi=80a059f8
eip=80a421dc esp=f75f6814 ebp=f75f6834 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
nt!KiDeferredReadyThread+0x5b4:
80a421dc 8b45f4 mov eax,dword ptr [ebp-0Ch] ss:0010:f75f6828=00000000
1: kd> kc
#
00 nt!KiDeferredReadyThread
01 nt!KiProcessDeferredReadyList
02 nt!KiExitDispatcher
03 nt!KeSetEvent
04 win32k!QueueMouseEvent
05 win32k!ProcessMouseInput
06 win32k!InputApc
07 nt!KiDeliverApc
08 nt!KiSwapThread
09 nt!KeWaitForMultipleObjects
0a win32k!xxxMsgWaitForMultipleObjects
0b win32k!xxxDesktopThread
0c win32k!xxxCreateSystemThreads
0d win32k!NtUserCallOneParam
0e nt!_KiSystemService
//
// Select the ideal processor as the processor to preempt, if possible.
//
TargetPrcb = KiProcessorBlock[Processor];
1: kd> dv Processor
Processor = 0
ThreadPriority = Thread->Priority;
1: kd> p
eax=ffdff9bc ebx=ffdff120 ecx=00000000 edx=00000001 esi=89555268 edi=80a059f8
eip=80a4226e esp=f75f6814 ebp=f75f6834 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
nt!KiDeferredReadyThread+0x646:
80a4226e 0fbe4e5b movsx ecx,byte ptr [esi+5Bh] ds:0023:895552c3=0e
1: kd> dt kthread 89555268
CSRSRV!KTHREAD
+0x000 Header : _DISPATCHER_HEADER
+0x010 MutantListHead : _LIST_ENTRY [ 0x89555278 - 0x89555278 ]
+0x018 InitialStack : 0xf75d7000 Void
+0x01c StackLimit : 0xf75d4000 Void
+0x020 KernelStack : 0xf75d6a18 Void
+0x024 ThreadLock : 0
+0x028 ContextSwitches : 0xa10
+0x02c State : 0x7 ''
+0x02d NpxState : 0xa ''
+0x02e WaitIrql : 0 ''
+0x02f WaitMode : 0 ''
+0x030 Teb : 0x7ffd9000 Void
+0x034 ApcState : _KAPC_STATE
+0x04c ApcQueueLock : 0
+0x050 WaitStatus : 0n1
+0x054 WaitBlockList : 0x898a5488 _KWAIT_BLOCK
+0x058 Alertable : 0x1 ''
+0x059 WaitNext : 0 ''
+0x05a WaitReason : 0xd ''
+0x05b Priority : 14 ''
if (((KiIdleSummary & TargetPrcb->SetMember) == 0) &&
(Thread->IdealProcessor == Processor)) {
1: kd> x nt!KiIdleSummary
80b16e80 nt!KiIdleSummary = 0
Thread->NextProcessor = (UCHAR)Processor;
1: kd> dv Processor
Processor = 0
1: kd> dx -id 0,0,89831250 -r1 ((basesrv!_KPRCB *)0xffdff120)
((basesrv!_KPRCB *)0xffdff120) : 0xffdff120 [Type: _KPRCB *]
[+0x000] MinorVersion : 0x1 [Type: unsigned short]
[+0x002] MajorVersion : 0x1 [Type: unsigned short]
[+0x004] CurrentThread : 0x895f2a78 [Type: _KTHREAD *]
[+0x008] NextThread : 0x0 [Type: _KTHREAD *]
1: kd> dx -id 0,0,89831250 -r1 ((basesrv!_KTHREAD *)0x895f2a78)
((basesrv!_KTHREAD *)0x895f2a78) : 0x895f2a78 [Type: _KTHREAD *]
[+0x000] Header [Type: _DISPATCHER_HEADER]
[+0x010] MutantListHead [Type: _LIST_ENTRY]
[+0x018] InitialStack : 0xba1b1000 [Type: void *]
[+0x01c] StackLimit : 0xba1ad000 [Type: void *]
[+0x020] KernelStack : 0xba1b0c5c [Type: void *]
[+0x024] ThreadLock : 0x0 [Type: unsigned long]
[+0x028] ContextSwitches : 0x470 [Type: unsigned long]
[+0x02c] State : 0x2 [Type: unsigned char]
[+0x02d] NpxState : 0xa [Type: unsigned char]
[+0x02e] WaitIrql : 0x0 [Type: unsigned char]
[+0x02f] WaitMode : 1 [Type: char]
[+0x030] Teb : 0x7ffd5000 [Type: void *]
[+0x034] ApcState [Type: _KAPC_STATE]
[+0x04c] ApcQueueLock : 0x0 [Type: unsigned long]
[+0x050] WaitStatus : 258 [Type: long]
[+0x054] WaitBlockList : 0x895f2b18 [Type: _KWAIT_BLOCK *]
[+0x058] Alertable : 0x0 [Type: unsigned char]
[+0x059] WaitNext : 0x0 [Type: unsigned char]
[+0x05a] WaitReason : 0x6 [Type: unsigned char]
[+0x05b] Priority : 15 [Type: char]
Thread->NextProcessor = (UCHAR)Processor;
if ((Thread1 = TargetPrcb->NextThread) != NULL) { 目标处理器下一个线程是否可以抢占
ASSERT(Thread1->State == Standby);
if (ThreadPriority > Thread1->Priority) {
Thread1->Preempted = TRUE;
Thread->State = Standby;
TargetPrcb->NextThread = Thread;
Thread1->State = DeferredReady;
Thread1->DeferredProcessor = CurrentPrcb->Number;
KiReleaseTwoPrcbLocks(CurrentPrcb, TargetPrcb);
KiDeferredReadyThread(Thread1);
return;
}
} else {
Thread1 = TargetPrcb->CurrentThread; 目标处理器当前线程是否可以抢占
if (ThreadPriority > Thread1->Priority) {
Thread1->Preempted = TRUE;
Thread->State = Standby;
TargetPrcb->NextThread = Thread; 抢占的含义是赋值为NextThread!!!
KiReleaseTwoPrcbLocks(CurrentPrcb, TargetPrcb);
KiRequestDispatchInterrupt(Thread->NextProcessor);
return;
}
}
[+0x05b] Priority : 15 不可抢占!!!
1: kd> dv ThreadPriority
ThreadPriority = 0n14
不可抢占,插入DispatcherReadyListHead列表
Thread->State = Ready;
Thread->WaitTime = KiQueryLowTickCount();
if (Preempted != FALSE) {
InsertHeadList(&TargetPrcb->DispatcherReadyListHead[ThreadPriority],
&Thread->WaitListEntry);
} else {
InsertTailList(&TargetPrcb->DispatcherReadyListHead[ThreadPriority],
&Thread->WaitListEntry);
}
TargetPrcb->ReadySummary |= PRIORITY_MASK(ThreadPriority);
1: kd> dv Preempted
Preempted = 0x00 ''
[+0x928] ReadySummary : 0x0 [Type: unsigned long]
[+0x92c] SelectNextLast : 0x0 [Type: unsigned long]
[+0x930] DispatcherReadyListHead [Type: _LIST_ENTRY [32]]
[14] [Type: _LIST_ENTRY]
1: kd> dx -id 0,0,89831250 -r1 (*((basesrv!_LIST_ENTRY *)0xffdffac0))
(*((basesrv!_LIST_ENTRY *)0xffdffac0)) [Type: _LIST_ENTRY]
[+0x000] Flink : 0xffdffac0 [Type: _LIST_ENTRY *]
[+0x004] Blink : 0xffdffac0 [Type: _LIST_ENTRY *]
} else {
InsertTailList(&TargetPrcb->DispatcherReadyListHead[ThreadPriority],
&Thread->WaitListEntry);
}
1: kd> dx -id 0,0,89831250 -r1 (*((basesrv!_LIST_ENTRY *)0xffdffac0))
(*((basesrv!_LIST_ENTRY *)0xffdffac0)) [Type: _LIST_ENTRY]
[+0x000]Flink : 0x895552c8[Type: _LIST_ENTRY *]
[+0x004] Blink : 0x895552c8 [Type: _LIST_ENTRY *]
TargetPrcb->ReadySummary |= PRIORITY_MASK(ThreadPriority);
#define PRIORITY_MASK(n) (KiMask32Array[n])
1: kd> x nt!KiMask32Array
80a05eb0 nt!KiMask32Array = unsigned long []
80a05eb0 nt!KiMask32Array = unsigned long [32]
80a05eb0 nt!KiMask32Array = unsigned long []
1: kd> dx -r1 (*((ntkrnlmp!unsigned long (*)[32])0x80a05eb0))
(*((ntkrnlmp!unsigned long (*)[32])0x80a05eb0)) [Type: unsigned long [32]]
[0] : 0x1 [Type: unsigned long]
[1] : 0x2 [Type: unsigned long]
[2] : 0x4 [Type: unsigned long]
[3] : 0x8 [Type: unsigned long]
[4] : 0x10 [Type: unsigned long]
[5] : 0x20 [Type: unsigned long]
[6] : 0x40 [Type: unsigned long]
[7] : 0x80 [Type: unsigned long]
[8] : 0x100 [Type: unsigned long]
[9] : 0x200 [Type: unsigned long]
[10] : 0x400 [Type: unsigned long]
[11] : 0x800 [Type: unsigned long]
[12] : 0x1000 [Type: unsigned long]
[13] : 0x2000 [Type: unsigned long]
[14] : 0x4000 [Type: unsigned long]
100 0000 0000 0000 14个0,第14位。
1: kd> dx -id 0,0,89831250 -r1 ((basesrv!_KPRCB *)0xffdff120)
((basesrv!_KPRCB *)0xffdff120) : 0xffdff120 [Type: _KPRCB *]
[+0x000] MinorVersion : 0x1 [Type: unsigned short]
[+0x002] MajorVersion : 0x1 [Type: unsigned short]
[+0x004] CurrentThread : 0x895f2a78 [Type: _KTHREAD *]
[+0x008]NextThread : 0x0[Type: _KTHREAD *] 下一个线程为空。
[+0x928]ReadySummary : 0x4000[Type: unsigned long] 准备大概位为0x4000
[+0x92c] SelectNextLast : 0x0 [Type: unsigned long]
[+0x930] DispatcherReadyListHead [Type: _LIST_ENTRY [32]]
第二部分:g之后,1号处理器需要KiSwapThread
nt!KiSwapThread函数分析之nt!KiFindReadyThread
1: kd> g
Breakpoint 30 hit
eax=ffdff120 ebx=f7737120 ecx=00000001 edx=ffdff120 esi=00000000 edi=80a059f8
eip=80a429d8 esp=f75f6948 ebp=f75f697c iopl=0 nv up ei pl nz na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000206
nt!KiFindReadyThread:
80a429d8 55 push ebp
1: kd> kc
#
00 nt!KiFindReadyThread
01 nt!KiSwapThread
02 nt!KeWaitForMultipleObjects
03 win32k!xxxMsgWaitForMultipleObjects
04 win32k!xxxDesktopThread
05 win32k!xxxCreateSystemThreads
06 win32k!NtUserCallOneParam
07 nt!_KiSystemService
08 SharedUserData!SystemCallStub
09 winsrv!NtUserCallOneParam
1: kd> !pcr
KPCR for Processor 1 at f7737000:
1: kd> dt KPCR f7737000
basesrv!KPCR
+0x000 NtTib : _NT_TIB
+0x000 Used_ExceptionList : 0xf75f6260 _EXCEPTION_REGISTRATION_RECORD
+0x004 Used_StackBase : (null)
+0x008 PerfGlobalGroupMask : (null)
+0x00c TssCopy : 0xf7737ef0 Void
+0x010 ContextSwitches : 0x8a1e
+0x014 SetMemberCopy : 2
+0x018 Used_Self : 0x7ffd8000 Void
+0x01c SelfPcr : 0xf7737000 _KPCR
+0x020 Prcb : 0xf7737120 _KPRCB
1: kd> dx -id 0,0,89831250 -r1 ((basesrv!_KPRCB *)0xf7737120)
((basesrv!_KPRCB *)0xf7737120) : 0xf7737120 [Type: _KPRCB *]
[+0x000] MinorVersion : 0x1 [Type: unsigned short]
[+0x002] MajorVersion : 0x1 [Type: unsigned short]
[+0x004] CurrentThread : 0x89804020 [Type: _KTHREAD *]
[+0x008] NextThread : 0x0 [Type: _KTHREAD *]
[+0x928] ReadySummary : 0x0 [Type: unsigned long]
[+0x92c] SelectNextLast : 0x0 [Type: unsigned long]
[+0x930] DispatcherReadyListHead [Type: _LIST_ENTRY [32]]
[+0xa30] DeferredReadyListHead [Type: _SINGLE_LIST_ENTRY]
[+0xa34] PrcbPad72 [Type: unsigned long [11]]
[+0xa60] ChainedInterruptList : 0x0 [Type: void *]
[+0xa64] LookasideIrpFloat : 32720 [Type: long]
[+0xa68] SpareFields0 [Type: unsigned long [4]]
[+0xa78] VendorString [Type: unsigned char [13]]
[+0xa85] InitialApicId : 0x1 [Type: unsigned char]
[+0xa86] LogicalProcessorsPerPhysicalProcessor : 0x2 [Type: unsigned char]
[+0xa88] MHz : 0xe0f [Type: unsigned long]
[+0xa8c] FeatureBits : 0x33fff [Type: unsigned long]
[+0xa90] UpdateSignature : {876173328384} [Type: _LARGE_INTEGER]
[+0xa98] IsrTime : 0x0 [Type: unsigned __int64]
[+0xaa0] NpxSaveArea [Type: _FX_SAVE_AREA]
[+0xcb0] PowerState [Type: _PROCESSOR_POWER_STATE]
1: kd> kv
# ChildEBP RetAddr Args to Child
00 f75f6944 80a43dd9 f7737120 89804020 89804080 nt!KiFindReadyThread (FPO: [Non-Fpo]) (CONV: fastcall) [d:\srv03rtm\base\ntos\ke\thredsup.c @ 722]
01 f75f697c 80a358c7 00000000 e1639460 00000002 nt!KiSwapThread+0x315 (FPO: [Non-Fpo]) (CONV: fastcall) [d:\srv03rtm\base\ntos\ke\thredsup.c @ 1854]
02 f75f69b4 bf8a4685 00000003 89804b50 00000001 nt!KeWaitForMultipleObjects+0x3b5 (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\base\ntos\ke\wait.c @ 816]
03 f75f6a04 bf8b123e 00000002 89804b50 bf8fe215 win32k!xxxMsgWaitForMultipleObjects+0xeb (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\windows\core\ntuser\kernel\queue.c @ 4540]
04 f75f6d1c bf8b21ba bfa70aa0 00000001 f75f6d48 win32k!xxxDesktopThread+0x437 (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\windows\core\ntuser\kernel\desktop.c @ 594]
05 f75f6d2c bf806d52 bfa70aa0 f75f6d58 008cfff4 win32k!xxxCreateSystemThreads+0x9c (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\windows\core\ntuser\kernel\desktop.c @ 347]
06 f75f6d48 80afbcb2 00000000 00000022 80afb956 win32k!NtUserCallOneParam+0xa0 (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\windows\core\ntuser\kernel\ntstubs.c @ 4789]
07 f75f6d48 7ffe0304 00000000 00000022 80afb956 nt!_KiSystemService+0x13f (FPO: [0,3] TrapFrame @ f75f6d64) (CONV: cdecl) [d:\srv03rtm\base\ntos\ke\i386\trap.asm @ 1328]
08 008cffe0 75340774 75318a89 00000000 00000022 SharedUserData!SystemCallStub+0x4 (FPO: [0,0,0])
09 008cffe8 00000000 00000022 00000004 00000000 winsrv!NtUserCallOneParam+0xc (FPO: [Non-Fpo]) (CONV: stdcall) [d:\srv03rtm\windows\core\umode\daytona\obj\i386\usrstubs.c @ 2683]
windbg> .open -a ffffffff80a43dd9
1: kd> dx -id 0,0,89831250 -r1 ((basesrv!_KPRCB *)0xffdff120)
((basesrv!_KPRCB *)0xffdff120) : 0xffdff120 [Type: _KPRCB *]
[+0x000] MinorVersion : 0x1 [Type: unsigned short]
[+0x002] MajorVersion : 0x1 [Type: unsigned short]
[+0x004] CurrentThread : 0x895f2a78 [Type: _KTHREAD *]
[+0x008] NextThread : 0x0 [Type: _KTHREAD *]
[+0x928] ReadySummary : 0x4000 [Type: unsigned long]
[+0x92c] SelectNextLast : 0x0 [Type: unsigned long]
[+0x930] DispatcherReadyListHead [Type: _LIST_ENTRY [32]]
1: kd> dx -id 0,0,89831250 -r1 (*((basesrv!_LIST_ENTRY (*)[32])0xffdffa50))
(*((basesrv!_LIST_ENTRY (*)[32])0xffdffa50)) [Type: _LIST_ENTRY [32]]
[14] [Type: _LIST_ENTRY]
1: kd> dx -id 0,0,89831250 -r1 (*((basesrv!_LIST_ENTRY *)0xffdffac0))
(*((basesrv!_LIST_ENTRY *)0xffdffac0)) [Type: _LIST_ENTRY]
[+0x000] Flink : 0x895552c8 [Type: _LIST_ENTRY *]
[+0x004] Blink : 0x895552c8 [Type: _LIST_ENTRY *]