Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
[Java] bump dependency to Java 7
[simgrid.git] / src / mc / mc_process.cpp
index fda88dd..2a70cb5 100644 (file)
 
 #include "mc_process.h"
 #include "mc_object_info.h"
-#include "AddressSpace.hpp"
 #include "mc_unw.h"
 #include "mc_snapshot.h"
 #include "mc_ignore.h"
 #include "mc_smx.h"
 #include "mc_server.h"
 
+#include "mc/AddressSpace.hpp"
+#include "mc/ObjectInformation.hpp"
+#include "mc/Variable.hpp"
+
 using simgrid::mc::remote;
 
 extern "C" {
@@ -51,7 +54,10 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_process, mc,
 static const char *const FILTERED_LIBS[] = {
   "ld",
   "libbz2",
+  "libboost_chrono",
   "libboost_context",
+  "libboost_system",
+  "libboost_thread",
   "libc",
   "libc++",
   "libcdt",
@@ -65,6 +71,7 @@ static const char *const FILTERED_LIBS[] = {
   "libm",
   "libpthread",
   "librt",
+  "libsigc",
   "libstdc++",
   "libunwind",
   "libunwind-x86_64",
@@ -124,6 +131,7 @@ static ssize_t pread_whole(int fd, void *buf, size_t count, std::uint64_t offset
     } else if (res==0) {
       return -1;
     } else if (errno != EINTR) {
+      perror("pread_whole");
       return -1;
     }
   }
@@ -164,6 +172,14 @@ static void MC_zero_buffer_init(void)
   close(fd);
 }
 
+static
+int open_process_file(pid_t pid, const char* file, int flags)
+{
+  char buff[50];
+  snprintf(buff, sizeof(buff), "/proc/%li/%s", (long) pid, file);
+  return open(buff, flags);
+}
+
 }
 
 namespace simgrid {
@@ -206,6 +222,8 @@ Process::Process(pid_t pid, int sockfd)
   process->heap = NULL;
   process->heap_info = NULL;
   process->init_memory_map_info();
+  process->clear_refs_fd_ = -1;
+  process->pagemap_fd_ = -1;
 
   // Open the memory file
   if (process->is_self())
@@ -218,7 +236,7 @@ Process::Process(pid_t pid, int sockfd)
   }
 
   // Read std_heap (is a struct mdesc*):
-  mc_variable_t std_heap_var = process->find_variable("__mmalloc_default_mdp");
+  simgrid::mc::Variable* std_heap_var = process->find_variable("__mmalloc_default_mdp");
   if (!std_heap_var)
     xbt_die("No heap information in the target process");
   if(!std_heap_var->address)
@@ -277,6 +295,11 @@ Process::~Process()
 
   free(process->heap_info);
   process->heap_info = NULL;
+
+  if (process->clear_refs_fd_ >= 0)
+    close(process->clear_refs_fd_);
+  if (process->pagemap_fd_ >= 0)
+    close(process->pagemap_fd_);
 }
 
 /** Refresh the information about the process
@@ -377,7 +400,7 @@ void Process::init_memory_map_info()
       }
     }
 
-    std::shared_ptr<s_mc_object_info_t> info =
+    std::shared_ptr<simgrid::mc::ObjectInformation> info =
       MC_find_object_info(this->memory_map_, pathname, is_executable);
     this->object_infos.push_back(info);
     if (is_executable)
@@ -400,7 +423,7 @@ void Process::init_memory_map_info()
   XBT_DEBUG("Get debug information done !");
 }
 
-std::shared_ptr<s_mc_object_info_t> Process::find_object_info(remote_ptr<void> addr) const
+std::shared_ptr<simgrid::mc::ObjectInformation> Process::find_object_info(remote_ptr<void> addr) const
 {
   for (auto const& object_info : this->object_infos) {
     if (addr.address() >= (std::uint64_t)object_info->start
@@ -433,29 +456,29 @@ std::shared_ptr<ObjectInformation> Process::find_object_info_rw(remote_ptr<void>
   return nullptr;
 }
 
-mc_frame_t Process::find_function(remote_ptr<void> ip) const
+simgrid::mc::Frame* Process::find_function(remote_ptr<void> ip) const
 {
-  std::shared_ptr<s_mc_object_info_t> info = this->find_object_info_exec(ip);
+  std::shared_ptr<simgrid::mc::ObjectInformation> info = this->find_object_info_exec(ip);
   return info ? info->find_function((void*) ip.address()) : nullptr;
 }
 
 /** Find (one occurence of) the named variable definition
  */
-mc_variable_t Process::find_variable(const char* name) const
+simgrid::mc::Variable* Process::find_variable(const char* name) const
 {
   // First lookup the variable in the executable shared object.
   // A global variable used directly by the executable code from a library
   // is reinstanciated in the executable memory .data/.bss.
   // We need to look up the variable in the execvutable first.
   if (this->binary_info) {
-    std::shared_ptr<s_mc_object_info_t> const& info = this->binary_info;
-    mc_variable_t var = info->find_variable(name);
+    std::shared_ptr<simgrid::mc::ObjectInformation> const& info = this->binary_info;
+    simgrid::mc::Variable* var = info->find_variable(name);
     if (var)
       return var;
   }
 
-  for (std::shared_ptr<s_mc_object_info_t> const& info : this->object_infos) {
-    mc_variable_t var = info->find_variable(name);
+  for (std::shared_ptr<simgrid::mc::ObjectInformation> const& info : this->object_infos) {
+    simgrid::mc::Variable* var = info->find_variable(name);
     if (var)
       return var;
   }
@@ -465,7 +488,7 @@ mc_variable_t Process::find_variable(const char* name) const
 
 void Process::read_variable(const char* name, void* target, size_t size) const
 {
-  mc_variable_t var = this->find_variable(name);
+  simgrid::mc::Variable* var = this->find_variable(name);
   if (!var->address)
     xbt_die("No simple location for this variable");
   if (!var->type->full_type)
@@ -515,9 +538,10 @@ const void *Process::read_bytes(void* buffer, std::size_t size,
   AddressSpace::ReadMode mode) const
 {
   if (process_index != simgrid::mc::ProcessIndexDisabled) {
-    std::shared_ptr<s_mc_object_info_t> const& info =
+    std::shared_ptr<simgrid::mc::ObjectInformation> const& info =
       this->find_object_info_rw((void*)address.address());
     // Segment overlap is not handled.
+#ifdef HAVE_SMPI
     if (info.get() && info.get()->privatized()) {
       if (process_index < 0)
         xbt_die("Missing process index");
@@ -537,6 +561,7 @@ const void *Process::read_bytes(void* buffer, std::size_t size,
       size_t offset = address.address() - (std::uint64_t)info->start_rw;
       address = remote((char*)privatisation_region.address + offset);
     }
+#endif
   }
 
   if (this->is_self()) {
@@ -633,5 +658,29 @@ void Process::ignore_region(std::uint64_t addr, std::size_t size)
     ignored_regions_.begin() + position, region);
 }
 
+void Process::reset_soft_dirty()
+{
+  if (this->clear_refs_fd_ < 0) {
+    this->clear_refs_fd_ = open_process_file(pid_, "clear_refs", O_WRONLY|O_CLOEXEC);
+    if (this->clear_refs_fd_ < 0)
+      xbt_die("Could not open clear_refs file for soft-dirty tracking. Run as root?");
+  }
+  if(::write(this->clear_refs_fd_, "4\n", 2) != 2)
+    xbt_die("Could not reset softdirty bits");
+}
+
+void Process::read_pagemap(uint64_t* pagemap, size_t page_start, size_t page_count)
+{
+  if (pagemap_fd_ < 0) {
+    pagemap_fd_ = open_process_file(pid_, "pagemap", O_RDONLY|O_CLOEXEC);
+    if (pagemap_fd_ < 0)
+      xbt_die("Could not open pagemap file for soft-dirty tracking. Run as root?");
+  }
+  ssize_t bytesize = sizeof(uint64_t) * page_count;
+  off_t offset = sizeof(uint64_t) * page_start;
+  if (pread_whole(pagemap_fd_, pagemap, bytesize, offset) != bytesize)
+    xbt_die("Could not read pagemap");
+}
+
 }
 }