我可能完全误解了如何使用Google Breakpad API,并且在这种情况下愿意接受评论/建议/粗鲁的言论。我正在尝试调用以下C++函数:

bool WriteMinidumpForException(EXCEPTION_POINTERS* exinfo);

我有一个std::exception的引用:
try {
  return QApplication::notify(receiver, event);
} catch (std::exception &ex) {
  eh_.WriteMinidumpForException(?????);
  // ... do some more stuff and ultimately kill this process
}

(eh_google_breakpad::ExceptionHandler。)

我在中放什么?

背景:之所以有必要(我认为)是因为Qt将不支持在事件处理程序中引发的异常。它不会正确传播,因此Breakpad生成的minidump完全无用,因为丢失了异常的实际上下文。相反,您必须捕获所有异常并在QApplication::notify()的重写中处理它们,这是我正在尝试做的事情。在发生异常的情况下,我想立即为该异常编写我的小型转储(听起来像WriteMinidumpForException会这样做),然后通知用户并退出应用程序。但是我不确定要作为EXCEPTION_POINTERS*参数传递什么。

最佳答案

在MSVC编译器中,C++异常搭载在 native Windows异常检测(SEH,结构化异常处理)上。尽管存在很大的阻抗失配,但是异常滤波器的概念在C++中并没有很好的匹配。在catch处理程序捕获到异常时,SEH异常已得到处理,并且堆栈已展开。 EXCEPTION_POINTERS信息是奇闻趣事。异常过滤器实际上是存在的,这就是它针对想要捕获的特定类型进行过滤的方式,但是它们是由编译器自动生成的。没有合理的C++语法可以使它们有用。

您需要使用编译器支持来处理SEH异常。使用__try, __except关键字(__finally是可选的),并使您的过滤器捕获C++异常的异常代码0xe04d5343('MSC')。但是,您确实失去了捕获特定C++异常类型的能力,因为管道没有源就埋在CRT中。将C++尝试放入__try内即可解决此问题,因此__except仅会看到C++代码未过滤的异常。

使用SetUnhandledExceptionFilter()是完成此操作的另一种方法,您确实应该将其视为任何未处理异常的最终支持,而与代码位置无关。这是创建崩溃的应用程序的小型转储的最佳方法。最后但并非最不重要的一点是,在流程本身内部创建崩溃的应用程序的小型转储不是最佳方法。很有可能这不能很好地工作,进程状态可能会严重损坏。一种故障模式是锁定进程堆。考虑到堆损坏是非常常见的崩溃原因,这并非没有可能。使用“保护进程”修复该问题,使用命名事件向其发出信号以进行小型转储。您的异常过滤器只需要设置事件即可,该事件始终有效。

09-05 11:57