我有一些必须继续运行的生产关键代码。
将代码视为
while (true){
init();
do_important_things(); //segfault here
clean();
}
我不能相信代码是没有bug的,我需要能够记录问题以便以后调查。
这一次,我知道代码中的某个地方抛出了一个分段错误,我需要至少能够记录该错误,然后重新开始。
阅读这里有几个解决方案,但每一个都是火焰战,声称解决方案实际上弊大于利,没有真正的解释。我也发现了这个我考虑使用的答案,但是我不确定它对我的用例是否有好处。
那么,从C上的分割故障中恢复的最佳方法是什么?
我建议您创建一个非常小的程序,使其非常安全,用于监视有缺陷的程序。如果错误程序以您不喜欢的方式退出,请重新启动该程序。
Posix示例:
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <cstdio>
#include <iostream>
int main(int argc, char* argv[]) {
if(argc < 2) {
std::cerr << "USAGE: " << argv[0] << " program_to_monitor <arguments...>\n";
return 1;
}
while(true) {
pid_t child = fork(); // create a child process
if(child == -1) {
std::perror("fork");
return 1;
}
if(child == 0) {
execvp(argv[1], argv + 1); // start the buggy program
perror(argv[1]); // starting failed
std::exit(0); // exit with 0 to not trigger a retry
}
// Wait for the buggy program to terminate and check the status
// to see if it should be restarted.
if(int wstatus; waitpid(child, &wstatus, 0) != -1) {
if(WIFEXITED(wstatus)) {
if(WEXITSTATUS(wstatus) == 0) return 0; // normal exit, terminate
std::cerr << argv[0] << ": " << argv[1] << " exited with "
<< WEXITSTATUS(wstatus) << '\n';
}
if(WIFSIGNALED(wstatus)) {
std::cerr << argv[0] << ": " << argv[1]
<< " terminated by signal " << WTERMSIG(wstatus);
if(WCOREDUMP(wstatus)) std::cout << " (core dumped)";
std::cout << '\n';
}
std::cout << argv[0] << ": Restarting " << argv[1] << '\n';
} else {
std::perror("wait");
break;
}
}
}
我有一些程序的问题,我已经搜索了关于分割错误,我不太理解他们,我唯一知道的是,大概我试图访问一些我不应该访问的内存。问题是我看到我的代码,不明白我做错了什么。 谢谢你的时间。
顺着我之前的一个问题,大部分评论都说“就是不要,你处于冷宫状态,你要杀光一切,重新开始”。还有一个“安全”的变通方法。 我不明白的是为什么分割错误本质上是不可恢复的。 写入受保护内存的时刻被捕获-否则,不会发送。 如果能够捕捉到写入受保护内存的时刻,我不明白为什么——理论上——它不能在某个低级别上恢复,并将SIGSEGV转换为标准软件异常。 请解释为什么在出现分段错误后,程序处于不确定状态,因为很
编辑:底部的工作代码 我对编程相对较新,我正在试图理解为什么这不起作用。我决定通过一个函数而不是来处理卡片,以保持它尽可能模块化。这是我下面的代码;我知道错误与指针有关,但我不明白我做错了什么。 工作代码:
1)以上假设是否正确。2)当发生故障时,滚动窗口有状态是否有意义,我们从最后一个kafka分区提交的偏移量开始。3)当滚动窗口有状态时,这个状态什么时候可以被flink使用。4)为什么检查点和保存点的状态大小不同。5)当发生故障时,flink总是从sorce运算符开始。对吗?
正在尝试读取输入。txt文件,并使用fscanf将行内容存储到int变量、数组和2D数组中,以便以后使用该值进行计算。我认为这里的问题是因为我没有使用fscanf处理“EOF”? 这是我的密码: 这是你的电话号码。txt输入文件: 这里是输出:
以下这段代码在编译期间会产生分段错误: (gdb)运行 启动程序: /home/anna/Desktop/a.out 程序接收信号SIGSEGV,分段故障。 0xb7e97845在strtok()从 /lib/i386-linux-gnu/libc.so.6 更改第5行后,不会引发任何错误。 为什么会发生这种情况?