c++ - 内存泄漏到 v8 共享库 (dll) 版本 4.1.0.3
问题描述
我在 Windows 下的简单应用程序中使用 Google V8 作为共享库。现在,应用程序只是编译 JavaScript 而不执行。Vld 显示内存泄漏到 v8.dll 中。这些泄漏具有如下调用堆栈:
c:\program files (x86)\microsoft visual studio 14.0\vc\include\xmemory0 (977): v8.dll!std::_Wrap_alloc<std::allocator<std::_Container_proxy> >::allocate()
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (580): v8.dll!std::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >::_Alloc_proxy() + 0xF bytes
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (545): v8.dll!std::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >() + 0xA bytes
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (706): v8.dll!std::vector<unsigned char,std::allocator<unsigned char> >::vector<unsigned char,std::allocator<unsigned char> >() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\type-feedback-vector.h (21): v8.dll!v8::internal::FeedbackVectorSpec::FeedbackVectorSpec() + 0x31 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (175): v8.dll!v8::internal::AstProperties::AstProperties() + 0x33 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (2607): v8.dll!v8::internal::FunctionLiteral::FunctionLiteral() + 0x22 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (3515): v8.dll!v8::internal::AstNodeFactory::NewFunctionLiteral() + 0xDC bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (3814): v8.dll!v8::internal::Parser::ParseFunctionLiteral() + 0xBD bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (1060): v8.dll!v8::internal::Parser::ParseLazy() + 0x71 bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (1000): v8.dll!v8::internal::Parser::ParseLazy() + 0x15 bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (5125): v8.dll!v8::internal::Parser::Parse() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\parser.h (673): v8.dll!v8::internal::Parser::Parse() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\compiler.cc (687): v8.dll!v8::internal::GetUnoptimizedCodeCommon() + 0xF bytes
c:\work\v8\4.1.0.3\v8\src\compiler.cc (966): v8.dll!v8::internal::Compiler::GetLazyCode() + 0x15 bytes
c:\work\v8\4.1.0.3\v8\src\runtime\runtime-compiler.cc (36): v8.dll!v8::internal::__RT_impl_Runtime_CompileLazy() + 0xF bytes
c:\work\v8\4.1.0.3\v8\src\runtime\runtime-compiler.cc (20): v8.dll!v8::internal::Runtime_CompileLazy() + 0x72 bytes
...
c:\program files (x86)\microsoft visual studio 14.0\vc\include\xmemory0 (977): v8.dll!std::_Wrap_alloc<std::allocator<std::_Container_proxy> >::allocate()
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (580): v8.dll!std::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >::_Alloc_proxy() + 0xF bytes
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (545): v8.dll!std::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >::_Vector_alloc<std::_Vec_base_types<unsigned char,std::allocator<unsigned char> > >() + 0xA bytes
c:\program files (x86)\microsoft visual studio 14.0\vc\include\vector (706): v8.dll!std::vector<unsigned char,std::allocator<unsigned char> >::vector<unsigned char,std::allocator<unsigned char> >() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\type-feedback-vector.h (21): v8.dll!v8::internal::FeedbackVectorSpec::FeedbackVectorSpec() + 0x31 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (175): v8.dll!v8::internal::AstProperties::AstProperties() + 0x33 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (2607): v8.dll!v8::internal::FunctionLiteral::FunctionLiteral() + 0x22 bytes
c:\work\v8\4.1.0.3\v8\src\ast.h (3515): v8.dll!v8::internal::AstNodeFactory::NewFunctionLiteral() + 0xDC bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (957): v8.dll!v8::internal::Parser::DoParseProgram() + 0x10B bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (861): v8.dll!v8::internal::Parser::ParseProgram() + 0x27 bytes
c:\work\v8\4.1.0.3\v8\src\parser.cc (5131): v8.dll!v8::internal::Parser::Parse() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\parser.h (673): v8.dll!v8::internal::Parser::Parse() + 0xA bytes
c:\work\v8\4.1.0.3\v8\src\compiler.cc (1148): v8.dll!v8::internal::CompileToplevel() + 0x12 bytes
c:\work\v8\4.1.0.3\v8\src\compiler.cc (1338): v8.dll!v8::internal::Compiler::CompileScript() + 0x15 bytes
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (1448): v8.dll!v8::internal::Genesis::CompileScriptCached() + 0x9E bytes
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (1418): v8.dll!v8::internal::Genesis::CompileNative() + 0x64 bytes
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (1404): v8.dll!v8::internal::Genesis::CompileExperimentalBuiltin()
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (2198): v8.dll!v8::internal::Genesis::InstallExperimentalNatives() + 0x19B bytes
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (2766): v8.dll!v8::internal::Genesis::Genesis() + 0xD bytes
c:\work\v8\4.1.0.3\v8\src\bootstrapper.cc (351): v8.dll!v8::internal::Bootstrapper::CreateEnvironment() + 0x32 bytes
c:\work\v8\4.1.0.3\v8\src\api.cc (5229): v8.dll!v8::CreateEnvironment() + 0x34 bytes
c:\work\v8\4.1.0.3\v8\src\api.cc (5260): v8.dll!v8::Context::New()
可能有人以前遇到过同样的问题,可以帮助我找到这些内存泄漏到 v8 dll 的根源以修复它。
V8 版本 3.31.26 没有这样的内存泄漏。
我的应用很简单,首先是init v8:
v8::V8::InitializeICU();
auto platform = platform_ptr(v8::platform::CreateDefaultPlatform());
v8::V8::InitializePlatform(platform.get());
v8::V8::Initialize();
创建隔离:
isolate_ = v8::Isolate::New();
v8::HandleScope handle_scope(isolate_);
global_template_ = std::make_unique<js_compilation::global_template_wrapper>(isolate_);
编译js代码:
void js_compilation::compile(const std::string &js_script)
{
v8::Locker locker(isolate_);
v8::Isolate::Scope scope(isolate_);
//Create a stack allocated handle scope
v8::HandleScope handle_scope(isolate_);
v8::TryCatch try_catch(isolate_);
//Create the global template
v8::Local<v8::ObjectTemplate> global_template = v8::ObjectTemplate::New(isolate_);
//Create a context
v8::Local<v8::Context> context = v8::Context::New(isolate_, NULL, global_template);
//Set the context scope
v8::Context::Scope context_scope(context);
v8::Local<v8::Object> global = context->Global();
v8::Local<v8::String> source = v8::String::NewFromUtf8(isolate_, js_script.c_str());
//Compile
auto script = v8::Script::Compile(source);
if (script.IsEmpty())
{
throw std::runtime_error(get_error_string("Compile error: ", isolate_, try_catch));
}
script->Run();
compiled_script_.Reset(isolate_, script->GetUnboundScript());
}
编译后:
compiled_script_.Reset();
isolate_->Dispose();
v8::V8::Dispose();
v8::V8::ShutdownPlatform();
编译脚本为:
const std::string jsScript = "function test_function() {\n" \
" var match = 0;\n" \
" if (arguments[0] == arguments[1]) {\n" \
" match = 1;\n" \
" }\n" \
" return match;\n" \
"}\n\n"\
"function JSrepeat(name, repeat) {\n" \
" var printthis = \"\";\n" \
" for (var i = 0; i < repeat; i++) {\n" \
" printthis += name;\n" \
" }\n" \
" return printthis;\n" \
"}\n\n" \
"function ReturnThis(anything) {\n"\
" return anything;\n" \
"}\n\n"\
"function $13625432() {\n"\
" return \"Jimmy\";\n"\
"}\n";
解决方案
V8 开发人员在这里。版本 4.1.0.3 很古老,从未被认为特别稳定(.3 正好在一个分支点之后,而不是稳定分支的结尾,所以它几乎就像任何随机的每日快照一样)。如果您可以使用版本 7.0.276.40(或更高版本)重现这些问题,我有兴趣仔细看看,但目前版本 4.x 不值得任何人花时间,抱歉。
推荐阅读
- node.js - 使用 EJS 模板引擎在 Node.js 中提交表单后,我不断收到验证器错误
- r - 限制相关矩阵的小数位数
- command-line - 有没有办法拦截子进程的输出,或者在第一次输入到标准输入后从“继承”更改为“管道”?
- msal - 无法使用用户名/密码流通过 Java 后端进行身份验证
- google-cloud-shell - 如何不在 cloudshell 中的项目中进行编辑?
- android - 使用 GradientDrawable 使渐变从远离视图的末端开始
- graphql - Apollo 联合网关:在编写超图时包含本地模式
- ruby - 在具有相同 utf-8 编码的 Ruby 中比较相同的字符串失败
- statistics - 统计分解数基的两个特征
- java - TomCat 8.5.51 增加线程堆栈大小