Div*_*ero 0 c++ memory-leaks c++20
在 C++20 中,我们可以分配内存constexpr
只要在上下文 \xe2\x80\x94 中释放内存,我们就可以在上下文中分配内存,即这是有效的:
constexpr int* g(){\n int* p = new int(100);\n return p;\n}\n\nconstexpr int f(){\n int* ret = g();\n int i = *ret;\n delete ret;\n return i;\n}\nstatic_assert(f() == 100);\n
Run Code Online (Sandbox Code Playgroud)\n然而这不会编译:
\nconstexpr int* g(){\n int* p = new int(100);\n return p;\n}\n\nconstexpr int f(){\n int* ret = g();\n int i = *ret;\n return i;\n}\nstatic_assert(f() == 100);\n
Run Code Online (Sandbox Code Playgroud)\n出现错误:
\nerror: '(f() == 100)' is not a constant expression because allocated storage has not been deallocated\n
Run Code Online (Sandbox Code Playgroud)\n现在这显然意味着编译器至少能够跟踪分配和释放 \xe2\x80\x94constexpr
。
我可以看到编译器如何在编译时控制分配,更好地跟踪内存泄漏,当然,这没有提到越界访问、释放后使用、双重释放等,但可以肯定的是,允许编译时泄漏检测的功能constexpr
可以扩展到某种程度的通用性编译时泄漏检测吗?
因此我的问题是:是否存在一些基本限制阻止编译器在非constexpr
编译时在非上下文中执行泄漏检测,或者该功能只是被认为是不必要的?
当然,允许编译时 constexpr 泄漏检测的功能也可以扩展到某种程度的通用编译时泄漏检测吗?
不,不能。
编译时代码执行意味着编译器正在执行代码。这就是“允许编译时 constexpr 泄漏检测的功能”:编译器正在执行此操作的事实。
非编译时执行由编译器生成的机器代码控制。当代码被执行时,编译器早已不在考虑之列了。为了进行泄漏检测,编译器必须在该机器代码中生成一堆额外的代码来进行检查。这会很慢。
此外,编译时代码必然受到限制。大多数使这一过程变得困难的技巧都是明确禁止的。仅卡紧reinterpret_cast
及其等效物就消除了问题的整个复杂性。您也不能抛出异常,因此这是您不必考虑的泄漏检测困难的另一个来源。大多数使泄漏检测变得困难的事情根本无法在代码中完成。constexpr