【问题标题】:How to appropriately track memory allocations and frees in C++ with overloads to operator news and operator deletes?如何正确跟踪 C++ 中的内存分配和释放,并重载运算符新闻和运算符删除?
【发布时间】:2021-04-01 07:49:30
【问题描述】:

要求:跟踪分配和删除。每个分配都用两个参数标识,我们暂时称它们为 P1 和 P2。

我使用带有两个附加参数的全局重载放置 new 运算符

void * operator new(size_t size, parameter_1_t p1, parameter_2_t p2);

大小在运行时适当填充。我使用 p1 和 p2 来索引一个二维数组,在该数组中,我将当前使用的内存分配增加为 (p1,p2) 和“大小”。 类似2dArray[p1][p2].increment_current_bytes(size);

现在,我的问题是,当我使用放置删除时,我如何知道要释放的内存大小?我需要知道它以相应地更新二维数组。 试着写这个 -

void * operator delete(void* ptr, size_t size, parameter_1_t p1, parameter_2_t p2);

不起作用,因为 C++ 中没有提供这样的操作符 delete。它希望我在显式调用 operator delete 函数时填写 size。

参考 - https://en.cppreference.com/w/cpp/memory/new/operator_delete

【问题讨论】:

  • 我如何知道要释放的内存大小? -- 我认为你需要一些更健壮的东西来实际保留大小信息.在致电new 之后,您是否只是将size 信息扔掉? valgrind 等工具如何工作?

标签: c++ operator-overloading new-operator delete-operator placement-new


【解决方案1】:

操作员删除预计只需要分配的指针。分配库使用 private 结构来存储分配的大小。例如,通常分配的内存比所要求的稍多,并使用返回指针之前的初始内存 用于各种内务变量。尝试检测堆粉碎的版本还在内存区域返回给调用者之后放置一个副本(实际上分配了请求的大小加上内部管理大小的两倍),并且在取消分配时控制两个区域仍然包含相同的信息。

如果您有特殊要求并使用特殊参数,您可以使用由返回指针索引的映射,或者模仿标准库并在分配的块中使用私有区域。

【讨论】:

    【解决方案2】:

    这是因为 C++ 不跟踪分配的内存大小。你必须自己记账。我想到的两个选项是记录表或内存前缀。

    使用记录表,您基本上可以将所有分配存储在哈希表之类的东西中。当调用new 时,将结果指针与分配大小一起存储在该表中。当delete 被调用时,只需在表中查找该指针以获取大小,然后将其删除。

    使用前缀,您必须分配比实际请求更多的内存。然后将缓冲区的大小存储在前 N 个字节中,并在 N 个字节后返回指向内存的指针。例如,如果用户请求 20 个字节,您分配 28 个字节 (N = 8) 并将请求的大小 20 存储在前 8 个字节中。然后返回一个指向剩余 20 个字节的指针。 然后在delete 上读取给定指针之前的 8 个字节以获取块大小。

    【讨论】:

      猜你喜欢
      • 2021-09-05
      • 1970-01-01
      • 2012-11-18
      • 2021-03-13
      • 2013-04-18
      • 2016-02-19
      • 1970-01-01
      • 2012-11-26
      相关资源
      最近更新 更多