Imported Upstream version 2.8.9
[platform/upstream/cmake.git] / Source / cmBuildCommand.cxx
1 /*============================================================================
2   CMake - Cross Platform Makefile Generator
3   Copyright 2000-2009 Kitware, Inc., Insight Software Consortium
4
5   Distributed under the OSI-approved BSD License (the "License");
6   see accompanying file Copyright.txt for details.
7
8   This software is distributed WITHOUT ANY WARRANTY; without even the
9   implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10   See the License for more information.
11 ============================================================================*/
12 #include "cmBuildCommand.h"
13
14 #include "cmLocalGenerator.h"
15 #include "cmGlobalGenerator.h"
16
17 //----------------------------------------------------------------------
18 bool cmBuildCommand
19 ::InitialPass(std::vector<std::string> const& args, cmExecutionStatus &)
20 {
21   // Support the legacy signature of the command:
22   //
23   if(2 == args.size())
24     {
25     return this->TwoArgsSignature(args);
26     }
27
28   return this->MainSignature(args);
29 }
30
31 //----------------------------------------------------------------------
32 bool cmBuildCommand
33 ::MainSignature(std::vector<std::string> const& args)
34 {
35   if(args.size() < 1)
36     {
37     this->SetError("requires at least one argument naming a CMake variable");
38     return false;
39     }
40
41   // The cmake variable in which to store the result.
42   const char* variable = args[0].c_str();
43
44   // Parse remaining arguments.
45   const char* configuration = 0;
46   const char* project_name = 0;
47   const char* target = 0;
48   enum Doing { DoingNone, DoingConfiguration, DoingProjectName, DoingTarget };
49   Doing doing = DoingNone;
50   for(unsigned int i=1; i < args.size(); ++i)
51     {
52     if(args[i] == "CONFIGURATION")
53       {
54       doing = DoingConfiguration;
55       }
56     else if(args[i] == "PROJECT_NAME")
57       {
58       doing = DoingProjectName;
59       }
60     else if(args[i] == "TARGET")
61       {
62       doing = DoingTarget;
63       }
64     else if(doing == DoingConfiguration)
65       {
66       doing = DoingNone;
67       configuration = args[i].c_str();
68       }
69     else if(doing == DoingProjectName)
70       {
71       doing = DoingNone;
72       project_name = args[i].c_str();
73       }
74     else if(doing == DoingTarget)
75       {
76       doing = DoingNone;
77       target = args[i].c_str();
78       }
79     else
80       {
81       cmOStringStream e;
82       e << "unknown argument \"" << args[i] << "\"";
83       this->SetError(e.str().c_str());
84       return false;
85       }
86     }
87
88   const char* makeprogram
89     = this->Makefile->GetDefinition("CMAKE_MAKE_PROGRAM");
90
91   // If null/empty CONFIGURATION argument, GenerateBuildCommand uses 'Debug'
92   // in the currently implemented multi-configuration global generators...
93   // so we put this code here to end up with the same default configuration
94   // as the original 2-arg build_command signature:
95   //
96   if(!configuration || !*configuration)
97     {
98     configuration = getenv("CMAKE_CONFIG_TYPE");
99     }
100   if(!configuration || !*configuration)
101     {
102     configuration = "Release";
103     }
104
105   // If null/empty PROJECT_NAME argument, use the Makefile's project name:
106   //
107   if(!project_name || !*project_name)
108     {
109     project_name = this->Makefile->GetProjectName();
110     }
111
112   // If null/empty TARGET argument, GenerateBuildCommand omits any mention
113   // of a target name on the build command line...
114   //
115   std::string makecommand = this->Makefile->GetLocalGenerator()
116     ->GetGlobalGenerator()->GenerateBuildCommand
117     (makeprogram, project_name, 0, target, configuration, true, false);
118
119   this->Makefile->AddDefinition(variable, makecommand.c_str());
120
121   return true;
122 }
123
124 //----------------------------------------------------------------------
125 bool cmBuildCommand
126 ::TwoArgsSignature(std::vector<std::string> const& args)
127 {
128   if(args.size() < 2 )
129     {
130     this->SetError("called with less than two arguments");
131     return false;
132     }
133
134   const char* define = args[0].c_str();
135   const char* cacheValue
136     = this->Makefile->GetDefinition(define);
137   std::string makeprogram = args[1];
138
139   std::string configType = "Release";
140   const char* cfg = getenv("CMAKE_CONFIG_TYPE");
141   if ( cfg )
142     {
143     configType = cfg;
144     }
145
146   std::string makecommand = this->Makefile->GetLocalGenerator()
147     ->GetGlobalGenerator()->GenerateBuildCommand
148     (makeprogram.c_str(), this->Makefile->GetProjectName(), 0,
149      0, configType.c_str(), true, false);
150
151   if(cacheValue)
152     {
153     return true;
154     }
155   this->Makefile->AddCacheDefinition(define,
156                                  makecommand.c_str(),
157                                  "Command used to build entire project "
158                                  "from the command line.",
159                                  cmCacheManager::STRING);
160   return true;
161 }