why is An extra worker thread created during the process startup?

1.3k views Asked by At

I am running a simple windows console application:- When the control comes at main I dumped the stack--

_ My main thread's stack:

5840    0   Main Thread Main Thread Normal


console.exe!wmain(int argc=1, wchar_t * * argv=0x006831a0)

console.exe!__tmainCRTStartup()  

console.exe!wmainCRTStartup()

kernel32.dll!@BaseThreadInitThunk@12()

ntdll.dll!___RtlUserThreadStart@8()

ntdll.dll!__RtlUserThreadStart@8()  

__

The above is fine by why do I see this at startup ??:

3740    0   Worker Thread   Win32 Thread Normal

Stack:

ntdll.dll!_KiFastSystemCallRet@0()  
ntdll.dll!_ZwDelayExecution@8()
ntdll.dll!__LdrpInitialize@8()
ntdll.dll!_LdrInitializeThunk@8()
1

There are 1 answers

0
Alois Kraus On

LdrInitializeThunk is the method to setup a new thread. I did create with VS2008 a plain Win32 console application (no MFC,ATL) and get only one thread. Only when I attach a debugger I get a second one because the debugger injects a thread to enable debugging of the process. Process startup is covered in great detail in the book here where nothing is mentioned that a second thread is needed. Asynchronous Procedure Calls APCs are also not to blame. Perhaps your call stack was created with not all symbols loaded and you wrongly suspect the debugger helper thread as a hidden thread inside your application. When you have a look at your process with process explorer without a debugger you should see only one thread.

Stage 6: Performing Process Initialization in the Context of the New Process

KiInitializeContextThread, which is called by KeInitializeThread, builds the initial context of the thread and the thread's kernel stack. The new thread begins life running the kernel-mode thread startup routine KiThreadStartup. (For a more detailed description of the thread startup steps leading to this, see the section "Flow of CreateThread.") The KiThreadStartup routine performs the following steps:

  1. Lowers the IRQL level from DPC/dispatch level to APC (asynchronous procedure call) level.

  2. Enables working set expansion.

  3. Queues a user-mode APC to the new thread to execute the user-mode thread startup routine LdrInitializeThunk inside Ntdll.dll.