在 C++ 中检测到内存泄漏
Detected memory leaks in c++
grpc (grpc.pb.cc) 生成的文件中的以下声明导致内存泄漏。
google::protobuf::ShutdownProtobufLibrary() 似乎没有释放此声明分配的内存。
能告诉我怎么发布吗?
PROTOBUF_ATTRIBUTE_INIT_PRIORITY static ::PROTOBUF_NAMESPACE_ID::internal::AddDescriptorsRunner dynamic_init_dummy_DxpGrpc_2eproto(&descriptor_table_DxpGrpc_2eproto);
Windows, C++, gRPC-1.40.0
在Windowsc++环境下创建控制台应用程序,执行以下代码
#include <crtdbg.h>.
#include "google/protobuf/service.h";
int main(int argc, char** argv) {
_CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
google::protobuf::ShutdownProtobufLibrary();
return 0;
}
下面的泄密内容会出来
Detected memory leaks!
Dumping objects -> {159}
{Normal block at 0x00E49B18, 8 bytes long.
Data: < k > 10 6B C9 00 00 00 00 00
Object dump complete.
当在grpc.pb.cc中声明AddDescriptorsRunner时,它调用以下class的DefaultConstruct()。
(文件:third_party\protobuf\src\google\protobuf\message_lite.h)
template <typename T>.
class ExplicitlyConstructed {
public:
void DefaultConstruct() { new (&union_) T(); }
template <typename... Args>
void Construct(Args&&... args) {
new (&union_) T(std::forward<Args>(args)...) ;
}
void Destruct() { get_mutable()->~T(); }
constexpr const T& get() const { return reinterpret_cast<const T&>(union_); }
T* get_mutable() { return reinterpret_cast<T*>(&union_); }
private:
// Prefer c++14 aligned_storage, but for compatibility this will do.
union AlignedUnion {
alignas(T) char space[sizeof(T)];
int64 align_to_int64;
void* align_to_ptr;
} union_;
};
静态或全局对象在 atexit
之后的最后一件事被释放,调试器报告错误泄漏。这个行为可以用这个例子重现:
#include <Windows.h>
std::string str;
int main()
{
_CrtDumpMemoryLeaks();//str is not freed yet
return 0;
}
您可以创建一个结构并将泄漏报告放在析构函数中,如下所示。请注意,在此示例中,std::string str;
用于导致泄漏报告。
如果 cleanup
没有定义,或者如果 cleanup
在 std::string str;
之后定义,那么会报告错误泄漏。定义的顺序很重要。
#include <iostream>
#include <string>
#include <Windows.h>
struct cleanup_t
{
~cleanup_t() { if(IsDebuggerPresent()) _CrtDumpMemoryLeaks(); }
} cleanup;
std::string str;
int main()
{
return 0;
}
grpc (grpc.pb.cc) 生成的文件中的以下声明导致内存泄漏。 google::protobuf::ShutdownProtobufLibrary() 似乎没有释放此声明分配的内存。 能告诉我怎么发布吗?
PROTOBUF_ATTRIBUTE_INIT_PRIORITY static ::PROTOBUF_NAMESPACE_ID::internal::AddDescriptorsRunner dynamic_init_dummy_DxpGrpc_2eproto(&descriptor_table_DxpGrpc_2eproto);
Windows, C++, gRPC-1.40.0
在Windowsc++环境下创建控制台应用程序,执行以下代码
#include <crtdbg.h>.
#include "google/protobuf/service.h";
int main(int argc, char** argv) {
_CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
google::protobuf::ShutdownProtobufLibrary();
return 0;
}
下面的泄密内容会出来
Detected memory leaks!
Dumping objects -> {159}
{Normal block at 0x00E49B18, 8 bytes long.
Data: < k > 10 6B C9 00 00 00 00 00
Object dump complete.
当在grpc.pb.cc中声明AddDescriptorsRunner时,它调用以下class的DefaultConstruct()。
(文件:third_party\protobuf\src\google\protobuf\message_lite.h)
template <typename T>.
class ExplicitlyConstructed {
public:
void DefaultConstruct() { new (&union_) T(); }
template <typename... Args>
void Construct(Args&&... args) {
new (&union_) T(std::forward<Args>(args)...) ;
}
void Destruct() { get_mutable()->~T(); }
constexpr const T& get() const { return reinterpret_cast<const T&>(union_); }
T* get_mutable() { return reinterpret_cast<T*>(&union_); }
private:
// Prefer c++14 aligned_storage, but for compatibility this will do.
union AlignedUnion {
alignas(T) char space[sizeof(T)];
int64 align_to_int64;
void* align_to_ptr;
} union_;
};
静态或全局对象在 atexit
之后的最后一件事被释放,调试器报告错误泄漏。这个行为可以用这个例子重现:
#include <Windows.h>
std::string str;
int main()
{
_CrtDumpMemoryLeaks();//str is not freed yet
return 0;
}
您可以创建一个结构并将泄漏报告放在析构函数中,如下所示。请注意,在此示例中,std::string str;
用于导致泄漏报告。
如果 cleanup
没有定义,或者如果 cleanup
在 std::string str;
之后定义,那么会报告错误泄漏。定义的顺序很重要。
#include <iostream>
#include <string>
#include <Windows.h>
struct cleanup_t
{
~cleanup_t() { if(IsDebuggerPresent()) _CrtDumpMemoryLeaks(); }
} cleanup;
std::string str;
int main()
{
return 0;
}