imr*_*eal 6 c++ exception-handling exception
当抛出异常C++并且堆栈被解开时,如何选择正确的处理程序(catch子句)来处理异常?
void f1()
{
throw 1;
}
void f2()
{
try
{
f1();
}
catch(const char* e)
{
std::cout << "exc1";
}
}
...
try
{
f2();
}
catch(int& e)
{
std::cout << "exc2";
}
...
Run Code Online (Sandbox Code Playgroud)
例如,这个代码不出所料地打印,"exc2"因为catch(int& e)它能够处理1 int类型化的对象.
我不明白的是,这怎么可以静态解决?还是动态解决?是否传播了类型信息?
对于大多数事情,C++ 标准没有指定实现,但限制了有效的实现。不会有一个了解具体细节的通用答案。
Itanium ABI 是一种流行的 ABI,它提供与语言无关的异常支持。在该实现中,展开 API 调用堆栈帧的个性函数,该函数接收异常上下文、异常结构以及对指导 catch 行为的异常处理表的引用。根据程序异常表中调用的返回地址查找个性函数;假设唯一可以引发异常的指令是调用指令。(GCC 具有允许通过启用“非调用异常”从信号处理程序中抛出异常的扩展。)使用 Itanium ABI 的编译器提供了一个个性函数,该函数知道如何检查异常对象的运行时类型,并将该类型与元素进行比较的异常表。
还有其他方法可以做到这一点。例如,在 32 位 Windows 上,异常处理通过在堆栈上设置处理函数作为链接列表项来工作。这些链表节点包含异常处理程序的地址,它们使用EXCEPTION_RECORD来确定从那里去哪里。不幸的是,我自己对细节的了解有点少。
顺便说一下,Itanium ABI 并不是 C++ 所独有的。例如,在 Apple 平台上,Objective-C 代码也使用 Itanium ABI 来处理异常。这有一个有趣的特性,即任何一种语言中的 catch-all 子句都可以捕获另一种语言中的异常。
| 归档时间: |
|
| 查看次数: |
143 次 |
| 最近记录: |