Coverage for /Syzygy/agent/memprof/memory_profiler.cc

CoverageLines executed / instrumented / missingexe / inst / missLanguageGroup
0.0%0096.C++source

Line-by-line coverage:

   1    :  // Copyright 2014 Google Inc. All Rights Reserved.
   2    :  //
   3    :  // Licensed under the Apache License, Version 2.0 (the "License");
   4    :  // you may not use this file except in compliance with the License.
   5    :  // You may obtain a copy of the License at
   6    :  //
   7    :  //     http://www.apache.org/licenses/LICENSE-2.0
   8    :  //
   9    :  // Unless required by applicable law or agreed to in writing, software
  10    :  // distributed under the License is distributed on an "AS IS" BASIS,
  11    :  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12    :  // See the License for the specific language governing permissions and
  13    :  // limitations under the License.
  14    :  
  15    :  #include "syzygy/agent/memprof/memory_profiler.h"
  16    :  
  17    :  #include "base/bind.h"
  18    :  #include "syzygy/agent/common/process_utils.h"
  19    :  
  20  m :  namespace agent {
  21  m :  namespace memprof {
  22    :  
  23  m :  MemoryProfiler::MemoryProfiler()
  24  m :      : function_call_logger_(&session_) {
  25  m :    SetDefaultParameters(&parameters_);
  26  m :  }
  27    :  
  28  m :  bool MemoryProfiler::Init() {
  29    :    // We don't care if parameter parsing fails at runtime; such parameters will
  30    :    // simply be ignored.
  31  m :    ParseParametersFromEnv(&parameters_);
  32  m :    PropagateParameters();
  33  m :    ThreadState* state = GetOrAllocateThreadState();
  34  m :    if (!trace::client::InitializeRpcSession(
  35  m :            &session_, state->segment())) {
  36  m :      return false;
  37  m :    }
  38    :  
  39    :    // Setup the DLL watcher. This will be notified of module load and unload
  40    :    // events as they occur.
  41  m :    dll_watcher_.Init(base::Bind(&MemoryProfiler::OnDllEvent,
  42  m :                                 base::Unretained(this)));
  43    :  
  44    :    // Log all modules that are already loaded when we are. Further modules
  45    :    // will be logged as they load and unload via the DllNotification
  46    :    // mechanism.
  47  m :    LogAllModules();
  48    :  
  49  m :    return true;
  50  m :  }
  51    :  
  52  m :  MemoryProfiler::ThreadState* MemoryProfiler::GetOrAllocateThreadState() {
  53  m :    ThreadState* data = GetOrAllocateThreadStateImpl();
  54  m :    if (!data->segment()->write_ptr && session_.IsTracing())
  55  m :      session_.AllocateBuffer(data->segment());
  56    :  
  57  m :    return data;
  58  m :  }
  59    :  
  60  m :  MemoryProfiler::ThreadState* MemoryProfiler::GetThreadState() {
  61  m :    return tls_.Get();
  62  m :  }
  63    :  
  64  m :  void MemoryProfiler::PropagateParameters() {
  65  m :    function_call_logger_.set_stack_trace_tracking(
  66  m :        parameters_.stack_trace_tracking);
  67  m :    function_call_logger_.set_serialize_timestamps(
  68  m :        parameters_.serialize_timestamps);
  69  m :  }
  70    :  
  71  m :  MemoryProfiler::ThreadState* MemoryProfiler::GetOrAllocateThreadStateImpl() {
  72  m :    ThreadState *data = tls_.Get();
  73  m :    if (data != NULL)
  74  m :      return data;
  75    :  
  76  m :    data = new ThreadState(this);
  77  m :    if (data == NULL) {
  78  m :      LOG(ERROR) << "Unable to allocate per-thread data";
  79  m :      return NULL;
  80  m :    }
  81    :  
  82  m :    thread_state_manager_.Register(data);
  83  m :    tls_.Set(data);
  84    :  
  85  m :    return data;
  86  m :  }
  87    :  
  88  m :  void MemoryProfiler::LogAllModules() {
  89  m :    agent::common::ModuleVector modules;
  90  m :    agent::common::GetProcessModules(&modules);
  91    :  
  92  m :    for (size_t i = 0; i < modules.size(); ++i) {
  93  m :      DCHECK(modules[i] != NULL);
  94  m :      LogModule(modules[i]);
  95  m :    }
  96    :  
  97    :    // We need to flush module events right away, so that the module is
  98    :    // defined in the trace file before events using that module start to
  99    :    // occur.
 100  m :    GetOrAllocateThreadState()->FlushSegment();
 101  m :  }
 102    :  
 103  m :  void MemoryProfiler::LogModule(HMODULE module) {
 104  m :    {
 105  m :      base::AutoLock lock(lock_);
 106  m :      bool inserted = logged_modules_.insert(module).second;
 107  m :      if (!inserted)
 108  m :        return;
 109  m :    }
 110    :  
 111  m :    ThreadState* state = GetOrAllocateThreadState();
 112  m :    agent::common::LogModule(module, &session_, state->segment());
 113  m :  }
 114    :  
 115  m :  void MemoryProfiler::OnDllEvent(
 116  m :      agent::common::DllNotificationWatcher::EventType type,
 117  m :      HMODULE module,
 118  m :      size_t module_size,
 119  m :      const base::StringPiece16& dll_path,
 120  m :      const base::StringPiece16& dll_base_name) {
 121  m :    switch (type) {
 122  m :      case agent::common::DllNotificationWatcher::kDllLoaded: {
 123  m :        LogModule(module);
 124  m :        break;
 125  m :      }
 126    :  
 127  m :      case agent::common::DllNotificationWatcher::kDllUnloaded: {
 128  m :        base::AutoLock lock(lock_);
 129  m :        logged_modules_.erase(module);
 130  m :        break;
 131  m :      }
 132  m :    }
 133    :  
 134  m :    return;
 135  m :  }
 136    :  
 137  m :  MemoryProfiler::ThreadState::ThreadState(MemoryProfiler* parent)
 138  m :      : parent_(parent) {
 139  m :    DCHECK_NE(static_cast<MemoryProfiler*>(nullptr), parent);
 140  m :  }
 141    :  
 142  m :  bool MemoryProfiler::ThreadState::FlushSegment() {
 143  m :    if (!parent_->session_.ExchangeBuffer(&segment_))
 144  m :      return false;
 145  m :    return true;
 146  m :  }
 147    :  
 148  m :  }  // namespace memprof
 149  m :  }  // namespace agent

Coverage information generated Thu Mar 26 16:15:41 2015.