Archive for July, 2009

Reading Notebook: 30-July-09

Thursday, July 30th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Idle process (p. 75) - in a dump we cannot see it in the process list !process 0 0 but if we have one such idle thread running on a processor we can see it attached to System process (args to functions are omitted for clarity):

0: kd> !running

System Processors 3 (affinity mask)
  Idle Processors 2

Prcbs  Current           Next           
  0    fffff80001987680  fffffa8005844060                    ................

0: kd> ~1s

1: kd> !thread
THREAD fffffa60005f5d40  Cid 0000.0000  Teb: 0000000000000000 Win32Thread: 0000000000000000 RUNNING on processor 1
Not impersonating
DeviceMap                 fffff88000007400
Owning Process            fffff8000198d0c0       Image:         Idle
Attached Process          fffffa8003bcd0b0       Image:         System

Wait Start TickCount      0              Ticks: 34803400 (6:06:48:56.519)
Context Switch Count      271743713            
UserTime                  00:00:00.000
KernelTime                6 Days 01:31:19.718
Win32 Start Address nt!KiIdleLoop (0xfffff80001871e10)
Stack Init fffffa600171bdb0 Current fffffa600171bd40
Base fffffa600171c000 Limit fffffa6001716000 Call 0
Priority 16 BasePriority 0 PriorityDecrement 0 IoPriority 0 PagePriority 0
Child-SP          RetAddr           : Call Site
fffffa60`0171bce8 fffffa60`00d9e685 : intelppm!C1Halt+0×2
fffffa60`0171bcf0 fffff800`01882ac8 : intelppm!C1Idle+0×9
fffffa60`0171bd20 fffff800`01871e31 : nt!PoIdle+0×148
fffffa60`0171bd80 fffff800`01a405c0 : nt!KiIdleLoop+0×21
fffffa60`0171bdb0 00000000`fffffa60 : nt!zzz_AsmCodeRange_End+0×4
fffffa60`005efd00 00000000`00000000 : 0xfffffa60

Interrupt and DPC time is added to system idle time in Task Manager (p. 75) - in a kernel dump we can use !prcb command:

1: kd> !prcb
PRCB for Processor 1 at fffffa60005ec180:
Current IRQL -- 0
Threads--  Current fffffa60005f5d40 Next 0000000000000000 Idle fffffa60005f5d40
Number 1 SetMember 2
Interrupt Count -- 121fe4dc
Times — Dpc    0000029d Interrupt 0000089b
         Kernel 0205b773 User      000d5745

and we can use !whattime to convert ticks to standard time:

1: kd> !whattime 0000ce05+000026cf
62676 Ticks in Standard Time: 16:17.751s

System threads can be created in the context of any process and not just System (p. 76) - sometimes we can see nt!PspSystemThreadStartup in stack traces when we list process threads

STATUS_SYSTEM_PROCESS_TERMINATED (C000021A) (p. 79) - I remember in the past support personnel used to kill csrss.exe in order to get manual kernel or complete memory dump. 

LogonUI process and SAS (p. 79) - I was wondering where are GUI dialog threads in W2K8 winlogon.exe and they seem are gone to that separately launched process

winlogon -> userinit -> shell (p. 80) - We can use Citrix CDF traces to learn about process launch sequence in Citrix terminal service environments: http://www.dumpanalysis.org/blog/index.php/2008/03/31/cdf-traces-analyzing-process-launch-sequence/ 

3 names of window services (p. 81) - In order to dump terminal service we need its PID. Here is the article: http://support.citrix.com/article/ctx106035

Many to one mapping: service - process (pp. 82 - 83) - I noticed that the number of ADVAPI32!ScSvcctrlThreadA(W) threads corresponds to the number of services in a service host process. 

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 28-July-09

Tuesday, July 28th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

APIC implies SMP (p. 65)

Use of drivers to access DDK functions not having Windows API counterpart (p. 69)

WDM vs. Legacy (p. 69) - I think that for non-hardware drivers to do some software function in kernel mode / space legacy model is sufficient

Use of filter drivers to fix hardware problems (p. 69)

UMDF driver as a service that communicates via ALPC to a kernel hardware wrapper (p. 70) - I’m still reading this book about KMDF and UMDF:  Developing Drivers with the Windows Driver Foundation. However I disagree that COM and C++ lower the barrier to write drivers. I remember that someone said (probably Kraig Brockschmidt) that it takes 6 month to understand COM for a Windows API programmer. Simple C is sufficient to grasp device driver concepts. I plan to prove that in the book Windows Device Drivers: Practical Foundations (ISBN: 978-0955832840). 

Zw (no parameter validation) vs. Nt (p. 73) - here is another look at their difference: http://www.dumpanalysis.org/blog/index.php/2007/04/10/yet-another-look-at-zw-and-nt-functions/

Idle pseudo-process threads do CPU accounting (p. 74)

Process Monitor boot trace (p. 74)

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 24-July-09

Friday, July 24th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Windows subsystem components (p. 54) - Never attach WinDbg to your session csrss.exe. Your session will freeze (input and graphics). However you can attach noninvasively to session 0 (non-interactive) on Vista and W2K8. You won’t be able to contact MS symbol server because Internet connections are not allowed in that session so prepare your symbols before. Also, once you invoke a secure desktop, it will freeze too, so be careful and detach as soon as possible. Here is the list thread stacks that give a picture of component relationships: 

0:000> ~*kc

.  0  Id: 1e4.1f4 Suspend: 1 Teb: 000007ff`fffdb000 Unfrozen
Call Site
ntdll!NtRequestWaitReplyPort
winsrv
ntdll!RtlUserThreadStart

   1  Id: 1e4.1f8 Suspend: 1 Teb: 000007ff`fffd9000 Unfrozen
Call Site
ntdll!ZwWaitForMultipleObjects
winsrv
ntdll!RtlUserThreadStart

   2  Id: 1e4.1fc Suspend: 1 Teb: 000007ff`fffd7000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
CSRSRV!CsrReplyToMessage
ntdll!RtlUserThreadStart

   3  Id: 1e4.200 Suspend: 1 Teb: 000007ff`fffd5000 Unfrozen
Call Site
ntdll!NtReplyWaitReceivePort
CSRSRV!CsrUnhandledExceptionFilter
ntdll!RtlUserThreadStart

   4  Id: 1e4.220 Suspend: 1 Teb: 000007ff`fffdd000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
CSRSRV!CsrReplyToMessage
ntdll!RtlUserThreadStart

   5  Id: 1e4.23c Suspend: 1 Teb: 000007ff`fffd3000 Unfrozen
Call Site
winsrv
winsrv
ntdll!RtlUserThreadStart

   6  Id: 1e4.240 Suspend: 1 Teb: 000007ff`fffae000 Unfrozen
Call Site
winsrv
winsrv
ntdll!RtlUserThreadStart

   7  Id: 1e4.280 Suspend: 1 Teb: 000007ff`fffac000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
CSRSRV!CsrReplyToMessage
ntdll!RtlUserThreadStart

   8  Id: 1e4.284 Suspend: 1 Teb: 000007ff`fffaa000 Unfrozen
Call Site
winsrv
winsrv
ntdll!RtlUserThreadStart

   9  Id: 1e4.288 Suspend: 1 Teb: 000007ff`fffa8000 Unfrozen
Call Site
USER32!ZwUserGetMessage
USER32!GetMessageW
winsrv
ntdll!RtlUserThreadStart

  10  Id: 1e4.848 Suspend: 1 Teb: 000007ff`fffa6000 Unfrozen
Call Site
USER32!ZwUserGetMessage
USER32!GetMessageW
winsrv
ntdll!RtlUserThreadStart

  11  Id: 1e4.b80 Suspend: 1 Teb: 000007ff`fffa4000 Unfrozen
Call Site
USER32!ZwUserGetMessage
USER32!GetMessageW
winsrv
ntdll!RtlUserThreadStart

USER and GDI functions (pp. 54 - 55) - Long time ago I created a UML component diagram depicting component dependencies extracted from stack traces: http://www.dumpanalysis.org/blog/index.php/2006/10/24/reverse-engineering-citrix-thinwire/ 

fork function (p. 56) - Windows NT/2000 Native API Reference book has a section that sketches its implementation using native API

SUA provides mixed-mode support (we can call POSIX along with Windows API) (pp. 56 - 57) - Seems there are also Windows Server 2003 R2 UNIX interoperability components and seems it is also called SUA for W2K3 R2. This is the link for Windows Server 2008: http://technet.microsoft.com/en-us/library/cc771672.aspx

ntdll.dll functions (pp. 57 - 58) - we can list all functions by attaching WinDbg to a process and run this command: x ntdll!*. Some API is explained in Windows NT/2000 Native API Reference book but of course more was added since W2K

Executive / kernel bipartition of ntoskrnl.exe (pp. 58 - 65) - we can list functions in any kernel memory dump by this WinDbg command: x nt!*

ALPC (p. 60) - seems it replaces LPC on Vista and W2K8. See also http://www.dumpanalysis.org/blog/index.php/2009/03/20/advanced-local-procedure-call-windbg-extension/ 

TxR and TxF, transactional registry and NTFS (p. 60)

Diagnostic Infrastructure (p. 61) - more here: http://technet.microsoft.com/en-us/library/cc774650(WS.10).aspx

Hardware Error Architecture (p. 62) - I found this WHEA presentation: http://download.microsoft.com/download/9/8/f/98f3fe47-dfc3-4e74-92a3-088782200fe7/TWAR05008_WinHEC05.ppt

Executive object encapsulates kernel objects and adds policies like security and handles (p. 61)

x86 / x64 access to KPCR: [FS] / [GS] (p. 62) - here is how to see _KPCR and _KPRCB manually using base WinDbg commands:

0: kd> dt _KPCR
nt!_KPCR
   +0x000 NtTib            : _NT_TIB
   +0x000 GdtBase          : Ptr64 _KGDTENTRY64
   +0x008 TssBase          : Ptr64 _KTSS64
   +0x010 UserRsp          : Uint8B
   +0×018 Self             : Ptr64 _KPCR
   +0×020 CurrentPrcb      : Ptr64 _KPRCB
   +0×028 LockArray        : Ptr64 _KSPIN_LOCK_QUEUE
   +0×030 Used_Self        : Ptr64 Void
   +0×038 IdtBase          : Ptr64 _KIDTENTRY64
   +0×040 Unused           : [2] Uint8B
   +0×050 Irql             : UChar
   +0×051 SecondLevelCacheAssociativity : UChar
   +0×052 ObsoleteNumber   : UChar
   +0×053 Fill0            : UChar
   +0×054 Unused0          : [3] Uint4B
   +0×060 MajorVersion     : Uint2B
   +0×062 MinorVersion     : Uint2B
   +0×064 StallScaleFactor : Uint4B
   +0×068 Unused1          : [3] Ptr64 Void
   +0×080 KernelReserved   : [15] Uint4B
   +0×0bc SecondLevelCacheSize : Uint4B
   +0×0c0 HalReserved      : [16] Uint4B
   +0×100 Unused2          : Uint4B
   +0×108 KdVersionBlock   : Ptr64 Void
   +0×110 Unused3          : Ptr64 Void
   +0×118 PcrAlign1        : [24] Uint4B
   +0×180 Prcb             : _KPRCB

0: kd> dq gs:0+18 l1
002b:00000000`00000018  fffff800`01987500

0: kd> dt _KPCR fffff800`01987500
nt!_KPCR
   +0x000 NtTib            : _NT_TIB
   +0x000 GdtBase          : 0xfffff800`03e77000 _KGDTENTRY64
   +0x008 TssBase          : 0xfffff800`03e78070 _KTSS64
   +0x010 UserRsp          : 0x12f5c8
   +0x018 Self             : 0xfffff800`01987500 _KPCR
   +0x020 CurrentPrcb      : 0xfffff800`01987680 _KPRCB
   +0x028 LockArray        : 0xfffff800`01987cf0 _KSPIN_LOCK_QUEUE
   +0x030 Used_Self        : 0x000007ff`fffde000
   +0x038 IdtBase          : 0xfffff800`03e77070 _KIDTENTRY64
   +0x040 Unused           : [2] 0
   +0x050 Irql             : 0 ''
   +0x051 SecondLevelCacheAssociativity : 0x8 ''
   +0x052 ObsoleteNumber   : 0 ''
   +0x053 Fill0            : 0 ''
   +0x054 Unused0          : [3] 0
   +0x060 MajorVersion     : 1
   +0x062 MinorVersion     : 1
   +0x064 StallScaleFactor : 0x702
   +0x068 Unused1          : [3] (null)
   +0x080 KernelReserved   : [15] 0
   +0x0bc SecondLevelCacheSize : 0x200000
   +0x0c0 HalReserved      : [16] 0x6af178d0
   +0x100 Unused2          : 0
   +0x108 KdVersionBlock   : (null)
   +0x110 Unused3          : (null)
   +0x118 PcrAlign1        : [24] 0
   +0x180 Prcb             : _KPRCB

0: kd> dt _KPRCB fffff800`01987500+180
nt!_KPRCB
   +0×000 MxCsr            : 0×1f80
   +0×004 Number           : 0
   +0×006 InterruptRequest : 0 ”
   +0×007 IdleHalt         : 0 ”
   +0×008 CurrentThread    : 0xfffffa80`05844060 _KTHREAD
   +0×010 NextThread       : (null)
   +0×018 IdleThread       : 0xfffff800`0198cb80 _KTHREAD
   +0×020 NestingLevel     : 0 ”
   +0×021 Group            : 0 ”
   +0×022 PrcbPad00        : [6]  “”
   +0×028 RspBase          : 0xfffffa60`05435db0
   +0×030 PrcbLock         : 0
   +0×038 SetMember        : 1
   +0×040 ProcessorState   : _KPROCESSOR_STATE
   +0×5f0 CpuType          : 6 ”
   +0×5f1 CpuID            : 1 ”
   +0×5f2 CpuStep          : 0xf02
   +0×5f2 CpuStepping      : 0×2 ”
   +0×5f3 CpuModel         : 0xf ”
   +0×5f4 MHz              : 0×702
   +0×5f8 HalReserved      : [8] 0
   +0×638 MinorVersion     : 1
   +0×63a MajorVersion     : 1
   +0×63c BuildType        : 0 ”
   +0×63d CpuVendor        : 0×2 ”
   +0×63e CoresPerPhysicalProcessor : 0×2 ”
   +0×63f LogicalProcessorsPerCore : 0×1 ”
   +0×640 ApicMask         : 0xfffffffe
   +0×644 CFlushSize       : 0×40
   +0×648 AcpiReserved     : (null)
   +0×650 InitialApicId    : 0
   +0×654 Stride           : 2
   +0×658 PrcbPad01        : [3] 0
   +0×670 LockQueue        : [49] _KSPIN_LOCK_QUEUE
   +0×980 PPLookasideList  : [16] _PP_LOOKASIDE_LIST
   +0xa80 PPNPagedLookasideList : [32] _GENERAL_LOOKASIDE_POOL
   +0×1680 PPPagedLookasideList : [32] _GENERAL_LOOKASIDE_POOL
   +0×2280 PacketBarrier    : 0
   +0×2288 DeferredReadyListHead : _SINGLE_LIST_ENTRY
   +0×2290 MmPageFaultCount : 104442883
   +0×2294 MmCopyOnWriteCount : 79492
   +0×2298 MmTransitionCount : 7930741
   +0×229c MmDemandZeroCount : 37175835
   +0×22a0 MmPageReadCount  : 30484924
   +0×22a4 MmPageReadIoCount : 1842657
   +0×22a8 MmDirtyPagesWriteCount : 69757
   +0×22ac MmDirtyWriteIoCount : 291
   +0×22b0 MmMappedPagesWriteCount : 92208
   +0×22b4 MmMappedWriteIoCount : 778
   +0×22b8 KeSystemCalls    : 0×7ef91c13
   +0×22bc KeContextSwitches : 0×407f5553
   +0×22c0 CcFastReadNoWait : 0
   +0×22c4 CcFastReadWait   : 0×17da4d
   +0×22c8 CcFastReadNotPossible : 0
   +0×22cc CcCopyReadNoWait : 0×171
   +0×22d0 CcCopyReadWait   : 0×187402
   +0×22d4 CcCopyReadNoWaitMiss : 0×12
   +0×22d8 LookasideIrpFloat : 916
   +0×22dc IoReadOperationCount : 3898535
   +0×22e0 IoWriteOperationCount : 1424180
   +0×22e4 IoOtherOperationCount : 10511442
   +0×22e8 IoReadTransferCount : _LARGE_INTEGER 0×2a`779e962f
   +0×22f0 IoWriteTransferCount : _LARGE_INTEGER 0xe`d374c96a
   +0×22f8 IoOtherTransferCount : _LARGE_INTEGER 0×2`bccbbfe4
   +0×2300 TargetSet        : 0
   +0×2308 IpiFrozen        : 0
   +0×230c PrcbPad3         : [116]  “”
   +0×2380 RequestMailbox   : [64] _REQUEST_MAILBOX
   +0×3380 SenderSummary    : 0
   +0×3388 PrcbPad4         : [120]  “”
   +0×3400 DpcData          : [2] _KDPC_DATA
   +0×3440 DpcStack         : 0xfffff800`03e84fb0
   +0×3448 SparePtr0        : (null)
   +0×3450 MaximumDpcQueueDepth : 4
   +0×3454 DpcRequestRate   : 1
   +0×3458 MinimumDpcRate   : 3
   +0×345c DpcInterruptRequested : 0 ”
   +0×345d DpcThreadRequested : 0 ”
   +0×345e DpcRoutineActive : 0 ”
   +0×345f DpcThreadActive  : 0 ”
   +0×3460 TimerHand        : 0
   +0×3460 TimerRequest     : 0
   +0×3468 TickOffset       : 48366
   +0×346c MasterOffset     : 48366
   +0×3470 DpcLastCount     : 0×3487538
   +0×3474 ThreadDpcEnable  : 0×1 ”
   +0×3475 QuantumEnd       : 0 ”
   +0×3476 PrcbPad50        : 0 ”
   +0×3477 IdleSchedule     : 0 ”
   +0×3478 DpcSetEventRequest : 0
   +0×347c KeExceptionDispatchCount : 0×1e44d8
   +0×3480 DpcEvent         : _KEVENT
   +0×3498 PrcbPad51        : (null)
   +0×34a0 CallDpc          : _KDPC
   +0×34e0 ClockKeepAlive   : 2
   +0×34e4 ClockCheckSlot   : 0×1 ”
   +0×34e5 ClockPollCycle   : 0×8 ”
   +0×34e6 PrcbPad6         : [2]  “”
   +0×34e8 DpcWatchdogPeriod : 1924
   +0×34ec DpcWatchdogCount : 1767
   +0×34f0 PrcbPad70        : [2] 0
   +0×3500 WaitListHead     : _LIST_ENTRY [ 0xfffffa80`04e9fc48 - 0xfffffa80`03bfc0d8 ]
   +0×3510 WaitLock         : 0
   +0×3518 ReadySummary     : 0
   +0×351c QueueIndex       : 1
   +0×3520 PrcbPad71        : [12] 0
   +0×3580 DispatcherReadyListHead : [32] _LIST_ENTRY [ 0xfffff800`0198ac00 - 0xfffff800`0198ac00 ]
   +0×3780 InterruptCount   : 0×127a01d4
   +0×3784 KernelTime       : 0×20af69a
   +0×3788 UserTime         : 0×8182f
   +0×378c DpcTime          : 0xce05
   +0×3790 InterruptTime    : 0×26cf
   +0×3794 AdjustDpcThreshold : 5
   +0×3798 SkipTick         : 0 ”
   +0×3799 DebuggerSavedIRQL : 0×2 ”
   +0×379a PollSlot         : 0 ”
   +0×379b PrcbPad80        : [5]  “”
   +0×37a0 DpcTimeCount     : 0
   +0×37a4 DpcTimeLimit     : 0×282
   +0×37a8 PeriodicCount    : 0
   +0×37ac PeriodicBias     : 0
   +0×37b0 PrcbPad81        : [2] 0
   +0×37c0 ParentNode       : 0xfffff800`0198b640 _KNODE
   +0×37c8 MultiThreadProcessorSet : 3
   +0×37d0 MultiThreadSetMaster : 0xfffff800`01987680 _KPRCB
   +0×37d8 StartCycles      : 0×375f7`ea78a322
   +0×37e0 MmSpinLockOrdering : 0
   +0×37e4 PageColor        : 0×7064
   +0×37e8 NodeColor        : 0
   +0×37ec NodeShiftedColor : 0
   +0×37f0 SecondaryColorMask : 0×3f
   +0×37f4 Sleeping         : 1
   +0×37f8 CycleTime        : 0×4f0`4392cb00
   +0×3800 CcFastMdlReadNoWait : 0
   +0×3804 CcFastMdlReadWait : 0
   +0×3808 CcFastMdlReadNotPossible : 0
   +0×380c CcMapDataNoWait  : 0
   +0×3810 CcMapDataWait    : 0×8e0ad8
   +0×3814 CcPinMappedDataCount : 0×1523da
   +0×3818 CcPinReadNoWait  : 0
   +0×381c CcPinReadWait    : 0xddb5c
   +0×3820 CcMdlReadNoWait  : 0
   +0×3824 CcMdlReadWait    : 0×98e
   +0×3828 CcLazyWriteHotSpots : 0×464
   +0×382c CcLazyWriteIos   : 0×2e39b
   +0×3830 CcLazyWritePages : 0×561520
   +0×3834 CcDataFlushes    : 0×70b8c
   +0×3838 CcDataPages      : 0xc0c0e0
   +0×383c CcLostDelayedWrites : 0
   +0×3840 CcFastReadResourceMiss : 0
   +0×3844 CcCopyReadWaitMiss : 0×12f3a0d
   +0×3848 CcFastMdlReadResourceMiss : 0
   +0×384c CcMapDataNoWaitMiss : 0
   +0×3850 CcMapDataWaitMiss : 0×69bc
   +0×3854 CcPinReadNoWaitMiss : 0×7dfb0
   +0×3858 CcPinReadWaitMiss : 0×1796
   +0×385c CcMdlReadNoWaitMiss : 0
   +0×3860 CcMdlReadWaitMiss : 0
   +0×3864 CcReadAheadIos   : 0×8e7589
   +0×3868 MmCacheTransitionCount : 0
   +0×386c MmCacheReadCount : 0
   +0×3870 MmCacheIoCount   : 0
   +0×3874 PrcbPad91        : [3] 0
   +0×3880 PowerState       : _PROCESSOR_POWER_STATE
   +0×3998 KeAlignmentFixupCount : 0
   +0×399c VendorString     : [13]  “GenuineIntel”
   +0×39a9 PrcbPad10        : [3]  “”
   +0×39ac FeatureBits      : 0×20193ffe
   +0×39b0 UpdateSignature  : _LARGE_INTEGER 0×56`00000000
   +0×39b8 DpcWatchdogDpc   : _KDPC
   +0×39f8 DpcWatchdogTimer : _KTIMER
   +0×3a38 Cache            : [5] _CACHE_DESCRIPTOR
   +0×3a74 CacheCount       : 3
   +0×3a78 CachedCommit     : 0×65
   +0×3a7c CachedResidentAvailable : 0×1a
   +0×3a80 HyperPte         : 0xfffffa60`00400027
   +0×3a88 WheaInfo         : 0xfffffa80`03d63b30
   +0×3a90 EtwSupport       : 0xfffffa80`03bbf290
   +0×3aa0 InterruptObjectPool : _SLIST_HEADER
   +0×3ab0 HypercallPageList : _SLIST_HEADER
   +0×3ac0 HypercallPageVirtual : (null)
   +0×3ac8 VirtualApicAssist : (null)
   +0×3ad0 StatisticsPage   : (null)
   +0×3ad8 RateControl      : 0xfffffa80`03fb0420
   +0×3ae0 CacheProcessorMask : [5] 1
   +0×3b08 PackageProcessorSet : 3
   +0×3b10 CoreProcessorSet : 1

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 21-July-09

Tuesday, July 21st, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

W2K3, per-CPU scheduling queues (p. 43)

MmProductType (p. 45) - we can query the value from the dump, 1 is for server version:

3: kd> dd MmProductType l1
808a8d00  00000001

ASSERT (p. 48) - disassembly of the function in W2K8 shows this collapsed sequence (conditional flow is ignored):

0: kd> uf nt!RtlAssert
nt!RtlAssert:
call    nt!RtlCaptureContext
call    nt!DbgPrintEx
call    nt!DbgPrompt
call    nt!ZwTerminateThread
call    nt!ZwTerminateProcess
call    nt!DbgPrintEx
call    nt!DbgBreakPoint
call    nt!DbgBreakPoint
call    nt!ZwTerminateProcess

Key system components (pp. 49 - 50) - I found it useful to look at thread stack traces from complete memory dumps to see the big picture of component relationships, for example, message loop:

kd> kc
nt!KiSwapContext
nt!KiSwapThread
nt!KeWaitForSingleObject
win32k!xxxSleepThread
win32k!xxxRealInternalGetMessage
win32k!NtUserGetMessage
nt!KiFastCallEntry
ntdll!KiFastSystemCallRet
USER32!NtUserGetMessage
USER32!GetMessageW
Application!WinMain
kernel32!BaseProcessStart

Some functions implemented in subsystem dlls (p. 53) - for example:

kd> uf GetCurrentProcess
kernel32!GetCurrentProcess:
77e62f9d or      eax,0FFFFFFFFh
77e62fa0 ret

kd> uf GetCurrentProcessId
kernel32!GetCurrentProcessId:
77e63c78 mov     eax,dword ptr fs:[00000018h]
77e63c7e mov     eax,dword ptr [eax+20h]
77e63c81 ret

kd> uf GetCurrentThread
kernel32!GetCurrentThread:
77e63868 push    0FFFFFFFEh
77e6386a pop     eax
77e6386b ret

kd> uf GetCurrentThreadId
kernel32!GetCurrentThreadId:
77e62fc7 mov     eax,dword ptr fs:[00000018h]
77e62fcd mov     eax,dword ptr [eax+24h]
77e62fd0 ret

Subsystem functions that require client-server call (p. 53) - collapsed disassembly example:

kd> uf CreateThread
call    kernel32!CreateRemoteThread

kd> uf kernel32!CreateRemoteThread
call    dword ptr [kernel32!_imp__CsrClientCallServer (77e41034)]

kd> dds 77e41034 l1
77e41034  7c82ebf3 ntdll!CsrClientCallServer

kd> uf ntdll!CsrClientCallServer
call    ntdll!NtRequestWaitReplyPort

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 20-July-09

Monday, July 20th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Simplified system architecture (p. 36) - I personally prefer space than mode partitioning or indicate both: http://www.dumpanalysis.org/blog/index.php/2009/07/17/on-space-and-mode/ and show user space at the bottom to highlight lower virtual addresses. Here is one example, UML component diagram for SystemDump tool: http://www.dumpanalysis.org/blog/index.php/2006/09/12/new-systemdump-tool/. More examples are in the forthcoming book Windows Device Drivers: Practical Foundations

Support processes (p. 36) - winlogon.exe process also uses subsystem DLLs:

0:000> ~*kc

.  0  Id: 23c.240 Suspend: 1 Teb: 000007ff`fffdc000 Unfrozen
Call Site
ntdll!ZwWaitForSingleObject
kernel32!WaitForSingleObjectEx
winlogon!StateMachineRun
winlogon!WinMain
winlogon!ConvertSidToStringSidW
kernel32!BaseThreadInitThunk
ntdll!RtlUserThreadStart

   1  Id: 23c.3c4 Suspend: 1 Teb: 000007ff`fffd4000 Unfrozen
Call Site
ntdll!ZwWaitForMultipleObjects
ntdll!TppWaiterpThread
kernel32!BaseThreadInitThunk
ntdll!RtlUserThreadStart

   2  Id: 23c.1190 Suspend: 1 Teb: 000007ff`fffda000 Unfrozen
Call Site
ntdll!NtRemoveIoCompletion
kernel32!GetQueuedCompletionStatus
RPCRT4!COMMON_ProcessCalls
RPCRT4!LOADABLE_TRANSPORT::ProcessIOEvents
RPCRT4!ProcessIOEventsWrapper
RPCRT4!BaseCachedThreadRoutine
RPCRT4!ThreadStartRoutine
kernel32!BaseThreadInitThunk
ntdll!RtlUserThreadStart

session manager smss.exe doesn’t indeed:

0:000> ~*kc

.  0  Id: 1a0.1a4 Suspend: 1 Teb: 000007ff`fffde000 Unfrozen
Call Site
ntdll!ZwWaitForMultipleObjects
smss!wmain
smss!NtProcessStartupW_AfterSecurityCookieInitialized
ntdll!RtlUserThreadStart

   1  Id: 1a0.1d4 Suspend: 1 Teb: 000007ff`fffdc000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
smss!SmpApiLoop
smss!SmpCreateInitialSession
ntdll!RtlUserThreadStart

   2  Id: 1a0.1e0 Suspend: 1 Teb: 000007ff`fffda000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
smss!SmpApiLoop
ntdll!RtlUserThreadStart

   3  Id: 1a0.204 Suspend: 1 Teb: 000007ff`fffd8000 Unfrozen
Call Site
ntdll!ZwAlpcSendWaitReceivePort
smss!SmpApiLoop
smss!SmpCreateInitialSession
ntdll!RtlUserThreadStart

SUA: Subsystem for Unix-based Applications (p. 36)

HAL isolation of platform specifics (i.e. motherboard diffs) (p. 37)

Hyperthreading: scheduling algorithms favour idle physical processor vs. idle logical (p. 40)

NUMA: scheduling and memory allocs preference for the same node (p. 40)

64 processors support for x64 (p. 40)

PAE kernel for most x86 systems due to NX/XD no-execute memory support (p. 41)

Uniprocessor backward compatibility field - could be interesting troubleshooting advise 

Checking system version (pp. 41 - 42) - there is another method. Attach WinDbg noninvasively to any process and run version command:

0:000> version
Windows Server 2008/Windows Vista Version 6002 (Service Pack 2) MP (2 procs) Free x64
Product: Server, suite: Enterprise TerminalServer SingleUserTS
kernel32.dll version: 6.0.6001.18000 (longhorn_rtm.080118-1840)

Machine Name:
Debug session time: Mon Jul 20 17:57:34.819 2009 (GMT+1)
System Uptime: 5 days 9:27:00.143
Process Uptime: 0 days 2:42:42.846
  Kernel time: 0 days 0:00:00.000
  User time: 0 days 0:00:00.000
Live user mode: <Local>

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 17-July-09

Friday, July 17th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Windows objects (incl. desktop, menu, window) vs. native Windows objects (p. 23)

Unicode and ANSI entry points (pp. 23 - 24) - example from a dump file:

0: kd> x kernel32!*
[...]
77e64849 kernel32!CreateFileW = <no type information>
[...]
77e41a63 kernel32!CreateFileA = <no type information>
[...]

0: kd> .asm no_code_bytes
Assembly options: no_code_bytes

0: kd> uf kernel32!CreateFileA
kernel32!CreateFileA:
77e41a63 mov     edi,edi
77e41a65 push    ebp
77e41a66 mov     ebp,esp
77e41a68 push    dword ptr [ebp+8]
77e41a6b call    kernel32!Basep8BitStringToStaticUnicodeString (77e64c27)
77e41a70 test    eax,eax
77e41a72 je      kernel32!CreateFileA+0x11 (77e41a92)

kernel32!CreateFileA+0x16:
77e41a74 push    dword ptr [ebp+20h]
77e41a77 push    dword ptr [ebp+1Ch]
77e41a7a push    dword ptr [ebp+18h]
77e41a7d push    dword ptr [ebp+14h]
77e41a80 push    dword ptr [ebp+10h]
77e41a83 push    dword ptr [ebp+0Ch]
77e41a86 push    dword ptr [eax+4]
77e41a89 call    kernel32!CreateFileW (77e64849)

kernel32!CreateFileA+0x30:
77e41a8e pop     ebp
77e41a8f ret     1Ch

kernel32!CreateFileA+0x11:
77e41a92 or      eax,0FFFFFFFFh
77e41a95 jmp     kernel32!CreateFileA+0x30 (77e41a8e)

Average CPU usage and Disk per-file I/O columns in Resource Monitor (p. 25)

Detecting background network activity in RM (p. 26)

Kernel debugging setup (pp. 26 - 31) - an alternative for study is to use kernel and complete memory dump files

Syser Debugger (www.sysersoft.com) - I give a try later (never used)

Symbols (pp. 26 - 27) - quick download links and symbol paths (including Citrix symbol server) are on www.windbg.org. If you don’t have correct symbols you might get these errors:

****************************************************************************
* Symbol loading may be unreliable without a symbol search path.           *
* Use .symfix to have the debugger choose a symbol path.                   *
* After setting your symbol path, use .reload to refresh symbol locations. *
****************************************************************************

*** ERROR: Symbol file could not be found.  Defaulted to export symbols for C:\Windows\system32\ntdll.dll -

*** ERROR: Symbol file could not be found.  Defaulted to export symbols for C:\Windows\system32\USER32.dll -

Invasive debugging - DebugActiveProcess / Noninvasive - OpenProcess (p. 27)

Live debugging (p. 28) - we can also use XenServer for it. You can also learn debugging basics from my book Windows Debugging: Practical Foundations

Inconsistency of dumps generated by LiveKd (pp. 30 - 31) - nevertheless I found it useful to list all processes and threads via !process 0 ff command and search for patterns like LPC wait chains and various anomalies from normal stack traces

Windows Driver Kit (pp. 31 - 32) - additional resources like books can be found in my post Moving to kernel space (updated references). I plan to add a few books there soon.

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 16-July-09

Thursday, July 16th, 2009

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Two stacks per thread (p. 12) - We can see different stack addresses in any thread from a complete memory dump that starts in user space and was caught up in kernel space:

1: kd> !thread 89025970 1f
THREAD 89025970  Cid 14f8.1518  Teb: 7ffd8000 Win32Thread: 00000000 WAIT: (Unknown) UserMode Non-Alertable
    8902abb8  QueueObject
    890259e8  NotificationTimer
Not impersonating
DeviceMap                 e155cbf8
Owning Process            89030d88       Image:         dllhost.exe
Attached Process          N/A            Image:         N/A
Wait Start TickCount      1795450        Ticks: 108 (0:00:00:01.687)
Context Switch Count      769            
UserTime                  00:00:00.046
KernelTime                00:00:00.000
Win32 Start Address ntdll!RtlpWorkerThread (0x7c959f2b)
Start Address kernel32!BaseThreadStartThunk (0x7c8217ec)
Stack Init b6047000 Current b6046c38 Base b6047000 Limit b6044000 Call 0
Priority 8 BasePriority 8 PriorityDecrement 0
ChildEBP RetAddr 
b6046c50 80833e95 nt!KiSwapContext+0×26
b6046c7c 8082b72b nt!KiSwapThread+0×2e5
b6046cc4 808ef652 nt!KeRemoveQueue+0×417
b6046d48 8088b19c nt!NtRemoveIoCompletion+0xdc
b6046d48 7c94860c nt!KiFastCallEntry+0xfc
00bfff70 7c9477f9 ntdll!KiFastSystemCallRet
00bfff74 7c959f68 ntdll!NtRemoveIoCompletion+0xc
00bfffb8 7c82482f ntdll!RtlpWorkerThread+0×3d
00bfffec 00000000 kernel32!BaseThreadStart+0×34

We can get kernel raw stack range from this !thread (in magenta above) and get user space raw stack range from !teb command after we switch to our process context and make the thread current:

1: kd> .process /r /p 89030d88
Implicit process is now 89030d88

1: kd> .thread 89025970
Implicit thread is now 89025970

1: kd> !teb
TEB at 7ffd8000
    ExceptionList:        00bfffdc
    StackBase:            00c00000
    StackLimit:           00bf9000

    SubSystemTib:         00000000
    FiberData:            00001e00
    ArbitraryUserPointer: 00000000
    Self:                 7ffd8000
    EnvironmentPointer:   00000000
    ClientId:             000014f8 . 00001518
    RpcHandle:            00000000
    Tls Storage:          00000000
    PEB Address:          7ffd4000
    LastErrorValue:       1008
    LastStatusValue:      0
    Count Owned Locks:    0
    HardErrorMode:        0

Thread local storage (p. 12) - !tls WinDbg command:

1: kd> !tls
Usage:
tls <slot> [teb]
  slot:  -1 to dump all allocated slots
         {0-0n1088} to dump specific slot
  teb:   <empty> for current thread
         0 for all threads in this process
         <teb address> (not threadid) to dump for specific thread.

1: kd> !tls -1
TLS slots on thread: 14f8.1518
0x0000 : 00000000
0x0001 : 00000000
0x0002 : 00000000
0x0003 : 00000000
0x0004 : 00000000
0x0005 : 00000000
0x0006 : 00000000
0x0007 : 00000000
0x0008 : 00000000
0x0009 : 00000000
0x000a : 00000000
0x000b : 00000000
0x000c : 00000000
0x000d : 00000000
0x000e : 00000000
0x000f : 00000000
0x0010 : 00000000
0x0011 : 00000000
0x0012 : 00000000
0x0040 : 00000000

Thread ID (p. 12) - examples of TID member of CID from a user dump and a kernel dump:

0:000> ~*kc

.  0  Id: 1350.1354 Suspend: 1 Teb: 000007ff`fffde000 Unfrozen
Call Site
USER32!GetWindowLongPtrW
USER32!GetMessageW
notepad
notepad
kernel32!BaseThreadInitThunk
ntdll!RtlUserThreadStart

1: kd> !thread fffffa8001cc7bb0
THREAD fffffa8001cc7bb0  Cid 13e4.01dc  Teb: 000000007efdb000 Win32Thread: fffff900c210ed50 WAIT: (WrLpcReply) UserMode Non-Alertable

See also PID -TID space graph from one memory dump: Memory Dump Analysis using Excel

Thread context (p. 12) - It is quite large structure. This is x64 context, for example:

0:000> dt _CONTEXT
ntdll!_CONTEXT
   +0x000 P1Home           : Uint8B
   +0x008 P2Home           : Uint8B
   +0x010 P3Home           : Uint8B
   +0x018 P4Home           : Uint8B
   +0x020 P5Home           : Uint8B
   +0x028 P6Home           : Uint8B
   +0x030 ContextFlags     : Uint4B
   +0x034 MxCsr            : Uint4B
   +0x038 SegCs            : Uint2B
   +0x03a SegDs            : Uint2B
   +0x03c SegEs            : Uint2B
   +0x03e SegFs            : Uint2B
   +0x040 SegGs            : Uint2B
   +0x042 SegSs            : Uint2B
   +0x044 EFlags           : Uint4B
   +0x048 Dr0              : Uint8B
   +0x050 Dr1              : Uint8B
   +0x058 Dr2              : Uint8B
   +0x060 Dr3              : Uint8B
   +0x068 Dr6              : Uint8B
   +0x070 Dr7              : Uint8B
   +0x078 Rax              : Uint8B
   +0x080 Rcx              : Uint8B
   +0x088 Rdx              : Uint8B
   +0x090 Rbx              : Uint8B
   +0x098 Rsp              : Uint8B
   +0x0a0 Rbp              : Uint8B
   +0x0a8 Rsi              : Uint8B
   +0x0b0 Rdi              : Uint8B
   +0x0b8 R8               : Uint8B
   +0x0c0 R9               : Uint8B
   +0x0c8 R10              : Uint8B
   +0x0d0 R11              : Uint8B
   +0x0d8 R12              : Uint8B
   +0x0e0 R13              : Uint8B
   +0x0e8 R14              : Uint8B
   +0x0f0 R15              : Uint8B
   +0x0f8 Rip              : Uint8B
   +0x100 FltSave          : _XMM_SAVE_AREA32
   +0x100 Header           : [2] _M128A
   +0x120 Legacy           : [8] _M128A
   +0x1a0 Xmm0             : _M128A
   +0x1b0 Xmm1             : _M128A
   +0x1c0 Xmm2             : _M128A
   +0x1d0 Xmm3             : _M128A
   +0x1e0 Xmm4             : _M128A
   +0x1f0 Xmm5             : _M128A
   +0x200 Xmm6             : _M128A
   +0x210 Xmm7             : _M128A
   +0x220 Xmm8             : _M128A
   +0x230 Xmm9             : _M128A
   +0x240 Xmm10            : _M128A
   +0x250 Xmm11            : _M128A
   +0x260 Xmm12            : _M128A
   +0x270 Xmm13            : _M128A
   +0x280 Xmm14            : _M128A
   +0x290 Xmm15            : _M128A
   +0x300 VectorRegister   : [26] _M128A
   +0x4a0 VectorControl    : Uint8B
   +0x4a8 DebugControl     : Uint8B
   +0x4b0 LastBranchToRip  : Uint8B
   +0x4b8 LastBranchFromRip : Uint8B
   +0x4c0 LastExceptionToRip : Uint8B
   +0x4c8 LastExceptionFromRip : Uint8B

increaseuserva in BCD (p. 14) - this might get your terminal server installation into problems. See example of Insufficient Memory (PTE) pattern.

AWE (p. 15) - reminds me of old overlay programming on PDP-11 RSX-11M

8192Gb VUS and the same for VKS on x64 (p. 15)

Transition from user mode to kernel mode (p. 17) - example from a complete memory dump (blue - user space and mode, red - kernel space and mode)    

THREAD 89fef020  Cid 0ebc.0ec0  Teb: 7ffdd000 Win32Thread: bc15eea8 WAIT: (Unknown) UserMode Non-Alertable
     8ab06754  NotificationEvent
Not impersonating
DeviceMap                 e1006df0
Owning Process            89e58570       Image:         svchost.exe
Wait Start TickCount      2613554        Ticks: 114791 (0:00:29:53.609)
Context Switch Count      5430                 LargeStack
UserTime                  00:00:00.093
KernelTime                00:00:00.062
Win32 Start Address svchost!wmainCRTStartup (0x010020c9)
Start Address kernel32!BaseProcessStartThunk (0x7c82b5ff)
Stack Init b86aa000 Current b86a9bec Base b86aa000 Limit b86a7000 Call 0
Priority 13 BasePriority 8 PriorityDecrement 0
Kernel stack not resident.
ChildEBP RetAddr 
b86a9c04 80832f7a nt!KiSwapContext+0×26
b86a9c30 8082925c nt!KiSwapThread+0×284
b86a9c78 808f482c nt!KeWaitForSingleObject+0×346
b86a9ca0 808f198b nt!IopSynchronousServiceTail+0×180
b86a9d38 80888c7c nt!NtReadFile+0×5cf
b86a9d38 7c94ed54 nt!KiFastCallEntry+0xfc

0007fc40 7c941b84 ntdll!KiFastSystemCallRet
0007fc44 7c80189f ntdll!NtReadFile+0xc
0007fcac 77f595ab kernel32!ReadFile+0×16c
0007fcd8 77f5943c ADVAPI32!ScGetPipeInput+0×2a
0007fd4c 77f596c1 ADVAPI32!ScDispatcherLoop+0×51
0007ffb0 0100214d ADVAPI32!StartServiceCtrlDispatcherW+0xe3
0007ffc0 7c8123e5 svchost!_wmainCRTStartup+0×7f
0007fff0 00000000 kernel32!BaseProcessStart+0×23

Special system instruction to switch to kernel mode (p. 17) - to see this instruction we can disassemble the code before the return address of the first user space function from the stack trace:

// W2K3

1: kd> k
  *** Stack trace for last set context - .thread/.cxr resets it
ChildEBP RetAddr 
b6046c50 80833e95 nt!KiSwapContext+0x26
b6046c7c 8082b72b nt!KiSwapThread+0x2e5
b6046cc4 808ef652 nt!KeRemoveQueue+0x417
b6046d48 8088b19c nt!NtRemoveIoCompletion+0xdc
b6046d48 7c94860c nt!KiFastCallEntry+0xfc
00bfff70 7c9477f9 ntdll!KiFastSystemCallRet
00bfff74 7c959f68 ntdll!NtRemoveIoCompletion+0xc
00bfffb8 7c82482f ntdll!RtlpWorkerThread+0×3d
00bfffec 00000000 kernel32!BaseThreadStart+0×34

1: kd> ub 7c94860c
[…]
ntdll!KiFastSystemCall:
7c948608 8bd4            mov     edx,esp
7c94860a 0f34            sysenter

// W2K

1: kd> k
ChildEBP RetAddr 
b3994950 8044b8fe nt!MiFreeSessionSpaceMap+0x3d
b3994b94 80537bf5 nt!MiDereferenceSession+0x29a
b3994ba0 80441f05 nt!MiSessionRemoveProcess+0x41
b3994c50 804e8582 nt!MmCleanProcessAddressSpace+0x14f
b3994d00 804e801c nt!PspExitThread+0x4e4
b3994d0c 8043110a nt!PsExitSpecialApc+0x1a
b3994d4c 804683f4 nt!KiDeliverApc+0x19a
b3994d4c 77f88b27 nt!KiServiceExit+0×59
[…]

1: kd> ub 77f88b27
[…]
77f88b1a 8bff            mov     edi,edi
77f88b1c b8ab000000      mov     eax,0ABh
77f88b21 8d542404        lea     edx,[esp+4]
77f88b25 cd2e            int     2Eh

Mode transition is not a context switch (p. 17) - This is one of questions I’m asked by engineers

Reliability and Performance Monitor (pp. 18 -19) - looks like it combines the old Performance Monitor and the new Reliability Monitor

Idle process (p. 19) - here is example from a dump:

3: kd> k
ChildEBP RetAddr 
f773d3b8 00000000 processr!AcpiC1Idle+0x12

3: kd> !process
PROCESS 8089fb40  SessionId: none  Cid: 0000    Peb: 00000000  ParentCid: 0000
    DirBase: 013d5000  ObjectTable: e10007b0  HandleCount: 8671.
    Image: Idle
    VadRoot 00000000 Vads 0 Clone 0 Private 0. Modified 16. Locked 0.
    DeviceMap 00000000
    Token                             e1002030
    ElapsedTime                       00:00:00.000
    UserTime                          00:00:00.000
    KernelTime                        1 Day 03:41:20.812
    QuotaPoolUsage[PagedPool]         0
    QuotaPoolUsage[NonPagedPool]      0
    Working Set Sizes (now,min,max)  (7, 50, 450) (28KB, 200KB, 1800KB)
    PeakWorkingSetSize                0
    VirtualSize                       0 Mb
    PeakVirtualSize                   0 Mb
    PageFaultCount                    0
    MemoryPriority                    BACKGROUND
    BasePriority                      0
    CommitCharge                      0

THREAD 8089f8c0  Cid 0000.0000  Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 0
THREAD f772a0a0  Cid 0000.0000  Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 1
THREAD f77320a0  Cid 0000.0000  Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 2
THREAD f773a0a0  Cid 0000.0000  Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 3

3: kd> !thread 8089f8c0
THREAD 8089f8c0  Cid 0000.0000  Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 0
Not impersonating
Owning Process            8089fb40       Image:         Idle
Attached Process          N/A            Image:         N/A
Wait Start TickCount      0              Ticks: 1795558 (0:07:47:35.593)
Context Switch Count      41020289            
UserTime                  00:00:00.000
KernelTime                07:03:12.406
Stack Init 8089c8b0 Current 8089c5fc Base 8089c8b0 Limit 808998b0 Call 0
Priority 0 BasePriority 0 PriorityDecrement 0
ChildEBP RetAddr  Args to Child             
8089c604 00000000 0000000e 00000000 00000000 nt!KiIdleLoop+0xa3

Terminal services (pp. 19 -20) - an for architectural overview (UML diagram) please see this post: Reverse Engineering Citrix ThinWire 

Objects, attributes and methods (p. 21) - here we can see some general methods from object headers:

0:000> dt _OBJECT_HEADER
ntdll!_OBJECT_HEADER
   +0x000 PointerCount     : Int8B
   +0x008 HandleCount      : Int8B
   +0x008 NextToFree       : Ptr64 Void
   +0×010 Type             : Ptr64 _OBJECT_TYPE
   +0×018 NameInfoOffset   : UChar
   +0×019 HandleInfoOffset : UChar
   +0×01a QuotaInfoOffset  : UChar
   +0×01b Flags            : UChar
   +0×020 ObjectCreateInfo : Ptr64 _OBJECT_CREATE_INFORMATION
   +0×020 QuotaBlockCharged : Ptr64 Void
   +0×028 SecurityDescriptor : Ptr64 Void
   +0×030 Body             : _QUAD

0:000> dt _OBJECT_TYPE
ntdll!_OBJECT_TYPE
   +0x000 TypeList         : _LIST_ENTRY
   +0x010 Name             : _UNICODE_STRING
   +0x020 DefaultObject    : Ptr64 Void
   +0x028 Index            : Uint4B
   +0x02c TotalNumberOfObjects : Uint4B
   +0x030 TotalNumberOfHandles : Uint4B
   +0x034 HighWaterNumberOfObjects : Uint4B
   +0x038 HighWaterNumberOfHandles : Uint4B
   +0×040 TypeInfo         : _OBJECT_TYPE_INITIALIZER
   +0×0b0 Mutex            : _ERESOURCE
   +0×118 TypeLock         : _EX_PUSH_LOCK
   +0×120 Key              : Uint4B
   +0×128 ObjectLocks      : [32] _EX_PUSH_LOCK
   +0×228 CallbackList     : _LIST_ENTRY

0:000> dt _OBJECT_TYPE_INITIALIZER
ntdll!_OBJECT_TYPE_INITIALIZER
   +0x000 Length           : Uint2B
   +0x002 ObjectTypeFlags  : UChar
   +0x002 CaseInsensitive  : Pos 0, 1 Bit
   +0x002 UnnamedObjectsOnly : Pos 1, 1 Bit
   +0x002 UseDefaultObject : Pos 2, 1 Bit
   +0x002 SecurityRequired : Pos 3, 1 Bit
   +0x002 MaintainHandleCount : Pos 4, 1 Bit
   +0x002 MaintainTypeList : Pos 5, 1 Bit
   +0x002 SupportsObjectCallbacks : Pos 6, 1 Bit
   +0x004 ObjectTypeCode   : Uint4B
   +0x008 InvalidAttributes : Uint4B
   +0x00c GenericMapping   : _GENERIC_MAPPING
   +0x01c ValidAccessMask  : Uint4B
   +0x020 RetainAccess     : Uint4B
   +0x024 PoolType         : _POOL_TYPE
   +0x028 DefaultPagedPoolCharge : Uint4B
   +0x02c DefaultNonPagedPoolCharge : Uint4B
   +0×030 DumpProcedure    : Ptr64     void
   +0×038 OpenProcedure    : Ptr64     long
   +0×040 CloseProcedure   : Ptr64     void
   +0×048 DeleteProcedure  : Ptr64     void
   +0×050 ParseProcedure   : Ptr64     long
   +0×058 SecurityProcedure : Ptr64     long
   +0×060 QueryNameProcedure : Ptr64     long
   +0×068 OkayToCloseProcedure : Ptr64     unsigned char

- Dmitry Vostokov @ SoftwareGeneralist.com -

Reading Notebook: 15-July-09

Wednesday, July 15th, 2009

Resuming reading notebook with the new book set to read

Comments in italics are mine and express my own views, thoughts and opinions

Windows Internals by M. Russinovich, D. Solomon and A. Ionescu:

Use Windows API term instead of Win32 API for both 32-bit and 64-bit code (p. 2)

Categories of Windows API (p. 2) - The good book that I can recommend for Graphics category that talks about GDI internals too:  Windows Graphics Programming: Win32 GDI and DirectDraw. For understanding Component services: Essential COM

.NET space (p. 3) - Another good book to recommend is Essential .NET, Volume I: The Common Language Runtime. From a typical combined .NET/unmanaged stack trace we can construct component relationships and see that mscorwks.dll is CLR DLL that calls kernel32.dll, for example (Windows API DLL). For some examples from crash dumps see patterns: Managed Code Exception or JIT Code.

UAC virtualization state and limited user account state (p. 5)

PID as part of internal CID (p.5) - Examples of CID (PID.TID) in blue in a user dump:

0:000> ~*kc

.  0  Id: 1350.1354 Suspend: 1 Teb: 000007ff`fffde000 Unfrozen
Call Site
USER32!GetWindowLongPtrW
USER32!GetMessageW
notepad
notepad
kernel32!BaseThreadInitThunk
ntdll!RtlUserThreadStart

1: kd> !thread fffffa8001cc7bb0
THREAD fffffa8001cc7bb0  Cid 13e4.01dc  Teb: 000000007efdb000 Win32Thread: fffff900c210ed50 WAIT: (WrLpcReply) UserMode Non-Alertable

The possibility of an empty process (p. 5) - One example is so the called “orphaned” process that finished its execution but some code still keeps a reference to it:

2: kd> !process 0364
Searching for Process with Cid == 364
Cid Handle table at e20ae000 with 6199 Entries in use
PROCESS 88eeac20  SessionId: 0  Cid: 0364    Peb: 7ffde000  ParentCid: 0724
    DirBase: cff97920  ObjectTable: 00000000  HandleCount:   0.
    Image: cmd.exe
    VadRoot 00000000 Vads 0 Clone 0 Private 0. Modified 4. Locked 0.
    DeviceMap e1006e10
    Token                             e2b28928
    ElapsedTime                       05:06:04.542
    UserTime                          00:00:00.000
    KernelTime                        415 Days 11:06:24.640
    QuotaPoolUsage[PagedPool]         0
    QuotaPoolUsage[NonPagedPool]      0
    Working Set Sizes (now,min,max)  (7, 50, 345) (28KB, 200KB, 1380KB)
    PeakWorkingSetSize                661
    VirtualSize                       11 Mb
    PeakVirtualSize                   15 Mb
    PageFaultCount                    707
    MemoryPriority                    BACKGROUND
    BasePriority                      8
    CommitCharge                      0

No active threads

Parent process (p.5) - See ParenCid in the example of !process output above. 

tlist /t (pp. 5 - 6)

End process tree in Task Manager (p. 6) - Could be useful to decimate certain runaway populations of processes. See Process Factory pattern for an example.

Ctrl-Shift-Esc to start Task Manager (p. 7) - Good to know, I always used Ctrl-Alt-Delete

Application tab: top-level visible windows from desktops in the interactive window station. Not Responding status means not in a state of waiting for user input (pp. 7 - 8 ) - Not in a message loop. I modelled this by running notepad.exe, attaching  a WinDbg to it:

0:000> k
Child-SP          RetAddr           Call Site
00000000`0028fcb8 00000000`7734d5be USER32!ZwUserGetMessage+0xa
00000000`0028fcc0 00000000`ffd06f4a USER32!GetMessageW+0x34
00000000`0028fcf0 00000000`ffd0d00b notepad!WinMain+0x176
00000000`0028fd70 00000000`7741be3d notepad!IsTextUTF8+0x24f
00000000`0028fe30 00000000`77556a51 kernel32!BaseThreadInitThunk+0xd
00000000`0028fe60 00000000`00000000 ntdll!RtlUserThreadStart+0x1d

Although the proccess is fozen it is still listed as Running in Task Manager. Then I put a breakpoint on GetMessageW return address and resumed the execution:

0:000> bp notepad!WinMain+0x176

0:000> g
Breakpoint 1 hit
notepad!WinMain+0x176:
00000000`ffd06f4a 85c0            test    eax,eax

The main GUI thread is no longer in message loop and it is now listed as Not Responding.

0:000> k
Child-SP          RetAddr           Call Site
00000000`0028fcf0 00000000`ffd0d00b notepad!WinMain+0x176
00000000`0028fd70 00000000`7741be3d notepad!IsTextUTF8+0x24f
00000000`0028fe30 00000000`77556a51 kernel32!BaseThreadInitThunk+0xd
00000000`0028fe60 00000000`00000000 ntdll!RtlUserThreadStart+0x1d

Using symbol servers for Process Explorer (p. 10) - Quick download links and symbol server information (for Citrix as well) can be found at WinDbg.org

Displaying hosted COM objects and rundll32 targets (p. 10)

- Dmitry Vostokov @ SoftwareGeneralist.com -