// Copyright 2017 The Crashpad Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "test/filesystem.h"

#include <errno.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/types.h>

#include "base/logging.h"
#include "base/strings/utf_string_conversions.h"
#include "build/build_config.h"
#include "gtest/gtest.h"
#include "test/errors.h"
#include "test/scoped_temp_dir.h"
#include "util/file/file_io.h"
#include "util/file/filesystem.h"
#include "util/misc/time.h"

#if BUILDFLAG(IS_POSIX)
#include <unistd.h>

#include "base/posix/eintr_wrapper.h"
#elif BUILDFLAG(IS_WIN)
#include <windows.h>
#endif

namespace crashpad {
namespace test {

namespace {

#if BUILDFLAG(IS_WIN)

// Detects the flags necessary to create symbolic links and stores them in
// |flags| if non-nullptr, and returns true on success. If symbolic links can’t
// be created, returns false.
bool SymbolicLinkFlags(DWORD* flags) {
  static DWORD symbolic_link_flags = []() {
    ScopedTempDir temp_dir_;

    base::FilePath target_path = temp_dir_.path().Append(L"target");
    base::FilePath symlink_path = temp_dir_.path().Append(L"symlink");
    if (::CreateSymbolicLink(
            symlink_path.value().c_str(), target_path.value().c_str(), 0)) {
      return 0;
    }

    DWORD error = GetLastError();
    if (error == ERROR_PRIVILEGE_NOT_HELD) {
      if (::CreateSymbolicLink(symlink_path.value().c_str(),
                               target_path.value().c_str(),
                               SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE)) {
        return SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE;
      }

      // This may fail with ERROR_INVALID_PARAMETER if the OS is too old to
      // understand SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE, so keep
      // ERROR_PRIVILEGE_NOT_HELD for |error|.
    }

    // Don’t use ErrorMessage() here because the second CreateSymbolicLink() may
    // have scrambled it. Use the saved |error| value instead.
    EXPECT_EQ(error, static_cast<DWORD>(ERROR_PRIVILEGE_NOT_HELD))
        << "CreateSymbolicLink: " << logging::SystemErrorCodeToString(error);
    return -1;
  }();

  if (symbolic_link_flags == static_cast<DWORD>(-1)) {
    return false;
  }

  if (flags) {
    *flags = symbolic_link_flags;
  }

  return true;
}

#endif  // BUILDFLAG(IS_WIN)

}  // namespace

bool CreateFile(const base::FilePath& file) {
  ScopedFileHandle fd(LoggingOpenFileForWrite(
      file, FileWriteMode::kCreateOrFail, FilePermissions::kOwnerOnly));
  EXPECT_TRUE(fd.is_valid());
  return fd.is_valid();
}

bool PathExists(const base::FilePath& path) {
#if BUILDFLAG(IS_POSIX)
  struct stat st;
  if (lstat(path.value().c_str(), &st) != 0) {
    EXPECT_EQ(errno, ENOENT) << ErrnoMessage("lstat ") << path.value();
    return false;
  }
  return true;
#elif BUILDFLAG(IS_WIN)
  if (GetFileAttributes(path.value().c_str()) == INVALID_FILE_ATTRIBUTES) {
    EXPECT_EQ(GetLastError(), static_cast<DWORD>(ERROR_FILE_NOT_FOUND))
        << ErrorMessage("GetFileAttributes ") << base::WideToUTF8(path.value());
    return false;
  }
  return true;
#endif
}

bool SetFileModificationTime(const base::FilePath& path,
                             const timespec& mtime) {
#if BUILDFLAG(IS_APPLE)
  // utimensat() isn't available on macOS until 10.13, so lutimes() is used
  // instead.
  struct stat st;
  if (lstat(path.value().c_str(), &st) != 0) {
    PLOG(ERROR) << "lstat " << path.value();
    return false;
  }
  timeval times[2];
  EXPECT_TRUE(TimespecToTimeval(st.st_atimespec, &times[0]));
  EXPECT_TRUE(TimespecToTimeval(mtime, &times[1]));
  if (lutimes(path.value().c_str(), times) != 0) {
    PLOG(ERROR) << "lutimes " << path.value();
    return false;
  }
  return true;
#elif BUILDFLAG(IS_POSIX)
  timespec times[2];
  times[0].tv_sec = 0;
  times[0].tv_nsec = UTIME_OMIT;
  times[1] = mtime;
  if (utimensat(AT_FDCWD, path.value().c_str(), times, AT_SYMLINK_NOFOLLOW) !=
      0) {
    PLOG(ERROR) << "utimensat " << path.value();
    return false;
  }
  return true;
#elif BUILDFLAG(IS_WIN)
  DWORD flags = FILE_FLAG_OPEN_REPARSE_POINT;
  if (IsDirectory(path, true)) {
    // required for directory handles
    flags |= FILE_FLAG_BACKUP_SEMANTICS;
  }

  ScopedFileHandle handle(::CreateFile(path.value().c_str(),
                                       GENERIC_WRITE,
                                       FILE_SHARE_READ | FILE_SHARE_WRITE,
                                       nullptr,
                                       OPEN_EXISTING,
                                       flags,
                                       nullptr));
  if (!handle.is_valid()) {
    PLOG(ERROR) << "CreateFile " << base::WideToUTF8(path.value());
    return false;
  }

  FILETIME filetime = TimespecToFiletimeEpoch(mtime);
  if (!SetFileTime(handle.get(), nullptr, nullptr, &filetime)) {
    PLOG(ERROR) << "SetFileTime " << base::WideToUTF8(path.value());
    return false;
  }
  return true;
#endif  // BUILDFLAG(IS_APPLE)
}

#if !BUILDFLAG(IS_FUCHSIA)

bool CanCreateSymbolicLinks() {
#if BUILDFLAG(IS_POSIX)
  return true;
#elif BUILDFLAG(IS_WIN)
  return SymbolicLinkFlags(nullptr);
#endif  // BUILDFLAG(IS_POSIX)
}

bool CreateSymbolicLink(const base::FilePath& target_path,
                        const base::FilePath& symlink_path) {
#if BUILDFLAG(IS_POSIX)
  int rv = HANDLE_EINTR(
      symlink(target_path.value().c_str(), symlink_path.value().c_str()));
  if (rv != 0) {
    PLOG(ERROR) << "symlink";
    return false;
  }
  return true;
#elif BUILDFLAG(IS_WIN)
  DWORD symbolic_link_flags = 0;
  SymbolicLinkFlags(&symbolic_link_flags);
  if (!::CreateSymbolicLink(
          symlink_path.value().c_str(),
          target_path.value().c_str(),
          symbolic_link_flags |
              (IsDirectory(target_path, true) ? SYMBOLIC_LINK_FLAG_DIRECTORY
                                              : 0))) {
    PLOG(ERROR) << "CreateSymbolicLink";
    return false;
  }
  return true;
#endif  // BUILDFLAG(IS_POSIX)
}

#endif  // !BUILDFLAG(IS_FUCHSIA)

}  // namespace test
}  // namespace crashpad
