Debugging WINLOGON.EXE on Windows 6.x

Is there any method of debugging the WINLOGON.EXE process on Windows 7
which successfully survives the user logoff action?

None of the documented or successful ways in which I did this under
Windows 5.x seem to be able to survive the user logoff. Or more
specifically, a WINLOGON.EXE process with the debugger attached to it
doesn’t survive the user logoff.

Instead of being returned to the logged-out state of the WINLOGON.EXE
in session ID 1, Windows appears to forcibly terminate the
WINLOGON.EXE from session ID 1, and the “logged out state” Windows
presents to me is actually a new instance of WINLOGON.EXE in session
ID 2.

The only method I’ve tried where the WINLOGON.EXE instance is allowed
to survive as expected is if I run DBGSRV as a remote process server
and connect with WinDBG from across the network. But in this process
server configuration apparently !htrace can’t be enabled (fails with
STATUS_OBJECT_TYPE_MISMATCH), and !htrace happens to be the entire
point of my exercise.

In the other configurations besides using a process server, !htrace
can be successfully enabled. But I’m not able to examine the
WINLOGON.EXE instance handle information post-logout because the
process being forcibly terminated for (currently) reasons unknown.

Since the point of my exercise is to capture a call stack for the
creator of a registry handle into HKEY_CURRENT_USER which has been
abandoned on the WINLOGON.EXE process (as declared by USERENV when
unloading the user profile), if someone knows of an even cleaner way
to capture that instead of !htrace, that would be useful towards a
solution too.

(UPClean 2.0.49’s stack trace does not engage or report this on
Windows 6.x.)

Methods which have been tried:

Controlling NTSD though kernel-mode debugger (the way WinDBG help file
recommends):

NTSD isn’t part of Windows itself any more, so I install Debugging
Tools for Windows 6.12.0002.633 and update the system environment PATH
variable such that NTSD.EXE can be located. Also add …\winext and
…\winxp subdirectories to the path as well, to NTSD in turn can
locate its extensions.

Setup Image File Execution Options to launch WINLOGON.EXE under “NTSD
-d -x”. Over a 1394 connection WinDBG 6.12.0002.633 is able to see
the initial breakpoint on WINLOGON.EXE that the successfully-attached
NTSD.EXE is presenting, and I can control the NTSD debugger
successfully.

But as soon as I initiate a user logout from Windows, a new instance
of NSTD presents a new initial breakpoint of the new WINLOGON.EXE
instance in session ID 2. Breaking into the kernel-mode debugger
confirms that the WINLOGON.EXE instance from session ID 1 is no longer
running.

Running an interactive instance of WinDBG as LocalSystem on the
Winlogon desktop of session ID 1:

“PsExec -d -x -s -i 1” is able to launch WinDBG successfully, and
using CTRL-ALT-DEL I am able to interact with that WinDBG on the
Winlogon desktop to successfully attach to the running WINLOGON.EXE
and enable !htrace.

But as soon as I initiate a user logout from Windows, I’m no longer in
the session where WinDBG was running and the WINLOGON.EXE with !htrace
enabled. Logging in again confirms that I’m now in session ID 2, and
none of the processes from session ID 1 are running any more.

Setup DBGSRV running as service to be process server controlled from
remote WinDBG over TCPIP:

Remote WinDBG is able to see and attach to WINLOGON.EXE instance in
session ID 1, but invoking “!htrace -enable” returns a failure citing
0xC0000024.

After user logout the instance of WINLOGON.EXE is still running and
the debugger is still attached.

The other thing I tried enabling was GFLAG’s “Silent Process Exit” to
try and write a dump of whatever is closing WINLOGON.EXE so
unexpectedly. But no dumps are generated from enabling that feature.

Alan Adams

What if you detach (qd) after enabling htrace? I think you should be able to dump the traces from kd, or perhaps you could attach another ntsd instance via dbgsrv.

Alternatively, you could try capturing a boot-time xperf trace with stack traces on RegCreateKey events. Process Explorer might also be able to do that.

Thanks
Pavel

-----Original Message-----
From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alan Adams
Sent: Friday, August 27, 2010 11:56 AM
To: Kernel Debugging Interest List
Subject: [windbg] Debugging WINLOGON.EXE on Windows 6.x

Is there any method of debugging the WINLOGON.EXE process on Windows 7 which successfully survives the user logoff action?

None of the documented or successful ways in which I did this under Windows 5.x seem to be able to survive the user logoff. Or more specifically, a WINLOGON.EXE process with the debugger attached to it doesn’t survive the user logoff.

Instead of being returned to the logged-out state of the WINLOGON.EXE in session ID 1, Windows appears to forcibly terminate the WINLOGON.EXE from session ID 1, and the “logged out state” Windows presents to me is actually a new instance of WINLOGON.EXE in session ID 2.

The only method I’ve tried where the WINLOGON.EXE instance is allowed to survive as expected is if I run DBGSRV as a remote process server and connect with WinDBG from across the network. But in this process server configuration apparently !htrace can’t be enabled (fails with STATUS_OBJECT_TYPE_MISMATCH), and !htrace happens to be the entire point of my exercise.

In the other configurations besides using a process server, !htrace can be successfully enabled. But I’m not able to examine the WINLOGON.EXE instance handle information post-logout because the process being forcibly terminated for (currently) reasons unknown.

Since the point of my exercise is to capture a call stack for the creator of a registry handle into HKEY_CURRENT_USER which has been abandoned on the WINLOGON.EXE process (as declared by USERENV when unloading the user profile), if someone knows of an even cleaner way to capture that instead of !htrace, that would be useful towards a solution too.

(UPClean 2.0.49’s stack trace does not engage or report this on Windows 6.x.)

Methods which have been tried:

Controlling NTSD though kernel-mode debugger (the way WinDBG help file
recommends):

NTSD isn’t part of Windows itself any more, so I install Debugging Tools for Windows 6.12.0002.633 and update the system environment PATH variable such that NTSD.EXE can be located. Also add …\winext and …\winxp subdirectories to the path as well, to NTSD in turn can locate its extensions.

Setup Image File Execution Options to launch WINLOGON.EXE under “NTSD -d -x”. Over a 1394 connection WinDBG 6.12.0002.633 is able to see the initial breakpoint on WINLOGON.EXE that the successfully-attached NTSD.EXE is presenting, and I can control the NTSD debugger successfully.

But as soon as I initiate a user logout from Windows, a new instance of NSTD presents a new initial breakpoint of the new WINLOGON.EXE instance in session ID 2. Breaking into the kernel-mode debugger confirms that the WINLOGON.EXE instance from session ID 1 is no longer running.

Running an interactive instance of WinDBG as LocalSystem on the Winlogon desktop of session ID 1:

“PsExec -d -x -s -i 1” is able to launch WinDBG successfully, and using CTRL-ALT-DEL I am able to interact with that WinDBG on the Winlogon desktop to successfully attach to the running WINLOGON.EXE and enable !htrace.

But as soon as I initiate a user logout from Windows, I’m no longer in the session where WinDBG was running and the WINLOGON.EXE with !htrace enabled. Logging in again confirms that I’m now in session ID 2, and none of the processes from session ID 1 are running any more.

Setup DBGSRV running as service to be process server controlled from remote WinDBG over TCPIP:

Remote WinDBG is able to see and attach to WINLOGON.EXE instance in session ID 1, but invoking “!htrace -enable” returns a failure citing 0xC0000024.

After user logout the instance of WINLOGON.EXE is still running and the debugger is still attached.

The other thing I tried enabling was GFLAG’s “Silent Process Exit” to try and write a dump of whatever is closing WINLOGON.EXE so unexpectedly. But no dumps are generated from enabling that feature.

Alan Adams


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

Pavel Lebedynskiy wrote:

> What if you detach (qd) after enabling htrace? I think you should be able
> to dump the traces from kd, or perhaps you could attach another ntsd
> instance via dbgsrv.

Thanks. Invoking qd takes the WINLOGON.EXE process with it though at
least in my configuration, so it still was not possible to continue.

> Alternatively, you could try capturing a boot-time xperf trace with stack
> traces on RegCreateKey events. Process Explorer might also be able to do that.

Yes, Process Monitor in boot logging mode throughout the entire login,
logout and subsequent re-login to collect the boot log got me close: I
can observe what appears to be the offending open of HKEY_CURRENT_USER
which has no countervailing close.

But the call stack captured by Process Monitor for the offending open
doesn’t go any higher than the advapi32!RegOpenKeyExW call itself. :slight_smile:
Always has to be something that keeps it from being easy.

Using other information revealed by Process Monitor about the timing
of exactly when the offending call occurred did allow me to finally
break on the offending RegOpenKeyExW and trace back into the caller.
So ultimately this approach was still successful.

I would still be interested to know what the highest-functioning
user-mode debugging of WINLOGON.EXE is expected to be. I’ve liked the
process server approach because I get an otherwise normal WinDBG user
mode debugging environment to work in, but if NTSD is as good as we
can get on Windows 6.x I can understand there being a slew of new
security considerations to work within. But at the moment, at least
for me, not even NTSD seemed to be having an entirely intended outcome
either.

Alan Adams

Sorry, I don’t know what changed in win7 with regard to winlogon debugging, or what the currently recommended method is. But if you wanted to see why the process is getting killed if a user debugger is attached, the easiest way is probably to set a break-on-write breakpoint on some EPROCESS field that gets reset by NtTerminateProcess, like EPROCESS->ObjectTable.

Thanks,
Pavel

-----Original Message-----
From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Alan Adams
Sent: Friday, August 27, 2010 1:27 PM
To: Kernel Debugging Interest List
Subject: Re:[windbg] Debugging WINLOGON.EXE on Windows 6.x

Pavel Lebedynskiy wrote:

> What if you detach (qd) after enabling htrace? I think you should be
> able to dump the traces from kd, or perhaps you could attach another
> ntsd instance via dbgsrv.

Thanks. Invoking qd takes the WINLOGON.EXE process with it though at least in my configuration, so it still was not possible to continue.

> Alternatively, you could try capturing a boot-time xperf trace with
> stack traces on RegCreateKey events. Process Explorer might also be able to do that.

Yes, Process Monitor in boot logging mode throughout the entire login, logout and subsequent re-login to collect the boot log got me close: I can observe what appears to be the offending open of HKEY_CURRENT_USER which has no countervailing close.

But the call stack captured by Process Monitor for the offending open doesn’t go any higher than the advapi32!RegOpenKeyExW call itself. :slight_smile: Always has to be something that keeps it from being easy.

Using other information revealed by Process Monitor about the timing of exactly when the offending call occurred did allow me to finally break on the offending RegOpenKeyExW and trace back into the caller.
So ultimately this approach was still successful.

I would still be interested to know what the highest-functioning user-mode debugging of WINLOGON.EXE is expected to be. I’ve liked the process server approach because I get an otherwise normal WinDBG user mode debugging environment to work in, but if NTSD is as good as we can get on Windows 6.x I can understand there being a slew of new security considerations to work within. But at the moment, at least for me, not even NTSD seemed to be having an entirely intended outcome either.

Alan Adams


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

Pavel Lebedynskiy wrote:

> Sorry, I don’t know what changed in win7 with regard to winlogon debugging,
> or what the currently recommended method is.

Thanks. We’ll see if anyone else on the list knows or has experience
at successfully doing it. I’m just not sure yet if this is course par
for Windows 7, or perhaps unique to the current version of NTSD.EXE,
or maybe in some other way unique to my environment & only happening
to me.

One thing I neglected to mention earlier: The !bpid extension wasn’t
working for me either in this configuration of NTSD.EXE from Debugging
Tools for Windows 6.12.0002.633 on Windows 7 either.

It would appear to run successfully all the way to the point of “the
next break should be in the requested process context”, but no
additional break ever comes. (The first break into WININIT.EXE does
arrive and gets automatically handled.)

> But if you wanted to see why the process is getting killed if a user debugger
> is attached, the easiest way is probably to set a break-on-write breakpoint
> on some EPROCESS field that gets reset by NtTerminateProcess, like
> EPROCESS->ObjectTable.

With a breakpoint on the WINLOGON.EXE process’ ObjectTable as
suggested, but also generically a breakpoint on nt!ExSweepHandleTable
to see the order of each process termination (and before abandoned
handles would have been cleaned up per my goals), what I seem to be
seeing is that the process actually being terminated is NTSD.EXE.
(Which of course ends up taking the debugee WINLOGON.EXE with it, once
termination of NTSD.EXE is successful.)

The WINLOGON.EXE in session ID 1 is issuing an ExitWindowsEx, with the
call stack implying an undocumented 0x10000 value is being passed for
the shutdown flags:

> 3: kd> !THREAD 8624d6f0
> THREAD 8624d6f0 Cid 02b8.02fc Teb: 7ffda000 Win32Thread: fe983a90 WAIT: (WrLpcReply) UserMode Non-Alertable
> 8624d924 Semaphore Limit 0x1
> Waiting for reply to ALPC Message 93f015f0 : queued at port 86230048 : owned by process 86c098f0
> Impersonation token: 99b39030 (Level Impersonation)
> DeviceMap 9273ba10
> Owning Process 86232700 Image: winlogon.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6753 Ticks: 20 (0:00:00:00.312)
> Context Switch Count 536
> UserTime 00:00:00.187
> KernelTime 00:00:00.156
> Win32 Start Address ntdll!TppWorkerThread (0x76dfd63e)
> Stack Init 8ffeefd0 Current 8ffeead0 Base 8ffef000 Limit 8ffec000 Call 0
> Priority 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2 PagePriority 5
> ChildEBP RetAddr Args to Child
> 8ffeeae8 82883b15 8624d6f0 00000000 8e100120 nt!KiSwapContext+0x26 (FPO: [Uses EBP] [0,0,4])
> 8ffeeb20 82882403 8624d7b0 8624d6f0 8624d924 nt!KiSwapThread+0x266
> 8ffeeb48 8287c2cf 8624d6f0 8624d7b0 00000000 nt!KiCommitThreadWait+0x1df
> 8ffeebc0 828cbb66 8624d924 00000011 8624d601 nt!KeWaitForSingleObject+0x393
> 8ffeebe8 82a8abee 8624d924 8624d601 00000000 nt!AlpcpSignalAndWait+0x7b
> 8ffeec0c 82a80c6f 8624d601 8ffeec78 00000000 nt!AlpcpReceiveSynchronousReply+0x27
> 8ffeec9c 82a742ca 8624b458 00020000 002cf668 nt!AlpcpProcessSynchronousRequest+0x276
> 8ffeecf8 82a8bb17 8624b458 002cf668 8624d601 nt!LpcpRequestWaitReplyPort+0x6a
> 8ffeed20 8285842a 0000001c 002cf668 002cf668 nt!NtRequestWaitReplyPort+0x4c
> 8ffeed20 76e164f4 0000001c 002cf668 002cf668 nt!KiFastCallEntry+0x12a (FPO: [0,3] TrapFrame @ 8ffeed34)
> 002cf62c 76e158ac 76e33027 0000001c 002cf668 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
> 002cf630 76e33027 0000001c 002cf668 002cf668 ntdll!NtRequestWaitReplyPort+0xc (FPO: [3,0,0])
> 002cf650 764ffb60 002cf668 00000000 00030400 ntdll!CsrClientCallServer+0xc3 (FPO: [Non-Fpo])
> 002cf6d8 7650027d 00010000 002cf71c 00020000 USER32!CallUserpExitWindowsEx+0x21 (FPO: [Non-Fpo])
> 002cf714 765007c3 00010000 00000000 00000000 USER32!ExitWindowsWorker+0x32 (FPO: [Non-Fpo])
> 002cf748 00886832 00010000 00000000 00000000 USER32!ExitWindowsEx+0xd4 (FPO: [Non-Fpo])
> 002cf76c 00886b89 008ab378 00010000 6fd20b57 winlogon!ShutdownWindowsWrapper+0x56 (FPO: [Non-Fpo])
> 002cf7bc 76deb7b8 002cf818 00000000 002f91f8 winlogon!ShutdownWindowsWorkerThread+0x3af (FPO: [Non-Fpo])
> 002cf7dc 76dfe8d1 002cf818 00311ab8 76c6b74a ntdll!TppSimplepExecuteCallback+0x102 (FPO: [Non-Fpo])
> 002cf93c 76911174 002f91f0 002cf988 76e2b3f5 ntdll!TppWorkerThread+0x572 (FPO: [Non-Fpo])
> 002cf948 76e2b3f5 002f91f0 76c6b7fe 00000000 kernel32!BaseThreadInitThunk+0xe (FPO: [Non-Fpo])
> 002cf988 76e2b3c8 76dfd63e 002f91f0 00000000 ntdll!__RtlUserThreadStart+0x70 (FPO: [Non-Fpo])
> 002cf9a0 00000000 76dfd63e 002f91f0 00000000 ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])

CSRSS in session ID 1 is processing the LPC as advertised, and has
ultimately decided it was appropriate to call winsrv!KillProcess with
a handle to the NTSD process:

> 3: kd> !thread 8a091030
> THREAD 8a091030 Cid 01e8.09f0 Teb: 7ffd7000 Win32Thread: fe672a40 WAIT: (UserRequest) UserMode Non-Alertable
> 86230520 ProcessObject
> Impersonation token: 93ec3030 (Level Impersonation)
> DeviceMap 9273ba10
> Owning Process 86c098f0 Image: csrss.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6773 Ticks: 0
> Context Switch Count 242
> UserTime 00:00:00.000
> KernelTime 00:00:00.031
> Win32 Start Address CSRSRV!CsrApiRequestThread (0x74f8499a)
> Stack Init 98b17fd0 Current 98b17bc8 Base 98b18000 Limit 98b15000 Call 0
> Priority 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2 PagePriority 5
> ChildEBP RetAddr Args to Child
> 98b17be0 82883b15 8a091030 82941f08 8293ed20 nt!KiSwapContext+0x26 (FPO: [Uses EBP] [0,0,4])
> 98b17c18 82882403 8a0910f0 8a091030 86230520 nt!KiSwapThread+0x266
> 98b17c40 8287c2cf 8a091030 8a0910f0 00000096 nt!KiCommitThreadWait+0x1df
> 98b17cb8 82a46515 86230520 00000006 86230501 nt!KeWaitForSingleObject+0x393
> 98b17d20 8285842a 0000017c 00000000 98b17ce4 nt!NtWaitForSingleObject+0xc6
> 98b17d20 76e164f4 0000017c 00000000 98b17ce4 nt!KiFastCallEntry+0x12a (FPO: [0,3] TrapFrame @ 98b17d34)
> 02bff9c4 76e15e6c 74f4a93a 0000017c 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
> 02bff9c8 74f4a93a 0000017c 00000000 02bff9dc ntdll!NtWaitForSingleObject+0xc (FPO: [3,0,0])
> 02bff9e4 74f4aa12 0000017c 000002ac 00000002 winsrv!KillProcess+0x50 (FPO: [Non-Fpo])
> 02bffaa8 74f4c4af 00218908 00019b83 80000108 winsrv!DefaultProcessShutdown+0xcf (FPO: [Non-Fpo])
> 02bffb14 74f85e20 80000108 00010200 74f85100 winsrv!UserClientShutdown+0x490 (FPO: [Non-Fpo])
> 02bffb44 74f85f39 00000003 00010200 00019b83 CSRSRV!ShutdownProcessForLuid+0x7d (FPO: [Non-Fpo])
> 02bffb64 74f4b6b5 02bffb98 00010200 74f89c80 CSRSRV!CsrShutdownProcesses+0x8c (FPO: [Non-Fpo])
> 02bffba0 74f4c005 00000000 00010200 00000000 winsrv!_ExitWindowsEx+0x103 (FPO: [Non-Fpo])
> 02bffbb8 74f84d55 02bffbd8 02bffcd0 6076d748 winsrv!SrvExitWindowsEx+0x27 (FPO: [Non-Fpo])
> 02bffd2c 76dd5d0b 00000000 7455b108 00000000 CSRSRV!CsrApiRequestThread+0x3bb (FPO: [Non-Fpo])
> 02bffd6c 76e2b3c8 74f8499a 00000000 00000000 ntdll!__RtlUserThreadStart+0x28 (FPO: [Non-Fpo])
> 02bffd84 00000000 74f8499a 00000000 00000000 ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])
>
> 3: kd> !handle 0000017c
>
> PROCESS 86c098f0 SessionId: 1 Cid: 01e8 Peb: 7ffd5000 ParentCid: 01d8
> DirBase: defe9040 ObjectTable: 926ef718 HandleCount: 136.
> Image: csrss.exe
>
> Handle table at 92725000 with 136 entries in use
>
> 017c: Object: 86230520 GrantedAccess: 001fffff Entry: 927252f8
> Object: 86230520 Type: (852cf978) Process
> ObjectHeader: 86230508 (new version)
> HandleCount: 4 PointerCount: 9
>
> 3: kd> !process 86230520
> PROCESS 86230520 SessionId: 1 Cid: 02ac Peb: 7ffde000 ParentCid: 01d8
> DirBase: defe9120 ObjectTable: 8cf24320 HandleCount: 58.
> Image: ntsd.exe
> VadRoot 86b11238 Vads 32 Clone 0 Private 538. Modified 0. Locked 0.
> DeviceMap 8ce050c8
> Token 82581d58
> ElapsedTime 00:01:29.512
> UserTime 00:00:00.000
> KernelTime 00:00:00.000
> QuotaPoolUsage[PagedPool] 0
> QuotaPoolUsage[NonPagedPool] 0
> Working Set Sizes (now,min,max) (1270, 50, 345) (5080KB, 200KB, 1380KB)
> PeakWorkingSetSize 1270
> VirtualSize 20 Mb
> PeakVirtualSize 22 Mb
> PageFaultCount 1297
> MemoryPriority BACKGROUND
> BasePriority 13
> CommitCharge 789
>
> THREAD 86232d00 Cid 02ac.02b0 Teb: 00000000 Win32Thread: 00000000 RUNNING on processor 3
> Not impersonating
> DeviceMap 8ce050c8
> Owning Process 86230520 Image: ntsd.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6771 Ticks: 2 (0:00:00:00.031)
> Context Switch Count 407
> UserTime 00:00:00.015
> KernelTime 00:00:00.655
> Win32 Start Address 0x007f2485
> Stack Init 8fee9fd0 Current 8fee9b50 Base 8feea000 Limit 8fee7000 Call 0
> Priority 15 BasePriority 15 UnusualBoost 0 ForegroundBoost 0 IoPriority 2 PagePriority 5
> ChildEBP RetAddr
> 8fee9c20 82a92227 nt!ExSweepHandleTable
> 8fee9c40 82a5dc78 nt!ObKillProcess+0x54
> 8fee9cb4 82a92151 nt!PspExitThread+0x5d9
> 8fee9ccc 828bd123 nt!PsExitSpecialApc+0x22
> 8fee9d1c 828584e4 nt!KiDeliverApc+0x28b
> 8fee9d1c 76e164f4 nt!KiServiceExit+0x64 (FPO: [0,3] TrapFrame @ 8fee9d34)
> 001ae5d8 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])

The nt!ExSweepHandleTable being invoked for NTSD.EXE is the breakpoint
I had stopped on to examine the other process states.

So its still not clear for my what has caused an apparent “terminate
all processes in session ID 1” rather than just the expected
“terminate all processes under the interactive user’s logon session”.
I did confirm via Process Explorer and Task Manager prior to breaking
that both NTSD and WINLOGON are running under LocalSystem / logon
session 999 as expected, so they are for sure not part of the
processes running under the interactive user’s logon session.

For what it’s worth, enabling !htrace under NTSD and then being able
to break on the WINLOGON.EXE process from KD while the handle table
was still valid did indeed work as you had suggested. It would have
taken me quite a while to figure out the user-mode handle tracing
would still be accessible by the kernel-mode extension, so I
appreciate that on multiple levels.

Ultimately to track down my issue I resorted to enabling handle
tracing using Application Verifier registry flags rather than
involving NTSD, so that with NTSD out of the picture my WINLOGON.EXE
instance would survive longer.

Which wasn’t ideal, since it leaves me unable to trigger the -snapshot
and -diff functions of !htrace. But since !bpid wasn’t working, that
capability wasn’t available in this scenario anyway.

CoolSwitch and the checked build of WINLOGON.EXE might have provided
the arbitrary ability to break into WINLOGON.EXE under NTSD.EXE, but
the handles I was interested in just happened to be within the
available trace history so I never had to find out.

Alan Adams

There’s an undocumented metacommand that name of which escapes me at the
moment that shows when symbols are failing to resolve. It might help
diagnose that you feel isn’t working is in fact working or not.

Perhaps Snoone (who told me about it a long time ago) will be along soon to
share the name of it,.

Good luck,

mm

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Alan Adams
Sent: Monday, August 30, 2010 2:11 AM
To: Kernel Debugging Interest List
Subject: Re:[windbg] Debugging WINLOGON.EXE on Windows 6.x

Pavel Lebedynskiy wrote:

> Sorry, I don’t know what changed in win7 with regard to winlogon
> debugging, or what the currently recommended method is.

Thanks. We’ll see if anyone else on the list knows or has experience at
successfully doing it. I’m just not sure yet if this is course par for
Windows 7, or perhaps unique to the current version of NTSD.EXE, or maybe in
some other way unique to my environment & only happening to me.

One thing I neglected to mention earlier: The !bpid extension wasn’t working
for me either in this configuration of NTSD.EXE from Debugging Tools for
Windows 6.12.0002.633 on Windows 7 either.

It would appear to run successfully all the way to the point of “the next
break should be in the requested process context”, but no additional break
ever comes. (The first break into WININIT.EXE does arrive and gets
automatically handled.)

> But if you wanted to see why the process is getting killed if a user
> debugger is attached, the easiest way is probably to set a
> break-on-write breakpoint on some EPROCESS field that gets reset by
> NtTerminateProcess, like
> EPROCESS->ObjectTable.

With a breakpoint on the WINLOGON.EXE process’ ObjectTable as suggested, but
also generically a breakpoint on nt!ExSweepHandleTable to see the order of
each process termination (and before abandoned handles would have been
cleaned up per my goals), what I seem to be seeing is that the process
actually being terminated is NTSD.EXE.
(Which of course ends up taking the debugee WINLOGON.EXE with it, once
termination of NTSD.EXE is successful.)

The WINLOGON.EXE in session ID 1 is issuing an ExitWindowsEx, with the call
stack implying an undocumented 0x10000 value is being passed for the
shutdown flags:

> 3: kd> !THREAD 8624d6f0
> THREAD 8624d6f0 Cid 02b8.02fc Teb: 7ffda000 Win32Thread: fe983a90 WAIT:
(WrLpcReply) UserMode Non-Alertable
> 8624d924 Semaphore Limit 0x1
> Waiting for reply to ALPC Message 93f015f0 : queued at port 86230048 :
> owned by process 86c098f0 Impersonation token: 99b39030 (Level
Impersonation)
> DeviceMap 9273ba10
> Owning Process 86232700 Image: winlogon.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6753 Ticks: 20 (0:00:00:00.312)
> Context Switch Count 536
> UserTime 00:00:00.187
> KernelTime 00:00:00.156
> Win32 Start Address ntdll!TppWorkerThread (0x76dfd63e) Stack Init
> 8ffeefd0 Current 8ffeead0 Base 8ffef000 Limit 8ffec000 Call 0 Priority
> 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2
PagePriority 5
> ChildEBP RetAddr Args to Child
> 8ffeeae8 82883b15 8624d6f0 00000000 8e100120 nt!KiSwapContext+0x26
> (FPO: [Uses EBP] [0,0,4])
> 8ffeeb20 82882403 8624d7b0 8624d6f0 8624d924 nt!KiSwapThread+0x266
> 8ffeeb48 8287c2cf 8624d6f0 8624d7b0 00000000
> nt!KiCommitThreadWait+0x1df
> 8ffeebc0 828cbb66 8624d924 00000011 8624d601
> nt!KeWaitForSingleObject+0x393
> 8ffeebe8 82a8abee 8624d924 8624d601 00000000
> nt!AlpcpSignalAndWait+0x7b 8ffeec0c 82a80c6f 8624d601 8ffeec78
> 00000000 nt!AlpcpReceiveSynchronousReply+0x27
> 8ffeec9c 82a742ca 8624b458 00020000 002cf668
> nt!AlpcpProcessSynchronousRequest+0x276
> 8ffeecf8 82a8bb17 8624b458 002cf668 8624d601
> nt!LpcpRequestWaitReplyPort+0x6a
> 8ffeed20 8285842a 0000001c 002cf668 002cf668
> nt!NtRequestWaitReplyPort+0x4c
> 8ffeed20 76e164f4 0000001c 002cf668 002cf668 nt!KiFastCallEntry+0x12a
> (FPO: [0,3] TrapFrame @ 8ffeed34) 002cf62c 76e158ac 76e33027 0000001c
> 002cf668 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
> 002cf630 76e33027 0000001c 002cf668 002cf668
> ntdll!NtRequestWaitReplyPort+0xc (FPO: [3,0,0])
> 002cf650 764ffb60 002cf668 00000000 00030400
> ntdll!CsrClientCallServer+0xc3 (FPO: [Non-Fpo])
> 002cf6d8 7650027d 00010000 002cf71c 00020000
> USER32!CallUserpExitWindowsEx+0x21 (FPO: [Non-Fpo])
> 002cf714 765007c3 00010000 00000000 00000000
> USER32!ExitWindowsWorker+0x32 (FPO: [Non-Fpo])
> 002cf748 00886832 00010000 00000000 00000000 USER32!ExitWindowsEx+0xd4
> (FPO: [Non-Fpo]) 002cf76c 00886b89 008ab378 00010000 6fd20b57
> winlogon!ShutdownWindowsWrapper+0x56 (FPO: [Non-Fpo]) 002cf7bc
> 76deb7b8 002cf818 00000000 002f91f8
> winlogon!ShutdownWindowsWorkerThread+0x3af (FPO: [Non-Fpo]) 002cf7dc
> 76dfe8d1 002cf818 00311ab8 76c6b74a
> ntdll!TppSimplepExecuteCallback+0x102 (FPO: [Non-Fpo]) 002cf93c
> 76911174 002f91f0 002cf988 76e2b3f5 ntdll!TppWorkerThread+0x572 (FPO:
> [Non-Fpo])
> 002cf948 76e2b3f5 002f91f0 76c6b7fe 00000000
> kernel32!BaseThreadInitThunk+0xe (FPO: [Non-Fpo])
> 002cf988 76e2b3c8 76dfd63e 002f91f0 00000000
> ntdll!__RtlUserThreadStart+0x70 (FPO: [Non-Fpo])
> 002cf9a0 00000000 76dfd63e 002f91f0 00000000
> ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])

CSRSS in session ID 1 is processing the LPC as advertised, and has
ultimately decided it was appropriate to call winsrv!KillProcess with a
handle to the NTSD process:

> 3: kd> !thread 8a091030
> THREAD 8a091030 Cid 01e8.09f0 Teb: 7ffd7000 Win32Thread: fe672a40 WAIT:
(UserRequest) UserMode Non-Alertable
> 86230520 ProcessObject
> Impersonation token: 93ec3030 (Level Impersonation)
> DeviceMap 9273ba10
> Owning Process 86c098f0 Image: csrss.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6773 Ticks: 0
> Context Switch Count 242
> UserTime 00:00:00.000
> KernelTime 00:00:00.031
> Win32 Start Address CSRSRV!CsrApiRequestThread (0x74f8499a) Stack Init
> 98b17fd0 Current 98b17bc8 Base 98b18000 Limit 98b15000 Call 0 Priority
> 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2
PagePriority 5
> ChildEBP RetAddr Args to Child
> 98b17be0 82883b15 8a091030 82941f08 8293ed20 nt!KiSwapContext+0x26
> (FPO: [Uses EBP] [0,0,4])
> 98b17c18 82882403 8a0910f0 8a091030 86230520 nt!KiSwapThread+0x266
> 98b17c40 8287c2cf 8a091030 8a0910f0 00000096
> nt!KiCommitThreadWait+0x1df
> 98b17cb8 82a46515 86230520 00000006 86230501
> nt!KeWaitForSingleObject+0x393
> 98b17d20 8285842a 0000017c 00000000 98b17ce4
> nt!NtWaitForSingleObject+0xc6
> 98b17d20 76e164f4 0000017c 00000000 98b17ce4 nt!KiFastCallEntry+0x12a
> (FPO: [0,3] TrapFrame @ 98b17d34)
> 02bff9c4 76e15e6c 74f4a93a 0000017c 00000000 ntdll!KiFastSystemCallRet
> (FPO: [0,0,0])
> 02bff9c8 74f4a93a 0000017c 00000000 02bff9dc
> ntdll!NtWaitForSingleObject+0xc (FPO: [3,0,0])
> 02bff9e4 74f4aa12 0000017c 000002ac 00000002 winsrv!KillProcess+0x50
> (FPO: [Non-Fpo])
> 02bffaa8 74f4c4af 00218908 00019b83 80000108
> winsrv!DefaultProcessShutdown+0xcf (FPO: [Non-Fpo])
> 02bffb14 74f85e20 80000108 00010200 74f85100
> winsrv!UserClientShutdown+0x490 (FPO: [Non-Fpo])
> 02bffb44 74f85f39 00000003 00010200 00019b83
> CSRSRV!ShutdownProcessForLuid+0x7d (FPO: [Non-Fpo])
> 02bffb64 74f4b6b5 02bffb98 00010200 74f89c80
> CSRSRV!CsrShutdownProcesses+0x8c (FPO: [Non-Fpo])
> 02bffba0 74f4c005 00000000 00010200 00000000
> winsrv!_ExitWindowsEx+0x103 (FPO: [Non-Fpo])
> 02bffbb8 74f84d55 02bffbd8 02bffcd0 6076d748
> winsrv!SrvExitWindowsEx+0x27 (FPO: [Non-Fpo]) 02bffd2c 76dd5d0b
> 00000000 7455b108 00000000 CSRSRV!CsrApiRequestThread+0x3bb (FPO:
> [Non-Fpo]) 02bffd6c 76e2b3c8 74f8499a 00000000 00000000
> ntdll!__RtlUserThreadStart+0x28 (FPO: [Non-Fpo])
> 02bffd84 00000000 74f8499a 00000000 00000000
> ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])
>
> 3: kd> !handle 0000017c
>
> PROCESS 86c098f0 SessionId: 1 Cid: 01e8 Peb: 7ffd5000 ParentCid:
01d8
> DirBase: defe9040 ObjectTable: 926ef718 HandleCount: 136.
> Image: csrss.exe
>
> Handle table at 92725000 with 136 entries in use
>
> 017c: Object: 86230520 GrantedAccess: 001fffff Entry: 927252f8
> Object: 86230520 Type: (852cf978) Process
> ObjectHeader: 86230508 (new version)
> HandleCount: 4 PointerCount: 9
>
> 3: kd> !process 86230520
> PROCESS 86230520 SessionId: 1 Cid: 02ac Peb: 7ffde000 ParentCid:
01d8
> DirBase: defe9120 ObjectTable: 8cf24320 HandleCount: 58.
> Image: ntsd.exe
> VadRoot 86b11238 Vads 32 Clone 0 Private 538. Modified 0. Locked 0.
> DeviceMap 8ce050c8
> Token 82581d58
> ElapsedTime 00:01:29.512
> UserTime 00:00:00.000
> KernelTime 00:00:00.000
> QuotaPoolUsage[PagedPool] 0
> QuotaPoolUsage[NonPagedPool] 0
> Working Set Sizes (now,min,max) (1270, 50, 345) (5080KB, 200KB,
1380KB)
> PeakWorkingSetSize 1270
> VirtualSize 20 Mb
> PeakVirtualSize 22 Mb
> PageFaultCount 1297
> MemoryPriority BACKGROUND
> BasePriority 13
> CommitCharge 789
>
> THREAD 86232d00 Cid 02ac.02b0 Teb: 00000000 Win32Thread:
00000000 RUNNING on processor 3
> Not impersonating
> DeviceMap 8ce050c8
> Owning Process 86230520 Image: ntsd.exe
> Attached Process N/A Image: N/A
> Wait Start TickCount 6771 Ticks: 2 (0:00:00:00.031)
> Context Switch Count 407
> UserTime 00:00:00.015
> KernelTime 00:00:00.655
> Win32 Start Address 0x007f2485
> Stack Init 8fee9fd0 Current 8fee9b50 Base 8feea000 Limit 8fee7000
Call 0
> Priority 15 BasePriority 15 UnusualBoost 0 ForegroundBoost 0
IoPriority 2 PagePriority 5
> ChildEBP RetAddr
> 8fee9c20 82a92227 nt!ExSweepHandleTable
> 8fee9c40 82a5dc78 nt!ObKillProcess+0x54
> 8fee9cb4 82a92151 nt!PspExitThread+0x5d9
> 8fee9ccc 828bd123 nt!PsExitSpecialApc+0x22
> 8fee9d1c 828584e4 nt!KiDeliverApc+0x28b
> 8fee9d1c 76e164f4 nt!KiServiceExit+0x64 (FPO: [0,3] TrapFrame @
8fee9d34)
> 001ae5d8 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])

The nt!ExSweepHandleTable being invoked for NTSD.EXE is the breakpoint I had
stopped on to examine the other process states.

So its still not clear for my what has caused an apparent “terminate all
processes in session ID 1” rather than just the expected “terminate all
processes under the interactive user’s logon session”.
I did confirm via Process Explorer and Task Manager prior to breaking that
both NTSD and WINLOGON are running under LocalSystem / logon session 999 as
expected, so they are for sure not part of the processes running under the
interactive user’s logon session.

For what it’s worth, enabling !htrace under NTSD and then being able to
break on the WINLOGON.EXE process from KD while the handle table was still
valid did indeed work as you had suggested. It would have taken me quite a
while to figure out the user-mode handle tracing would still be accessible
by the kernel-mode extension, so I appreciate that on multiple levels.

Ultimately to track down my issue I resorted to enabling handle tracing
using Application Verifier registry flags rather than involving NTSD, so
that with NTSD out of the picture my WINLOGON.EXE instance would survive
longer.

Which wasn’t ideal, since it leaves me unable to trigger the -snapshot and
-diff functions of !htrace. But since !bpid wasn’t working, that capability
wasn’t available in this scenario anyway.

CoolSwitch and the checked build of WINLOGON.EXE might have provided the
arbitrary ability to break into WINLOGON.EXE under NTSD.EXE, but the handles
I was interested in just happened to be within the available trace history
so I never had to find out.

Alan Adams


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer

.show_sym_failures

http://analyze-v.com/?p=325

(Also actually documented now:
http://msdn.microsoft.com/en-us/library/ff565343(VS.85).aspx)

-scott


Scott Noone
Consulting Associate
OSR Open Systems Resources, Inc.
http://www.osronline.com

“M. M. O’Brien” wrote in message
news:xxxxx@windbg…
> There’s an undocumented metacommand that name of which escapes me at the
> moment that shows when symbols are failing to resolve. It might help
> diagnose that you feel isn’t working is in fact working or not.
>
> Perhaps Snoone (who told me about it a long time ago) will be along soon
> to
> share the name of it,.
>
>
> Good luck,
>
> mm
>
> -----Original Message-----
> From: xxxxx@lists.osr.com
> [mailto:xxxxx@lists.osr.com] On Behalf Of Alan Adams
> Sent: Monday, August 30, 2010 2:11 AM
> To: Kernel Debugging Interest List
> Subject: Re:[windbg] Debugging WINLOGON.EXE on Windows 6.x
>
> Pavel Lebedynskiy wrote:
>
>> Sorry, I don’t know what changed in win7 with regard to winlogon
>> debugging, or what the currently recommended method is.
>
> Thanks. We’ll see if anyone else on the list knows or has experience at
> successfully doing it. I’m just not sure yet if this is course par for
> Windows 7, or perhaps unique to the current version of NTSD.EXE, or maybe
> in
> some other way unique to my environment & only happening to me.
>
> One thing I neglected to mention earlier: The !bpid extension wasn’t
> working
> for me either in this configuration of NTSD.EXE from Debugging Tools for
> Windows 6.12.0002.633 on Windows 7 either.
>
> It would appear to run successfully all the way to the point of “the next
> break should be in the requested process context”, but no additional break
> ever comes. (The first break into WININIT.EXE does arrive and gets
> automatically handled.)
>
>
>> But if you wanted to see why the process is getting killed if a user
>> debugger is attached, the easiest way is probably to set a
>> break-on-write breakpoint on some EPROCESS field that gets reset by
>> NtTerminateProcess, like
>> EPROCESS->ObjectTable.
>
> With a breakpoint on the WINLOGON.EXE process’ ObjectTable as suggested,
> but
> also generically a breakpoint on nt!ExSweepHandleTable to see the order of
> each process termination (and before abandoned handles would have been
> cleaned up per my goals), what I seem to be seeing is that the process
> actually being terminated is NTSD.EXE.
> (Which of course ends up taking the debugee WINLOGON.EXE with it, once
> termination of NTSD.EXE is successful.)
>
> The WINLOGON.EXE in session ID 1 is issuing an ExitWindowsEx, with the
> call
> stack implying an undocumented 0x10000 value is being passed for the
> shutdown flags:
>
>> 3: kd> !THREAD 8624d6f0
>> THREAD 8624d6f0 Cid 02b8.02fc Teb: 7ffda000 Win32Thread: fe983a90 WAIT:
> (WrLpcReply) UserMode Non-Alertable
>> 8624d924 Semaphore Limit 0x1
>> Waiting for reply to ALPC Message 93f015f0 : queued at port 86230048 :
>> owned by process 86c098f0 Impersonation token: 99b39030 (Level
> Impersonation)
>> DeviceMap 9273ba10
>> Owning Process 86232700 Image: winlogon.exe
>> Attached Process N/A Image: N/A
>> Wait Start TickCount 6753 Ticks: 20 (0:00:00:00.312)
>> Context Switch Count 536
>> UserTime 00:00:00.187
>> KernelTime 00:00:00.156
>> Win32 Start Address ntdll!TppWorkerThread (0x76dfd63e) Stack Init
>> 8ffeefd0 Current 8ffeead0 Base 8ffef000 Limit 8ffec000 Call 0 Priority
>> 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2
> PagePriority 5
>> ChildEBP RetAddr Args to Child
>> 8ffeeae8 82883b15 8624d6f0 00000000 8e100120 nt!KiSwapContext+0x26
>> (FPO: [Uses EBP] [0,0,4])
>> 8ffeeb20 82882403 8624d7b0 8624d6f0 8624d924 nt!KiSwapThread+0x266
>> 8ffeeb48 8287c2cf 8624d6f0 8624d7b0 00000000
>> nt!KiCommitThreadWait+0x1df
>> 8ffeebc0 828cbb66 8624d924 00000011 8624d601
>> nt!KeWaitForSingleObject+0x393
>> 8ffeebe8 82a8abee 8624d924 8624d601 00000000
>> nt!AlpcpSignalAndWait+0x7b 8ffeec0c 82a80c6f 8624d601 8ffeec78
>> 00000000 nt!AlpcpReceiveSynchronousReply+0x27
>> 8ffeec9c 82a742ca 8624b458 00020000 002cf668
>> nt!AlpcpProcessSynchronousRequest+0x276
>> 8ffeecf8 82a8bb17 8624b458 002cf668 8624d601
>> nt!LpcpRequestWaitReplyPort+0x6a
>> 8ffeed20 8285842a 0000001c 002cf668 002cf668
>> nt!NtRequestWaitReplyPort+0x4c
>> 8ffeed20 76e164f4 0000001c 002cf668 002cf668 nt!KiFastCallEntry+0x12a
>> (FPO: [0,3] TrapFrame @ 8ffeed34) 002cf62c 76e158ac 76e33027 0000001c
>> 002cf668 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
>> 002cf630 76e33027 0000001c 002cf668 002cf668
>> ntdll!NtRequestWaitReplyPort+0xc (FPO: [3,0,0])
>> 002cf650 764ffb60 002cf668 00000000 00030400
>> ntdll!CsrClientCallServer+0xc3 (FPO: [Non-Fpo])
>> 002cf6d8 7650027d 00010000 002cf71c 00020000
>> USER32!CallUserpExitWindowsEx+0x21 (FPO: [Non-Fpo])
>> 002cf714 765007c3 00010000 00000000 00000000
>> USER32!ExitWindowsWorker+0x32 (FPO: [Non-Fpo])
>> 002cf748 00886832 00010000 00000000 00000000 USER32!ExitWindowsEx+0xd4
>> (FPO: [Non-Fpo]) 002cf76c 00886b89 008ab378 00010000 6fd20b57
>> winlogon!ShutdownWindowsWrapper+0x56 (FPO: [Non-Fpo]) 002cf7bc
>> 76deb7b8 002cf818 00000000 002f91f8
>> winlogon!ShutdownWindowsWorkerThread+0x3af (FPO: [Non-Fpo]) 002cf7dc
>> 76dfe8d1 002cf818 00311ab8 76c6b74a
>> ntdll!TppSimplepExecuteCallback+0x102 (FPO: [Non-Fpo]) 002cf93c
>> 76911174 002f91f0 002cf988 76e2b3f5 ntdll!TppWorkerThread+0x572 (FPO:
>> [Non-Fpo])
>> 002cf948 76e2b3f5 002f91f0 76c6b7fe 00000000
>> kernel32!BaseThreadInitThunk+0xe (FPO: [Non-Fpo])
>> 002cf988 76e2b3c8 76dfd63e 002f91f0 00000000
>> ntdll!__RtlUserThreadStart+0x70 (FPO: [Non-Fpo])
>> 002cf9a0 00000000 76dfd63e 002f91f0 00000000
>> ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])
>
> CSRSS in session ID 1 is processing the LPC as advertised, and has
> ultimately decided it was appropriate to call winsrv!KillProcess with a
> handle to the NTSD process:
>
>> 3: kd> !thread 8a091030
>> THREAD 8a091030 Cid 01e8.09f0 Teb: 7ffd7000 Win32Thread: fe672a40 WAIT:
> (UserRequest) UserMode Non-Alertable
>> 86230520 ProcessObject
>> Impersonation token: 93ec3030 (Level Impersonation)
>> DeviceMap 9273ba10
>> Owning Process 86c098f0 Image: csrss.exe
>> Attached Process N/A Image: N/A
>> Wait Start TickCount 6773 Ticks: 0
>> Context Switch Count 242
>> UserTime 00:00:00.000
>> KernelTime 00:00:00.031
>> Win32 Start Address CSRSRV!CsrApiRequestThread (0x74f8499a) Stack Init
>> 98b17fd0 Current 98b17bc8 Base 98b18000 Limit 98b15000 Call 0 Priority
>> 14 BasePriority 13 UnusualBoost 0 ForegroundBoost 0 IoPriority 2
> PagePriority 5
>> ChildEBP RetAddr Args to Child
>> 98b17be0 82883b15 8a091030 82941f08 8293ed20 nt!KiSwapContext+0x26
>> (FPO: [Uses EBP] [0,0,4])
>> 98b17c18 82882403 8a0910f0 8a091030 86230520 nt!KiSwapThread+0x266
>> 98b17c40 8287c2cf 8a091030 8a0910f0 00000096
>> nt!KiCommitThreadWait+0x1df
>> 98b17cb8 82a46515 86230520 00000006 86230501
>> nt!KeWaitForSingleObject+0x393
>> 98b17d20 8285842a 0000017c 00000000 98b17ce4
>> nt!NtWaitForSingleObject+0xc6
>> 98b17d20 76e164f4 0000017c 00000000 98b17ce4 nt!KiFastCallEntry+0x12a
>> (FPO: [0,3] TrapFrame @ 98b17d34)
>> 02bff9c4 76e15e6c 74f4a93a 0000017c 00000000 ntdll!KiFastSystemCallRet
>> (FPO: [0,0,0])
>> 02bff9c8 74f4a93a 0000017c 00000000 02bff9dc
>> ntdll!NtWaitForSingleObject+0xc (FPO: [3,0,0])
>> 02bff9e4 74f4aa12 0000017c 000002ac 00000002 winsrv!KillProcess+0x50
>> (FPO: [Non-Fpo])
>> 02bffaa8 74f4c4af 00218908 00019b83 80000108
>> winsrv!DefaultProcessShutdown+0xcf (FPO: [Non-Fpo])
>> 02bffb14 74f85e20 80000108 00010200 74f85100
>> winsrv!UserClientShutdown+0x490 (FPO: [Non-Fpo])
>> 02bffb44 74f85f39 00000003 00010200 00019b83
>> CSRSRV!ShutdownProcessForLuid+0x7d (FPO: [Non-Fpo])
>> 02bffb64 74f4b6b5 02bffb98 00010200 74f89c80
>> CSRSRV!CsrShutdownProcesses+0x8c (FPO: [Non-Fpo])
>> 02bffba0 74f4c005 00000000 00010200 00000000
>> winsrv!_ExitWindowsEx+0x103 (FPO: [Non-Fpo])
>> 02bffbb8 74f84d55 02bffbd8 02bffcd0 6076d748
>> winsrv!SrvExitWindowsEx+0x27 (FPO: [Non-Fpo]) 02bffd2c 76dd5d0b
>> 00000000 7455b108 00000000 CSRSRV!CsrApiRequestThread+0x3bb (FPO:
>> [Non-Fpo]) 02bffd6c 76e2b3c8 74f8499a 00000000 00000000
>> ntdll!__RtlUserThreadStart+0x28 (FPO: [Non-Fpo])
>> 02bffd84 00000000 74f8499a 00000000 00000000
>> ntdll!_RtlUserThreadStart+0x1b (FPO: [Non-Fpo])
>>
>> 3: kd> !handle 0000017c
>>
>> PROCESS 86c098f0 SessionId: 1 Cid: 01e8 Peb: 7ffd5000 ParentCid:
> 01d8
>> DirBase: defe9040 ObjectTable: 926ef718 HandleCount: 136.
>> Image: csrss.exe
>>
>> Handle table at 92725000 with 136 entries in use
>>
>> 017c: Object: 86230520 GrantedAccess: 001fffff Entry: 927252f8
>> Object: 86230520 Type: (852cf978) Process
>> ObjectHeader: 86230508 (new version)
>> HandleCount: 4 PointerCount: 9
>>
>> 3: kd> !process 86230520
>> PROCESS 86230520 SessionId: 1 Cid: 02ac Peb: 7ffde000 ParentCid:
> 01d8
>> DirBase: defe9120 ObjectTable: 8cf24320 HandleCount: 58.
>> Image: ntsd.exe
>> VadRoot 86b11238 Vads 32 Clone 0 Private 538. Modified 0. Locked 0.
>> DeviceMap 8ce050c8
>> Token 82581d58
>> ElapsedTime 00:01:29.512
>> UserTime 00:00:00.000
>> KernelTime 00:00:00.000
>> QuotaPoolUsage[PagedPool] 0
>> QuotaPoolUsage[NonPagedPool] 0
>> Working Set Sizes (now,min,max) (1270, 50, 345) (5080KB, 200KB,
> 1380KB)
>> PeakWorkingSetSize 1270
>> VirtualSize 20 Mb
>> PeakVirtualSize 22 Mb
>> PageFaultCount 1297
>> MemoryPriority BACKGROUND
>> BasePriority 13
>> CommitCharge 789
>>
>> THREAD 86232d00 Cid 02ac.02b0 Teb: 00000000 Win32Thread:
> 00000000 RUNNING on processor 3
>> Not impersonating
>> DeviceMap 8ce050c8
>> Owning Process 86230520 Image: ntsd.exe
>> Attached Process N/A Image: N/A
>> Wait Start TickCount 6771 Ticks: 2
>> (0:00:00:00.031)
>> Context Switch Count 407
>> UserTime 00:00:00.015
>> KernelTime 00:00:00.655
>> Win32 Start Address 0x007f2485
>> Stack Init 8fee9fd0 Current 8fee9b50 Base 8feea000 Limit 8fee7000
> Call 0
>> Priority 15 BasePriority 15 UnusualBoost 0 ForegroundBoost 0
> IoPriority 2 PagePriority 5
>> ChildEBP RetAddr
>> 8fee9c20 82a92227 nt!ExSweepHandleTable
>> 8fee9c40 82a5dc78 nt!ObKillProcess+0x54
>> 8fee9cb4 82a92151 nt!PspExitThread+0x5d9
>> 8fee9ccc 828bd123 nt!PsExitSpecialApc+0x22
>> 8fee9d1c 828584e4 nt!KiDeliverApc+0x28b
>> 8fee9d1c 76e164f4 nt!KiServiceExit+0x64 (FPO: [0,3] TrapFrame @
> 8fee9d34)
>> 001ae5d8 00000000 ntdll!KiFastSystemCallRet (FPO: [0,0,0])
>
> The nt!ExSweepHandleTable being invoked for NTSD.EXE is the breakpoint I
> had
> stopped on to examine the other process states.
>
> So its still not clear for my what has caused an apparent “terminate all
> processes in session ID 1” rather than just the expected “terminate all
> processes under the interactive user’s logon session”.
> I did confirm via Process Explorer and Task Manager prior to breaking that
> both NTSD and WINLOGON are running under LocalSystem / logon session 999
> as
> expected, so they are for sure not part of the processes running under the
> interactive user’s logon session.
>
>
> For what it’s worth, enabling !htrace under NTSD and then being able to
> break on the WINLOGON.EXE process from KD while the handle table was still
> valid did indeed work as you had suggested. It would have taken me quite
> a
> while to figure out the user-mode handle tracing would still be accessible
> by the kernel-mode extension, so I appreciate that on multiple levels.
>
> Ultimately to track down my issue I resorted to enabling handle tracing
> using Application Verifier registry flags rather than involving NTSD, so
> that with NTSD out of the picture my WINLOGON.EXE instance would survive
> longer.
>
> Which wasn’t ideal, since it leaves me unable to trigger the -snapshot and
> -diff functions of !htrace. But since !bpid wasn’t working, that
> capability
> wasn’t available in this scenario anyway.
>
> CoolSwitch and the checked build of WINLOGON.EXE might have provided the
> arbitrary ability to break into WINLOGON.EXE under NTSD.EXE, but the
> handles
> I was interested in just happened to be within the available trace history
> so I never had to find out.
>
> Alan Adams
>
> —
> WINDBG is sponsored by OSR
>
> For our schedule of WDF, WDM, debugging and other seminars visit:
> http://www.osr.com/seminars
>
> To unsubscribe, visit the List Server section of OSR Online at
> http://www.osronline.com/page.cfm?name=ListServer
>
>