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

#include <sstream>

#include "cmCustomCommand.h"
#include "cmGlobalGenerator.h"
#include "cmMakefile.h"
#include "cmProperty.h"
#include "cmState.h"
#include "cmSystemTools.h"
#include "cmake.h"

cmSourceFile::cmSourceFile(cmMakefile* mf, const std::string& name,
                           cmSourceFileLocationKind kind)
  : Location(mf, name, kind)
{
  this->CustomCommand = nullptr;
  this->FindFullPathFailed = false;
}

cmSourceFile::~cmSourceFile()
{
  this->SetCustomCommand(nullptr);
}

std::string const& cmSourceFile::GetExtension() const
{
  return this->Extension;
}

const std::string cmSourceFile::propLANGUAGE = "LANGUAGE";

void cmSourceFile::SetObjectLibrary(std::string const& objlib)
{
  this->ObjectLibrary = objlib;
}

std::string cmSourceFile::GetObjectLibrary() const
{
  return this->ObjectLibrary;
}

std::string cmSourceFile::GetLanguage()
{
  // If the language was set explicitly by the user then use it.
  if (const char* lang = this->GetProperty(propLANGUAGE)) {
    return lang;
  }

  // Perform computation needed to get the language if necessary.
  if (this->FullPath.empty() && this->Language.empty()) {
    // If a known extension is given or a known full path is given
    // then trust that the current extension is sufficient to
    // determine the language.  This will fail only if the user
    // specifies a full path to the source but leaves off the
    // extension, which is kind of weird.
    if (this->Location.ExtensionIsAmbiguous() &&
        this->Location.DirectoryIsAmbiguous()) {
      // Finalize the file location to get the extension and set the
      // language.
      this->GetFullPath();
    } else {
      // Use the known extension to get the language if possible.
      std::string ext =
        cmSystemTools::GetFilenameLastExtension(this->Location.GetName());
      this->CheckLanguage(ext);
    }
  }

  // Now try to determine the language.
  return static_cast<cmSourceFile const*>(this)->GetLanguage();
}

std::string cmSourceFile::GetLanguage() const
{
  // If the language was set explicitly by the user then use it.
  if (const char* lang = this->GetProperty(propLANGUAGE)) {
    return lang;
  }

  // If the language was determined from the source file extension use it.
  if (!this->Language.empty()) {
    return this->Language;
  }

  // The language is not known.
  return "";
}

cmSourceFileLocation const& cmSourceFile::GetLocation() const
{
  return this->Location;
}

std::string const& cmSourceFile::GetFullPath(std::string* error)
{
  if (this->FullPath.empty()) {
    if (this->FindFullPath(error)) {
      this->CheckExtension();
    }
  }
  return this->FullPath;
}

std::string const& cmSourceFile::GetFullPath() const
{
  return this->FullPath;
}

bool cmSourceFile::FindFullPath(std::string* error)
{
  // If this method has already failed once do not try again.
  if (this->FindFullPathFailed) {
    return false;
  }

  // If the file is generated compute the location without checking on
  // disk.
  if (this->GetPropertyAsBool("GENERATED")) {
    // The file is either already a full path or is relative to the
    // build directory for the target.
    this->Location.DirectoryUseBinary();
    this->FullPath = this->Location.GetDirectory();
    this->FullPath += "/";
    this->FullPath += this->Location.GetName();
    return true;
  }

  // The file is not generated.  It must exist on disk.
  cmMakefile const* mf = this->Location.GetMakefile();
  const char* tryDirs[3] = { nullptr, nullptr, nullptr };
  if (this->Location.DirectoryIsAmbiguous()) {
    tryDirs[0] = mf->GetCurrentSourceDirectory();
    tryDirs[1] = mf->GetCurrentBinaryDirectory();
  } else {
    tryDirs[0] = "";
  }

  cmake const* const cmakeInst = mf->GetCMakeInstance();
  std::vector<std::string> const& srcExts = cmakeInst->GetSourceExtensions();
  std::vector<std::string> const& hdrExts = cmakeInst->GetHeaderExtensions();
  for (const char* const* di = tryDirs; *di; ++di) {
    std::string tryPath = this->Location.GetDirectory();
    if (!tryPath.empty()) {
      tryPath += "/";
    }
    tryPath += this->Location.GetName();
    tryPath = cmSystemTools::CollapseFullPath(tryPath, *di);
    if (this->TryFullPath(tryPath, "")) {
      return true;
    }
    for (std::string const& ext : srcExts) {
      if (this->TryFullPath(tryPath, ext)) {
        return true;
      }
    }
    for (std::string const& ext : hdrExts) {
      if (this->TryFullPath(tryPath, ext)) {
        return true;
      }
    }
  }

  std::ostringstream e;
  std::string missing = this->Location.GetDirectory();
  if (!missing.empty()) {
    missing += "/";
  }
  missing += this->Location.GetName();
  e << "Cannot find source file:\n  " << missing << "\nTried extensions";
  for (std::string const& srcExt : srcExts) {
    e << " ." << srcExt;
  }
  for (std::string const& ext : hdrExts) {
    e << " ." << ext;
  }
  if (error) {
    *error = e.str();
  } else {
    this->Location.GetMakefile()->IssueMessage(cmake::FATAL_ERROR, e.str());
  }
  this->FindFullPathFailed = true;
  return false;
}

bool cmSourceFile::TryFullPath(const std::string& path, const std::string& ext)
{
  std::string tryPath = path;
  if (!ext.empty()) {
    tryPath += ".";
    tryPath += ext;
  }
  if (cmSystemTools::FileExists(tryPath)) {
    this->FullPath = tryPath;
    return true;
  }
  return false;
}

void cmSourceFile::CheckExtension()
{
  // Compute the extension.
  std::string realExt =
    cmSystemTools::GetFilenameLastExtension(this->FullPath);
  if (!realExt.empty()) {
    // Store the extension without the leading '.'.
    this->Extension = realExt.substr(1);
  }

  // Look for object files.
  if (this->Extension == "obj" || this->Extension == "o" ||
      this->Extension == "lo") {
    this->SetProperty("EXTERNAL_OBJECT", "1");
  }

  // Try to identify the source file language from the extension.
  if (this->Language.empty()) {
    this->CheckLanguage(this->Extension);
  }
}

void cmSourceFile::CheckLanguage(std::string const& ext)
{
  // Try to identify the source file language from the extension.
  cmMakefile const* mf = this->Location.GetMakefile();
  cmGlobalGenerator* gg = mf->GetGlobalGenerator();
  std::string l = gg->GetLanguageFromExtension(ext.c_str());
  if (!l.empty()) {
    this->Language = l;
  }
}

bool cmSourceFile::Matches(cmSourceFileLocation const& loc)
{
  return this->Location.Matches(loc);
}

void cmSourceFile::SetProperty(const std::string& prop, const char* value)
{
  this->Properties.SetProperty(prop, value);
}

void cmSourceFile::AppendProperty(const std::string& prop, const char* value,
                                  bool asString)
{
  this->Properties.AppendProperty(prop, value, asString);
}

const char* cmSourceFile::GetPropertyForUser(const std::string& prop)
{
  // This method is a consequence of design history and backwards
  // compatibility.  GetProperty is (and should be) a const method.
  // Computed properties should not be stored back in the property map
  // but instead reference information already known.  If they need to
  // cache information in a mutable ivar to provide the return string
  // safely then so be it.
  //
  // The LOCATION property is particularly problematic.  The CMake
  // language has very loose restrictions on the names that will match
  // a given source file (for historical reasons).  Implementing
  // lookups correctly with such loose naming requires the
  // cmSourceFileLocation class to commit to a particular full path to
  // the source file as late as possible.  If the users requests the
  // LOCATION property we must commit now.
  if (prop == "LOCATION") {
    // Commit to a location.
    this->GetFullPath();
  }

  // Perform the normal property lookup.
  return this->GetProperty(prop);
}

const char* cmSourceFile::GetProperty(const std::string& prop) const
{
  // Check for computed properties.
  if (prop == "LOCATION") {
    if (this->FullPath.empty()) {
      return nullptr;
    }
    return this->FullPath.c_str();
  }

  const char* retVal = this->Properties.GetPropertyValue(prop);
  if (!retVal) {
    cmMakefile const* mf = this->Location.GetMakefile();
    const bool chain =
      mf->GetState()->IsPropertyChained(prop, cmProperty::SOURCE_FILE);
    if (chain) {
      return mf->GetProperty(prop, chain);
    }
  }

  return retVal;
}

const char* cmSourceFile::GetSafeProperty(const std::string& prop) const
{
  const char* ret = this->GetProperty(prop);
  if (!ret) {
    return "";
  }
  return ret;
}

bool cmSourceFile::GetPropertyAsBool(const std::string& prop) const
{
  return cmSystemTools::IsOn(this->GetProperty(prop));
}

cmCustomCommand* cmSourceFile::GetCustomCommand()
{
  return this->CustomCommand;
}

cmCustomCommand const* cmSourceFile::GetCustomCommand() const
{
  return this->CustomCommand;
}

void cmSourceFile::SetCustomCommand(cmCustomCommand* cc)
{
  cmCustomCommand* old = this->CustomCommand;
  this->CustomCommand = cc;
  delete old;
}
