在c++中,进程获得SIGABRT的场景是什么?这个信号总是来自进程内部还是可以从一个进程发送到另一个进程?
有没有办法确定是哪个进程在发送这个信号?
在c++中,进程获得SIGABRT的场景是什么?这个信号总是来自进程内部还是可以从一个进程发送到另一个进程?
有没有办法确定是哪个进程在发送这个信号?
当前回答
进程从自身获取SIGABRT的情况: Hrvoje提到了一个从ctor调用的被掩埋的纯虚拟生成一个中止,我为此重新创建了一个例子。 这里,当要构造d时,它首先调用它的基类A ctor, 并将内部指针传递给自身。 在表被有效指针填满之前调用纯虚方法, 因为d还没有被构造。
#include<iostream>
using namespace std;
class A {
public:
A(A *pa){pa->f();}
virtual void f()=0;
};
class D : public A {
public:
D():A(this){}
virtual void f() {cout<<"D::f\n";}
};
int main(){
D d;
A *pa = &d;
pa->f();
return 0;
}
编译:g++ -o aa aa.cpp
无限制
:运行。/ aa
pure virtual method called
terminate called without an active exception
Aborted (core dumped)
现在让我们快速查看核心文件,并验证SIGABRT确实被调用:
gdb aa core
见规则:
i r
rdx 0x6 6
rsi 0x69a 1690
rdi 0x69a 1690
rip 0x7feae3170c37
校验码:
灾害学0 x7feae3170c37
mov $0xea,%eax = 234 <- this is the kill syscall, sends signal to process
syscall <-----
http://blog.rchapman.org/posts/Linux_System_Call_Table_for_x86_64/
234 sys_tgkill pid_t tgid pid_t pid int sig = 6 = SIGABRT
:)
其他回答
正如“@sarnold”,恰当地指出,任何进程都可以向任何其他进程发送信号,因此,一个进程可以向其他进程发送SIGABORT,在这种情况下,接收进程无法区分它是否因为自己的内存调整等而到来,或者其他人已经“unicastly”发送给它。
在我工作的一个系统中,有一个死锁检测器,它实际上可以通过心跳来检测进程是否从某些任务中出来。如果不是,则声明该进程处于死锁状态,并向其发送SIGABORT。
我只是想分享这一前景参考问题。
进程从自身获取SIGABRT的情况: Hrvoje提到了一个从ctor调用的被掩埋的纯虚拟生成一个中止,我为此重新创建了一个例子。 这里,当要构造d时,它首先调用它的基类A ctor, 并将内部指针传递给自身。 在表被有效指针填满之前调用纯虚方法, 因为d还没有被构造。
#include<iostream>
using namespace std;
class A {
public:
A(A *pa){pa->f();}
virtual void f()=0;
};
class D : public A {
public:
D():A(this){}
virtual void f() {cout<<"D::f\n";}
};
int main(){
D d;
A *pa = &d;
pa->f();
return 0;
}
编译:g++ -o aa aa.cpp
无限制
:运行。/ aa
pure virtual method called
terminate called without an active exception
Aborted (core dumped)
现在让我们快速查看核心文件,并验证SIGABRT确实被调用:
gdb aa core
见规则:
i r
rdx 0x6 6
rsi 0x69a 1690
rdi 0x69a 1690
rip 0x7feae3170c37
校验码:
灾害学0 x7feae3170c37
mov $0xea,%eax = 234 <- this is the kill syscall, sends signal to process
syscall <-----
http://blog.rchapman.org/posts/Linux_System_Call_Table_for_x86_64/
234 sys_tgkill pid_t tgid pid_t pid int sig = 6 = SIGABRT
:)
我将从竞争性编程(cp)的角度给出我的答案,但它也适用于其他领域。
很多时候在做cp的时候,约束条件是相当大的。
例如:我有一个关于变量N, M, Q的问题,使得1≤N, M, Q < 10^5。
我犯的错误是我在c++中声明了一个大小为10000 x 10000的2D整数数组,并在Codechef中挣扎了近2天的SIGABRT错误。
现在,如果我们计算:
整数的典型大小:4字节 不。数组中的单元格:10000 x 10000 总大小(字节):400000000字节= 4*10^8≈400mb
你对这些问题的解决方案将在你的PC上工作(不总是),因为它可以负担得起这个大小。
但编码网站(在线裁判)的资源有限,只有几kb。
因此,会出现SIGABRT错误和其他此类错误。
结论:
在这样的问题中,我们不应该声明一个数组或向量或任何其他这种大小的DS,但我们的任务是使我们的算法如此高效,以至于它可以在没有它们(DS)或内存更少的情况下工作。
PS:这个错误可能有其他原因;上面是其中一个。
它通常发生在内存分配有问题的时候。
当我的程序试图分配一个 大小为负的数组。
在c++中还有另一个简单的原因。
std::thread::~thread{
if((joinable ())
std::terminate ();
}
例如,线程范围结束,但你忘记调用
thread::join();
or
thread::detach();