/*============================================================================
  CMake - Cross Platform Makefile Generator
  Copyright 2000-2009 Kitware, Inc., Insight Software Consortium

  Distributed under the OSI-approved BSD License (the "License");
  see accompanying file Copyright.txt for details.

  This software is distributed WITHOUT ANY WARRANTY; without even the
  implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  See the License for more information.
============================================================================*/
#include "cmIncludeExternalMSProjectCommand.h"

// cmIncludeExternalMSProjectCommand
bool cmIncludeExternalMSProjectCommand
::InitialPass(std::vector<std::string> const& args, cmExecutionStatus &)
{
  if(args.size() < 2)
  {
  this->SetError("INCLUDE_EXTERNAL_MSPROJECT called with incorrect "
                 "number of arguments");
  return false;
  }
// only compile this for win32 to avoid coverage errors
#ifdef _WIN32
  if(this->Makefile->GetDefinition("WIN32"))
    {
    enum Doing { DoingNone, DoingType, DoingGuid, DoingPlatform };

    Doing doing = DoingNone;

    std::string customType;
    std::string customGuid;
    std::string platformMapping;

    std::vector<std::string> depends;
    for (unsigned int i=2; i<args.size(); ++i)
      {
      if (args[i] == "TYPE")
        {
        doing = DoingType;
        }
      else if (args[i] == "GUID")
        {
        doing = DoingGuid;
        }
      else if (args[i] == "PLATFORM")
        {
        doing = DoingPlatform;
        }
      else
        {
        switch (doing)
          {
          case DoingNone: depends.push_back(args[i]);    break;
          case DoingType: customType = args[i];          break;
          case DoingGuid: customGuid = args[i];          break;
          case DoingPlatform: platformMapping = args[i]; break;
          }
        doing = DoingNone;
        }
      }

    // Hack together a utility target storing enough information
    // to reproduce the target inclusion.
    std::string utility_name = args[0];

    std::string path = args[1];
    cmSystemTools::ConvertToUnixSlashes(path);

    if (!customGuid.empty())
      {
      std::string guidVariable = utility_name + "_GUID_CMAKE";
      this->Makefile->GetCMakeInstance()->AddCacheEntry(
        guidVariable.c_str(), customGuid.c_str(),
        "Stored GUID", cmCacheManager::INTERNAL);
      }

    // Create a target instance for this utility.
    cmTarget* target=this->Makefile->AddNewTarget(cmTarget::UTILITY,
                                                  utility_name.c_str());

    target->SetProperty("GENERATOR_FILE_NAME", utility_name.c_str());
    target->SetProperty("EXTERNAL_MSPROJECT", path.c_str());
    target->SetProperty("EXCLUDE_FROM_ALL", "FALSE");

    if (!customType.empty())
      target->SetProperty("VS_PROJECT_TYPE",customType.c_str());
    if (!platformMapping.empty())
      target->SetProperty("VS_PLATFORM_MAPPING",platformMapping.c_str());

    for (std::vector<std::string>::const_iterator it = depends.begin();
         it != depends.end();
         ++it)
      {
      target->AddUtility(it->c_str());
      }
    }
#endif
  return true;
}
