<commit_before>//-----------------------------------
// Copyright <NAME> 2013-2017
//-----------------------------------

#include "LinuxUtils.h"

#include <asm/unistd.h>
#include <cxxabi.h>
#include <linux/perf_event.h>
#include <linux/types.h>
#include <linux/version.h>
#include <signal.h>
#include <string.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/syscall.h>
#include <sys/types.h>
#include <sys/utsname.h>
#include <sys/wait.h>
#include <unistd.h>

#include <cstdlib>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <memory>
#include <sstream>
#include <string>

#include "Callstack.h"
#include "Capture.h"
#include "ConnectionManager.h"
#include "EventBuffer.h"
#include "OrbitModule.h"
#include "OrbitProcess.h"
#include "Path.h"
#include "PrintVar.h"
#include "SamplingProfiler.h"
#include "ScopeTimer.h"
#include "TcpClient.h"
#include "Utils.h"
#include "absl/strings/str_format.h"

namespace LinuxUtils {

//-----------------------------------------------------------------------------
std::vector<std::string> ListModules(pid_t a_PID) {
  std::vector<std::string> modules;
  // TODO: we should read the file directly instead or memory map it.
  std::string result =
      ExecuteCommand(absl::StrFormat("cat /proc/%u/maps", a_PID).c_str());

  std::stringstream ss(result);
  std::string line;
  while (std::getline(ss, line, '\n')) {
    modules.push_back(line);
  }

  return modules;
}

//-----------------------------------------------------------------------------
std::vector<pid_t> ListThreads(pid_t a_PID) {
  std::vector<pid_t> threads;
  std::string result =
      ExecuteCommand(absl::StrFormat("ls /proc/%u/task", a_PID).c_str());

  std::stringstream ss(result);
  std::string line;
  while (std::getline(ss, line, '\n')) {
    threads.push_back(std::stol(line));
  }

  return threads;
}

//-----------------------------------------------------------------------------
std::string ReadMaps(pid_t a_PID) {
  std::ifstream maps_file{"/proc/" + std::to_string(a_PID) + "/maps"};
  if (!maps_file) {
    return "";
  }

  std::string maps_buffer;
  std::string maps_line;
  while (std::getline(maps_file, maps_line)) {
    maps_buffer.append(maps_line).append("\n");
  }
  return maps_buffer;
}

//-----------------------------------------------------------------------------
uint64_t GetTracePointID(const char* a_Group, const char* a_Event) {
  std::string cmd = absl::StrFormat(
      "cat /sys/kernel/debug/tracing/events/%s/%s/id", a_Group, a_Event);
  std::string result = ExecuteCommand(cmd.c_str());
  trim(result);
  return std::stoull(result);
}

//-----------------------------------------------------------------------------
std::string ExecuteCommand(const char* a_Cmd) {
  std::array<char, 128> buffer;
  std::string result;
  std::unique_ptr<FILE, decltype(&pclose)> pipe(popen(a_Cmd, "r"), pclose);
  if (!pipe) {
    std::cout << "Could not open pipe" << std::endl;
  }
  while (fgets(buffer.data(), buffer.size(), pipe.get()) != nullptr) {
    result += buffer.data();
  }
  return result;
}

//-----------------------------------------------------------------------------
void ListModules(pid_t a_PID,
                 std::map<uint64_t, std::shared_ptr<Module>>& o_ModuleMap) {
  std::map<std::string, std::shared_ptr<Module>> modules;
  std::vector<std::string> result = ListModules(a_PID);
  for (const std::string& line : result) {
    std::vector<std::string> tokens = Tokenize(line);
    if (tokens.size() == 6) {
      std::string& moduleName = tokens[5];<commit_msg>When listing modules on Linux, only keep the executable address ranges.<commit_after>//-----------------------------------
// Copyright <NAME> 2013-2017
//-----------------------------------

#include "LinuxUtils.h"

#include <asm/unistd.h>
#include <cxxabi.h>
#include <linux/perf_event.h>
#include <linux/types.h>
#include <linux/version.h>
#include <signal.h>
#include <string.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/syscall.h>
#include <sys/types.h>
#include <sys/utsname.h>
#include <sys/wait.h>
#include <unistd.h>

#include <cstdlib>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <memory>
#include <sstream>
#include <string>

#include "Callstack.h"
#include "Capture.h"
#include "ConnectionManager.h"
#include "EventBuffer.h"
#include "OrbitModule.h"
#include "OrbitProcess.h"
#include "Path.h"
#include "PrintVar.h"
#include "SamplingProfiler.h"
#include "ScopeTimer.h"
#include "TcpClient.h"
#include "Utils.h"
#include "absl/strings/str_format.h"

namespace LinuxUtils {

//-----------------------------------------------------------------------------
std::vector<std::string> ListModules(pid_t a_PID) {
  std::vector<std::string> modules;
  // TODO: we should read the file directly instead or memory map it.
  std::string result =
      ExecuteCommand(absl::StrFormat("cat /proc/%u/maps", a_PID).c_str());

  std::stringstream ss(result);
  std::string line;
  while (std::getline(ss, line, '\n')) {
    modules.push_back(line);
  }

  return modules;
}

//-----------------------------------------------------------------------------
std::vector<pid_t> ListThreads(pid_t a_PID) {
  std::vector<pid_t> threads;
  std::string result =
      ExecuteCommand(absl::StrFormat("ls /proc/%u/task", a_PID).c_str());

  std::stringstream ss(result);
  std::string line;
  while (std::getline(ss, line, '\n')) {
    threads.push_back(std::stol(line));
  }

  return threads;
}

//-----------------------------------------------------------------------------
std::string ReadMaps(pid_t a_PID) {
  std::ifstream maps_file{"/proc/" + std::to_string(a_PID) + "/maps"};
  if (!maps_file) {
    return "";
  }

  std::string maps_buffer;
  std::string maps_line;
  while (std::getline(maps_file, maps_line)) {
    maps_buffer.append(maps_line).append("\n");
  }
  return maps_buffer;
}

//-----------------------------------------------------------------------------
uint64_t GetTracePointID(const char* a_Group, const char* a_Event) {
  std::string cmd = absl::StrFormat(
      "cat /sys/kernel/debug/tracing/events/%s/%s/id", a_Group, a_Event);
  std::string result = ExecuteCommand(cmd.c_str());
  trim(result);
  return std::stoull(result);
}

//-----------------------------------------------------------------------------
std::string ExecuteCommand(const char* a_Cmd) {
  std::array<char, 128> buffer;
  std::string result;
  std::unique_ptr<FILE, decltype(&pclose)> pipe(popen(a_Cmd, "r"), pclose);
  if (!pipe) {
    std::cout << "Could not open pipe" << std::endl;
  }
  while (fgets(buffer.data(), buffer.size(), pipe.get()) != nullptr) {
    result += buffer.data();
  }
  return result;
}

//-----------------------------------------------------------------------------
void ListModules(pid_t a_PID,
                 std::map<uint64_t, std::shared_ptr<Module>>& o_ModuleMap) {
  std::map<std::string, std::shared_ptr<Module>> modules;
  std::vector<std::string> result = ListModules(a_PID);
  for (const std::string& line : result) {
    std::vector<std::string> tokens = Tokenize(line);
    if (tokens.size() == 6) {
      const std::string& moduleName = tokens[5];
      const std::string& permission = tokens[1];

      // Only keep address ranges that are executable.
      if (!Contains(permission, "x"))
        continue;
{'fraction_non_alphanumeric': 0.29673308933170667, 'fraction_numerical': 0.004744476074284939, 'mean_word_length': 2.3475499092558985, 'pattern_counts': {'":': 0, '<': 81, '<?xml version=': 0, '>': 73, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1646870', 'n_tokens_mistral': 2417, 'n_tokens_neox': 2357, 'n_words': 483}