// Copyright 2020 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "crash-reporter/vm_support_proper.h"

#include <base/files/file.h>
#include <base/files/file_path.h>
#include <base/files/file_util.h>
#include <base/logging.h>
#include <base/strings/stringprintf.h>
#include <brillo/key_value_store.h>
#include <chromeos/constants/vm_tools.h>
#include <grpcpp/grpcpp.h>

#include <sys/socket.h>
#include <utility>

#include <linux/vm_sockets.h>

#include "crash-reporter/constants.h"
#include "crash-reporter/paths.h"
#include "crash-reporter/user_collector.h"
#include "crash-reporter/util.h"

namespace {

constexpr char kLsbBoardKey[] = "CHROMEOS_RELEASE_BOARD";
constexpr char kOsNameKey[] = "PRETTY_NAME";
constexpr char kContainerOsReleasePath[] =
    "/mnt/stateful/lxd/storage-pools/default/containers/penguin/rootfs/etc/"
    "os-release";

}  // namespace

class ScopedFileDeleter {
 public:
  explicit ScopedFileDeleter(base::FilePath path) : path_(path) {}
  ~ScopedFileDeleter() {
    if (!base::DeleteFile(path_)) {
      LOG(ERROR) << "Failed to delete file " << path_.value();
    }
  }

 private:
  const base::FilePath path_;
};

VmSupportProper::VmSupportProper() {
  std::string addr = base::StringPrintf("vsock:%u:%u", VMADDR_CID_HOST,
                                        vm_tools::kCrashListenerPort);

  // It's safe to use an unencrypted/authenticated channel here because the
  // whole channel exists within a single machine, and so we can rely on the
  // kernel to provide us with confidentiality and integrity. Our usage of a
  // vsock address guarantees this.
  auto channel =
      grpc::CreateChannel(std::move(addr), grpc::InsecureChannelCredentials());
  stub_ = std::make_unique<vm_tools::cicerone::CrashListener::Stub>(
      std::move(channel));
}

void VmSupportProper::AddMetadata(UserCollector* collector) {
  std::string value;
  base::FilePath lsb_path =
      base::FilePath(paths::kEtcDirectory).Append(paths::kLsbRelease);
  util::GetCachedKeyValue(lsb_path.BaseName(), kLsbBoardKey,
                          {lsb_path.DirName()}, &value);
  collector->AddCrashMetaData("board", value);

  base::FilePath os_path = base::FilePath(kContainerOsReleasePath);
  util::GetCachedKeyValue(os_path.BaseName(), kOsNameKey, {os_path.DirName()},
                          &value);
  collector->AddCrashMetaData("upload_var_vm_os_release", value);
}

void VmSupportProper::ProcessFileData(
    const base::FilePath& crash_meta_path,
    const brillo::KeyValueStore& metadata,
    const std::string& key,
    vm_tools::cicerone::CrashReport* crash_report) {
  std::string file_name;
  metadata.GetString(key, &file_name);
  base::FilePath path = crash_meta_path.DirName().Append(file_name);
  ScopedFileDeleter file_deleter(path);

  std::string* dest = nullptr;
  if (key == "payload") {
    dest = crash_report->mutable_minidump();
  } else if (key ==
             std::string(constants::kUploadTextPrefix) + "process_tree") {
    dest = crash_report->mutable_process_tree();
  }
  if (dest && !base::ReadFileToString(path, dest)) {
    LOG(ERROR) << "Failed to read file " << file_name;
  }
}

void VmSupportProper::FinishCrash(const base::FilePath& crash_meta_path) {
  // We send crash reports outside the VM via GRPC instead of storing them on
  // disk, so we delete files as we finish processing them.
  ScopedFileDeleter metadata_deleter(crash_meta_path);
  brillo::KeyValueStore metadata;
  if (!metadata.Load(crash_meta_path)) {
    LOG(ERROR) << "Failed to read metadata file";
    return;
  }

  grpc::ClientContext ctx;
  vm_tools::cicerone::CrashReport crash_report;
  vm_tools::EmptyMessage response;
  for (const auto& key : metadata.GetKeys()) {
    // These keys store file names, not raw values, which need to be read into
    // the crash report protobuf and deleted.
    if (base::StartsWith(key, constants::kUploadFilePrefix,
                         base::CompareCase::SENSITIVE) ||
        base::StartsWith(key, constants::kUploadTextPrefix,
                         base::CompareCase::SENSITIVE) ||
        key == "payload") {
      ProcessFileData(crash_meta_path, metadata, key, &crash_report);
    } else {
      std::string value;
      metadata.GetString(key, &value);
      (*crash_report.mutable_metadata())[key] = value;
    }
  }

  grpc::Status status = stub_->SendCrashReport(&ctx, crash_report, &response);
  if (!status.ok()) {
    LOG(ERROR) << "Failed to send crash report to cicerone: "
               << status.error_code() << ", " << status.error_message();
  }
}

bool VmSupportProper::GetMetricsConsent() {
  grpc::ClientContext ctx;
  vm_tools::EmptyMessage request;
  vm_tools::cicerone::MetricsConsentResponse response;
  grpc::Status status = stub_->CheckMetricsConsent(&ctx, request, &response);
  return status.ok() && response.consent_granted();
}

bool VmSupportProper::ShouldDump(pid_t pid, std::string* out_reason) {
  // Namespaces are accessed via the /proc/*/ns/* set of paths. The kernel
  // guarantees that if two processes share a namespace, their corresponding
  // namespace files will have the same inode number, as reported by stat.
  //
  // For now, we are only interested in processes in the root PID
  // namespace. When invoked by the kernel in response to a crash,
  // crash_reporter will be run in the root of all the namespace hierarchies, so
  // we can easily check this by comparing the crashed process PID namespace
  // with our own.
  struct stat st;

  auto namespace_path = base::StringPrintf("/proc/%d/ns/pid", pid);
  if (stat(namespace_path.c_str(), &st) < 0) {
    *out_reason = "failed to get process PID namespace";
    return false;
  }
  ino_t inode = st.st_ino;

  if (stat("/proc/self/ns/pid", &st) < 0) {
    *out_reason = "failed to get own PID namespace";
    return false;
  }
  ino_t self_inode = st.st_ino;

  if (inode != self_inode) {
    *out_reason = "ignoring - process not in root namespace";
    return false;
  }

  return true;
}
