C:\> TLIST /t
System Process (0)
System (2)
 smss.exe (20)
  csrss.exe (30)
  WINLOGON.EXE (34)
  SERVICES.EXE (40)
   SPOOLSS.EXE (66)
   NCPHONE.EXE (77)
   RPCSS.EXE (80)
    mdm.exe (153)
   TAPISRV.EXE (84)
   RASMAN.EXE (102)
   PSTORES.EXE (110)
  LSASS.EXE (43)
  NDDEAGNT.EXE (46)
explorer.exe (140) Program Manager
 systray.exe (162)
 REMINDER.EXE (172)
 UpFront.exe (44)
 DDHELP.EXE (220)
 OUTLOOK.EXE (186) Inbox - Microsoft Outlook
  MAPISP32.EXE (211)
 MSDEV.EXE (223) Unfrag - Microsoft Developer Studio - [InfoViewer Topic]
 WINWORD.EXE (168) Microsoft Word - Q & A in Progress.DOC
 CMD.EXE (59) C:\WINNT\System32\cmd.exe - tlist -t 
  TLIST.EXE (196)
mswheel.exe (174)
TASKMGR.EXE (130)
RASMON.EXE (252) Dial-Up Networking Monitor
Figure 2 SmallApp.cpp
 /******************************************************************************
 Module name: SmallApp.cpp
 Written by:  Jeffrey Richter
 Purpose:     Spawn helper that kills everything in its Process Group.
 ******************************************************************************/
 
 //#define UNICODE
 //#define _UNICODE
 
 #define STRICT
 #include <Windows.h>
 #include <process.h>
 #include <tchar.h>
 #include <stdio.h>
 
 ///////////////////////////////////////////////////////////////////////////////
 
 extern "C" int  _tmain(int argc, TCHAR* argv[]) {
 
    // Make sure that we've been passed the right number of arguments
    if (argc < 3) {
       _tprintf(
          __TEXT("Usage: %s (InheritableEventHandle) (CommandLineToSpawn)\n"), 
          argv[0]);
       return(0);
    }
 
    // Construct the full command line
    TCHAR szCmdLine[MAX_PATH] = { 0 };
    for (int x = 2; x < argc; x++) {
       _tcscat(szCmdLine, argv[x]); 
       _tcscat(szCmdLine, __TEXT(" ")); 
    }
 
    STARTUPINFO         si = { sizeof(si) };
    PROCESS_INFORMATION pi = { 0 };
    DWORD dwExitCode = 0;
 
    HANDLE h[2];
    h[0] = (HANDLE) _ttoi(argv[1]);  // The inherited event handle
 
    // Spawn the other processes as part of this Process Group
    BOOL f = CreateProcess(NULL, szCmdLine, NULL, NULL, TRUE, 
                           0, NULL, NULL, &si, &pi);
 
    if (f) {
       CloseHandle(pi.hThread);
       h[1] = pi.hProcess;
 
       // Wait for the spawned-process to die or for the event
       // indicating that the processes should be forcibly killed.
       switch (WaitForMultipleObjects(2, h, FALSE, INFINITE)) {
          case WAIT_OBJECT_0 + 0:  // Force termination
             GenerateConsoleCtrlEvent(CTRL_BREAK_EVENT, 0);
             WaitForSingleObject(pi.hProcess, INFINITE);
             break;
 
          case WAIT_OBJECT_0 + 1:  // App terminated normally
             // Make its exit code our exit code
             GetExitCodeProcess(pi.hProcess, &dwExitCode);
             break;
       }
       CloseHandle(pi.hProcess);
    }
    CloseHandle(h[0]);   // Close the inherited event handle
    return(dwExitCode);
 }
 
 //////////////////////////////// End of File //////////////////////////////////