微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

用于Windows的进程间通信IPC

我有一个使用Microsoft Visual C ++编写的C程序,我需要实现某种“keepalive”,所以我能够接受它认为进程间通信成一个新的程序,将杀死和重新启动第一个如果在过去的5秒内没有收到味精。

问题是,我一直在寻找C语言的任何教程或Windows的例子,但几乎所有我find的是C ++。

任何帮助或资源?

编辑:正如@Adriano在答案中build议,我试图使用共享内存。 但是由于某种我无法捕捉到的exception,启动程序正在被Windows终止。 调用copyMemory时会发生。

如何编码看门狗定时器以重新启动Windows服务?

Linux软件看门狗

软锁的原因是什么?

如何使用linux软件看门狗

Windows文件系统的看门狗Python脚本

代码如下:

#include "stdafx.h" #include "windows.h" #include "iostream" using namespace std; int launchMyProcess(); void killMyProcess(); bool checkIfMyProcessIsAlive(); STARTUPINFO sInfo; PROCESS_@R_859_4045@ION pInfo; HANDLE mappedFile; LPVOID pSharedMemory; long lastReceivedBeatTimeStamp; const int MSECONDS_WITHOUT_BEAT = 500; const LPTSTR lpCommandLine = "MyProcess.exe configuration.txt"; int main(int argc,char* argv[]) { mappedFile = CreateFileMapping(INVALID_HANDLE_VALUE,NULL,PAGE_READWRITE,sizeof(int),"Global\ActivityMonitor"); LPVOID pSharedMemory = MapViewOfFile(mappedFile,FILE_MAP_READ,sizeof(int)); if(!launchMyProcess()){ cout<<"Error creating MyProcess.exe"<<endl; UnmapViewOfFile(pSharedMemory); CloseHandle(mappedFile); return -1; } while(true){ Sleep(100); if(!checkIfMyProcessIsAlive()){ cout<<"relaunching MyProcess..."; killMyProcess(); if(!launchMyProcess()){ cout<<"Error relaunching MyProcess.exe"<<endl; UnmapViewOfFile(pSharedMemory); CloseHandle(mappedFile); return -1; } } } UnmapViewOfFile(pSharedMemory); CloseHandle(mappedFile); return 0; } bool checkIfMyProcessIsAlive() { static int volatile latestMagicNumber = 0; int currentMagicNumber = 0; copyMemory(&currentMagicNumber,pSharedMemory,sizeof(int)); if(currentMagicNumber != latestMagicNumber){ latestMagicNumber = currentMagicNumber; return true; } return false; } int launchMyProcess() { ZeroMemory(&sInfo,sizeof(sInfo)); sInfo.cb = sizeof(sInfo); ZeroMemory(&pInfo,sizeof(pInfo)); return CreateProcess(NULL,lpCommandLine,FALSE,&sInfo,&pInfo); } void killMyProcess() { TerminateProcess(pInfo.hProcess,0); CloseHandle(pInfo.hProcess); CloseHandle(pInfo.hThread); Sleep(3000); }

Systemctl依赖性失败,停止依赖服务

如何在linuxembedded式中更改看门狗定时器

语法错误附近的意外令牌“做”与sudo运行时

将“V”写入看门狗设备文件的含义

Linux在崩溃时自动重启应用程序 – 守护进程

如果你的老C应用程序有一个消息泵(因为它有一个UI),也许最简单的方法来检查它是否存在是IsHungAppWindow()函数,Windows将为你做的东西。

如果这不是你的情况,你需要IPC有很多选择,这取决于你想使用什么样的IPC机制。 这里我只列出一些资源。

有关IPC技术的概述,请访问: http : //msdn.microsoft.com/en-us/library/windows/desktop/aa365574 (v= vs.85).aspx

一些例子:

MSMQ: http : //msdn.microsoft.com/en-us/library/windows/desktop/ms705205​​( v= vs.85).aspx

命名管道: http : //msdn.microsoft.com/en-us/library/windows/desktop/aa365590 ( v = vs.85).aspx和http://msdn.microsoft.com/en-us/library/窗户/桌面/ aa365592(v = vs.85)的.aspx

共享内存: http : //msdn.microsoft.com/en-us/library/windows/desktop/aa366551(v=vs.85).aspx

编辑

我认为一个小例子将会比单纯的文字更清晰。 在这个例子中,我将使用共享内存,但是你可以使用任何你喜欢的(你感觉更舒适)。 它没有经过测试,所以请使用它作为参考。

MONITOR进程应该先启动。

VOID CALLBACK CheckItIsAlive(PVOID lpParam,BOOLEAN TimerOrWaitFired) { static int volatile latestMagicNumber = 0; int currentMagicNumber = 0; copyMemory(&currentMagicNumber,lpParam,sizeof(int)); if (currentMagicNumber != latestMagicNumber) latestMagicNumber = currentMagicNumber; else { // Do something,it's hanged } } void main() { // Shared memory used to communicate with the other process HANDLE mappedFile = CreateFileMapping(INVALID_HANDLE_VALUE,"Global\MyActivityMonitor"); LPVOID pSharedMemory = MapViewOfFile(mappedFile,sizeof(int)); // Thread used to check activity HANDLE queue = CreateTimerQueue(); HANDLE hTimer = NULL; CreateTimerQueueTimer(&hTimer,queue,(WAITORTIMERCALLBACK)CheckItIsAlive,5000,WT_EXECUTEDEFAULT); // Do your work here... // Clean up DeleteTimerQueue(queue); UnmapViewOfFile(pSharedMemory); CloseHandle(mappedFile); }

MONITORED进程将向Monitor进程发送信号。

VOID CALLBACK NotifyImAlive(PVOID lpParam,BOOLEAN TimerOrWaitFired) { static int volatile counter = 1; int tick = counter++; copyMemory(lpParam,&tick,sizeof(int)); } void main() { // Shared memory used to communicate with the other process HANDLE mappedFile = OpenFileMapping(FILE_MAP_ALL_ACCESS,FILE_MAP_WRITE,sizeof(int)); // Thread used to signal activity HANDLE queue = CreateTimerQueue(); HANDLE hTimer = NULL; CreateTimerQueueTimer(&hTimer,(WAITORTIMERCALLBACK)NotifyImAlive,WT_EXECUTEINTIMERTHREAD); // Do your work here... // Clean up DeleteTimerQueue(queue); UnmapViewOfFile(pSharedMemory); CloseHandle(mappedFile); }

共享内存是一个非常轻量级的资源,你可以使用任何你喜欢的定时器(如果时间不是一个严格的要求,你可以做一些空闲的处理。我个人喜欢这个因为你不需要锁定任何线程并可能你有一个空闲时间处理线程)。

定时器函数从Windows 2000开始支持,请确保_WIN32_WINNT宏定义为0x0500(或更多)。

附录

我没有在列表中提到,因为它们只存在于较新版本的操作系统中,但您甚至可以使用条件变量 。 Windows 8将支持一个非常有用的WaitOnAddress函数,但它仍然是未来,所以我认为你不能使用它。

从OP和各种意见,听起来好像主要目标是确定应用程序是否挂起。 一些相当简单的方法来创建一种可以由另一个应用程序监视的“心跳”,可以是共享内存或命名的信号量。

您可以在一个进程中使用CreateFileMapping和MapViewOfFile来创建共享内存,然后在另一个进程中使用MapViewOfFile来获取指向它的指针。 如果将其创建为整数的大小,则保持活动的一个简单方法是让该进程每隔几秒增加内存中的值。 另一个进程可以每隔几秒读取一次以验证它正在改变。

有了一个命名的信号量( CreateSemaphore和OpenSemaphore ),你可以做基本相同的事情。 让受监视的应用程序周期性地发出信号,让监视器等待,以确保它已经发出信号。

这似乎是另外一个由于不熟悉你所处理的平台而走了很长的路。

如果你在评论中所说的只是你的程序是否还活着,那么你可以杀死它,甚至不需要IPC。

在你希望监控的节目开始时:

HANDLE hMutex = CreateMutex(NULL,_T("MyMagicKey")); WaitForSingleObject(hMutex,INFINITE);

在“看门狗”程序中,您检查其他实用程序是否像这样是活着的:

HANDLE hMutex = OpenMutex(SYNCHRONIZE,_T("MyMagicKey")); if (hMutex == NULL && GetLastError() == ERROR_FILE_NOT_FOUND) //The app being watched is already dead else //whatever you want

还有其他六种同样适用(或更好)的解决方案。 如果您的看门狗是唯一一个创建将要被监视的应用程序,那么您可以等待CreateProcess (或ShellExecuteEx )的HANDLE 。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐