对nodejs进行profiling

node.js by 达达 at 2012-03-17

想在服务器上捣腾一下node.js,编译的时候加了--profile参数,想要开启profile功能,安装了node.js后,运行 nodejs --prof {js文件} 可以得到一个v8.log文件,但是到 {nodejs代码}/deps/v8/tools 目录下运行 linux-tick-processor {v8.log文件} 的时候,提示:

d8 shell not found in .
To build, execute 'scons  d8' from the V8 directory

上网搜了一圈,最后按以下步骤成功编译了d8 shell,并正常使用linux-tick-processor:

  1. cd {nodejs代码}/deps/v8
  2. scons prof=on
  3. scons d8
  4. 把目录 {nodejs代码}/deps/v8 加入PATH环境变量

按以上步骤配置后,就可以用 nodejs --prof {js文件} 的方式运行,并获得一个v8.log文件,然后到 {nodejs代码}/deps/v8/tools 目录下运行 linux-tick-processor {v8.log文件},就可以得到类似这样的输出结果:

Statistical profiling result from ../../../v8.log, (82093 ticks, 0 unaccounted, 0 excluded).

 [Shared libraries]:
   ticks  total  nonlib   name
      3    0.0%    0.0%  /lib/x86_64-linux-gnu/libc-2.13.so
      2    0.0%    0.0%  /lib/x86_64-linux-gnu/libpthread-2.13.so

 [JavaScript]:
   ticks  total  nonlib   name
      1    0.0%    0.0%  Stub: InstanceofStub
      1    0.0%    0.0%  Builtin: A builtin from the snapshot

 [C++]:
   ticks  total  nonlib   name
  81995   99.9%   99.9%  epoll_wait
     15    0.0%    0.0%  __write
     11    0.0%    0.0%  node::WrappedScript::CompileRunInThisContext(v8::Arguments const&)
      5    0.0%    0.0%  node::Parser::Execute(v8::Arguments const&)
      4    0.0%    0.0%  v8::internal::RelocIterator::next()
      4    0.0%    0.0%  _IO_vfprintf
      2    0.0%    0.0%  v8::internal::UpdatingVisitor::VisitPointers(v8::internal::Object**, v8::internal::Object**)
      2    0.0%    0.0%  v8::internal::StaticMarkingVisitor::VisitUnmarkedObjects(v8::internal::Heap*, v8::internal::Object**, v8::internal::Object**)
      2    0.0%    0.0%  v8::internal::Parser::ParseMemberWithNewPrefixesExpression(v8::internal::PositionStack*, bool*)
      2    0.0%    0.0%  node::Binding(v8::Arguments const&)
      1    0.0%    0.0%  v8::internal::Zone::New(int)
      1    0.0%    0.0%  v8::internal::UpdatingVisitor::VisitPointer(v8::internal::Object**)
      1    0.0%    0.0%  v8::internal::TextNode::EatsAtLeast(int, int, bool)
      1    0.0%    0.0%  v8::internal::StubCache::ComputeKeyedLoadField(v8::internal::String*, v8::internal::JSObject*, v8::internal::JSObject*, int)
      1    0.0%    0.0%  v8::internal::String::IsAsciiEqualTo(v8::internal::Vector)
      1    0.0%    0.0%  v8::internal::StaticMarkingVisitor::VisitSharedFunctionInfoAndFlushCode(v8::internal::Map*, v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::StaticMarkingVisitor::VisitCode(v8::internal::Map*, v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::Scope::LookupRecursive(v8::internal::Handle, bool, v8::internal::Variable**)
      1    0.0%    0.0%  v8::internal::RelocInfoWriter::Write(v8::internal::RelocInfo const*)
      1    0.0%    0.0%  v8::internal::Parser::ParseStatement(v8::internal::ZoneList >*, bool*)
      1    0.0%    0.0%  v8::internal::Parser::ParseLeftHandSideExpression(bool*)
      1    0.0%    0.0%  v8::internal::Parser::ParseLazy(v8::internal::CompilationInfo*, v8::internal::UC16CharacterStream*, v8::internal::ZoneScope*)
      1    0.0%    0.0%  v8::internal::OldSpace::PrepareForMarkCompact(bool)
      1    0.0%    0.0%  v8::internal::OldSpace::PageAllocationLimit(v8::internal::Page*)
      1    0.0%    0.0%  v8::internal::MemoryAllocator::InitializePagesInChunk(int, int, v8::internal::PagedSpace*)
      1    0.0%    0.0%  v8::internal::MarkCompactCollector::UpdatePointersInOldObject(v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::MarkCompactCollector::RelocateCodeObject(v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::MacroAssembler::InvokeFunction(v8::internal::JSFunction*, v8::internal::ParameterCount const&, InvokeFlag, v8::internal::CallWrapper const&, v8::internal::CallKind)
      1    0.0%    0.0%  v8::internal::LoadStubCompiler::CompileLoadField(v8::internal::JSObject*, v8::internal::JSObject*, int, v8::internal::String*)
      1    0.0%    0.0%  v8::internal::LargeObjectSpace::Contains(v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::LargeObjectChunk::New(int, v8::internal::Executability)
      1    0.0%    0.0%  v8::internal::LAllocator::LiveRangeFor(int)
      1    0.0%    0.0%  v8::internal::JavaScriptScanner::SkipSingleLineComment()
      1    0.0%    0.0%  v8::internal::JavaScriptScanner::ScanIdentifierOrKeyword()
      1    0.0%    0.0%  v8::internal::JavaScriptScanner::Scan()
      1    0.0%    0.0%  v8::internal::JavaScriptScanner::Next()
      1    0.0%    0.0%  v8::internal::JSReceiver::LocalLookup(v8::internal::String*, v8::internal::LookupResult*)
      1    0.0%    0.0%  v8::internal::IC::Clear(unsigned char*)
      1    0.0%    0.0%  v8::internal::Heap::DoScavenge(v8::internal::ObjectVisitor*, unsigned char*)
      1    0.0%    0.0%  v8::internal::Heap::AllocateRaw(int, v8::internal::AllocationSpace, v8::internal::AllocationSpace)
      1    0.0%    0.0%  v8::internal::FullCodeGenerator::StackValueContext::Plug(v8::internal::Variable*) const
      1    0.0%    0.0%  v8::internal::FullCodeGenerator::EmitClassOf(v8::internal::ZoneList*)
      1    0.0%    0.0%  v8::internal::FlexibleBodyVisitor::Visit(v8::internal::Map*, v8::internal::HeapObject*)
      1    0.0%    0.0%  v8::internal::CallICBase::ReceiverToObjectIfRequired(v8::internal::Handle, v8::internal::Handle)
      1    0.0%    0.0%  v8::internal::Assembler::movq(v8::internal::Register, v8::internal::Operand const&)
      1    0.0%    0.0%  v8::internal::Assembler::call(v8::internal::Handle, v8::internal::RelocInfo::Mode, unsigned int)
      1    0.0%    0.0%  node::TCPWrap::OnConnection(uv_stream_s*, int)
      1    0.0%    0.0%  node::HandleWrap::Close(v8::Arguments const&)
      1    0.0%    0.0%  __pthread_mutex_lock
      1    0.0%    0.0%  __libc_free
      1    0.0%    0.0%  _ZN2v88internal8JSObject11LocalLookupEPNS0_6StringEPNS0_12LookupResultE.constprop.306
      1    0.0%    0.0%  _ZN2v88internal20HGlobalValueNumberer12AnalyzeBlockEPNS0_11HBasicBlockEPNS0_9HValueMapE.constprop.605
      1    0.0%    0.0%  _IO_file_xsputn
      1    0.0%    0.0%  _IO_default_xsputn

 [GC]:
   ticks  total  nonlib   name
     33    0.0%

 [Bottom up (heavy) profile]:
  Note: percentage shows a share of a particular caller in the total
  amount of its parent calls.
  Callers occupying less than 2.0% are not shown.

   ticks parent  name
  81995   99.9%  epoll_wait