C++ 内存泄漏。Valgrind - 不匹配的删除

Bop*_*Bop -1 c++ linux valgrind memory-leaks

我从线程 #1 接收对象 - 它是第 3 方库代码 - 我的回调调用了它。

对象具有固定长度的字符串字段:

typedef struct somestr_t {
    char * Data;
    int    Len; } somestr_t;
Run Code Online (Sandbox Code Playgroud)

每次我都必须手动创建对象的副本,然后才能将其进一步传递给我的代码。因此,除其他外,我也使用这个助手复制这些字符串:

inline void CopyStr(somestr_t * dest, somestr_t * src)
{
    if (src->Len == 0) {
        dest->Len = 0;
        return;
    }

    char* data = new char[src->Len];

    memcpy(data, src->Data, src->Len);

    dest->Data = data;
    dest->Len = src->Len;
}
Run Code Online (Sandbox Code Playgroud)

然后我删除该对象及其字符串字段:

if (someobj != nullptr)
{
    if (someobj ->somestr.Len != 0) delete someobj ->somestr.Data;
    . . .
    delete someobj ;
}
Run Code Online (Sandbox Code Playgroud)

当我运行时,valgrind我在希望删除字符串的地方得到了这些:

==33332== Mismatched free() / delete / delete []
==33332==    at 0x48478DD: operator delete(void*, unsigned long) (vg_replace_malloc.c:935)
==33332==    by 0x41B517: cleanup() (Recorder.cpp:86)
==33332==    by 0x41BB29: signal_callback(int) (Recorder.cpp:129)
==33332==    by 0x4C11DAF: ??? (in /usr/lib64/libc.so.6)
==33332==    by 0x4CD14D4: clock_nanosleep@@GLIBC_2.17 (clock_nanosleep.c:48)
==33332==    by 0x4CD6086: nanosleep (nanosleep.c:25)
==33332==    by 0x4D02DE8: usleep (usleep.c:32)
==33332==    by 0x41C3EF: Logger(void*) (LogThreads.h:28)
==33332==    by 0x4C5C6C9: start_thread (pthread_create.c:443)
==33332==    by 0x4BFC2B3: clone (clone.S:100)
==33332==  Address 0xd661260 is 0 bytes inside a block of size 12 alloc'd
==33332==    at 0x484622F: operator new[](unsigned long) (vg_replace_malloc.c:640)
==33332==    by 0x419E72: CopyStr (CbOverrides.h:23)
Run Code Online (Sandbox Code Playgroud)

和总结报告:

==34077== HEAP SUMMARY:
==34077==     in use at exit: 328,520 bytes in 3,828 blocks
==34077==   total heap usage: 124,774 allocs, 120,946 frees, 559,945,294 bytes allocated
==34077==
==34077== LEAK SUMMARY:
==34077==    definitely lost: 0 bytes in 0 blocks
==34077==    indirectly lost: 0 bytes in 0 blocks
==34077==      possibly lost: 0 bytes in 0 blocks
==34077==    still reachable: 328,520 bytes in 3,828 blocks
==34077==         suppressed: 0 bytes in 0 blocks

Run Code Online (Sandbox Code Playgroud)

valgrind以前从未使用过(或任何 C++ 工具),所以我不确定 - 为什么mismatch delete会被报告?为什么退出时还有328K未释放内存?

Pau*_*oyd 5

    char* data = new char[src->Len];
Run Code Online (Sandbox Code Playgroud)

    if (someobj ->somestr.Len != 0) delete someobj ->somestr.Data;
Run Code Online (Sandbox Code Playgroud)

delete应该是这样delete []

为什么会有still reachable: 425,333 bytes in 3,860 blocks。抱歉,我的水晶球坏了。

通常 Valgrind 确实会提示您需要做什么

==19283== Rerun with --leak-check=full to see details of leaked memory
Run Code Online (Sandbox Code Playgroud)

这有点意思,因为在你完成之后它会告诉你另一个选择

==21816== Reachable blocks (those to which a pointer was found) are not shown.
==21816== To see them, rerun with: --leak-check=full --show-leak-kinds=all
Run Code Online (Sandbox Code Playgroud)

尝试这些并开始处理未释放的内存。

  • 请注意,如果混合使用 malloc/delete 和 new/free,也会出现不匹配的错误。我还没有添加对不匹配对齐/未对齐新/删除的检测。一天 ... (2认同)