【问题标题】:Can the Exception Handling be used to prevent the crashes issued by bad pointers?异常处理可以用来防止坏指针导致的崩溃吗?
【发布时间】:2021-12-16 03:25:55
【问题描述】:

为了防止崩溃,我总是使用 Windows API VirtualQuery 检查指针是否有效;特别是,检查标志PAGE_NOACCESS 以验证指针没有指向错误的内存分配。如果指针是好的,那么我继续使用它。

我可以使用异常处理来获得相同的结果吗?我想使用try 块中的指针读取/写入,然后使用catch 可能的异常来防止崩溃。这是一种不好的做法,甚至可能吗?

【问题讨论】:

  • 尝试故意进行错误访问并亲自查看。我希望您看到的是崩溃不会生成 C++ 异常。
  • 感谢您的回复 dratenik。该软件无论如何都会随着处理而崩溃。我认为我应该继续使用 VirtualQuary。你认为 VirtualQuary 是不是有点矫枉过正?
  • 最好的解决方案是找到任何产生错误指针的错误并修复它。如果由于某种原因您无法做到这一点(通过使用您无法控制的 3rd 方二进制文件来固定错误),那么 VirtualQuery 可能是一个好主意。
  • 反对使用 VirtualQuery 的理由是,如果你把检查放在任何地方,你的代码就会变得一团糟。相反,现代 C++ 方法倾向于尽可能避免使用指针,并提供地址清理器等工具来帮助查找错误。
  • 谢谢。我刚刚发现了一个小技巧。我可以尝试检查指针是否在程序使用的内存范围内,而不是 VirtualQuery。如果我正在工作的模块从0x0AAA分配到0x0FFF,并且指针试图指向这个范围之外,那么它可能是无效的。

标签: c++ windows pointers exception


【解决方案1】:

这个问题 (How to catch segmentation fault in Linux?) 有很多关于这样做的信息,包括关于它的一些问题的好措辞,所以请阅读所有答案和 cmets。

从该帖子中收集的信息:

  1. 据说可以通过__try__catch 使用MSVC
  2. 取消引用未映射的指针最终会以发送到进程的段故障信号结束。您可以使用自定义处理程序捕获此信号,但从技术上讲,从它返回是 UB。
  3. 存在一些第三方库,可以在某些 Linux 平台上将信号​​转换为异常。 (他们如何做到这一点可能值得怀疑。)
  4. 尝试从 seg 故障中恢复可能没有意义。

尝试捕获错误的取消引用是否有意义?

解除对错误指针的引用可能无法通过检查指针来捕获。它可能会随机指向有效内存,在这种情况下,您可能会得到一些奇怪的 UB。

现代 C++ 通过完全避免拥有指针(使用 RAII 指针)来避免一些指针问题。您仍然可以传递指针(作为非拥有指针)。具有智能指针的良好设计可以更轻松地管理生命周期问题,例如悬空引用和未初始化/垃圾值。但它不会解决所有可能的问题。

在某些情况下检查/清理指针仍然很有用,例如在 API 边界处。例如在以指针为输入的公开函数中。

如果您在使用指针时遇到很多问题,也许这表明您需要简化设计或找到更好的方法来管理指针?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-08-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-13
    • 1970-01-01
    相关资源
    最近更新 更多