《Windows核心编程》——进程

  • 进程由进程内核对象(操作系统用来管理进程)和地址空间(代码、数据和堆栈)组成。
  • 每个进程至少拥有一个线程(主线程),来执行进程的地址空间中的代码。
  • 实例句柄:加载到进程地址空间的每个可执行文件或DLL文件均被赋予一个独一无二的实例句柄。获取当前进程句柄:
    • 1 HMODULE GetModuleHandle( 
      2   LPCTSTR lpModuleName
      3 );
  • 命令行:当一个新进程创建时,它要传递一个命令行。默认为lpszImageName。获取命令行参数:
    • 1 LPTSTR GetCommandLine(void);
  • 环境变量:WinCE不支持进程环境变量
  • 当前目录:WinCE不支持
  • 创建进程
    • 当一个线程调用CreateProcess时,系统就会创建一个进程内核对象,其初始使用计数是1。
    • 系统为新进程创建一个虚拟地址空间,并将可执行文件或任何必要的DLL文件的代码和数据加载到该进程的地址空间中。
    • 系统为新进程的主线程创建一个线程内核对象(其使用计数为 1)。通过执行 C/C++运行期启动代码,该主线程便开始运行,它最终调用 WinMain、wWinMain、main或wmain函数。
  • 关于函数CreateProcess:
    • lpCommandLine参数:lpCommandLine参数的原型是LPTSTR。这意味着CreateProcess期望你将传递一个非常量字符串的地址。从内部来讲,CreateProcess实际上并不修改你传递给它的命令行字符串。不过,在CreateProcess返回之前,它将该字符串恢复为它的原始形式(??)。注:Windows版本函数是如此,不过WinCE版本函数就变成了LPCWSTR常量字符串,测试了下,WinCE下常量字符串没有出现违规访问。函数原型:
       1 //Windows版本
       2  BOOL CreateProcess(
       3    LPCTSTR lpApplicationName,
       4    LPTSTR lpCommandLine,//非常量字符串
       5    LPSECURITY_ATTRIBUTES lpProcessAttributes,
       6    LPSECURITY_ATTRIBUTES lpThreadAttributes,
       7    BOOL bInheritHandles,
       8    DWORD dwCreationFlags,
       9    LPVOID lpEnvironment,
      10    LPCTSTR lpCurrentDirectory,
      11    LPSTARTUPINFO lpStartupInfo,
      12    LPPROCESS_INFORMATION lpProcessInformation
      13  );
      14  
      15  //WinCE版本
      16  BOOL CreateProcess( 
      17    LPCWSTR pszImageName, 
      18    LPCWSTR pszCmdLine, //常量字符串
      19    LPSECURITY_ATTRIBUTES psaProcess, 
      20    LPSECURITY_ATTRIBUTES psaThread, 
      21    BOOL fInheritHandles, 
      22    DWORD fdwCreate, 
      23    LPVOID pvEnvironment, 
      24    LPWSTR pszCurDir, 
      25    LPSTARTUPINFOW psiStartInfo, 
      26    LPPROCESS_INFORMATION pProcInfo
      27  );
    • lpProcessInformation参数:创建新进程可使系统建立一个进程内核对象和一个线程内核对象。在创建进程的时候,系统为每个对象赋予一个初始使用计数值1。然后,在CreateProcess返回之前,该函数打开进程对象和线程对象,并将每个对象的与进程相关的句柄放入PROCESS_INFORMATION结构的hProcess和hThread成员中。当CreateProcess在内部打开这些对象时,每个对象的使用计数就变为2。注:要想使父进程和子进程脱离关系,可在CreateProcess成功后,调用CloseHandle,使进程和线程计数变为1.当子进程退出时,则内核对象被销毁。否则,即使子进程退出了,该进程内核对象依然存在,造成内存泄漏。如:
       1 BOOL _WceExecute(LPCTSTR pExeFile)
       2 {
       3     ASSERT(pExeFile);
       4     PROCESS_INFORMATION pi = {0};
       5 
       6     BOOL b = CreateProcess(pExeFile, NULL, NULL, NULL, FALSE, 0, NULL, NULL, NULL, &pi);
       7     if (b)
       8     {
       9         CloseHandle(pi.hThread);
      10         CloseHandle(pi.hProcess);
      11     }
      12     return b;
      13 }
  • 终止进程:
    • 主线程的进入点函数返回(最好使用这个方法)。 

    • 进程中的一个线程调用ExitProcess函数(应该避免使用这种方法) 。

    • 另一个进程中的线程调用TerminateProcess函数(应该避免使用这种方法) 。

    • 进程中的所有线程自行终止运行(这种情况几乎从未发生) 。

原文地址:https://www.cnblogs.com/dahai/p/2818338.html