【问题标题】:Delphi Monitoring Existing ProcessesDelphi 监控现有进程
【发布时间】:2015-02-18 13:55:21
【问题描述】:

我是新手,很抱歉,如果我的问题看起来很愚蠢,我正在编写一个 Delphi 程序,在该程序中,我通过队列中的多个线程运行外部可执行文件列表并等待它们完成使用 CreateProcess 之类的:

 CreateProcess(Pchar(NotepadExe), Nil, Nil, Nil,
                 False, NORMAL_PRIORITY_CLASS,
                 Nil, Nil, StartupInfo,ProcessInfo), 

WaitForSingleObject(ProcessInfo.hProcess, INFINITE);

现在我调用的程序正在执行冗长的工作,所以如果我的程序在外部可执行文件仍在运行时关闭,是否有一种简单的方法可以重新获得对进程的访问并再次等待它们?还有一些已经完成的情况呢?

【问题讨论】:

  • 这些流程是您开发的还是第三方程序?如果它们是由你开发的,你可以在它们中实现代码,让它们中的每一个去注册自己的互斥体,然后你可以检查它的存在。
  • 关闭时记下子进程和您的进程的 ID。再次运行时,搜索父 pid 等于您之前的 pid 的子进程 pid 打开同步句柄并等待。从理论上讲,可能会遇到具有相同关系但应用程序不同的相同 pid。实际上,可以忽略不计。
  • 请参阅this question 了解从 Delphi 枚举正在运行的进程的一种方法。
  • 如果您的程序为每个子进程调用WaitForSingleObject(ProcessInfo.hProcess, INFINITE);,那么在每个子进程完成之前它究竟是如何“干净地”关闭的?

标签: delphi winapi


【解决方案1】:

我按照@SertacAkyuz 的建议做了一些事情,而且效果很好

在执行期间,我使用

将当前进程 ID 添加到文件中
GetCurrentProcessId

当我启动我的程序时,我从文件中读取保存的 processIds 然后确定哪些当前正在运行的进程是我已经运行的子进程,然后我创建一个线程来再次打开和监视它

uses tlhelp32;
----
var Snap:THandle;
ProcessE:TProcessEntry32;
----
Snap:=CreateToolhelp32Snapshot(TH32CS_SNAPALL, 0);
 ProcessE.dwSize:=SizeOf(ProcessE);

 if Process32First(Snap,ProcessE) then
 begin \\Iterate through running processes
      while Process32Next(Snap,ProcessE) do
       \\Determine whether it's a child process of the saved PiD
          if ProcessE.th32ParentProcessID = mySavedPiD then
\\ Creating the thread to monitor the process 
cnThread:=TContinueThread.Create(ProcessE.th32ProcessID);
cnThread.Start;
\\ In the thread Execute 
var hndl:THandle;   
----
    hndl:=OpenProcess(PROCESS_ALL_ACCESS ,False,PiD);
    WaitForSingleObject(hndl, INFINITE);

这可能不是最好的解决方案,但它现在对我有用,但是,我仍然需要处理增量(在我的程序缺席期间完成的进程)

【讨论】:

    【解决方案2】:

    为每个启动的进程创建一个线程,浪费了一个线程。还有internal thread resources are limited。如果您现在使用WaitForSingleObject(,INFINITE),请花时间了解WaitForMultipleObjects 并启动单个线程以等待多个进程。 (或者像@DavidHeffernan 建议的那样了解jobs

    【讨论】:

    • 进程是系统控制的容器,管理系统资源。在这些资源中至少有一个线程。我不太确定如何在没有 "wasting" 线程的情况下创建进程。如果你能告诉我一个不消耗线程资源的进程,我会给你一个赞成票。
    • 如果您有一个进程 A 创建一个线程来启动进程 B,然后在 B 的句柄上执行WaitForSingleObject(ProcessInfo.hProcess,INFINITE),那么进程 A 中就有一个停滞的线程坐在那里。对我来说看起来很浪费,尤其是 B 的倍数。
    • 我还有一些其他的排序/并行功能,除非我使用不同的线程,否则我无法实现。
    猜你喜欢
    • 2023-03-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多