在不使用pkill的情况下优雅地退出程序的最佳方式
Best way to exit a program gracefully without using pkill
我当前正在使用一个脚本调用pkill
来终止我的C++程序。然而,我注意到在使用pkill时,并没有从我的跟踪中调用析构函数。
有没有其他好方法可以让我优雅地退出程序pkill
看起来有点乱,缓冲区中的一些日志没有被记录下来。我希望能够在我的fstream上进行刷新,并通过程序关闭所有资源(而不是依靠O/S来清理我的烂摊子)。
该应用程序全天候运行,没有任何问题,我唯一想停止它的时间是在维护期间。该应用程序没有任何可供我键入exit的用户界面。
您可以通过以下几行为SIGTERM
定义一个信号处理程序来实现这一点:
包含块中的某个位置:
#include <signal.h>
#include <stdio.h>
是的,我们正在做i C
风格!
在代码的初始化部分:
signal (SIGTERM, handler);
然后定义信号处理程序代码(清除所有内容等):
void handler(int num)
{
// we might use this handler for many signals
switch (num)
{
case SIGTERM:
// clean up code.
break;
}
}
现在,当您运行pkill <app>
时,其中<app>
是可执行文件的名称,handler()
的代码将运行。
如果没有开关,默认的SIGTERM
信号将发送到应用程序。如果你选择使用不同的信号,你必须确保你发送的信号与你在handler()
中"捕获"的信号相同。
相关信息可以通过man 7 signal
找到,当然还有man kill
。
除了Zrvan的答案之外,请注意,只有一组受限的函数才能从信号处理程序中安全地调用。signal(7)手册页和Posix标准要求在信号处理程序内部只能直接或间接调用异步信号安全函数。请注意,printf
或malloc
在信号处理程序中是不安全的。信号处理程序的代码编写起来很棘手(而且您无法轻松调试它,因为信号发送是不可复制的)。
正如Glibc文档所建议的那样,您的信号处理程序只需设置一个volatile sig_atomic_t
变量,您的主循环将对其进行测试和处理。
如果您的应用程序是基于事件的,您还可以决定某个套接字或命名管道专用于控制它。该事件循环(可能使用select(2)或poll(2),甚至使用pselect
或ppoll
)可以处理管道或套接字上的控制消息。
您可能对像libevent这样的事件循环库感兴趣。您也可以使用像洋葱或Wt这样的HTTP服务器库。您也可能对SNMP或D-bus感兴趣。
克服信号处理程序限制的一个技巧是让它们在同一进程的管道上写入,例如Qt的doc所建议的。然后事件循环将处理该管道上的读取。
如果您的应用程序是多线程的,那么信号处理就更加棘手。一些信号被传递到单个线程。
除非您修改目标应用程序,否则我看不到任何方法。
考虑以下内容:
int main()
{
MyClass a;
while ( true )
{
}
}
你必须告诉程序退出循环。但除非你的应用程序上有某种信号处理机制,否则这似乎是不可能的。
你需要这样的东西:
int main()
{
MyClass a;
while ( !killSignalReceived() )
{
}
}
最好的方法是处理程序中的信号,然后使用kill
发送该信号。在信号处理程序中,标记一个将导致主循环结束的标志。
- 为什么异常不退出程序?
- 虽然循环在使用回车键时不退出程序
- 如果 I/O read() 处于阻塞阶段,如何使用 Ctrl+C 退出 C++ 程序?
- 捕获异常后如何退出程序执行
- 在C++中使用exit()退出程序有问题吗
- 从函数打印 CLI 帮助消息后,我应该如何干净地退出 C++ 程序?
- 如何实现否定用户输入退出程序和打印列表?
- gdb 退出:程序接收信号 SIGILL,使用 gcc / intel_mkl / gfortran -mavx 编译的
- 试图调节我的 do-while 以停止在终端中退出程序.菜单不会根据需要循环使用当前语句
- 如何在C 中按ENTER/返回键时退出程序循环
- 退出程序,默认开关
- 我想让程序保持运行,直到用户输入 n 退出程序
- 我找不到第一个用户输入后立即退出程序的原因
- 安全地退出程序 Win32 C++从分离的 std::线程
- 如何使用QCloseEvent退出程序
- 在主之前退出程序是明确的行为吗?
- C++键盘挂钩-退出程序,但也防止密钥在其他地方被处理
- 以程序方式关闭对话框-win32
- 在类中运行析构函数时退出程序
- 在不使用pkill的情况下优雅地退出程序的最佳方式