This commit is contained in:
Ken Martin 2002-09-06 13:06:23 -04:00
parent 2c7e9b3b59
commit 25ff4552b3
14 changed files with 690 additions and 526 deletions

View File

@ -5,7 +5,6 @@ cmake.cxx
cmakewizard.cxx
cmMakeDepend.cxx
cmMakefile.cxx
cmMakefileGenerator.cxx
cmRegularExpression.cxx
cmSourceFile.cxx
cmSystemTools.cxx
@ -17,6 +16,10 @@ cmCustomCommand.cxx
cmCacheManager.cxx
cmSourceGroup.cxx
cmListFileCache.cxx
cmGlobalGenerator.cxx
cmGlobalUnixMakefileGenerator.cxx
cmLocalGenerator.cxx
cmLocalUnixMakefileGenerator.cxx
cmake.h
cmakewizard.h
cmMakeDepend.h
@ -33,6 +36,10 @@ cmCustomCommand.h
cmCacheManager.h
cmSourceGroup.h
cmListFileCache.h
cmGlobalGenerator.h
cmGlobalUnixMakefileGenerator.h
cmLocalGenerator.h
cmLocalUnixMakefileGenerator.h
)
# configure the .h file
@ -50,18 +57,22 @@ ADD_DEFINITIONS(-DCMAKE_BUILD_WITH_CMAKE)
IF (WIN32)
IF(NOT UNIX)
SET(SRCS ${SRCS}
cmDSWWriter.cxx
cmDSPWriter.cxx
cmMSProjectGenerator.cxx
cmBorlandMakefileGenerator.cxx
cmNMakeMakefileGenerator.cxx
cmMSDotNETGenerator.cxx
cmDSWWriter.h
cmDSPWriter.h
cmMSProjectGenerator.h
cmBorlandMakefileGenerator.h
cmNMakeMakefileGenerator.h
cmMSDotNETGenerator.h
cmGlobalBorlandMakefileGenerator.cxx
cmLocalBorlandMakefileGenerator.cxx
cmGlobalNMakeMakefileGenerator.cxx
cmLocalNMakeMakefileGenerator.cxx
cmGlobalVisualStudio6Generator.cxx
cmLocalVisualStudio6Generator.cxx
cmGlobalVisualStudio7Generator.cxx
cmLocalVisualStudio7Generator.cxx
cmGlobalBorlandMakefileGenerator.h
cmLocalBorlandMakefileGenerator.h
cmGlobalNMakeMakefileGenerator.h
cmLocalNMakeMakefileGenerator.h
cmGlobalVisualStudio6Generator.h
cmLocalVisualStudio6Generator.h
cmGlobalVisualStudio7Generator.h
cmLocalVisualStudio7Generator.h
)
IF( NOT BORLAND )
LINK_LIBRARIES( rpcrt4.lib )
@ -70,8 +81,6 @@ IF (WIN32)
ENDIF(NOT UNIX)
ENDIF (WIN32)
SET(SRCS ${SRCS} cmUnixMakefileGenerator.cxx cmUnixMakefileGenerator.h)
# create a library used by the command line and the GUI
ADD_LIBRARY(CMakeLib ${SRCS})
@ -111,9 +120,6 @@ CONFIGURE_FILE(
ADD_EXECUTABLE(cmaketest cmaketest.cxx)
TARGET_LINK_LIBRARIES(cmaketest CMakeLib)
#ADD_LIBRARY(TEST_PLUGIN SHARED cmSimpleCommandPlugin.c)
#TARGET_LINK_LIBRARIES(TEST_PLUGIN CMakeLib)
IF(BUILD_TESTING)
ADD_TEST(DumpDocumentation ${CMake_BINARY_DIR}/Source/DumpDocumentation
${CMake_BINARY_DIR}/CMakeDoc.html)

View File

@ -12,7 +12,7 @@
#include "CMakeCommandLineInfo.h"
#include "../cmCacheManager.h"
#include "../cmake.h"
#include "../cmMakefileGenerator.h"
#include "../cmGlobalGenerator.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
@ -52,7 +52,7 @@ class CAboutDlg : public CDialog
public:
CAboutDlg();
// Dialog Data
// Dialog Data
//{{AFX_DATA(CAboutDlg)
enum { IDD = IDD_ABOUTBOX };
//}}AFX_DATA
@ -146,7 +146,7 @@ CMakeSetupDialog::CMakeSetupDialog(const CMakeCommandLineInfo& cmdInfo,
m_oldCX = -1;
m_deltaXRemainder = 0;
m_CMakeInstance = 0;
m_CMakeInstance = new cmake;
}
void CMakeSetupDialog::DoDataExchange(CDataExchange* pDX)
@ -184,15 +184,15 @@ BEGIN_MESSAGE_MAP(CMakeSetupDialog, CDialog)
ON_CBN_SELCHANGE(IDC_WhereBuild, OnSelendokWhereBuild)
ON_CBN_EDITCHANGE(IDC_WhereSource, OnChangeWhereSource)
ON_CBN_SELENDOK(IDC_WhereSource, OnSelendokWhereSource)
ON_WM_SIZE()
ON_WM_SIZE()
ON_WM_GETMINMAXINFO()
ON_BN_CLICKED(IDC_OK, OnOk)
ON_CBN_EDITCHANGE(IDC_Generator, OnEditchangeGenerator)
ON_BN_CLICKED(IDC_HELP_BUTTON, OnHelpButton)
ON_BN_CLICKED(IDC_OK, OnOk)
ON_CBN_EDITCHANGE(IDC_Generator, OnEditchangeGenerator)
ON_BN_CLICKED(IDC_HELP_BUTTON, OnHelpButton)
ON_BN_CLICKED(IDCANCEL, OnCancel)
ON_BN_CLICKED(IDC_AdvancedValues, OnAdvancedValues)
ON_BN_DOUBLECLICKED(IDC_AdvancedValues, OnDoubleclickedAdvancedValues)
//}}AFX_MSG_MAP
ON_BN_CLICKED(IDC_AdvancedValues, OnAdvancedValues)
ON_BN_DOUBLECLICKED(IDC_AdvancedValues, OnDoubleclickedAdvancedValues)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
@ -245,7 +245,6 @@ BOOL CMakeSetupDialog::OnInitDialog()
SetIcon(m_hIcon, FALSE); // Set small icon
// Load source and build dirs from registry
this->LoadFromRegistry();
this->m_CMakeInstance = new cmake;
std::vector<std::string> names;
this->m_CMakeInstance->GetRegisteredGenerators(names);
for(std::vector<std::string>::iterator i = names.begin();
@ -266,8 +265,8 @@ BOOL CMakeSetupDialog::OnInitDialog()
// Set the version number
char tmp[1024];
sprintf(tmp,"Version %d.%d - %s", cmMakefile::GetMajorVersion(),
cmMakefile::GetMinorVersion(), cmMakefile::GetReleaseVersion());
sprintf(tmp,"Version %d.%d - %s", cmake::GetMajorVersion(),
cmake::GetMinorVersion(), cmake::GetReleaseVersion());
SetDlgItemText(IDC_CMAKE_VERSION, tmp);
this->UpdateData(FALSE);
return TRUE; // return TRUE unless you set the focus to a control
@ -560,38 +559,37 @@ void CMakeSetupDialog::RunCMake(bool generateProjectFiles)
this->UpdateData();
// always save the current gui values to disk
this->SaveCacheFromGUI();
// free the old cmake and create a new one here
if (this->m_CMakeInstance)
{
delete this->m_CMakeInstance;
this->m_CMakeInstance = 0;
}
this->m_CMakeInstance = new cmake;
// Make sure we are working from the cache on disk
this->LoadCacheFromDiskToGUI();
m_OKButton.EnableWindow(false);
// create the arguments for the cmake object
std::vector<std::string> args;
args.push_back((const char*)m_PathToExecutable);
std::string arg;
arg = "-H";
arg += m_WhereSource;
args.push_back(arg);
arg = "-B";
arg += m_WhereBuild;
args.push_back(arg);
arg = "-G";
arg += m_GeneratorChoiceString;
args.push_back(arg);
// run the generate process
if(this->m_CMakeInstance->Generate(args, generateProjectFiles) != 0)
// setup the cmake instance
if (generateProjectFiles)
{
cmSystemTools::Error(
"Error in generation process, project files may be invalid");
if(m_CMakeInstance->Generate() != 0)
{
cmSystemTools::Error(
"Error in generation process, project files may be invalid");
}
}
// update the GUI with any new values in the caused by the
// generation process
this->LoadCacheFromDiskToGUI();
else
{
m_CMakeInstance->SetHomeDirectory(m_WhereSource);
m_CMakeInstance->SetStartDirectory(m_WhereSource);
m_CMakeInstance->SetHomeOutputDirectory(m_WhereBuild);
m_CMakeInstance->SetStartOutputDirectory(m_WhereBuild);
m_CMakeInstance->SetGlobalGenerator(
m_CMakeInstance->CreateGlobalGenerator(m_GeneratorChoiceString));
if(m_CMakeInstance->Configure(m_PathToExecutable) != 0)
{
cmSystemTools::Error(
"Error in configuration process, project files may be invalid");
}
// update the GUI with any new values in the caused by the
// generation process
this->LoadCacheFromDiskToGUI();
}
// save source and build paths to registry
this->SaveToRegistry();
// path is up-to-date now
@ -647,6 +645,11 @@ void CMakeSetupDialog::OnChangeWhereBuild()
std::string path = this->m_WhereBuild;
cmSystemTools::ConvertToUnixSlashes(path);
// adjust the cmake instance
m_CMakeInstance->SetHomeOutputDirectory(m_WhereBuild);
m_CMakeInstance->SetStartOutputDirectory(m_WhereBuild);
std::string cache_file = path;
cache_file += "/CMakeCache.txt";

View File

@ -55,7 +55,7 @@ protected:
const char *aadefault);
void ShowAdvancedValues();
void RemoveAdvancedValues();
// Dialog Data
// Dialog Data
//{{AFX_DATA(CMakeSetupDialog)
enum { IDD = IDD_CMakeSetupDialog_DIALOG };
CButton m_HelpButton;

View File

@ -19,12 +19,14 @@ cmakewizard.o \
cmakemain.o \
cmMakeDepend.o \
cmMakefile.o \
cmMakefileGenerator.o \
cmGlobalGenerator.o \
cmLocalGenerator.o \
cmRegularExpression.o \
cmSourceFile.o \
cmSystemTools.o \
cmDirectory.o \
cmUnixMakefileGenerator.o \
cmGlobalUnixMakefileGenerator.o \
cmLocalUnixMakefileGenerator.o \
cmCommands.o \
cmTarget.o \
cmCustomCommand.o \
@ -39,13 +41,15 @@ cmake.o : $(DEPENDS)
cmakemain.o : $(DEPENDS)
cmMakeDepend.o : $(DEPENDS)
cmMakefile.o : $(DEPENDS)
cmMakefileGenerator.o : $(DEPENDS)
cmGlobalGenerator.o : $(DEPENDS)
cmLocalGenerator.o : $(DEPENDS)
cmAuxSourceDirectoryCommand.o : $(DEPENDS)
cmRegularExpression.o : $(DEPENDS)
cmSourceFile.o : $(DEPENDS)
cmDirectory.o : $(DEPENDS)
cmCustomCommand.o : $(DEPENDS)
cmUnixMakefileGenerator.o : $(DEPENDS)
cmGlobalUnixMakefileGenerator.o : $(DEPENDS)
cmLocalUnixMakefileGenerator.o : $(DEPENDS)
cmCommands.o : $(DEPENDS) $(srcdir)/*Command*.cxx
cmTarget.o : $(DEPENDS)
cmCacheManager.o : $(DEPENDS)

View File

@ -52,6 +52,9 @@ void cmGlobalGenerator::ClearEnabledLanguages()
void cmGlobalGenerator::Configure()
{
// reset theLanguages
m_LanguagesEnabled = false;
// Delete any existing cmLocalGenerators
int i;
for (i = 0; i < m_LocalGenerators.size(); ++i)
@ -65,8 +68,8 @@ void cmGlobalGenerator::Configure()
m_LocalGenerators.push_back(lg);
// set the Start directories
lg->GetMakefile()->SetStartDirectory(m_CMakeInstance->GetHomeDirectory());
lg->GetMakefile()->SetStartOutputDirectory(m_CMakeInstance->GetHomeOutputDirectory());
lg->GetMakefile()->SetStartDirectory(m_CMakeInstance->GetStartDirectory());
lg->GetMakefile()->SetStartOutputDirectory(m_CMakeInstance->GetStartOutputDirectory());
lg->GetMakefile()->MakeStartDirectoriesCurrent();
// now do it
@ -124,8 +127,8 @@ void cmGlobalGenerator::LocalGenerate()
cmLocalGenerator *lg = this->CreateLocalGenerator();
// set the Start directories
lg->GetMakefile()->SetStartDirectory(m_CMakeInstance->GetHomeDirectory());
lg->GetMakefile()->SetStartOutputDirectory(m_CMakeInstance->GetHomeOutputDirectory());
lg->GetMakefile()->SetStartDirectory(m_CMakeInstance->GetStartDirectory());
lg->GetMakefile()->SetStartOutputDirectory(m_CMakeInstance->GetStartOutputDirectory());
lg->GetMakefile()->MakeStartDirectoriesCurrent();
// now do trhe configure

View File

@ -17,6 +17,7 @@
#include "cmGlobalUnixMakefileGenerator.h"
#include "cmLocalUnixMakefileGenerator.h"
#include "cmMakefile.h"
#include "cmake.h"
void cmGlobalUnixMakefileGenerator::EnableLanguage(const char* lang,
cmMakefile *mf)
@ -25,58 +26,68 @@ void cmGlobalUnixMakefileGenerator::EnableLanguage(const char* lang,
{
m_LanguagesEnabled = true;
// see man putenv for explaination of this stupid code....
static char envCXX[5000];
static char envCC[5000];
if(mf->GetDefinition("CMAKE_CXX_COMPILER"))
// only do for global runs
if (!m_CMakeInstance->GetLocal())
{
std::string env = "CXX=${CMAKE_CXX_COMPILER}";
mf->ExpandVariablesInString(env);
strncpy(envCXX, env.c_str(), 4999);
envCXX[4999] = 0;
putenv(envCXX);
}
if(mf->GetDefinition("CMAKE_C_COMPILER"))
{
std::string env = "CC=${CMAKE_C_COMPILER}";
mf->ExpandVariablesInString(env);
strncpy(envCC, env.c_str(), 4999);
envCC[4999] = 0;
putenv(envCC);
}
std::string output;
std::string root
= cmSystemTools::ConvertToOutputPath(mf->GetDefinition("CMAKE_ROOT"));
// if no lang specified use CXX
if(!lang )
{
lang = "CXX";
}
// if CXX or C, then enable C
if((!this->GetLanguageEnabled(lang) && lang[0] == 'C'))
{
std::string cmd = root;
cmd += "/Templates/cconfigure";
cmSystemTools::RunCommand(cmd.c_str(), output,
cmSystemTools::ConvertToOutputPath(mf->GetHomeOutputDirectory()).c_str());
std::string fpath = mf->GetHomeOutputDirectory();
fpath += "/CCMakeSystemConfig.cmake";
mf->ReadListFile(NULL,fpath.c_str());
this->SetLanguageEnabled("C");
}
// if CXX
if(!this->GetLanguageEnabled(lang) || strcmp(lang, "CXX") == 0)
{
std::string cmd = root;
cmd += "/Templates/cxxconfigure";
cmSystemTools::RunCommand(cmd.c_str(), output,
cmSystemTools::ConvertToOutputPath(mf->GetHomeOutputDirectory()).c_str());
std::string fpath = mf->GetHomeOutputDirectory();
fpath += "/CXXCMakeSystemConfig.cmake";
mf->ReadListFile(NULL,fpath.c_str());
this->SetLanguageEnabled("CXX");
// see man putenv for explaination of this stupid code....
static char envCXX[5000];
static char envCC[5000];
if(mf->GetDefinition("CMAKE_CXX_COMPILER"))
{
std::string env = "CXX=${CMAKE_CXX_COMPILER}";
mf->ExpandVariablesInString(env);
strncpy(envCXX, env.c_str(), 4999);
envCXX[4999] = 0;
putenv(envCXX);
}
if(mf->GetDefinition("CMAKE_C_COMPILER"))
{
std::string env = "CC=${CMAKE_C_COMPILER}";
mf->ExpandVariablesInString(env);
strncpy(envCC, env.c_str(), 4999);
envCC[4999] = 0;
putenv(envCC);
}
std::string output;
std::string root
= cmSystemTools::ConvertToOutputPath(mf->GetDefinition("CMAKE_ROOT"));
// if no lang specified use CXX
if(!lang )
{
lang = "CXX";
}
// if CXX or C, then enable C
if((!this->GetLanguageEnabled(lang) && lang[0] == 'C'))
{
std::string cmd = root;
cmd += "/Templates/cconfigure";
cmSystemTools::RunCommand(cmd.c_str(), output,
cmSystemTools::ConvertToOutputPath(mf->GetHomeOutputDirectory()).c_str());
std::string fpath = mf->GetHomeOutputDirectory();
fpath += "/CCMakeSystemConfig.cmake";
mf->ReadListFile(NULL,fpath.c_str());
this->SetLanguageEnabled("C");
}
// if CXX
if(!this->GetLanguageEnabled(lang) || strcmp(lang, "CXX") == 0)
{
std::string cmd = root;
cmd += "/Templates/cxxconfigure";
cmSystemTools::RunCommand(cmd.c_str(), output,
cmSystemTools::ConvertToOutputPath(mf->GetHomeOutputDirectory()).c_str());
std::string fpath = mf->GetHomeOutputDirectory();
fpath += "/CXXCMakeSystemConfig.cmake";
mf->ReadListFile(NULL,fpath.c_str());
this->SetLanguageEnabled("CXX");
}
}
}
if (!m_CMakeInstance->GetLocal())
{
// if we are from the top, always define this
mf->AddDefinition("RUN_CONFIGURE", true);
}
}
///! Create a local generator appropriate to this Global Generator

View File

@ -97,7 +97,9 @@ void cmLocalUnixMakefileGenerator::Generate(bool fromTheTop)
this->ProcessDepends(md);
}
// output the makefile fragment
this->OutputMakefile("Makefile", !fromTheTop);
std::string dest = m_Makefile->GetStartOutputDirectory();
dest += "/Makefile";
this->OutputMakefile(dest.c_str(), !fromTheTop);
}
void cmLocalUnixMakefileGenerator::ProcessDepends(const cmMakeDepend &md)

View File

@ -20,7 +20,8 @@
#include "cmSourceFile.h"
#include "cmDirectory.h"
#include "cmSystemTools.h"
#include "cmMakefileGenerator.h"
#include "cmGlobalGenerator.h"
#include "cmLocalGenerator.h"
#include "cmCommands.h"
#include "cmCacheManager.h"
#include "cmFunctionBlocker.h"
@ -48,8 +49,7 @@ cmMakefile::cmMakefile()
m_HeaderFileExtensions.push_back( "in" );
m_DefineFlags = " ";
m_MakefileGenerator = 0;
m_CacheManager = 0;
m_LocalGenerator = 0;
this->AddSourceGroup("", "^.*$");
this->AddSourceGroup("Source Files", "\\.(cpp|C|c|cxx|rc|def|r|odl|idl|hpj|bat)$");
this->AddSourceGroup("Header Files", "\\.(h|hh|hpp|hxx|hm|inl)$");
@ -59,20 +59,20 @@ cmMakefile::cmMakefile()
unsigned int cmMakefile::GetCacheMajorVersion()
{
if(!this->m_CacheManager->GetCacheValue("CMAKE_CACHE_MAJOR_VERSION"))
if(!this->GetCacheManager()->GetCacheValue("CMAKE_CACHE_MAJOR_VERSION"))
{
return 0;
}
return atoi(this->m_CacheManager->GetCacheValue("CMAKE_CACHE_MAJOR_VERSION"));
return atoi(this->GetCacheManager()->GetCacheValue("CMAKE_CACHE_MAJOR_VERSION"));
}
unsigned int cmMakefile::GetCacheMinorVersion()
{
if(!this->m_CacheManager->GetCacheValue("Cmake_Cache_MINOR_VERSION"))
if(!this->GetCacheManager()->GetCacheValue("Cmake_Cache_MINOR_VERSION"))
{
return 0;
}
return atoi(this->m_CacheManager->GetCacheValue("CMAKE_CACHE_MINOR_VERSION"));
return atoi(this->GetCacheManager()->GetCacheValue("CMAKE_CACHE_MINOR_VERSION"));
}
@ -132,7 +132,6 @@ cmMakefile::~cmMakefile()
m_FunctionBlockers.remove(*pos);
delete b;
}
delete m_MakefileGenerator;
}
void cmMakefile::PrintStringVector(const char* s, const std::vector<std::string>& v) const
@ -384,15 +383,9 @@ void cmMakefile::AddCommand(cmCommand* wg)
}
// Set the make file
void cmMakefile::SetMakefileGenerator(cmMakefileGenerator* mf)
void cmMakefile::SetLocalGenerator(cmLocalGenerator* lg)
{
if(mf == m_MakefileGenerator)
{
return;
}
delete m_MakefileGenerator;
m_MakefileGenerator = mf;
mf->SetMakefile(this);
m_LocalGenerator = lg;
}
void cmMakefile::FinalPass()
@ -430,8 +423,6 @@ void cmMakefile::GenerateMakefile()
}
l->second.AnalyzeLibDependencies(*this);
}
// now do the generation
m_MakefileGenerator->GenerateMakefile();
}
@ -462,10 +453,10 @@ void cmMakefile::AddCustomCommand(const char* source,
m_Targets[target].GetCustomCommands().push_back(cc);
std::string cacheCommand = command;
this->ExpandVariablesInString(cacheCommand);
if(this->m_CacheManager->GetCacheValue(cacheCommand.c_str()))
if(this->GetCacheManager()->GetCacheValue(cacheCommand.c_str()))
{
m_Targets[target].AddUtility(
this->m_CacheManager->GetCacheValue(cacheCommand.c_str()));
this->GetCacheManager()->GetCacheValue(cacheCommand.c_str()));
}
}
}
@ -596,7 +587,7 @@ void cmMakefile::AddCacheDefinition(const char* name, const char* value,
const char* doc,
cmCacheManager::CacheEntryType type)
{
this->m_CacheManager->AddCacheEntry(name, value, doc, type);
this->GetCacheManager()->AddCacheEntry(name, value, doc, type);
this->AddDefinition(name, value);
}
@ -618,7 +609,7 @@ void cmMakefile::AddDefinition(const char* name, bool value)
void cmMakefile::AddCacheDefinition(const char* name, bool value, const char* doc)
{
this->m_CacheManager->AddCacheEntry(name, value, doc);
this->GetCacheManager()->AddCacheEntry(name, value, doc);
this->AddDefinition(name, value);
}
@ -671,7 +662,7 @@ void cmMakefile::AddLibrary(const char* lname, int shared,
// hence useless.
std::string depname = lname;
depname += "_LIB_DEPENDS";
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(depname.c_str(), "",
"Dependencies for target", cmCacheManager::STATIC);
@ -684,7 +675,7 @@ void cmMakefile::AddLibrary(const char* lname, int shared,
// Add an entry into the cache
std::string libPath = lname;
libPath += "_CMAKE_PATH";
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(libPath.c_str(),
this->GetCurrentOutputDirectory(),
"Path to a library", cmCacheManager::INTERNAL);
@ -695,26 +686,26 @@ void cmMakefile::AddLibrary(const char* lname, int shared,
switch (shared)
{
case 0:
this->m_CacheManager->AddCacheEntry(ltname.c_str(),"STATIC",
this->GetCacheManager()->AddCacheEntry(ltname.c_str(),"STATIC",
"Whether a library is static, shared or module.",
cmCacheManager::INTERNAL);
break;
case 1:
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(ltname.c_str(),
"SHARED",
"Whether a library is static, shared or module.",
cmCacheManager::INTERNAL);
break;
case 2:
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(ltname.c_str(),
"MODULE",
"Whether a library is static, shared or module.",
cmCacheManager::INTERNAL);
break;
default:
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(ltname.c_str(),
"STATIC",
"Whether a library is static, shared or module.",
@ -751,7 +742,7 @@ void cmMakefile::AddExecutable(const char *exeName,
// Add an entry into the cache
std::string exePath = exeName;
exePath += "_CMAKE_PATH";
this->m_CacheManager->
this->GetCacheManager()->
AddCacheEntry(exePath.c_str(),
this->GetCurrentOutputDirectory(),
"Path to an executable", cmCacheManager::INTERNAL);
@ -904,7 +895,7 @@ const char* cmMakefile::GetDefinition(const char* name) const
{
return (*pos).second.c_str();
}
return this->m_CacheManager->GetCacheValue(name);
return this->GetCacheManager()->GetCacheValue(name);
}
int cmMakefile::DumpDocumentationToFile(std::ostream& f)
@ -1126,59 +1117,6 @@ void cmMakefile::RemoveVariablesInString(std::string& source,
}
}
// recursive function to create a vector of cmMakefile objects
// This is done by reading the sub directory CMakeLists.txt files,
// then calling this function with the new cmMakefile object
void
cmMakefile::FindSubDirectoryCMakeListsFiles(std::vector<cmMakefile*>& makefiles)
{
// loop over all the sub directories of this makefile
const std::vector<std::string>& subdirs = this->GetSubDirectories();
for(std::vector<std::string>::const_iterator i = subdirs.begin();
i != subdirs.end(); ++i)
{
std::string subdir = *i;
// Create a path to the list file in the sub directory
std::string listFile = this->GetCurrentDirectory();
listFile += "/";
listFile += subdir;
listFile += "/CMakeLists.txt";
// if there is a CMakeLists.txt file read it
if(!cmSystemTools::FileExists(listFile.c_str()))
{
cmSystemTools::Error("CMakeLists.txt file missing from sub directory:",
listFile.c_str());
}
else
{
cmMakefile* mf = new cmMakefile;
mf->SetMakefileGenerator(m_MakefileGenerator->CreateObject());
mf->SetCacheManager(this->m_CacheManager);
makefiles.push_back(mf);
// initialize new makefile
mf->SetHomeOutputDirectory(this->GetHomeOutputDirectory());
mf->SetHomeDirectory(this->GetHomeDirectory());
// add the subdir to the start output directory
std::string outdir = this->GetStartOutputDirectory();
outdir += "/";
outdir += subdir;
mf->SetStartOutputDirectory(outdir.c_str());
// add the subdir to the start source directory
std::string currentDir = this->GetStartDirectory();
currentDir += "/";
currentDir += subdir;
mf->SetStartDirectory(currentDir.c_str());
// Parse the CMakeLists.txt file
currentDir += "/CMakeLists.txt";
mf->MakeStartDirectoriesCurrent();
mf->ReadListFile(currentDir.c_str());
// recurse into nextDir
mf->FindSubDirectoryCMakeListsFiles(makefiles);
}
}
}
/**
* Add the default definitions to the makefile. These values must not
* be dependent on anything that isn't known when this cmMakefile instance
@ -1399,7 +1337,7 @@ cmSourceFile* cmMakefile::AddSource(cmSourceFile const&sf)
void cmMakefile::EnableLanguage(const char* lang)
{
m_MakefileGenerator->EnableLanguage(lang);
m_LocalGenerator->GetGlobalGenerator()->EnableLanguage(lang, this);
}
void cmMakefile::ExpandSourceListArguments(
@ -1437,7 +1375,7 @@ void cmMakefile::ExpandSourceListArguments(
int cmMakefile::TryCompile(const char *srcdir, const char *bindir,
const char *projectName)
{
if (!m_MakefileGenerator)
if (!m_LocalGenerator)
{
cmSystemTools::Error("Internal CMake error, Attempt to call Try Compile without the generator being set");
return 1;
@ -1454,43 +1392,58 @@ int cmMakefile::TryCompile(const char *srcdir, const char *bindir,
std::string cwd = cmSystemTools::GetCurrentWorkingDirectory();
cmSystemTools::ChangeDirectory(bindir);
std::vector<std::string> args;
// make sure the same generator is used
// use this program as the cmake to be run, it should not
// be run that way but the cmake object requires a vailid path
std::string cmakeCommand = this->GetDefinition("CMAKE_COMMAND");
args.push_back(cmakeCommand.c_str());
args.push_back(srcdir);
std::string generator = "-G";
generator += this->GetDefinition("CMAKE_GENERATOR");
args.push_back(generator);
cmake cm;
if (cm.Generate(args) != 0)
cmGlobalGenerator *gg =
cm.CreateGlobalGenerator(this->GetDefinition("CMAKE_GENERATOR"));
if (!gg)
{
cmSystemTools::Error(
"Internal CMake error, TryCompile execution of cmake failed");
"Internal CMake error, TryCompile bad GlobalGenerator");
// return to the original directory
cmSystemTools::ChangeDirectory(cwd.c_str());
return 1;
}
// do a configure
cm.SetHomeDirectory(srcdir);
cm.SetHomeOutputDirectory(bindir);
cm.SetStartDirectory(srcdir);
cm.SetStartOutputDirectory(bindir);
if (cm.Configure(cmakeCommand.c_str()) != 0)
{
cmSystemTools::Error(
"Internal CMake error, TryCompile configure of cmake failed");
// return to the original directory
cmSystemTools::ChangeDirectory(cwd.c_str());
return 1;
}
cmake cm2;
if (cm2.Generate(args) != 0)
if (cm.Generate() != 0)
{
cmSystemTools::Error(
"Internal CMake error, TryCompile execution of cmake failed");
"Internal CMake error, TryCompile generation of cmake failed");
// return to the original directory
cmSystemTools::ChangeDirectory(cwd.c_str());
return 1;
}
// finally call the generator to actually build the resulting project
m_MakefileGenerator->TryCompile(srcdir,bindir,projectName);
cmSystemTools::ChangeDirectory(cwd.c_str());
gg->TryCompile(srcdir,bindir,projectName);
cmSystemTools::ChangeDirectory(cwd.c_str());
return 0;
}
cmCacheManager *cmMakefile::GetCacheManager() const
{
if (m_LocalGenerator)
{
return m_LocalGenerator->GetGlobalGenerator()->GetCMakeInstance()->GetCacheManager();
}
return 0;
}

View File

@ -27,7 +27,7 @@
class cmFunctionBlocker;
class cmCommand;
class cmMakefileGenerator;
class cmLocalGenerator;
class cmMakeDepend;
/** \class cmMakefile
@ -96,11 +96,11 @@ public:
* dependent, although the interface is through a generic
* superclass.
*/
void SetMakefileGenerator(cmMakefileGenerator*);
void SetLocalGenerator(cmLocalGenerator*);
///! Get the current makefile generator.
cmMakefileGenerator* GetMakefileGenerator()
{ return m_MakefileGenerator;}
cmLocalGenerator* GetLocalGenerator()
{ return m_LocalGenerator;}
/**
* Produce the output makefile.
@ -485,15 +485,6 @@ public:
*/
void ExpandVariables();
/** Recursivly read and create a cmMakefile object for
* all CMakeLists.txt files in the GetSubDirectories list.
* Once the file is found, it ReadListFile is called on
* the cmMakefile created for it. CreateObject is called on
* the prototype to create a cmMakefileGenerator for each cmMakefile that
* is created.
*/
void FindSubDirectoryCMakeListsFiles(std::vector<cmMakefile*>& makefiles);
/**
* find what source group this source is in
*/
@ -519,14 +510,9 @@ public:
* Set/Get the name of the parent directories CMakeLists file
* given a current CMakeLists file name
*/
void SetCacheManager(cmCacheManager *cm) {
this->m_CacheManager = cm; }
cmCacheManager *GetCacheManager() {
return m_CacheManager; }
cmCacheManager *GetCacheManager() const;
protected:
cmCacheManager *m_CacheManager;
// add link libraries and directories to the target
void AddGlobalLinkInformation(const char* name, cmTarget& target);
@ -573,7 +559,7 @@ protected:
DefinitionMap m_Definitions;
RegisteredCommandsMap m_Commands;
std::vector<cmCommand*> m_UsedCommands;
cmMakefileGenerator* m_MakefileGenerator;
cmLocalGenerator* m_LocalGenerator;
bool IsFunctionBlocked(const char *name, std::vector<std::string> const& args);
private:

View File

@ -17,39 +17,34 @@
#include "cmake.h"
#include "time.h"
#include "cmCacheManager.h"
#include "cmMakefile.h"
#include "cmLocalGenerator.h"
// include the generator
#if defined(_WIN32) && !defined(__CYGWIN__)
#include "cmMSProjectGenerator.h"
#include "cmMSDotNETGenerator.h"
#include "cmBorlandMakefileGenerator.h"
#include "cmNMakeMakefileGenerator.h"
#include "cmGlobalVisualStudio6Generator.h"
#include "cmGlobalVisualStudio7Generator.h"
#include "cmGlobalBorlandMakefileGenerator.h"
#include "cmGlobalNMakeMakefileGenerator.h"
#else
#include "cmUnixMakefileGenerator.h"
#include "cmGlobalUnixMakefileGenerator.h"
#endif
cmake::cmake()
{
m_Verbose = false;
#if defined(_WIN32) && !defined(__CYGWIN__)
this->RegisterGenerator(new cmMSProjectGenerator);
this->RegisterGenerator(new cmMSDotNETGenerator);
this->RegisterGenerator(new cmNMakeMakefileGenerator);
this->RegisterGenerator(new cmBorlandMakefileGenerator);
#else
this->RegisterGenerator(new cmUnixMakefileGenerator);
#endif
m_CacheManager = new cmCacheManager;
m_GlobalGenerator = 0;
}
cmake::~cmake()
{
for(std::map<cmStdString, cmMakefileGenerator*>::iterator i
= m_RegisteredGenerators.begin();
i != m_RegisteredGenerators.end(); ++i)
delete m_CacheManager;
if (m_GlobalGenerator)
{
delete i->second;
delete m_GlobalGenerator;
m_GlobalGenerator = 0;
}
m_RegisteredGenerators = std::map<cmStdString, cmMakefileGenerator*>();
}
@ -79,8 +74,7 @@ void cmake::Usage(const char* program)
}
// Parse the args
void cmake::SetCacheArgs(cmMakefile& builder,
const std::vector<std::string>& args)
void cmake::SetCacheArgs(const std::vector<std::string>& args)
{
for(unsigned int i=1; i < args.size(); ++i)
{
@ -92,9 +86,7 @@ void cmake::SetCacheArgs(cmMakefile& builder,
cmCacheManager::CacheEntryType type;
if(cmCacheManager::ParseEntry(entry.c_str(), var, value, type))
{
this->m_CacheManager.AddCacheEntry(
var.c_str(),
value.c_str(),
this->m_CacheManager->AddCacheEntry(var.c_str(), value.c_str(),
"No help, variable specified on the command line.",
type);
}
@ -108,17 +100,46 @@ void cmake::SetCacheArgs(cmMakefile& builder,
{
std::string path = arg.substr(2);
std::cerr << "loading initial cache file " << path.c_str() << "\n";
if(!builder.ReadListFile(path.c_str()))
{
std::cerr << "Error in reading cmake initial cache file:"
<< path.c_str() << "\n";
}
this->ReadListFile(path.c_str());
}
}
}
void cmake::ReadListFile(const char *path)
{
// if a generator was not yet created, temporarily create one
cmGlobalGenerator *gg = this->GetGlobalGenerator();
bool created;
// if a generator was not specified use a generic one
if (!gg)
{
gg = new cmGlobalGenerator;
gg->SetCMakeInstance(this);
created = true;
}
// read in the list file to fill the cache
if(path)
{
cmLocalGenerator *lg = gg->CreateLocalGenerator();
lg->SetGlobalGenerator(gg);
if (!lg->GetMakefile()->ReadListFile(path))
{
std::cerr << "Error in reading cmake initial cache file:"
<< path << "\n";
}
}
// free generic one if generated
if (created)
{
delete gg;
}
}
// Parse the args
void cmake::SetArgs(cmMakefile& builder, const std::vector<std::string>& args)
void cmake::SetArgs(const std::vector<std::string>& args)
{
m_Local = false;
bool directoriesSet = false;
@ -126,22 +147,22 @@ void cmake::SetArgs(cmMakefile& builder, const std::vector<std::string>& args)
if (args.size() <= 2)
{
directoriesSet = true;
builder.SetHomeOutputDirectory
this->SetHomeOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetStartOutputDirectory
this->SetStartOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
if (args.size() == 2)
{
builder.SetHomeDirectory
this->SetHomeDirectory
(cmSystemTools::CollapseFullPath(args[1].c_str()).c_str());
builder.SetStartDirectory
this->SetStartDirectory
(cmSystemTools::CollapseFullPath(args[1].c_str()).c_str());
}
else
{
builder.SetHomeDirectory
this->SetHomeDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetStartDirectory
this->SetStartDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
}
}
@ -153,26 +174,26 @@ void cmake::SetArgs(cmMakefile& builder, const std::vector<std::string>& args)
{
directoriesSet = true;
std::string path = arg.substr(2);
builder.SetHomeDirectory(path.c_str());
this->SetHomeDirectory(path.c_str());
}
else if(arg.find("-S",0) == 0)
{
directoriesSet = true;
m_Local = true;
std::string path = arg.substr(2);
builder.SetStartDirectory(path.c_str());
this->SetStartDirectory(path.c_str());
}
else if(arg.find("-O",0) == 0)
{
directoriesSet = true;
std::string path = arg.substr(2);
builder.SetStartOutputDirectory(path.c_str());
this->SetStartOutputDirectory(path.c_str());
}
else if(arg.find("-B",0) == 0)
{
directoriesSet = true;
std::string path = arg.substr(2);
builder.SetHomeOutputDirectory(path.c_str());
this->SetHomeOutputDirectory(path.c_str());
}
else if(arg.find("-V",0) == 0)
{
@ -189,8 +210,8 @@ void cmake::SetArgs(cmMakefile& builder, const std::vector<std::string>& args)
else if(arg.find("-G",0) == 0)
{
std::string value = arg.substr(2);
cmMakefileGenerator* gen =
this->CreateGenerator(value.c_str());
cmGlobalGenerator* gen =
this->CreateGlobalGenerator(value.c_str());
if(!gen)
{
cmSystemTools::Error("Could not create named generator ",
@ -198,47 +219,47 @@ void cmake::SetArgs(cmMakefile& builder, const std::vector<std::string>& args)
}
else
{
builder.SetMakefileGenerator(gen);
this->SetGlobalGenerator(gen);
}
}
// no option assume it is the path to the source
else
{
directoriesSet = true;
builder.SetHomeOutputDirectory
this->SetHomeOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetStartOutputDirectory
this->SetStartOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetHomeDirectory
this->SetHomeDirectory
(cmSystemTools::CollapseFullPath(arg.c_str()).c_str());
builder.SetStartDirectory
this->SetStartDirectory
(cmSystemTools::CollapseFullPath(arg.c_str()).c_str());
}
}
if(!directoriesSet)
{
builder.SetHomeOutputDirectory
this->SetHomeOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetStartOutputDirectory
this->SetStartOutputDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetHomeDirectory
this->SetHomeDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
builder.SetStartDirectory
this->SetStartDirectory
(cmSystemTools::GetCurrentWorkingDirectory().c_str());
}
if (!m_Local)
{
builder.SetStartDirectory(builder.GetHomeDirectory());
builder.SetStartOutputDirectory(builder.GetHomeOutputDirectory());
this->SetStartDirectory(this->GetHomeDirectory());
this->SetStartOutputDirectory(this->GetHomeOutputDirectory());
}
}
// at the end of this CMAKE_ROOT and CMAKE_COMMAND should be added to the cache
int cmake::AddCMakePaths(const std::vector<std::string>& args)
int cmake::AddCMakePaths(const char *arg0)
{
// Find our own executable.
std::vector<cmStdString> failures;
std::string cMakeSelf = args[0];
std::string cMakeSelf = arg0;
cmSystemTools::ConvertToUnixSlashes(cMakeSelf);
failures.push_back(cMakeSelf);
cMakeSelf = cmSystemTools::FindProgram(cMakeSelf.c_str());
@ -268,7 +289,7 @@ int cmake::AddCMakePaths(const std::vector<std::string>& args)
failures.push_back(cMakeSelf);
cmStringStream msg;
msg << "CMAKE can not find the command line program cmake.\n";
msg << " argv[0] = \"" << args[0].c_str() << "\"\n";
msg << " argv[0] = \"" << arg0 << "\"\n";
msg << " Attempted paths:\n";
std::vector<cmStdString>::iterator i;
for(i=failures.begin(); i != failures.end(); ++i)
@ -279,7 +300,7 @@ int cmake::AddCMakePaths(const std::vector<std::string>& args)
return 0;
}
// Save the value in the cache
this->m_CacheManager.AddCacheEntry
this->m_CacheManager->AddCacheEntry
("CMAKE_COMMAND",cMakeSelf.c_str(), "Path to CMake executable.",
cmCacheManager::INTERNAL);
@ -293,7 +314,7 @@ int cmake::AddCMakePaths(const std::vector<std::string>& args)
}
if(cmSystemTools::FileExists(editCacheCommand.c_str()))
{
this->m_CacheManager.AddCacheEntry
this->m_CacheManager->AddCacheEntry
("CMAKE_EDIT_COMMAND", editCacheCommand.c_str(),
"Path to cache edit program executable.", cmCacheManager::INTERNAL);
}
@ -363,7 +384,7 @@ int cmake::AddCMakePaths(const std::vector<std::string>& args)
modules.c_str());
return 0;
}
this->m_CacheManager.AddCacheEntry
this->m_CacheManager->AddCacheEntry
("CMAKE_ROOT", cMakeRoot.c_str(),
"Path to CMake installation.", cmCacheManager::INTERNAL);
return 1;
@ -371,182 +392,6 @@ int cmake::AddCMakePaths(const std::vector<std::string>& args)
int cmake::Generate(const std::vector<std::string>& args, bool buildMakefiles)
{
if(args.size() == 1 && !cmSystemTools::FileExists("CMakeLists.txt"))
{
this->Usage(args[0].c_str());
return -1;
}
// look for obvious request for help
for(unsigned int i=1; i < args.size(); ++i)
{
std::string arg = args[i];
if(arg.find("-help",0) != std::string::npos ||
arg.find("--help",0) != std::string::npos ||
arg.find("/?",0) != std::string::npos ||
arg.find("-usage",0) != std::string::npos)
{
this->Usage(args[0].c_str());
return -1;
}
}
// Create a makefile
cmMakefile mf;
mf.SetCacheManager(&this->m_CacheManager);
// extract the directory arguments, could create a Generator
this->SetArgs(mf, args);
// Read and parse the input makefile
mf.MakeStartDirectoriesCurrent();
this->m_CacheManager.LoadCache(&mf);
if(mf.GetDefinition("CMAKE_HOME_DIRECTORY"))
{
std::string cacheStart = mf.GetDefinition("CMAKE_HOME_DIRECTORY");
cacheStart += "/CMakeLists.txt";
std::string currentStart = mf.GetHomeDirectory();
currentStart += "/CMakeLists.txt";
if(!cmSystemTools::SameFile(cacheStart.c_str(), currentStart.c_str()))
{
std::string message = "Error: source : ";
message += currentStart;
message += "\nDoes not match source used to generate cache: ";
message += cacheStart;
message += "\nRe-run cmake with a different source directory.";
cmSystemTools::Error(message.c_str());
return -2;
}
}
mf.AddCacheDefinition("CMAKE_HOME_DIRECTORY", mf.GetHomeDirectory(),
"Start directory with the top level CMakeLists.txt file for this project",
cmCacheManager::INTERNAL);
// extract command line arguments that might add cache entries
this->SetCacheArgs(mf, args);
// no generator specified on the command line
if(!mf.GetMakefileGenerator())
{
cmMakefileGenerator* gen;
const char* genName = mf.GetDefinition("CMAKE_GENERATOR");
if(genName)
{
gen = this->CreateGenerator(genName);
}
else
{
#if defined(__BORLANDC__)
gen = new cmBorlandMakefileGenerator;
#elif defined(_WIN32) && !defined(__CYGWIN__)
gen = new cmMSProjectGenerator;
#else
gen = new cmUnixMakefileGenerator;
#endif
}
if(!gen)
{
cmSystemTools::Error("Could not create generator");
return -1;
}
mf.SetMakefileGenerator(gen);
// add the
}
cmMakefileGenerator* gen = mf.GetMakefileGenerator();
gen->SetLocal(m_Local);
const char* genName = mf.GetDefinition("CMAKE_GENERATOR");
if(genName)
{
if(strcmp(gen->GetName(), genName) != 0)
{
std::string message = "Error: generator : ";
message += gen->GetName();
message += "\nDoes not match the generator used previously: ";
message += genName;
message +=
"\nEither remove the CMakeCache.txt file or choose a different"
" binary directory.";
cmSystemTools::Error(message.c_str());
return -2;
}
}
if(!mf.GetDefinition("CMAKE_GENERATOR"))
{
mf.AddCacheDefinition("CMAKE_GENERATOR",
gen->GetName(),
"Name of generator.",
cmCacheManager::INTERNAL);
}
// setup CMAKE_ROOT and CMAKE_COMMAND
if(!this->AddCMakePaths(args))
{
return -3;
}
// reset any system configuration information
cmMakefileGenerator::ClearEnabledLanguages();
std::string lf = mf.GetStartDirectory();
lf += "/CMakeLists.txt";
if(!mf.ReadListFile(lf.c_str()))
{
this->Usage(args[0].c_str());
return -1;
}
// if buildMakefiles, then call GenerateMakefile
if(buildMakefiles)
{
mf.GenerateMakefile();
}
else // do not build, but let the commands finalize
{
std::vector<cmMakefile*> makefiles;
mf.FindSubDirectoryCMakeListsFiles(makefiles);
for(std::vector<cmMakefile*>::iterator i = makefiles.begin();
i != makefiles.end(); ++i)
{
cmMakefile* mf = *i;
mf->FinalPass();
delete mf;
}
mf.FinalPass();
}
// Before saving the cache
// if the project did not define one of the entries below, add them now
// so users can edit the values in the cache:
// LIBRARY_OUTPUT_PATH
// EXECUTABLE_OUTPUT_PATH
if(!this->m_CacheManager.GetCacheValue("LIBRARY_OUTPUT_PATH"))
{
this->m_CacheManager.AddCacheEntry("LIBRARY_OUTPUT_PATH", "",
"Single output directory for building all libraries.",
cmCacheManager::PATH);
}
if(!this->m_CacheManager.GetCacheValue("EXECUTABLE_OUTPUT_PATH"))
{
this->m_CacheManager.AddCacheEntry("EXECUTABLE_OUTPUT_PATH", "",
"Single output directory for building all executables.",
cmCacheManager::PATH);
}
this->m_CacheManager.SaveCache(&mf);
if(m_Verbose)
{
this->m_CacheManager.PrintCache(std::cout);
}
if(cmSystemTools::GetErrorOccuredFlag())
{
return -1;
}
return 0;
}
void CMakeCommandUsage(const char* program)
{
cmStringStream errorStream;
@ -678,39 +523,291 @@ int cmake::CMakeCommand(std::vector<std::string>& args)
void cmake::GetRegisteredGenerators(std::vector<std::string>& names)
{
for(std::map<cmStdString, cmMakefileGenerator*>::iterator i
= this->m_RegisteredGenerators.begin();
i != this->m_RegisteredGenerators.end(); ++i)
{
names.push_back(i->first);
}
#if defined(_WIN32) && !defined(__CYGWIN__)
names.push_back(cmGlobalVisualStudio6Generator::GetActualName());
names.push_back(cmGlobalVisualStudio7Generator::GetActualName());
names.push_back(cmGlobalBorlandMakefileGenerator::GetActualName());
names.push_back(cmGlobalNMakeMakefileGenerator::GetActualName());
#else
names.push_back(cmGlobalUnixMakefileGenerator::GetActualName());
#endif
}
void cmake::RegisterGenerator(cmMakefileGenerator* mg)
cmGlobalGenerator* cmake::CreateGlobalGenerator(const char* name)
{
std::map<cmStdString, cmMakefileGenerator*>::iterator i =
this->m_RegisteredGenerators.find(mg->GetName());
// delete re-registered objects
if(i != this->m_RegisteredGenerators.end())
cmGlobalGenerator *ret = 0;
#if defined(_WIN32) && !defined(__CYGWIN__)
if (!strcmp(name,cmGlobalNMakeMakefileGenerator::GetActualName()))
{
delete i->second;
ret = new cmGlobalNMakeMakefileGenerator;
ret->SetCMakeInstance(this);
}
this->m_RegisteredGenerators[mg->GetName()] = mg;
if (!strcmp(name,cmGlobalVisualStudio6Generator::GetActualName()))
{
ret = new cmGlobalVisualStudio6Generator;
ret->SetCMakeInstance(this);
}
if (!strcmp(name,cmGlobalVisualStudio7Generator::GetActualName()))
{
ret = new cmGlobalVisualStudio7Generator;
ret->SetCMakeInstance(this);
}
if (!strcmp(name,cmGlobalBorlandMakefileGenerator::GetActualName()))
{
ret = new cmGlobalBorlandMakefileGenerator;
ret->SetCMakeInstance(this);
}
#else
if (!strcmp(name,cmGlobalUnixMakefileGenerator::GetActualName()))
{
ret = new cmGlobalUnixMakefileGenerator;
ret->SetCMakeInstance(this);
}
#endif
return ret;
}
cmMakefileGenerator* cmake::CreateGenerator(const char* name)
void cmake::SetHomeDirectory(const char* dir)
{
std::map<cmStdString, cmMakefileGenerator*>::iterator i;
for(i = this->m_RegisteredGenerators.begin();
i != this->m_RegisteredGenerators.end(); ++i)
m_cmHomeDirectory = dir;
cmSystemTools::ConvertToUnixSlashes(m_cmHomeDirectory);
}
void cmake::SetHomeOutputDirectory(const char* lib)
{
m_HomeOutputDirectory = lib;
cmSystemTools::ConvertToUnixSlashes(m_HomeOutputDirectory);
}
void cmake::SetGlobalGenerator(cmGlobalGenerator *gg)
{
// delete the old generator
if (m_GlobalGenerator)
{
cmMakefileGenerator* gen = i->second;
if(strcmp(name, gen->GetName()) == 0)
delete m_GlobalGenerator;
}
// set the new
m_GlobalGenerator = gg;
// set the cmake instance just to be sure
gg->SetCMakeInstance(this);
}
int cmake::Configure(const char *arg0, const std::vector<std::string>* args)
{
// Read in the cache
m_CacheManager->LoadCache(this->GetHomeOutputDirectory());
if(m_CacheManager->GetCacheValue("CMAKE_HOME_DIRECTORY"))
{
std::string cacheStart =
m_CacheManager->GetCacheValue("CMAKE_HOME_DIRECTORY");
cacheStart += "/CMakeLists.txt";
std::string currentStart = this->GetHomeDirectory();
currentStart += "/CMakeLists.txt";
if(!cmSystemTools::SameFile(cacheStart.c_str(), currentStart.c_str()))
{
return gen->CreateObject();
std::string message = "Error: source : ";
message += currentStart;
message += "\nDoes not match source used to generate cache: ";
message += cacheStart;
message += "\nRe-run cmake with a different source directory.";
cmSystemTools::Error(message.c_str());
return -2;
}
}
else
{
m_CacheManager->AddCacheEntry("CMAKE_HOME_DIRECTORY",
this->GetHomeDirectory(),
"Start directory with the top level CMakeLists.txt file for this project",
cmCacheManager::INTERNAL);
}
// extract command line arguments that might add cache entries
if (args)
{
this->SetCacheArgs(*args);
}
// setup CMAKE_ROOT and CMAKE_COMMAND
if(!this->AddCMakePaths(arg0))
{
return -3;
}
// no generator specified on the command line
if(!m_GlobalGenerator)
{
const char* genName = m_CacheManager->GetCacheValue("CMAKE_GENERATOR");
if(genName)
{
m_GlobalGenerator = this->CreateGlobalGenerator(genName);
}
else
{
#if defined(__BORLANDC__)
this->SetGlobalGenerator(new cmGlobalBorlandMakefileGenerator);
#elif defined(_WIN32) && !defined(__CYGWIN__)
this->SetGlobalGenerator(new cmGlobalVisualStudio6Generator);
#else
this->SetGlobalGenerator(new cmGlobalUnixMakefileGenerator);
#endif
}
if(!m_GlobalGenerator)
{
cmSystemTools::Error("Could not create generator");
return -1;
}
}
const char* genName = m_CacheManager->GetCacheValue("CMAKE_GENERATOR");
if(genName)
{
if(strcmp(m_GlobalGenerator->GetName(), genName) != 0)
{
std::string message = "Error: generator : ";
message += m_GlobalGenerator->GetName();
message += "\nDoes not match the generator used previously: ";
message += genName;
message +=
"\nEither remove the CMakeCache.txt file or choose a different"
" binary directory.";
cmSystemTools::Error(message.c_str());
return -2;
}
}
if(!m_CacheManager->GetCacheValue("CMAKE_GENERATOR"))
{
m_CacheManager->AddCacheEntry("CMAKE_GENERATOR", m_GlobalGenerator->GetName(),
"Name of generator.",
cmCacheManager::INTERNAL);
}
// reset any system configuration information
m_GlobalGenerator->ClearEnabledLanguages();
// actually do the configure
m_GlobalGenerator->Configure();
// Before saving the cache
// if the project did not define one of the entries below, add them now
// so users can edit the values in the cache:
// LIBRARY_OUTPUT_PATH
// EXECUTABLE_OUTPUT_PATH
if(!m_CacheManager->GetCacheValue("LIBRARY_OUTPUT_PATH"))
{
m_CacheManager->AddCacheEntry("LIBRARY_OUTPUT_PATH", "",
"Single output directory for building all libraries.",
cmCacheManager::PATH);
}
if(!m_CacheManager->GetCacheValue("EXECUTABLE_OUTPUT_PATH"))
{
m_CacheManager->AddCacheEntry("EXECUTABLE_OUTPUT_PATH", "",
"Single output directory for building all executables.",
cmCacheManager::PATH);
}
this->m_CacheManager->SaveCache(this->GetHomeOutputDirectory());
if(cmSystemTools::GetErrorOccuredFlag())
{
return -1;
}
return 0;
}
// handle a command line invocation
int cmake::Run(const std::vector<std::string>& args)
{
// a quick check for args
if(args.size() == 1 && !cmSystemTools::FileExists("CMakeLists.txt"))
{
this->Usage(args[0].c_str());
return -1;
}
// look for obvious request for help
for(unsigned int i=1; i < args.size(); ++i)
{
std::string arg = args[i];
if(arg.find("-help",0) != std::string::npos ||
arg.find("--help",0) != std::string::npos ||
arg.find("/?",0) != std::string::npos ||
arg.find("-usage",0) != std::string::npos)
{
this->Usage(args[0].c_str());
return -1;
}
}
// Process the arguments
this->SetArgs(args);
// if we are local do the local thing, otherwise do global
if (m_Local)
{
return this->LocalGenerate();
}
// otherwise global
int ret = this->Configure(args[0].c_str(),&args);
if (ret)
{
return ret;
}
return this->Generate();
}
int cmake::Generate()
{
m_GlobalGenerator->Generate();
if(cmSystemTools::GetErrorOccuredFlag())
{
return -1;
}
return 0;
}
int cmake::LocalGenerate()
{
// Read in the cache
m_CacheManager->LoadCache(this->GetHomeOutputDirectory());
// create the generator based on the cache if it isn't already there
const char* genName = m_CacheManager->GetCacheValue("CMAKE_GENERATOR");
if(genName)
{
m_GlobalGenerator = this->CreateGlobalGenerator(genName);
}
else
{
cmSystemTools::Error("Could local Generate called without the GENERATOR being specified in the CMakeCache");
return -1;
}
// do the local generate
m_GlobalGenerator->LocalGenerate();
if(cmSystemTools::GetErrorOccuredFlag())
{
return -1;
}
return 0;
}
unsigned int cmake::GetMajorVersion()
{
return cmMakefile::GetMajorVersion();
}
unsigned int cmake::GetMinorVersion()
{
return cmMakefile::GetMinorVersion();
}
const char *cmake::GetReleaseVersion()
{
return cmMakefile::GetReleaseVersion();
}
const char* cmake::GetCacheDefinition(const char* name) const
{
return m_CacheManager->GetCacheValue(name);
}

View File

@ -18,18 +18,81 @@
// running cmake. Most cmake based GUIS should primarily create an instance
// of this class and communicate with it.
#include "cmMakefile.h"
#include "cmStandardIncludes.h"
#include "cmSystemTools.h"
class cmGlobalGenerator;
class cmLocalGenerator;
class cmCacheManager;
class cmMakefile;
class cmake
{
public:
///! construct an instance of cmake
cmake();
///! destruct an instance of cmake
~cmake();
/**
* Generate the SourceFilesList from the SourceLists. This should only be
* done once to be safe.
* Return major and minor version numbers for cmake.
*/
void Usage(const char *program);
static unsigned int GetMajorVersion();
static unsigned int GetMinorVersion();
static const char *GetReleaseVersion();
//@{
/**
* Set/Get the home directory (or output directory) in the project. The
* home directory is the top directory of the project. It is where
* cmake was run. Remember that CMake processes
* CMakeLists files by recursing up the tree starting at the StartDirectory
* and going up until it reaches the HomeDirectory.
*/
void SetHomeDirectory(const char* dir);
const char* GetHomeDirectory() const
{
return m_cmHomeDirectory.c_str();
}
void SetHomeOutputDirectory(const char* lib);
const char* GetHomeOutputDirectory() const
{
return m_HomeOutputDirectory.c_str();
}
//@}
//@{
/**
* Set/Get the start directory (or output directory). The start directory
* is the directory of the CMakeLists.txt file that started the current
* round of processing. Remember that CMake processes CMakeLists files by
* recursing up the tree starting at the StartDirectory and going up until
* it reaches the HomeDirectory.
*/
void SetStartDirectory(const char* dir)
{
m_cmStartDirectory = dir;
cmSystemTools::ConvertToUnixSlashes(m_cmStartDirectory);
}
const char* GetStartDirectory() const
{
return m_cmStartDirectory.c_str();
}
void SetStartOutputDirectory(const char* lib)
{
m_StartOutputDirectory = lib;
cmSystemTools::ConvertToUnixSlashes(m_StartOutputDirectory);
}
const char* GetStartOutputDirectory() const
{
return m_StartOutputDirectory.c_str();
}
//@}
/**
* Handle a command line invocation of cmake.
*/
int Run(const std::vector<std::string>&args);
/**
* Generate the SourceFilesList from the SourceLists. This should only be
@ -41,7 +104,35 @@ class cmake
* If you only want to parse the CMakeLists.txt files,
* but not actually generate the makefiles, use buildMakefiles = false.
*/
int Generate(const std::vector<std::string>&, bool buildMakefiles = true);
int Generate();
/**
* Configure the cmMakefiles. This routine will create a GlobalGenerator if
* one has not already been set. It will then Call Configure on the
* GlobalGenerator. This in turn will read in an process all the CMakeList
* files for the tree. It will not produce any actual Makefiles, or
* workspaces. Generate does that. */
int Configure(const char *cmakeexec, const std::vector<std::string> *args = 0);
///! Create a GlobalGenerator
cmGlobalGenerator* CreateGlobalGenerator(const char* name);
///! Return the global generator assigned to this instance of cmake
cmGlobalGenerator* GetGlobalGenerator() { return m_GlobalGenerator; };
///! Return the global generator assigned to this instance of cmake
void SetGlobalGenerator(cmGlobalGenerator *);
///! Get the names of the current registered generators
void GetRegisteredGenerators(std::vector<std::string>& names);
///! get the cmCachemManager used by this invocation of cmake
cmCacheManager *GetCacheManager() { return m_CacheManager; }
/**
* Given a variable name, return its value (as a string).
*/
const char* GetCacheDefinition(const char*) const;
/**
* Execute commands during the build process. Supports options such
@ -49,36 +140,43 @@ class cmake
*/
static int CMakeCommand(std::vector<std::string>&);
///! Parse command line arguments
void SetArgs(cmMakefile& builder, const std::vector<std::string>&);
///! Parse command line arguments that might set cache values
void SetCacheArgs(cmMakefile& builder, const std::vector<std::string>&);
/**
* Is cmake in the process of a local cmake invocation. If so, we know the
* cache is already configured and ready to go.
*/
bool GetLocal()
{
return m_Local;
}
///! Display command line useage
void Usage(const char *program);
///! Parse command line arguments
void SetArgs(const std::vector<std::string>&);
protected:
cmGlobalGenerator *m_GlobalGenerator;
cmCacheManager *m_CacheManager;
std::string m_cmHomeDirectory;
std::string m_HomeOutputDirectory;
std::string m_cmStartDirectory;
std::string m_StartOutputDirectory;
///! Parse command line arguments that might set cache values
void SetCacheArgs(const std::vector<std::string>&);
///! read in a cmake list file to initialize the cache
void ReadListFile(const char *path);
/**
* Generate CMAKE_ROOT and CMAKE_COMMAND cache entries
*/
int AddCMakePaths(const std::vector<std::string>&);
int AddCMakePaths(const char *arg0);
/**
* constructor
*/
cmake();
~cmake();
///! used by Run
int LocalGenerate();
///! Create a named generator
cmMakefileGenerator* CreateGenerator(const char* name);
///! Register a generator
void RegisterGenerator(cmMakefileGenerator*);
///! Get the names of the current registered generators
void GetRegisteredGenerators(std::vector<std::string>& names);
///! get the cmCachemManager used by this invocation of cmake
cmCacheManager *GetCacheManager() {
return &m_CacheManager; }
protected:
std::map<cmStdString, cmMakefileGenerator*> m_RegisteredGenerators;
cmCacheManager m_CacheManager;
private:
bool m_Verbose;
bool m_Local;

View File

@ -55,6 +55,6 @@ int main(int ac, char** av)
return 0;
}
cmake cm;
int ret = cm.Generate(args);
int ret = cm.Run(args);
return ret;
}

View File

@ -115,7 +115,7 @@ int main (int argc, char **argv)
std::cout << "Generating build files...\n";
cmake cm;
if (cm.Generate(args) != 0)
if (cm.Run(args) != 0)
{
std::cerr << "Error: cmake execution failed\n";
// return to the original directory
@ -126,7 +126,7 @@ int main (int argc, char **argv)
cmake cm2;
std::cout << "Generating build files (again)...\n";
if (cm2.Generate(args) != 0)
if (cm2.Run(args) != 0)
{
std::cerr << "Error: cmake execution failed\n";
// return to the original directory

View File

@ -98,7 +98,7 @@ void cmakewizard::RunWizard(std::vector<std::string> const& args)
asked = false;
// run cmake
this->ShowMessage("Please wait while cmake processes CMakeLists.txt files....\n");
make.Generate(args);
make.Configure(args[0].c_str(),&args);
this->ShowMessage("\n");
// load the cache from disk
cmCacheManager *cachem = make.GetCacheManager();
@ -140,5 +140,6 @@ void cmakewizard::RunWizard(std::vector<std::string> const& args)
cachem->SaveCache(cmSystemTools::GetCurrentWorkingDirectory().c_str());
}
while(asked);
make.Generate();
this->ShowMessage("CMake complete, run make to build project.\n");
}