/* Distributed under the OSI-approved BSD 3-Clause License.  See accompanying
   file Copyright.txt or https://cmake.org/licensing for details.  */
#include "cmFileTimeComparison.h"

#include <string>
#include <time.h>
#include <unordered_map>
#include <utility>

// Use a platform-specific API to get file times efficiently.
#if !defined(_WIN32) || defined(__CYGWIN__)
#  include "cm_sys_stat.h"
#  define cmFileTimeComparison_Type struct stat
#else
#  include "cmsys/Encoding.hxx"
#  include <windows.h>
#  define cmFileTimeComparison_Type FILETIME
#endif

class cmFileTimeComparisonInternal
{
public:
  // Internal comparison method.
  inline bool FileTimeCompare(const std::string& f1, const std::string& f2,
                              int* result);

  bool FileTimesDiffer(const std::string& f1, const std::string& f2);

private:
  typedef std::unordered_map<std::string, cmFileTimeComparison_Type>
    FileStatsMap;
  FileStatsMap Files;

  // Internal methods to lookup and compare modification times.
  inline bool Stat(const std::string& fname, cmFileTimeComparison_Type* st);
  inline int Compare(cmFileTimeComparison_Type* st1,
                     cmFileTimeComparison_Type* st2);
  inline bool TimesDiffer(cmFileTimeComparison_Type* st1,
                          cmFileTimeComparison_Type* st2);
};

bool cmFileTimeComparisonInternal::Stat(const std::string& fname,
                                        cmFileTimeComparison_Type* st)
{
  // Use the stored time if available.
  cmFileTimeComparisonInternal::FileStatsMap::iterator fit =
    this->Files.find(fname);
  if (fit != this->Files.end()) {
    *st = fit->second;
    return true;
  }

#if !defined(_WIN32) || defined(__CYGWIN__)
  // POSIX version.  Use the stat function.
  int res = ::stat(fname.c_str(), st);
  if (res != 0) {
    return false;
  }
#else
  // Windows version.  Get the modification time from extended file
  // attributes.
  WIN32_FILE_ATTRIBUTE_DATA fdata;
  if (!GetFileAttributesExW(cmsys::Encoding::ToWide(fname).c_str(),
                            GetFileExInfoStandard, &fdata)) {
    return false;
  }

  // Copy the file time to the output location.
  *st = fdata.ftLastWriteTime;
#endif

  // Store the time for future use.
  this->Files[fname] = *st;
  return true;
}

cmFileTimeComparison::cmFileTimeComparison()
{
  this->Internals = new cmFileTimeComparisonInternal;
}

cmFileTimeComparison::~cmFileTimeComparison()
{
  delete this->Internals;
}

bool cmFileTimeComparison::FileTimeCompare(const std::string& f1,
                                           const std::string& f2, int* result)
{
  return this->Internals->FileTimeCompare(f1, f2, result);
}

bool cmFileTimeComparison::FileTimesDiffer(const std::string& f1,
                                           const std::string& f2)
{
  return this->Internals->FileTimesDiffer(f1, f2);
}

int cmFileTimeComparisonInternal::Compare(cmFileTimeComparison_Type* s1,
                                          cmFileTimeComparison_Type* s2)
{
#if !defined(_WIN32) || defined(__CYGWIN__)
#  if CMake_STAT_HAS_ST_MTIM
  // Compare using nanosecond resolution.
  if (s1->st_mtim.tv_sec < s2->st_mtim.tv_sec) {
    return -1;
  }
  if (s1->st_mtim.tv_sec > s2->st_mtim.tv_sec) {
    return 1;
  }
  if (s1->st_mtim.tv_nsec < s2->st_mtim.tv_nsec) {
    return -1;
  }
  if (s1->st_mtim.tv_nsec > s2->st_mtim.tv_nsec) {
    return 1;
  }
#  elif CMake_STAT_HAS_ST_MTIMESPEC
  // Compare using nanosecond resolution.
  if (s1->st_mtimespec.tv_sec < s2->st_mtimespec.tv_sec) {
    return -1;
  }
  if (s1->st_mtimespec.tv_sec > s2->st_mtimespec.tv_sec) {
    return 1;
  }
  if (s1->st_mtimespec.tv_nsec < s2->st_mtimespec.tv_nsec) {
    return -1;
  }
  if (s1->st_mtimespec.tv_nsec > s2->st_mtimespec.tv_nsec) {
    return 1;
  }
#  else
  // Compare using 1 second resolution.
  if (s1->st_mtime < s2->st_mtime) {
    return -1;
  }
  if (s1->st_mtime > s2->st_mtime) {
    return 1;
  }
#  endif
  // Files have the same time.
  return 0;
#else
  // Compare using system-provided function.
  return (int)CompareFileTime(s1, s2);
#endif
}

bool cmFileTimeComparisonInternal::TimesDiffer(cmFileTimeComparison_Type* s1,
                                               cmFileTimeComparison_Type* s2)
{
#if !defined(_WIN32) || defined(__CYGWIN__)
#  if CMake_STAT_HAS_ST_MTIM
  // Times are integers in units of 1ns.
  long long bil = 1000000000;
  long long t1 = s1->st_mtim.tv_sec * bil + s1->st_mtim.tv_nsec;
  long long t2 = s2->st_mtim.tv_sec * bil + s2->st_mtim.tv_nsec;
  if (t1 < t2) {
    return (t2 - t1) >= bil;
  }
  if (t2 < t1) {
    return (t1 - t2) >= bil;
  }
  return false;
#  elif CMake_STAT_HAS_ST_MTIMESPEC
  // Times are integers in units of 1ns.
  long long bil = 1000000000;
  long long t1 = s1->st_mtimespec.tv_sec * bil + s1->st_mtimespec.tv_nsec;
  long long t2 = s2->st_mtimespec.tv_sec * bil + s2->st_mtimespec.tv_nsec;
  if (t1 < t2) {
    return (t2 - t1) >= bil;
  }
  if (t2 < t1) {
    return (t1 - t2) >= bil;
  }
  return false;
#  else
  // Times are integers in units of 1s.
  if (s1->st_mtime < s2->st_mtime) {
    return (s2->st_mtime - s1->st_mtime) >= 1;
  }
  if (s1->st_mtime > s2->st_mtime) {
    return (s1->st_mtime - s2->st_mtime) >= 1;
  }
  return false;
#  endif
#else
  // Times are integers in units of 100ns.
  LARGE_INTEGER t1;
  LARGE_INTEGER t2;
  t1.LowPart = s1->dwLowDateTime;
  t1.HighPart = s1->dwHighDateTime;
  t2.LowPart = s2->dwLowDateTime;
  t2.HighPart = s2->dwHighDateTime;
  if (t1.QuadPart < t2.QuadPart) {
    return (t2.QuadPart - t1.QuadPart) >= static_cast<LONGLONG>(10000000);
  } else if (t2.QuadPart < t1.QuadPart) {
    return (t1.QuadPart - t2.QuadPart) >= static_cast<LONGLONG>(10000000);
  } else {
    return false;
  }
#endif
}

bool cmFileTimeComparisonInternal::FileTimeCompare(const std::string& f1,
                                                   const std::string& f2,
                                                   int* result)
{
  // Get the modification time for each file.
  cmFileTimeComparison_Type s1;
  cmFileTimeComparison_Type s2;
  if (this->Stat(f1, &s1) && this->Stat(f2, &s2)) {
    // Compare the two modification times.
    *result = this->Compare(&s1, &s2);
    return true;
  }
  // No comparison available.  Default to the same time.
  *result = 0;
  return false;
}

bool cmFileTimeComparisonInternal::FileTimesDiffer(const std::string& f1,
                                                   const std::string& f2)
{
  // Get the modification time for each file.
  cmFileTimeComparison_Type s1;
  cmFileTimeComparison_Type s2;
  if (this->Stat(f1, &s1) && this->Stat(f2, &s2)) {
    // Compare the two modification times.
    return this->TimesDiffer(&s1, &s2);
  }
  // No comparison available.  Default to different times.
  return true;
}
