销毁对象后未调用析构函数放置新的

发布于 2024-10-07 00:23:46 字数 1370 浏览 10 评论 0原文

我不知道为什么这不起作用。以下Function是通过placement new创建的。提供了一个函数来检查它是否应该被破坏,如果是,则手动调用其析构函数。

这是测试用例,似乎从未调用析构函数:

/* Represents a function at runtime */ 
class Function {
public:
  /* Creates an invalid function */
  Function():codeptr(0) { }

  /* Creates a function with the given code pointer */
  Function(void *codeptr):codeptr(codeptr) { }

  /* Frees the function machine code */
  ~Function() {
    if(*this) {
      /* <- I explicitly put a debug output here! */
      destroyLLVMCode(codeptr);
    }
  }

public:
  /* Returns true if the function is valid 
   * (if the code pointer is non-null)
   */
  operator bool() const { return codeptr != 0; }

  /* Destroy this function by calling its destructor */
  void destroy() { ~Function(); }

private:
  void *codeptr;
};

我像下面这样使用它。将下面仍然存在问题的代码减少到最少。当然,在我的实际程序中,内存是通过分配器以另一种方式分配的。

#include <new>
#include <cstdlib>

int main() { 
  void *buffer = std::malloc(sizeof(Function));
  Function *f = new (buffer) Function(someExecutableLLVMCode);
  /* more code .. register with symbol tables etc.. */
  f->destroy();
}

您可以看到我正在读取 ~Function() 行中调用析构函数。编译器接受,但它最终不会调用它:我通过检查它是否真的删除了我给它的 LLVM 代码来验证它(在删除 codeptr 的 LLVM 代码之前将一些代码放入析构函数中) > 指向,如果 Function 有效)。

后来我才知道是什么原因造成的。您能给我一个解释吗?

I had no clue why this doesn't work. The following Function is created by placement new. A function is provided that checks whether it should be destructed, and if so, calls its destructor manually.

Here is the testcase where it seems the destructor is never called:

/* Represents a function at runtime */ 
class Function {
public:
  /* Creates an invalid function */
  Function():codeptr(0) { }

  /* Creates a function with the given code pointer */
  Function(void *codeptr):codeptr(codeptr) { }

  /* Frees the function machine code */
  ~Function() {
    if(*this) {
      /* <- I explicitly put a debug output here! */
      destroyLLVMCode(codeptr);
    }
  }

public:
  /* Returns true if the function is valid 
   * (if the code pointer is non-null)
   */
  operator bool() const { return codeptr != 0; }

  /* Destroy this function by calling its destructor */
  void destroy() { ~Function(); }

private:
  void *codeptr;
};

I used this like the following. Cut down the code below to the minimum that still exhibits the problem. In my real program, of course, the memory is allocated in another manner, from an allocator.

#include <new>
#include <cstdlib>

int main() { 
  void *buffer = std::malloc(sizeof(Function));
  Function *f = new (buffer) Function(someExecutableLLVMCode);
  /* more code .. register with symbol tables etc.. */
  f->destroy();
}

You can see I'm calling the destructor in the line reading ~Function(). The compiler accepts, but it doesn't end up calling it: I verified it by checking whether it really deletes the LLVM code I gave it (put some code into the destructor before deleting the LLVM code that the codeptr points to, in case the Function is valid).

I found out later on what is causing that. Could you please provide me with an explanation?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

苄①跕圉湢 2024-10-14 00:23:46

这是因为 ~Function(); 在语法上不是析构函数调用。请使用 this->~Function(); 代替。

~Function(); 被解析为运算符 ~ 并在堆栈上创建 Function 对象。 Function 类有一个 operator bool 这就是它被编译的原因。

This is because ~Function(); in not a destructor call syntactically here. Use this->~Function(); instead.

~Function(); is parsed as an operator ~ and creation of the Function object on the stack. Function class has an operator bool that's why this will be compiled.

ゝ杯具 2024-10-14 00:23:46

将显式析构函数调用更改为

this->~Function();

当前 ~Function 正在构造一个“函数”,然后调用 ~ 按位运算符(合法,因为您有一个到 bool 的转换),然后破坏它,而不是被调用的对象。

Change your explicit destructor call to

this->~Function();

Currently the ~Function is constructing a "Function" and then calling the ~ bitwise operator, (legal because you have a conversion to bool), and then destructing that, not the called object.

千笙结 2024-10-14 00:23:46

我记得析构函数不能被显式调用。尝试将清理代码从析构函数移至其他函数并调用它。

As I recall the destructor cannot be called explicitely. Try moving the cleanup code from destructor to other function and call it instead.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文