- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我们有一个要分发的 C 库以及 C 示例代码。
库当然是在 Release模式下构建的。示例代码项目在 cmake 中,因此它可以轻松地在 Linux 和 Windows 上运行。在 Linux(调试和发布)以及 Windows(发布)上,我们没有问题。然而,在 Windows 上(调试),我们在离开 main 时遇到了一个问题:程序触发了一个断言:
Invalid address specified to RtlValidateHeap
Expression: _CrtIsValidHeapPointer(block)
然后在继续该过程时,会引发以下异常:
Unhandled exception at [...] (ntdll.dll)
0xC000000D STATUS_INVALID_PARAMETER
由于这似乎与运行时库有关,我们尝试将其从 MDd(多线程 dll 调试)更改为 MD(多线程 dll)[ more on these here ] 它解决了这个问题。然而,这似乎是一种解决方法而不是修复方法:发布库(使用 MD 构建)应该可以在使用 MDd 的调试程序中使用,对吗?
据我们了解,运行时库中的冲突仅在调用方进行分配并在被调用方进行释放时出现,反之亦然。所以我们跟踪所有分配以检查它们,一切似乎都正常。我们在 Linux (Valgrind) 和 Windows (CrtDbg) 中对示例代码进行了泄漏检测,但他们没有发现任何泄漏,一切似乎都很好。
期望使用 MD 构建的发布库在 MDd 程序中运行是否正确?如果不是,这似乎很奇怪:库总是在发布时分发,但在开发时用于调试解决方案......如果是,是什么导致了这个问题?
最佳答案
这听起来更像是堆损坏而不是泄漏。这意味着有人正在覆盖堆(传递了它分配的内存)。找到它可能会很痛苦。
首先,检查您的示例代码。将它剥离到最低限度的“hello world”,然后构建它直到它再次发生。然后检查示例代码。如果不是示例代码,请检查调用了哪些库函数并进行代码审查。
作为辅助,您可以使用 MS 堆检查功能。将它们放在函数入口和函数导出处,或者维护您定期检查的全局版本。下面是一个例子:
#include <crtdbg.h>
void example(void)
{
_CrtMemState memStateStart, memStateEnd, memStateDelta;
// Make a checkpoint of the heap's state so we can later check the heap is still OK
_CrtMemCheckpoint( &memStateStart );
//
// do your things
//
// Check the heap
_CrtMemCheckpoint( &memStateEnd );
_CrtSetReportMode( _CRT_WARN, _CRTDBG_MODE_WNDW );
_CrtSetReportMode( _CRT_ERROR, _CRTDBG_MODE_WNDW );
_CrtSetReportMode( _CRT_ASSERT, _CRTDBG_MODE_WNDW );
if (_CrtMemDifference( &memStateDelta, &memStateStart, &memStateEnd ))
_CrtMemDumpStatistics( &memStateDelta );
_CrtDumpMemoryLeaks();
}
关于C 运行时库问题 MD/MDd,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57462705/
我是一名优秀的程序员,十分优秀!