// Copyright 2018 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 "crosdns/hosts_modifier.h"

#include <arpa/inet.h>

#include <base/files/file.h>
#include <base/files/file_util.h>
#include <base/logging.h>
#include <base/strings/string_util.h>
#include <base/strings/stringprintf.h>

namespace {
// To avoid reading something too big, this should never happen.
constexpr size_t kMaxFileSize = 1048576;  // 1MB.
// This is the delimiter we write out before our changes so that if we crash and
// are restarted we know what the base file was before we modified it.
constexpr char kFileModificationDelimeter[] =
    "\n#####DYNAMIC-CROSDNS-ENTRIES#####\n";
constexpr char kAllowedHostnameSuffix[] = ".linux.test";
constexpr uint32_t kAllowedIpSubnet = 0x64735c00;  // 100.115.92.0
constexpr uint32_t kAllowedIpMask = 0xFFFFFF00;

// Only allow IPs in the 100.115.92.0/24 subnet.
bool IsAllowedIpv4Address(uint32_t ipv4, std::string* err_out) {
  if ((ipv4 & kAllowedIpMask) != kAllowedIpSubnet) {
    *err_out = "IP address disallowed in mapping";
    return false;
  }
  return true;
}

// Hostname must be *.test and use legal chars.
bool IsAllowedHostname(const std::string& hostname, std::string* err_out) {
  // Make sure this is a legal hostname. It must be comprised of alphanumeric
  // characters, dashes or dots. The dot or dash may not be the first character.
  // It may not have consecutive dots. It must also have the '.test' suffix.
  if (!base::EndsWith(hostname, kAllowedHostnameSuffix,
                      base::CompareCase::SENSITIVE)) {
    *err_out = "Attempt to add invalid hostname to mapping of: " + hostname;
    return false;
  }
  if (hostname[0] == '-' || hostname[0] == '.') {
    *err_out = "First char in hostname may not be a dot or dash: " + hostname;
    return false;
  }
  bool last_was_dot = false;
  for (auto c : hostname) {
    if (!base::IsAsciiAlpha(c) && !base::IsAsciiDigit(c) && c != '-') {
      if (c == '.' && !last_was_dot) {
        last_was_dot = true;
        continue;
      }
      *err_out = "Invalid char in hostname: " + hostname;
      return false;
    }
    last_was_dot = false;
  }
  return true;
}
}  // namespace

namespace crosdns {

HostsModifier::HostsModifier() = default;
HostsModifier::~HostsModifier() = default;

bool HostsModifier::Init(const base::FilePath& hosts_filepath) {
  filepath_ = hosts_filepath;
  if (!base::ReadFileToStringWithMaxSize(filepath_, &base_hosts_contents_,
                                         kMaxFileSize)) {
    PLOG(ERROR) << "Failed reading in existing hostname file from "
                << filepath_.value();
    return false;
  }
  // See if our delimiter was in there or not, if it is then we strip everything
  // off after it (including the delimiter) and then rewrite out the file so
  // that any stale entries are removed.
  size_t delim_pos = base_hosts_contents_.find(kFileModificationDelimeter);
  if (delim_pos == std::string::npos) {
    return true;
  }
  // Delimeter was in there, strip it off and rewrite the file.
  base_hosts_contents_.erase(delim_pos);
  return WriteHostsFile();
}

bool HostsModifier::SetHostnameIpMapping(const std::string& hostname,
                                         const std::string& ipv4,
                                         const std::string& ipv6,
                                         std::string* err_out) {
  CHECK(err_out);
  uint32_t int_ip;
  if (inet_pton(AF_INET, ipv4.c_str(), &int_ip) != 1) {
    *err_out = "Failed parsing IPv4 address: " + ipv4;
    return false;
  }
  int_ip = htonl(int_ip);
  if (!IsAllowedIpv4Address(int_ip, err_out)) {
    return false;
  }
  // TODO(jkardatzke): Add IPv6 support when it is needed.
  if (!IsAllowedHostname(hostname, err_out)) {
    return false;
  }
  hostname_ipv4_map_[hostname] = ipv4;
  if (!WriteHostsFile()) {
    *err_out = "Failed writing the updated /etc/hosts file";
    return false;
  }
  return true;
}

bool HostsModifier::RemoveHostnameIpMapping(const std::string& hostname,
                                            std::string* err_out) {
  CHECK(err_out);
  if (!hostname_ipv4_map_.erase(hostname)) {
    *err_out =
        "Attempt to remove non-existent hostname mapping for: " + hostname;
    return false;
  }
  if (!WriteHostsFile()) {
    *err_out = "Failed writing the updated /etc/hosts file";
    return false;
  }
  return true;
}

bool HostsModifier::WriteHostsFile() {
  // We first write this to an adjacent temp file and then atomically rename
  // that file to be our target aftewards.
  base::FilePath temp_file_path;
  if (!base::CreateTemporaryFileInDir(filepath_.DirName(), &temp_file_path)) {
    PLOG(ERROR) << "Failed creating temp file in dir for hostname writing "
                << filepath_.DirName().value();
    return false;
  }

  // Open our file for writing.
  base::File temp_file(temp_file_path,
                       base::File::FLAG_OPEN | base::File::FLAG_WRITE);
  if (!temp_file.IsValid()) {
    PLOG(ERROR) << "Failed opening temp file for writing: "
                << temp_file_path.value();
    return false;
  }

  // First write out the base contents for the file.
  if (temp_file.WriteAtCurrentPos(base_hosts_contents_.c_str(),
                                  base_hosts_contents_.size()) !=
      base_hosts_contents_.size()) {
    PLOG(ERROR) << "Failed writing base contents to temp file: "
                << temp_file_path.value();
    return false;
  }
  // We only write out more if we have contents in our map.
  if (!hostname_ipv4_map_.empty()) {
    // Now write out our delimiter, which includes newlines at both ends so we
    // are sure it is on its own line and we will be on a new line after this.
    if (temp_file.WriteAtCurrentPos(kFileModificationDelimeter,
                                    sizeof(kFileModificationDelimeter) - 1) !=
        sizeof(kFileModificationDelimeter) - 1) {
      PLOG(ERROR) << "Failed writing delimiter to temp file: "
                  << temp_file_path.value();
      return false;
    }

    // Now write out all of our entries, one per line.
    for (const auto& entry : hostname_ipv4_map_) {
      std::string curr_line = base::StringPrintf(
          "%s %s\n", entry.second.c_str(), entry.first.c_str());
      if (temp_file.WriteAtCurrentPos(curr_line.c_str(), curr_line.size()) !=
          curr_line.size()) {
        PLOG(ERROR) << "Failed writing hostname entry to temp file: "
                    << temp_file_path.value();
        return false;
      }
    }
  }

  // Done writing to the file, close it, ensure permissions are correct and
  // rename it.
  temp_file.Close();
  if (!base::SetPosixFilePermissions(temp_file_path,
                                     base::FILE_PERMISSION_READ_BY_USER |
                                         base::FILE_PERMISSION_READ_BY_GROUP |
                                         base::FILE_PERMISSION_READ_BY_OTHERS |
                                         base::FILE_PERMISSION_WRITE_BY_USER)) {
    PLOG(ERROR) << "Failed setting file permissions on our temp file: "
                << temp_file_path.value();
    return false;
  }

  if (!base::ReplaceFile(temp_file_path, filepath_, nullptr)) {
    PLOG(ERROR) << "Failed replacing existing hosts file with our temp file";
    return false;
  }

  return true;
}

}  // namespace crosdns
