等待程序的最后一个实例

我有两个程序,X是用户交互的正常程序,Y程序清理了程序Y获得的资源。可以有多个X的实例,但是只有一个Y(我已经用命名的互斥体解决了这个部分)。 现在,由于Y是一个清理程序,它应该被阻塞,直到X的最后一个实例消失。

我尝试使用信号量,但我无法弄清楚。 有人可以帮我吗?

信号量是这样做的一个有效方式,但不一定是最好的。 每当程序X启动,调用ReleaseSemaphore 。 每当一个进程终止时,在信号量句柄上调用WaitForSingleObject的超时时间为零(确保在异常处理程序中包含这个函数,以防程序崩溃)。
进程Y可以定期轮询一个零(或几毫秒)超时WaitForSingleObject 。 如果返回值是WAIT_OBJECT_0 ,它必须立即再次释放信号量(否则会阻止最后一个X进程试图退出!)。 如果返回值是WAIT_TIMEOUT ,则不再有X个进程。

最好的解决方案当然是从Y启动所有的X进程。在这种情况下,Y可以只是从CreateProcess获得的进程句柄上的WaitForMultipleObjects ,而没有额外的“ifs和whens”。 这将永远“只是工作”。 它也更高效。
这导致第二个最好的解决方案…得到处理与OpenProcessWaitForMultipleObjects在运行的进程。 问题是从哪里获取进程ID。 共享内存区可能会做,管道可能会做,或CreateToolhelp32Snapshot可能会给你的信息。

另一种方法是使用一个命名的互斥对象。 所有进程都调用CreateMutex 。 如果互斥量已经存在,则不会造成任何危害(GetLastError将返回ERROR_ALREADY_EXISTS ,但如此)。 如果进程终止或崩溃,所有打开的句柄都关闭,因此互斥量引用计数递减。
Y进程调用OpenMutex 。 这要么成功要么失败。 如果成功,它再次关闭手柄,睡觉,并再次尝试。 如果失败,则没有单个X进程正在运行。

另一种方式(虽然它可能有种族问题)将创建一个命名的共享内存段,并在进程X启动和退出调用InterlockedIncrementInterlockedDecrement 。 进程Y知道如果共享内存对象无法打开或计数器为零,则不会运行X进程。