/*=========================================================================

  Program:   CMake - Cross-Platform Makefile Generator
  Module:    $RCSfile$
  Language:  C++
  Date:      $Date$
  Version:   $Revision$

  Copyright (c) 2002 Kitware, Inc., Insight Consortium.  All rights reserved.
  See Copyright.txt or http://www.cmake.org/HTML/Copyright.html for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notices for more information.

=========================================================================*/
#include "cmInstallTargetGenerator.h"

#include "cmGlobalGenerator.h"
#include "cmLocalGenerator.h"
#include "cmMakefile.h"
#include "cmTarget.h"

//----------------------------------------------------------------------------
cmInstallTargetGenerator
::cmInstallTargetGenerator(cmTarget& t, const char* dest, bool implib,
                           const char* permissions,
                           std::vector<std::string> const& configurations,
                           const char* component):
  Target(&t), Destination(dest), ImportLibrary(implib),
  Permissions(permissions), Configurations(configurations),
  Component(component)
{
  this->Target->SetHaveInstallRule(true);
}

//----------------------------------------------------------------------------
cmInstallTargetGenerator
::~cmInstallTargetGenerator()
{
}

//----------------------------------------------------------------------------
void cmInstallTargetGenerator::GenerateScript(std::ostream& os)
{
  // Compute the build tree directory from which to copy the target.
  std::string fromDir;
  if(this->Target->NeedRelinkBeforeInstall())
    {
    fromDir = this->Target->GetMakefile()->GetStartOutputDirectory();
    fromDir += "/CMakeFiles/CMakeRelink.dir/";
    }
  else
    {
    fromDir = this->Target->GetDirectory();
    fromDir += "/";
    }

  // Write variable settings to do per-configuration references.
  this->PrepareScriptReference(os, this->Target, "BUILD", true, false);

  // Create the per-configuration reference.
  std::string fromName = this->GetScriptReference(this->Target, "BUILD",
                                                  false);
  std::string fromFile = fromDir;
  fromFile += fromName;

  // Choose the final destination.  This may be modified for certain
  // target types.
  std::string destination = this->Destination;

  // Setup special properties for some target types.
  std::string props;
  const char* properties = 0;
  cmTarget::TargetType type = this->Target->GetType();
  switch(type)
    {
    case cmTarget::SHARED_LIBRARY:
      {
      // Add shared library installation properties if this platform
      // supports them.
      const char* lib_version = this->Target->GetProperty("VERSION");
      const char* lib_soversion = this->Target->GetProperty("SOVERSION");
      if(!this->Target->GetMakefile()
         ->GetDefinition("CMAKE_SHARED_LIBRARY_SONAME_C_FLAG"))
        {
        // Versioning is supported only for shared libraries and modules,
        // and then only when the platform supports an soname flag.
        lib_version = 0;
        lib_soversion = 0;
        }
      if(lib_version)
        {
        props += " VERSION ";
        props += lib_version;
        }
      if(lib_soversion)
        {
        props += " SOVERSION ";
        props += lib_soversion;
        }
      properties = props.c_str();
      }
      break;
    case cmTarget::EXECUTABLE:
      {
      // Add executable installation properties if this platform
      // supports them.
#if defined(_WIN32) && !defined(__CYGWIN__)
      const char* exe_version = 0;
#else
      const char* exe_version = this->Target->GetProperty("VERSION");
#endif
      if(exe_version)
        {
        props += " VERSION ";
        props += exe_version;
        properties = props.c_str();
        }

      // Handle OSX Bundles.
      if(this->Target->GetMakefile()->IsOn("APPLE") &&
         this->Target->GetPropertyAsBool("MACOSX_BUNDLE"))
        {
        // Compute the source locations of the bundle executable and
        // Info.plist file.
        this->PrepareScriptReference(os, this->Target, "INSTALL",
                                     false, false);
        fromFile += ".app";
        type = cmTarget::INSTALL_DIRECTORY;
        }
      }
      break;
    case cmTarget::STATIC_LIBRARY:
    case cmTarget::MODULE_LIBRARY:
      // Nothing special for modules or static libraries.
      break;
    default:
      break;
    }

  // An import library looks like a static library.
  if(this->ImportLibrary)
    {
    type = cmTarget::STATIC_LIBRARY;
    }

  // Write code to install the target file.
  this->AddInstallRule(os, destination.c_str(), type, fromFile.c_str(),
                       this->ImportLibrary, properties,
                       this->Permissions.c_str(),
                       this->Configurations,
                       this->Component.c_str());

  // Fix the install_name settings in installed binaries.
  if(type == cmTarget::SHARED_LIBRARY ||
     type == cmTarget::MODULE_LIBRARY ||
     type == cmTarget::EXECUTABLE)
    {
    this->AddInstallNamePatchRule(os, destination.c_str());
    }
}

//----------------------------------------------------------------------------
void
cmInstallTargetGenerator
::PrepareScriptReference(std::ostream& os, cmTarget* target,
                         const char* place, bool useConfigDir,
                         bool useSOName)
{
  // If the target name may vary with the configuration type then
  // store all possible names ahead of time in variables.
  std::string fname;
  for(std::vector<std::string>::const_iterator i =
        this->ConfigurationTypes->begin();
      i != this->ConfigurationTypes->end(); ++i)
    {
    // Initialize the name.
    fname = "";

    if(useConfigDir)
      {
      // Start with the configuration's subdirectory.
      target->GetMakefile()->GetLocalGenerator()->GetGlobalGenerator()->
        AppendDirectoryForConfig("", i->c_str(), "/", fname);
      }

    // Compute the name of the library.
    std::string targetName;
    std::string targetNameSO;
    std::string targetNameReal;
    std::string targetNameImport;
    target->GetLibraryNames(targetName, targetNameSO, targetNameReal,
                            targetNameImport, i->c_str());
    if(this->ImportLibrary)
      {
      // Use the import library name.
      fname += targetNameImport;
      }
    else if(useSOName)
      {
      // Use the soname.
      fname += targetNameSO;
      }
    else
      {
      // Use the canonical name.
      fname += targetName;
      }

    // Set a variable with the target name for this configuration.
    os << "SET(" << target->GetName() << "_" << place
       << (this->ImportLibrary? "_IMPNAME_" : "_NAME_") << *i
       << " \"" << fname << "\")\n";
    }
}

//----------------------------------------------------------------------------
std::string cmInstallTargetGenerator::GetScriptReference(cmTarget* target,
                                                         const char* place,
                                                         bool useSOName)
{
  if(this->ConfigurationTypes->empty())
    {
    // Reference the target by its one configuration name.
    std::string targetName;
    std::string targetNameSO;
    std::string targetNameReal;
    std::string targetNameImport;
    target->GetLibraryNames(targetName, targetNameSO, targetNameReal,
                            targetNameImport, this->ConfigurationName);
    if(this->ImportLibrary)
      {
      // Use the import library name.
      return targetNameImport;
      }
    else if(useSOName)
      {
      // Use the soname.
      return targetNameSO;
      }
    else
      {
      // Use the canonical name.
      return targetName;
      }
    }
  else
    {
    // Reference the target using the per-configuration variable.
    std::string ref = "${";
    ref += target->GetName();
    if(this->ImportLibrary)
      {
      ref += "_";
      ref += place;
      ref += "_IMPNAME_";
      }
    else
      {
      ref += "_";
      ref += place;
      ref += "_NAME_";
      }
    ref += "${CMAKE_INSTALL_CONFIG_NAME}}";
    return ref;
    }
}

//----------------------------------------------------------------------------
void cmInstallTargetGenerator
::AddInstallNamePatchRule(std::ostream& os,
                                                       const char* destination)
{
  // Build a map of build-tree install_name to install-tree install_name for
  // shared libraries linked to this target.
  std::map<cmStdString, cmStdString> install_name_remap;
  cmTarget::LinkLibraryType linkType = cmTarget::OPTIMIZED;
  const char* config = this->ConfigurationName;
  if(config && cmSystemTools::UpperCase(config) == "DEBUG")
    {
    linkType = cmTarget::DEBUG;
    }
  // TODO: Merge with ComputeLinkInformation.
  const cmTarget::LinkLibraryVectorType& inLibs = 
    this->Target->GetLinkLibraries();
  for(cmTarget::LinkLibraryVectorType::const_iterator j = inLibs.begin();
      j != inLibs.end(); ++j)
    {
    std::string lib = j->first;
    if((this->Target->GetType() == cmTarget::EXECUTABLE ||
        lib != this->Target->GetName()) &&
       (j->second == cmTarget::GENERAL || j->second == linkType))
      {
      if(cmTarget* tgt = this->Target->GetMakefile()->
         GetLocalGenerator()->GetGlobalGenerator()->
         FindTarget(0, lib.c_str()))
        {
        if(tgt->GetType() == cmTarget::SHARED_LIBRARY)
          {
          // If the build tree and install tree use different path
          // components of the install_name field then we need to create a
          // mapping to be applied after installation.
          std::string for_build = tgt->GetInstallNameDirForBuildTree(config);
          std::string for_install = 
            tgt->GetInstallNameDirForInstallTree(config);
          if(for_build != for_install)
            {
            // Map from the build-tree install_name.
            this->PrepareScriptReference(os, tgt, "REMAP_FROM",
                                         !for_build.empty(), true);
            for_build += this->GetScriptReference(tgt, "REMAP_FROM", true);

            // Map to the install-tree install_name.
            this->PrepareScriptReference(os, tgt, "REMAP_TO",
                                         false, true);
            for_install += this->GetScriptReference(tgt, "REMAP_TO", true);

            // Store the mapping entry.
            install_name_remap[for_build] = for_install;
            }
          }
        }
      }
    }

  // Edit the install_name of the target itself if necessary.
  this->PrepareScriptReference(os, this->Target, "REMAPPED", false, true);
  std::string new_id;
  if(this->Target->GetType() == cmTarget::SHARED_LIBRARY)
    {
    std::string for_build = 
      this->Target->GetInstallNameDirForBuildTree(config);
    std::string for_install = 
      this->Target->GetInstallNameDirForInstallTree(config);
    if(for_build != for_install)
      {
      // Prepare to refer to the install-tree install_name.
      new_id = for_install;
      new_id += this->GetScriptReference(this->Target, "REMAPPED", true);
      }
    }

  // Write a rule to run install_name_tool to set the install-tree
  // install_name value and references.
  if(!new_id.empty() || !install_name_remap.empty())
    {
    std::string component_test = "NOT CMAKE_INSTALL_COMPONENT OR "
      "\"${CMAKE_INSTALL_COMPONENT}\" MATCHES \"^(";
    component_test += this->Component;
    component_test += ")$\"";
    os << "IF(" << component_test << ")\n";
    os << "  EXECUTE_PROCESS(COMMAND install_name_tool";
    if(!new_id.empty())
      {
      os << "\n    -id \"" << new_id << "\"";
      }
    for(std::map<cmStdString, cmStdString>::const_iterator
          i = install_name_remap.begin();
        i != install_name_remap.end(); ++i)
      {
      os << "\n    -change \"" << i->first << "\" \"" << i->second << "\"";
      }
    os << "\n    \"" << destination << "/"
       << this->GetScriptReference(this->Target, "REMAPPED", true) << "\")\n";
    os << "ENDIF(" << component_test << ")\n";
    }
}
