diff options
Diffstat (limited to 'Source/cmServerProtocol.cxx')
-rw-r--r-- | Source/cmServerProtocol.cxx | 179 |
1 files changed, 171 insertions, 8 deletions
diff --git a/Source/cmServerProtocol.cxx b/Source/cmServerProtocol.cxx index 13b18c2..ad66467 100644 --- a/Source/cmServerProtocol.cxx +++ b/Source/cmServerProtocol.cxx @@ -8,9 +8,12 @@ #include "cmGeneratorExpression.h" #include "cmGeneratorTarget.h" #include "cmGlobalGenerator.h" +#include "cmInstallGenerator.h" +#include "cmInstallTargetGenerator.h" #include "cmLinkLineComputer.h" #include "cmLocalGenerator.h" #include "cmMakefile.h" +#include "cmProperty.h" #include "cmServer.h" #include "cmServerDictionary.h" #include "cmSourceFile.h" @@ -19,6 +22,8 @@ #include "cmStateSnapshot.h" #include "cmStateTypes.h" #include "cmSystemTools.h" +#include "cmTarget.h" +#include "cmTest.h" #include "cm_uv.h" #include "cmake.h" @@ -28,6 +33,7 @@ #include <functional> #include <limits> #include <map> +#include <memory> #include <set> #include <string> #include <unordered_map> @@ -250,7 +256,7 @@ bool cmServerProtocol::DoActivate(const cmServerRequest& /*request*/, std::pair<int, int> cmServerProtocol1::ProtocolVersion() const { - return std::make_pair(1, 1); + return std::make_pair(1, 2); } static void setErrorMessage(std::string* errorMessage, const std::string& text) @@ -474,6 +480,9 @@ const cmServerResponse cmServerProtocol1::Process( if (request.Type == kSET_GLOBAL_SETTINGS_TYPE) { return this->ProcessSetGlobalSettings(request); } + if (request.Type == kCTEST_INFO_TYPE) { + return this->ProcessCTests(request); + } return request.ReportError("Unknown command!"); } @@ -682,6 +691,8 @@ static Json::Value DumpSourceFilesList( std::vector<cmSourceFile*> files; target->GetSourceFiles(files, config); + cmGeneratorExpressionInterpreter genexInterpreter( + target->GetLocalGenerator(), target, config); std::unordered_map<LanguageData, std::vector<std::string>> fileGroups; for (cmSourceFile* file : files) { @@ -693,21 +704,23 @@ static Json::Value DumpSourceFilesList( std::string compileFlags = ld.Flags; if (const char* cflags = file->GetProperty("COMPILE_FLAGS")) { - cmGeneratorExpression ge; - auto cge = ge.Parse(cflags); - const char* processed = - cge->Evaluate(target->GetLocalGenerator(), config); - lg->AppendFlags(compileFlags, processed); + lg->AppendFlags(compileFlags, genexInterpreter.Evaluate(cflags)); } fileData.Flags = compileFlags; fileData.IncludePathList = ld.IncludePathList; std::set<std::string> defines; - lg->AppendDefines(defines, file->GetProperty("COMPILE_DEFINITIONS")); + if (const char* defs = file->GetProperty("COMPILE_DEFINITIONS")) { + lg->AppendDefines(defines, genexInterpreter.Evaluate(defs)); + } + const std::string defPropName = "COMPILE_DEFINITIONS_" + cmSystemTools::UpperCase(config); - lg->AppendDefines(defines, file->GetProperty(defPropName)); + if (const char* config_defs = file->GetProperty(defPropName)) { + lg->AppendDefines(defines, genexInterpreter.Evaluate(config_defs)); + } + defines.insert(ld.Defines.begin(), ld.Defines.end()); fileData.SetDefines(defines); @@ -730,6 +743,97 @@ static Json::Value DumpSourceFilesList( return result; } +static Json::Value DumpCTestInfo(cmTest* testInfo) +{ + Json::Value result = Json::objectValue; + result[kCTEST_NAME] = testInfo->GetName(); + + // Concat command entries together. After the first should be the arguments + // for the command + std::string command; + for (auto const& cmd : testInfo->GetCommand()) { + command.append(cmd); + command.append(" "); + } + result[kCTEST_COMMAND] = command; + + // Build up the list of properties that may have been specified + Json::Value properties = Json::arrayValue; + for (auto& prop : testInfo->GetProperties()) { + Json::Value entry = Json::objectValue; + entry[kKEY_KEY] = prop.first; + entry[kVALUE_KEY] = prop.second.GetValue(); + properties.append(entry); + } + result[kPROPERTIES_KEY] = properties; + + return result; +} + +static void DumpMakefileTests(cmMakefile* mf, const std::string& config, + Json::Value* result) +{ + std::vector<cmTest*> tests; + mf->GetTests(config, tests); + for (auto test : tests) { + Json::Value tmp = DumpCTestInfo(test); + if (!tmp.isNull()) { + result->append(tmp); + } + } +} + +static Json::Value DumpCTestProjectList(const cmake* cm, + std::string const& config) +{ + Json::Value result = Json::arrayValue; + + auto globalGen = cm->GetGlobalGenerator(); + + for (const auto& projectIt : globalGen->GetProjectMap()) { + Json::Value pObj = Json::objectValue; + pObj[kNAME_KEY] = projectIt.first; + + Json::Value tests = Json::arrayValue; + + // Gather tests for every generator + for (const auto& lg : projectIt.second) { + // Make sure they're generated. + lg->GenerateTestFiles(); + cmMakefile* mf = lg->GetMakefile(); + DumpMakefileTests(mf, config, &tests); + } + + pObj[kCTEST_INFO] = tests; + + result.append(pObj); + } + + return result; +} + +static Json::Value DumpCTestConfiguration(const cmake* cm, + const std::string& config) +{ + Json::Value result = Json::objectValue; + result[kNAME_KEY] = config; + + result[kPROJECTS_KEY] = DumpCTestProjectList(cm, config); + + return result; +} + +static Json::Value DumpCTestConfigurationsList(const cmake* cm) +{ + Json::Value result = Json::arrayValue; + + for (const std::string& c : getConfigurations(cm)) { + result.append(DumpCTestConfiguration(cm, c)); + } + + return result; +} + static Json::Value DumpTarget(cmGeneratorTarget* target, const std::string& config) { @@ -754,6 +858,8 @@ static Json::Value DumpTarget(cmGeneratorTarget* target, Json::Value result = Json::objectValue; result[kNAME_KEY] = target->GetName(); + result[kIS_GENERATOR_PROVIDED_KEY] = + target->Target->GetIsGeneratorProvided(); result[kTYPE_KEY] = typeName; result[kSOURCE_DIRECTORY_KEY] = lg->GetCurrentSourceDirectory(); result[kBUILD_DIRECTORY_KEY] = lg->GetCurrentBinaryDirectory(); @@ -764,6 +870,34 @@ static Json::Value DumpTarget(cmGeneratorTarget* target, result[kFULL_NAME_KEY] = target->GetFullName(config); + if (target->Target->GetHaveInstallRule()) { + result[kHAS_INSTALL_RULE] = true; + + Json::Value installPaths = Json::arrayValue; + auto targetGenerators = target->Makefile->GetInstallGenerators(); + for (auto installGenerator : targetGenerators) { + auto installTargetGenerator = + dynamic_cast<cmInstallTargetGenerator*>(installGenerator); + if (installTargetGenerator != nullptr && + installTargetGenerator->GetTarget()->Target == target->Target) { + auto dest = installTargetGenerator->GetDestination(config); + + std::string installPath; + if (!dest.empty() && cmSystemTools::FileIsFullPath(dest.c_str())) { + installPath = dest; + } else { + std::string installPrefix = + target->Makefile->GetSafeDefinition("CMAKE_INSTALL_PREFIX"); + installPath = installPrefix + '/' + dest; + } + + installPaths.append(installPath); + } + } + + result[kINSTALL_PATHS] = installPaths; + } + if (target->HaveWellDefinedOutputFiles()) { Json::Value artifacts = Json::arrayValue; artifacts.append( @@ -884,10 +1018,26 @@ static Json::Value DumpProjectList(const cmake* cm, std::string const& config) // Project structure information: const cmMakefile* mf = lg->GetMakefile(); + pObj[kMINIMUM_CMAKE_VERSION] = + mf->GetDefinition("CMAKE_MINIMUM_REQUIRED_VERSION"); pObj[kSOURCE_DIRECTORY_KEY] = mf->GetCurrentSourceDirectory(); pObj[kBUILD_DIRECTORY_KEY] = mf->GetCurrentBinaryDirectory(); pObj[kTARGETS_KEY] = DumpTargetsList(projectIt.second, config); + // For a project-level install rule it might be defined in any of its + // associated generators. + bool hasInstallRule = false; + for (const auto generator : projectIt.second) { + hasInstallRule = + generator->GetMakefile()->GetInstallGenerators().empty() == false; + + if (hasInstallRule) { + break; + } + } + + pObj[kHAS_INSTALL_RULE] = hasInstallRule; + result.append(pObj); } @@ -1141,6 +1291,19 @@ cmServerResponse cmServerProtocol1::ProcessFileSystemWatchers( return request.Reply(result); } +cmServerResponse cmServerProtocol1::ProcessCTests( + const cmServerRequest& request) +{ + if (this->m_State < STATE_COMPUTED) { + return request.ReportError("This instance was not yet computed."); + } + + Json::Value result = Json::objectValue; + result[kCONFIGURATIONS_KEY] = + DumpCTestConfigurationsList(this->CMakeInstance()); + return request.Reply(result); +} + cmServerProtocol1::GeneratorInformation::GeneratorInformation( const std::string& generatorName, const std::string& extraGeneratorName, const std::string& toolset, const std::string& platform, |