我正在寻找一种跨平台方法,通知多个客户端应用程序服务/守护程序已启动并能够处理传入连接。客户端将一直运行,而服务可能不会运行。通常,服务/守护程序将在计算机启动时自动启动,但在某些情况下可能不会启动,在这种情况下,客户端应在服务/守护程序启动时自动连接。
客户端的基本流程是等到他们注意到服务正在运行,然后连接。如果连接中断或者无法连接,则只需从头开始重试。
对于Windows,我有一个解决方案,其中服务在启动时发出全局事件对象的信号,以便客户端可以等待此事件。这实际上可行,但我很确定它不能处理所有潜在的情况(例如崩溃服务或运行的服务的多个实例)。我不介意客户“不小心”偶尔醒来,即使服务没有运行。我只是想避免客户端进入繁忙的循环尝试连接,同时快速响应服务启动。即只是在连接尝试之间添加一个睡眠并不是很好。
是否有跨平台方法来检测服务是否正在运行并准备接受连接?
更新:我将使用内存中的近似代码添加有关当前机制如何在Windows上运行的更多信息,所以请原谅任何拼写错误:
服务:
SECURITY_ATTRIBUTES sa;
// Set up empty SECURITY_ATTRIBUTES so that everyone has access
// ...
// Create a manual reset event, initially set to nonsignaled
HANDLE event = ::CreateEvent(&sa, TRUE, FALSE, "Global\\unique_name");
// Signal the event - service is running and ready
::SetEvent(event);
// Handle connections, do work
// If the service dies for whatever reason, Windows deletes the event handle
// The event is deleted when the last open handle to it is closed
// So the event is signaled for at least as long as the service lives
客户端:
while (true) {
// Set up event the same way as the service, including empty security attributes
// ...
HANDLE event = ::CreateEvent(&sa, TRUE, FALSE, "Global\\unique_name");
// Wait for the service to start
DWORD ret = ::WaitForSingleObject(event, INFINITE);
// Close the handle to avoid keeping the event object alive
// This isn´t enough in theory, but works in real usage as the number of clients
// will always be low
::CloseHandle(event);
// Check if we woke up because the event is signaled
if (WAIT_OBJECT_0 == ret) {
// connect to service, do work
// ...
}
}
我怎样才能在OS X和Linux上实现大致相同的效果?