我有以下程序:

#include <vector>

struct Comp1
{
    float x;
    std::vector<int> vec;
};

int main()
{
    std::vector<char> data;

    data.resize(sizeof(Comp1));

    Comp1* ptr1 = new (&data[0]) Comp1({.3f,{3,4,2,1}});

    data.resize(sizeof(Comp1)*2);

    Comp1* ptr2 = new (&data[sizeof(Comp1)]) Comp1({.2f,{2,3,4}});

    ptr1->~Comp1();

    std::vector<char>::iterator itrStart = data.begin();
    std::vector<char>::iterator itrEnd = itrStart + sizeof(Comp1);
    data.erase(itrStart,itrEnd);

    ptr2 = reinterpret_cast<Comp1*>(&data[0]);

    ptr2->~Comp1();

    return 0;
}

编译没有问题。在我的机器上执行没有问题。通过GDB运行它,没有任何报告。我的理解是,我在上面所做的一切都是正确的(除了当我将std::launderreinterpret_cast转换为char*吗?也许我错过了Comp1*的使用)。

但是,使用以下方法在此程序上调用DrMemory:
drmemory.exe test.exe -callstack_max_frames 40 -malloc_max_frames 40 -free_max_frames 40

给我以下错误输出:
Dr. Memory version 2.2.0 build 1 built on Jul  1 2019 00:42:20
Windows version: WinVer=105;Rel=1909;Build=18363;Edition=Enterprise
Dr. Memory results for pid 20424: "test.exe"
Application cmdline: "bin/test.exe -callstack_max_frames 40 -malloc_max_frames 40 -free_max_frames 40"
Recorded 117 suppression(s) from default C:\Program Files (x86)\Dr. Memory\bin\suppress-default.txt

Error #1: UNADDRESSABLE ACCESS of freed memory: reading 0x01975230-0x01975234 4 byte(s)
# 0 std::vector<>::~vector               [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:680]
# 1 Comp1::~Comp1                        [C:/Tests/test.cpp:3]
# 2 main                                 [C:/Tests/test.cpp:21]
Note: @0:00:01.329 in thread 2068
Note: next higher malloc: 0x01975258-0x01975268
Note: 0x01975230-0x01975234 overlaps memory 0x01975228-0x01975238 that was freed here:
Note: # 0 replace_operator_delete                              [d:\drmemory_package\common\alloc_replace.c:2975]
Note: # 1 __gnu_cxx::new_allocator<>::deallocate               [C:/MSYS2-32/mingw32/include/c++/10.1.0/ext/new_allocator.h:133]
Note: # 2 std::allocator_traits<>::deallocate                  [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/allocator.h:187]
Note: # 3 std::_Vector_base<>::_M_deallocate                   [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:354]
Note: # 4 std::vector<>::_M_default_append                     [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/vector.tcc:675]
Note: # 5 std::vector<>::resize                                [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:940]
Note: instruction: mov    0x04(%edx) -> %ecx

Error #2: UNADDRESSABLE ACCESS of freed memory: reading 0x0197522c-0x01975230 4 byte(s)
# 0 std::vector<>::~vector               [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:680]
# 1 Comp1::~Comp1                        [C:/Tests/test.cpp:3]
# 2 main                                 [C:/Tests/test.cpp:21]
Note: @0:00:01.447 in thread 2068
Note: next higher malloc: 0x01975258-0x01975268
Note: 0x0197522c-0x01975230 overlaps memory 0x01975228-0x01975238 that was freed here:
Note: # 0 replace_operator_delete                              [d:\drmemory_package\common\alloc_replace.c:2975]
Note: # 1 __gnu_cxx::new_allocator<>::deallocate               [C:/MSYS2-32/mingw32/include/c++/10.1.0/ext/new_allocator.h:133]
Note: # 2 std::allocator_traits<>::deallocate                  [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/allocator.h:187]
Note: # 3 std::_Vector_base<>::_M_deallocate                   [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:354]
Note: # 4 std::vector<>::_M_default_append                     [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/vector.tcc:675]
Note: # 5 std::vector<>::resize                                [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:940]
Note: instruction: mov    (%edx) -> %edx

Error #3: UNADDRESSABLE ACCESS of freed memory: reading 0x01975234-0x01975238 4 byte(s)
# 0 std::_Vector_base<>::~_Vector_base               [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:336]
# 1 std::vector<>::~vector                           [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:683]
# 2 Comp1::~Comp1                                    [C:/Tests/test.cpp:3]
# 3 main                                             [C:/Tests/test.cpp:21]
Note: @0:00:01.471 in thread 2068
Note: next higher malloc: 0x01975258-0x01975268
Note: 0x01975234-0x01975238 overlaps memory 0x01975228-0x01975238 that was freed here:
Note: # 0 replace_operator_delete                              [d:\drmemory_package\common\alloc_replace.c:2975]
Note: # 1 __gnu_cxx::new_allocator<>::deallocate               [C:/MSYS2-32/mingw32/include/c++/10.1.0/ext/new_allocator.h:133]
Note: # 2 std::allocator_traits<>::deallocate                  [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/allocator.h:187]
Note: # 3 std::_Vector_base<>::_M_deallocate                   [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:354]
Note: # 4 std::vector<>::_M_default_append                     [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/vector.tcc:675]
Note: # 5 std::vector<>::resize                                [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:940]
Note: instruction: mov    0x08(%eax) -> %edx

Error #4: UNADDRESSABLE ACCESS of freed memory: reading 0x0197522c-0x01975230 4 byte(s)
# 0 std::_Vector_base<>::~_Vector_base               [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:336]
# 1 std::vector<>::~vector                           [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:683]
# 2 Comp1::~Comp1                                    [C:/Tests/test.cpp:3]
# 3 main                                             [C:/Tests/test.cpp:21]
Note: @0:00:01.489 in thread 2068
Note: next higher malloc: 0x01975258-0x01975268
Note: 0x0197522c-0x01975230 overlaps memory 0x01975228-0x01975238 that was freed here:
Note: # 0 replace_operator_delete                              [d:\drmemory_package\common\alloc_replace.c:2975]
Note: # 1 __gnu_cxx::new_allocator<>::deallocate               [C:/MSYS2-32/mingw32/include/c++/10.1.0/ext/new_allocator.h:133]
Note: # 2 std::allocator_traits<>::deallocate                  [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/allocator.h:187]
Note: # 3 std::_Vector_base<>::_M_deallocate                   [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:354]
Note: # 4 std::vector<>::_M_default_append                     [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/vector.tcc:675]
Note: # 5 std::vector<>::resize                                [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:940]
Note: instruction: mov    (%eax) -> %ecx

Error #5: UNADDRESSABLE ACCESS of freed memory: reading 0x0197522c-0x01975230 4 byte(s)
# 0 std::_Vector_base<>::~_Vector_base               [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:335]
# 1 std::vector<>::~vector                           [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:683]
# 2 Comp1::~Comp1                                    [C:/Tests/test.cpp:3]
# 3 main                                             [C:/Tests/test.cpp:21]
Note: @0:00:01.504 in thread 2068
Note: next higher malloc: 0x01975258-0x01975268
Note: 0x0197522c-0x01975230 overlaps memory 0x01975228-0x01975238 that was freed here:
Note: # 0 replace_operator_delete                              [d:\drmemory_package\common\alloc_replace.c:2975]
Note: # 1 __gnu_cxx::new_allocator<>::deallocate               [C:/MSYS2-32/mingw32/include/c++/10.1.0/ext/new_allocator.h:133]
Note: # 2 std::allocator_traits<>::deallocate                  [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/allocator.h:187]
Note: # 3 std::_Vector_base<>::_M_deallocate                   [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:354]
Note: # 4 std::vector<>::_M_default_append                     [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/vector.tcc:675]
Note: # 5 std::vector<>::resize                                [C:/MSYS2-32/mingw32/include/c++/10.1.0/bits/stl_vector.h:940]
Note: instruction: mov    (%eax) -> %edx

===========================================================================
FINAL SUMMARY:

DUPLICATE ERROR COUNTS:

SUPPRESSIONS USED:

ERRORS FOUND:
      5 unique,     5 total unaddressable access(es)
      0 unique,     0 total uninitialized access(es)
      0 unique,     0 total invalid heap argument(s)
      0 unique,     0 total GDI usage error(s)
      0 unique,     0 total handle leak(s)
      0 unique,     0 total warning(s)
      0 unique,     0 total,      0 byte(s) of leak(s)
      0 unique,     0 total,      0 byte(s) of possible leak(s)
ERRORS IGNORED:
      2 potential error(s) (suspected false positives)
         (details: C:\Users\david\AppData\Roaming\Dr. Memory\DrMemory-test.exe.20424.000\potential_errors.txt)
      8 unique,    14 total,  19443 byte(s) of still-reachable allocation(s)
         (re-run with "-show_reachable" for details)
Details: C:\Users\david\AppData\Roaming\Dr. Memory\DrMemory-test.exe.20424.000\results.txt

我是否错过了我的程序的某些内容,还是在这种情况下DrMemory无法真正确定我在做什么?

最佳答案

用你的代码

data.resize(sizeof(Comp1)*2);

这是 vector 使用的存储空间的修改事件。发生这种情况时, vector 中的所有指针,迭代器和引用都会失效。那意味着
ptr1->~Comp1();

正在访问无效对象,并且您有未定义的行为。这不是内存泄漏,而是非法访问问题,这是Memory Dr诊断的原因。

09-07 09:44