| /* Distributed under the OSI-approved BSD 3-Clause License. See accompanying |
| file Copyright.txt or https://cmake.org/licensing for details. */ |
| #pragma once |
| |
| #include "cmConfigure.h" // IWYU pragma: keep |
| |
| #include <cstddef> |
| #include <deque> |
| #include <functional> |
| #include <map> |
| #include <memory> |
| #include <set> |
| #include <stack> |
| #include <string> |
| #include <unordered_map> |
| #include <utility> |
| #include <vector> |
| |
| #include <cm/optional> |
| #include <cm/string_view> |
| |
| #include "cmsys/RegularExpression.hxx" |
| |
| #include "cm_sys_stat.h" |
| |
| #include "cmAlgorithms.h" |
| #include "cmCustomCommand.h" |
| #include "cmFunctionBlocker.h" |
| #include "cmListFileCache.h" |
| #include "cmMessageType.h" // IWYU pragma: keep |
| #include "cmNewLineStyle.h" |
| #include "cmPolicies.h" |
| #include "cmSourceFileLocationKind.h" |
| #include "cmStateSnapshot.h" |
| #include "cmStateTypes.h" |
| #include "cmValue.h" |
| |
| // IWYU does not see that 'std::unordered_map<std::string, cmTarget>' |
| // will not compile without the complete type. |
| #include "cmTarget.h" // IWYU pragma: keep |
| |
| #if !defined(CMAKE_BOOTSTRAP) |
| # include "cmSourceGroup.h" |
| #endif |
| |
| enum class cmCustomCommandType; |
| enum class cmObjectLibraryCommands; |
| |
| class cmCompiledGeneratorExpression; |
| class cmCustomCommandLines; |
| class cmExecutionStatus; |
| class cmExpandedCommandArgument; |
| class cmExportBuildFileGenerator; |
| class cmGeneratorExpressionEvaluationFile; |
| class cmGlobalGenerator; |
| class cmInstallGenerator; |
| class cmLocalGenerator; |
| class cmMessenger; |
| class cmSourceFile; |
| class cmState; |
| class cmTest; |
| class cmTestGenerator; |
| class cmVariableWatch; |
| class cmake; |
| |
| /** A type-safe wrapper for a string representing a directory id. */ |
| class cmDirectoryId |
| { |
| public: |
| cmDirectoryId(std::string s); |
| std::string String; |
| }; |
| |
| /** \class cmMakefile |
| * \brief Process the input CMakeLists.txt file. |
| * |
| * Process and store into memory the input CMakeLists.txt file. |
| * Each CMakeLists.txt file is parsed and the commands found there |
| * are added into the build process. |
| */ |
| class cmMakefile |
| { |
| public: |
| /* Mark a variable as used */ |
| void MarkVariableAsUsed(const std::string& var); |
| /* return true if a variable has been initialized */ |
| bool VariableInitialized(const std::string&) const; |
| |
| /** |
| * Construct an empty makefile. |
| */ |
| cmMakefile(cmGlobalGenerator* globalGenerator, |
| const cmStateSnapshot& snapshot); |
| |
| /** |
| * Destructor. |
| */ |
| ~cmMakefile(); |
| |
| cmMakefile(cmMakefile const&) = delete; |
| cmMakefile& operator=(cmMakefile const&) = delete; |
| |
| cmDirectoryId GetDirectoryId() const; |
| |
| bool ReadListFile(const std::string& filename); |
| |
| bool ReadListFileAsString(const std::string& content, |
| const std::string& virtualFileName); |
| |
| bool ReadDependentFile(const std::string& filename, |
| bool noPolicyScope = true); |
| |
| /** |
| * Add a function blocker to this makefile |
| */ |
| void AddFunctionBlocker(std::unique_ptr<cmFunctionBlocker> fb); |
| |
| /// @return whether we are processing the top CMakeLists.txt file. |
| bool IsRootMakefile() const; |
| |
| /** |
| * Remove the function blocker whose scope ends with the given command. |
| * This returns ownership of the function blocker object. |
| */ |
| std::unique_ptr<cmFunctionBlocker> RemoveFunctionBlocker(); |
| |
| /** |
| * Try running cmake and building a file. This is used for dynamically |
| * loaded commands, not as part of the usual build process. |
| */ |
| int TryCompile(const std::string& srcdir, const std::string& bindir, |
| const std::string& projectName, const std::string& targetName, |
| bool fast, int jobs, |
| const std::vector<std::string>* cmakeArgs, |
| std::string& output); |
| |
| bool GetIsSourceFileTryCompile() const; |
| |
| /** |
| * Help enforce global target name uniqueness. |
| */ |
| bool EnforceUniqueName(std::string const& name, std::string& msg, |
| bool isCustom = false) const; |
| |
| class GeneratorAction |
| { |
| using ActionT = |
| std::function<void(cmLocalGenerator&, const cmListFileBacktrace&)>; |
| using CCActionT = |
| std::function<void(cmLocalGenerator&, const cmListFileBacktrace&, |
| std::unique_ptr<cmCustomCommand> cc)>; |
| |
| public: |
| GeneratorAction(ActionT&& action) |
| : Action(std::move(action)) |
| { |
| } |
| |
| GeneratorAction(std::unique_ptr<cmCustomCommand> tcc, CCActionT&& action) |
| : CCAction(std::move(action)) |
| , cc(std::move(tcc)) |
| { |
| } |
| |
| void operator()(cmLocalGenerator& lg, const cmListFileBacktrace& lfbt); |
| |
| private: |
| ActionT Action; |
| |
| // FIXME: Use std::variant |
| CCActionT CCAction; |
| std::unique_ptr<cmCustomCommand> cc; |
| }; |
| |
| /** |
| * Register an action that is executed during Generate |
| */ |
| void AddGeneratorAction(GeneratorAction&& action); |
| |
| /// Helper to insert the constructor GeneratorAction(args...) |
| template <class... Args> |
| void AddGeneratorAction(Args&&... args) |
| { |
| AddGeneratorAction(GeneratorAction(std::move(args)...)); |
| } |
| |
| /** |
| * Perform generate actions, Library dependency analysis etc before output of |
| * the makefile. |
| */ |
| void Generate(cmLocalGenerator& lg); |
| |
| /** |
| * Get the target for PRE_BUILD, PRE_LINK, or POST_BUILD commands. |
| */ |
| cmTarget* GetCustomCommandTarget(const std::string& target, |
| cmObjectLibraryCommands objLibCommands, |
| const cmListFileBacktrace& lfbt) const; |
| |
| /** |
| * Dispatch adding a custom PRE_BUILD, PRE_LINK, or POST_BUILD command to a |
| * target. |
| */ |
| cmTarget* AddCustomCommandToTarget(const std::string& target, |
| cmCustomCommandType type, |
| std::unique_ptr<cmCustomCommand> cc); |
| |
| /** |
| * Called for each file with custom command. |
| */ |
| using CommandSourceCallback = std::function<void(cmSourceFile*)>; |
| |
| /** |
| * Dispatch adding a custom command to a source file. |
| */ |
| void AddCustomCommandToOutput( |
| std::unique_ptr<cmCustomCommand> cc, |
| const CommandSourceCallback& callback = nullptr, bool replace = false); |
| void AddCustomCommandOldStyle(const std::string& target, |
| const std::vector<std::string>& outputs, |
| const std::vector<std::string>& depends, |
| const std::string& source, |
| const cmCustomCommandLines& commandLines, |
| const char* comment); |
| void AppendCustomCommandToOutput( |
| const std::string& output, const std::vector<std::string>& depends, |
| const cmImplicitDependsList& implicit_depends, |
| const cmCustomCommandLines& commandLines); |
| |
| /** |
| * Add a define flag to the build. |
| */ |
| void AddDefineFlag(std::string const& definition); |
| void RemoveDefineFlag(std::string const& definition); |
| void AddCompileDefinition(std::string const& definition); |
| void AddCompileOption(std::string const& option); |
| void AddLinkOption(std::string const& option); |
| void AddLinkDirectory(std::string const& directory, bool before = false); |
| |
| /** Create a new imported target with the name and type given. */ |
| cmTarget* AddImportedTarget(const std::string& name, |
| cmStateEnums::TargetType type, bool global); |
| |
| std::pair<cmTarget&, bool> CreateNewTarget( |
| const std::string& name, cmStateEnums::TargetType type, |
| cmTarget::PerConfig perConfig = cmTarget::PerConfig::Yes, |
| cmTarget::Visibility vis = cmTarget::Visibility::Normal); |
| |
| cmTarget* AddNewTarget(cmStateEnums::TargetType type, |
| const std::string& name); |
| cmTarget* AddSynthesizedTarget(cmStateEnums::TargetType type, |
| const std::string& name); |
| |
| /** Create a target instance for the utility. */ |
| cmTarget* AddNewUtilityTarget(const std::string& utilityName, |
| bool excludeFromAll); |
| |
| /** |
| * Add an executable to the build. |
| */ |
| cmTarget* AddExecutable(const std::string& exename, |
| const std::vector<std::string>& srcs, |
| bool excludeFromAll = false); |
| |
| /** |
| * Dispatch adding a utility to the build. A utility target is a command |
| * that is run every time the target is built. |
| */ |
| cmTarget* AddUtilityCommand(const std::string& utilityName, |
| bool excludeFromAll, |
| std::unique_ptr<cmCustomCommand> cc); |
| |
| /** |
| * Add a subdirectory to the build. |
| */ |
| void AddSubDirectory(const std::string& fullSrcDir, |
| const std::string& fullBinDir, bool excludeFromAll, |
| bool immediate, bool system); |
| |
| void Configure(); |
| |
| /** |
| * Configure a subdirectory |
| */ |
| void ConfigureSubDirectory(cmMakefile* mf); |
| |
| /** |
| * Add an include directory to the build. |
| */ |
| void AddIncludeDirectories(const std::vector<std::string>& incs, |
| bool before = false); |
| |
| /** |
| * Add a variable definition to the build. This variable |
| * can be used in CMake to refer to lists, directories, etc. |
| */ |
| void AddDefinition(const std::string& name, cm::string_view value); |
| void AddDefinition(const std::string& name, cmValue value) |
| { |
| this->AddDefinition(name, *value); |
| } |
| /** |
| * Add bool variable definition to the build. |
| */ |
| void AddDefinitionBool(const std::string& name, bool); |
| //! Add a definition to this makefile and the global cmake cache. |
| void AddCacheDefinition(const std::string& name, cmValue value, cmValue doc, |
| cmStateEnums::CacheEntryType type, |
| bool force = false); |
| void AddCacheDefinition(const std::string& name, cmValue value, |
| const std::string& doc, |
| cmStateEnums::CacheEntryType type, |
| bool force = false) |
| { |
| this->AddCacheDefinition(name, value, cmValue{ doc }, type, force); |
| } |
| void AddCacheDefinition(const std::string& name, const std::string& value, |
| const std::string& doc, |
| cmStateEnums::CacheEntryType type, |
| bool force = false) |
| { |
| this->AddCacheDefinition(name, cmValue{ value }, cmValue{ doc }, type, |
| force); |
| } |
| |
| /** |
| * Remove a variable definition from the build. This is not valid |
| * for cache entries, and will only affect the current makefile. |
| */ |
| void RemoveDefinition(const std::string& name); |
| //! Remove a definition from the cache. |
| void RemoveCacheDefinition(const std::string& name) const; |
| |
| /** |
| * Specify the name of the project for this build. |
| */ |
| void SetProjectName(std::string const& name); |
| |
| void InitCMAKE_CONFIGURATION_TYPES(std::string const& genDefault); |
| |
| /* Get the default configuration */ |
| std::string GetDefaultConfiguration() const; |
| |
| enum GeneratorConfigQuery |
| { |
| IncludeEmptyConfig, // Include "" aka noconfig |
| ExcludeEmptyConfig, // Exclude "" aka noconfig |
| OnlyMultiConfig, |
| }; |
| |
| /** Get the configurations for dependency checking. */ |
| std::vector<std::string> GetGeneratorConfigs( |
| GeneratorConfigQuery mode) const; |
| |
| /** |
| * Set the name of the library. |
| */ |
| cmTarget* AddLibrary(const std::string& libname, |
| cmStateEnums::TargetType type, |
| const std::vector<std::string>& srcs, |
| bool excludeFromAll = false); |
| void AddAlias(const std::string& libname, const std::string& tgt, |
| bool globallyVisible = true); |
| |
| //@{ |
| /** |
| * Set, Push, Pop policy values for CMake. |
| */ |
| bool SetPolicy(cmPolicies::PolicyID id, cmPolicies::PolicyStatus status); |
| bool SetPolicy(const char* id, cmPolicies::PolicyStatus status); |
| cmPolicies::PolicyStatus GetPolicyStatus(cmPolicies::PolicyID id, |
| bool parent_scope = false) const; |
| bool SetPolicyVersion(std::string const& version_min, |
| std::string const& version_max); |
| void RecordPolicies(cmPolicies::PolicyMap& pm) const; |
| //@} |
| |
| /** Helper class to push and pop policies automatically. */ |
| class PolicyPushPop |
| { |
| public: |
| PolicyPushPop(cmMakefile* m); |
| ~PolicyPushPop(); |
| |
| PolicyPushPop(const PolicyPushPop&) = delete; |
| PolicyPushPop& operator=(const PolicyPushPop&) = delete; |
| |
| private: |
| cmMakefile* Makefile; |
| }; |
| friend class PolicyPushPop; |
| |
| /** Helper class to push and pop variables scopes automatically. */ |
| class VariablePushPop |
| { |
| public: |
| VariablePushPop(cmMakefile* m); |
| ~VariablePushPop(); |
| |
| VariablePushPop(VariablePushPop const&) = delete; |
| VariablePushPop& operator=(VariablePushPop const&) = delete; |
| |
| private: |
| cmMakefile* Makefile; |
| }; |
| |
| /** |
| * Determine if the given context, name pair has already been reported |
| * in context of CMP0054. |
| */ |
| bool HasCMP0054AlreadyBeenReported(const cmListFileContext& context) const; |
| |
| bool IgnoreErrorsCMP0061() const; |
| |
| std::string const& GetHomeDirectory() const; |
| std::string const& GetHomeOutputDirectory() const; |
| |
| /** |
| * Set CMAKE_SCRIPT_MODE_FILE variable when running a -P script. |
| */ |
| void SetScriptModeFile(std::string const& scriptfile); |
| |
| /** |
| * Set CMAKE_ARGC, CMAKE_ARGV0 ... variables. |
| */ |
| void SetArgcArgv(const std::vector<std::string>& args); |
| |
| std::string const& GetCurrentSourceDirectory() const; |
| std::string const& GetCurrentBinaryDirectory() const; |
| |
| //@} |
| |
| /** |
| * Set a regular expression that include files must match |
| * in order to be considered as part of the depend information. |
| */ |
| void SetIncludeRegularExpression(const std::string& regex) |
| { |
| this->SetProperty("INCLUDE_REGULAR_EXPRESSION", regex); |
| } |
| const std::string& GetIncludeRegularExpression() const |
| { |
| return this->GetProperty("INCLUDE_REGULAR_EXPRESSION"); |
| } |
| |
| /** |
| * Set a regular expression that include files that are not found |
| * must match in order to be considered a problem. |
| */ |
| void SetComplainRegularExpression(const std::string& regex) |
| { |
| this->ComplainFileRegularExpression = regex; |
| } |
| const std::string& GetComplainRegularExpression() const |
| { |
| return this->ComplainFileRegularExpression; |
| } |
| |
| // -- List of targets |
| using cmTargetMap = std::unordered_map<std::string, cmTarget>; |
| /** Get the target map */ |
| cmTargetMap& GetTargets() { return this->Targets; } |
| /** Get the target map - const version */ |
| cmTargetMap const& GetTargets() const { return this->Targets; } |
| |
| const std::vector<std::unique_ptr<cmTarget>>& GetOwnedImportedTargets() const |
| { |
| return this->ImportedTargetsOwned; |
| } |
| std::vector<cmTarget*> GetImportedTargets() const; |
| |
| cmTarget* FindLocalNonAliasTarget(const std::string& name) const; |
| |
| /** Find a target to use in place of the given name. The target |
| returned may be imported or built within the project. */ |
| cmTarget* FindTargetToUse(const std::string& name, |
| bool excludeAliases = false) const; |
| bool IsAlias(const std::string& name) const; |
| |
| std::map<std::string, std::string> GetAliasTargets() const |
| { |
| return this->AliasTargets; |
| } |
| |
| /** |
| * Mark include directories as system directories. |
| */ |
| void AddSystemIncludeDirectories(const std::set<std::string>& incs); |
| |
| /** Get a cmSourceFile pointer for a given source name, if the name is |
| * not found, then a null pointer is returned. |
| */ |
| cmSourceFile* GetSource( |
| const std::string& sourceName, |
| cmSourceFileLocationKind kind = cmSourceFileLocationKind::Ambiguous) const; |
| |
| /** Create the source file and return it. generated |
| * indicates if it is a generated file, this is used in determining |
| * how to create the source file instance e.g. name |
| */ |
| cmSourceFile* CreateSource( |
| const std::string& sourceName, bool generated = false, |
| cmSourceFileLocationKind kind = cmSourceFileLocationKind::Ambiguous); |
| |
| /** Get a cmSourceFile pointer for a given source name, if the name is |
| * not found, then create the source file and return it. generated |
| * indicates if it is a generated file, this is used in determining |
| * how to create the source file instance e.g. name |
| */ |
| cmSourceFile* GetOrCreateSource( |
| const std::string& sourceName, bool generated = false, |
| cmSourceFileLocationKind kind = cmSourceFileLocationKind::Ambiguous); |
| |
| /** Get a cmSourceFile pointer for a given source name and always mark the |
| * file as generated, if the name is not found, then create the source file |
| * and return it. |
| */ |
| cmSourceFile* GetOrCreateGeneratedSource(const std::string& sourceName); |
| |
| void AddTargetObject(std::string const& tgtName, std::string const& objFile); |
| |
| /** |
| * Given a variable name, return its value (as a string). |
| * If the variable is not found in this makefile instance, the |
| * cache is then queried. |
| */ |
| cmValue GetDefinition(const std::string&) const; |
| const std::string& GetSafeDefinition(const std::string&) const; |
| const std::string& GetRequiredDefinition(const std::string& name) const; |
| bool IsDefinitionSet(const std::string&) const; |
| bool IsNormalDefinitionSet(const std::string&) const; |
| /** |
| * Get the list of all variables in the current space. If argument |
| * cacheonly is specified and is greater than 0, then only cache |
| * variables will be listed. |
| */ |
| std::vector<std::string> GetDefinitions() const; |
| |
| /** |
| * Test a boolean variable to see if it is true or false. |
| * If the variable is not found in this makefile instance, the |
| * cache is then queried. |
| * Returns false if no entry defined. |
| */ |
| bool IsOn(const std::string& name) const; |
| bool IsSet(const std::string& name) const; |
| |
| /** Return whether the target platform is 32-bit. */ |
| bool PlatformIs32Bit() const; |
| |
| /** Return whether the target platform is 64-bit. */ |
| bool PlatformIs64Bit() const; |
| /** Return whether the target platform is x32. */ |
| bool PlatformIsx32() const; |
| |
| /** Apple SDK Type */ |
| enum class AppleSDK |
| { |
| MacOS, |
| IPhoneOS, |
| IPhoneSimulator, |
| AppleTVOS, |
| AppleTVSimulator, |
| WatchOS, |
| WatchSimulator, |
| XROS, |
| XRSimulator, |
| }; |
| |
| /** What SDK type points CMAKE_OSX_SYSROOT to? */ |
| AppleSDK GetAppleSDKType() const; |
| |
| /** Return whether the target platform is Apple iOS. */ |
| bool PlatformIsAppleEmbedded() const; |
| |
| /** Return whether the target platform is an Apple simulator. */ |
| bool PlatformIsAppleSimulator() const; |
| |
| /** Return whether the target platform supports generation of text base stubs |
| (.tbd file) describing exports (Apple specific). */ |
| bool PlatformSupportsAppleTextStubs() const; |
| |
| /** Retrieve soname flag for the specified language if supported */ |
| const char* GetSONameFlag(const std::string& language) const; |
| |
| /** |
| * Get a list of preprocessor define flags. |
| */ |
| std::string GetDefineFlags() const { return this->DefineFlags; } |
| |
| /** |
| * Make sure CMake can write this file |
| */ |
| bool CanIWriteThisFile(std::string const& fileName) const; |
| |
| #if !defined(CMAKE_BOOTSTRAP) |
| /** |
| * Get the vector source groups. |
| */ |
| const std::vector<cmSourceGroup>& GetSourceGroups() const |
| { |
| return this->SourceGroups; |
| } |
| |
| /** |
| * Get the source group |
| */ |
| cmSourceGroup* GetSourceGroup(const std::vector<std::string>& name) const; |
| |
| /** |
| * Add a root source group for consideration when adding a new source. |
| */ |
| void AddSourceGroup(const std::string& name, const char* regex = nullptr); |
| |
| /** |
| * Add a source group for consideration when adding a new source. |
| * name is tokenized. |
| */ |
| void AddSourceGroup(const std::vector<std::string>& name, |
| const char* regex = nullptr); |
| |
| /** |
| * Get and existing or create a new source group. |
| */ |
| cmSourceGroup* GetOrCreateSourceGroup( |
| const std::vector<std::string>& folders); |
| |
| /** |
| * Get and existing or create a new source group. |
| * The name will be tokenized. |
| */ |
| cmSourceGroup* GetOrCreateSourceGroup(const std::string& name); |
| |
| /** |
| * find what source group this source is in |
| */ |
| cmSourceGroup* FindSourceGroup(const std::string& source, |
| std::vector<cmSourceGroup>& groups) const; |
| #endif |
| |
| /** |
| * Get the vector of list files on which this makefile depends |
| */ |
| const std::vector<std::string>& GetListFiles() const |
| { |
| return this->ListFiles; |
| } |
| //! When the file changes cmake will be re-run from the build system. |
| void AddCMakeDependFile(const std::string& file) |
| { |
| this->ListFiles.push_back(file); |
| } |
| void AddCMakeDependFilesFromUser(); |
| |
| std::string FormatListFileStack() const; |
| |
| /** |
| * Get the current context backtrace. |
| */ |
| cmListFileBacktrace GetBacktrace() const; |
| |
| /** |
| * Get the vector of files created by this makefile |
| */ |
| const std::vector<std::string>& GetOutputFiles() const |
| { |
| return this->OutputFiles; |
| } |
| void AddCMakeOutputFile(const std::string& file) |
| { |
| this->OutputFiles.push_back(file); |
| } |
| |
| /** |
| * Expand all defined variables in the string. |
| * Defined variables come from the this->Definitions map. |
| * They are expanded with ${var} where var is the |
| * entry in the this->Definitions map. Also \@var\@ is |
| * expanded to match autoconf style expansions. |
| */ |
| const std::string& ExpandVariablesInString(std::string& source) const; |
| const std::string& ExpandVariablesInString( |
| std::string& source, bool escapeQuotes, bool noEscapes, |
| bool atOnly = false, const char* filename = nullptr, long line = -1, |
| bool removeEmpty = false, bool replaceAt = false) const; |
| |
| /** |
| * Remove any remaining variables in the string. Anything with ${var} or |
| * \@var\@ will be removed. |
| */ |
| void RemoveVariablesInString(std::string& source, bool atOnly = false) const; |
| |
| /** |
| * Expand variables in the makefiles ivars such as link directories etc |
| */ |
| void ExpandVariablesCMP0019(); |
| |
| /** |
| * Replace variables and #cmakedefine lines in the given string. |
| * See cmConfigureFileCommand for details. |
| */ |
| void ConfigureString(const std::string& input, std::string& output, |
| bool atOnly, bool escapeQuotes) const; |
| |
| /** |
| * Copy file but change lines according to ConfigureString |
| */ |
| int ConfigureFile(const std::string& infile, const std::string& outfile, |
| bool copyonly, bool atOnly, bool escapeQuotes, |
| mode_t permissions = 0, cmNewLineStyle = cmNewLineStyle()); |
| |
| enum class CommandMissingFromStack |
| { |
| No, |
| Yes, |
| }; |
| |
| /** |
| * Print a command's invocation |
| */ |
| void PrintCommandTrace( |
| cmListFileFunction const& lff, cmListFileBacktrace const& bt, |
| CommandMissingFromStack missing = CommandMissingFromStack::No) const; |
| |
| /** |
| * Set a callback that is invoked whenever ExecuteCommand is called. |
| */ |
| void OnExecuteCommand(std::function<void()> callback); |
| |
| /** |
| * Execute a single CMake command. Returns true if the command |
| * succeeded or false if it failed. |
| */ |
| bool ExecuteCommand(const cmListFileFunction& lff, cmExecutionStatus& status, |
| cm::optional<std::string> deferId = {}); |
| |
| //! Enable support for named language, if nil then all languages are |
| /// enabled. |
| void EnableLanguage(std::vector<std::string> const& languages, |
| bool optional); |
| |
| cmState* GetState() const; |
| |
| /** |
| * Get the variable watch. This is used to determine when certain variables |
| * are accessed. |
| */ |
| #ifndef CMAKE_BOOTSTRAP |
| cmVariableWatch* GetVariableWatch() const; |
| #endif |
| |
| //! Display progress or status message. |
| void DisplayStatus(const std::string&, float) const; |
| |
| /** |
| * Expand the given list file arguments into the full set after |
| * variable replacement and list expansion. |
| */ |
| bool ExpandArguments(std::vector<cmListFileArgument> const& inArgs, |
| std::vector<std::string>& outArgs) const; |
| bool ExpandArguments(std::vector<cmListFileArgument> const& inArgs, |
| std::vector<cmExpandedCommandArgument>& outArgs) const; |
| |
| /** |
| * Get the instance |
| */ |
| cmake* GetCMakeInstance() const; |
| cmMessenger* GetMessenger() const; |
| cmGlobalGenerator* GetGlobalGenerator() const; |
| |
| /** |
| * Get all the source files this makefile knows about |
| */ |
| const std::vector<std::unique_ptr<cmSourceFile>>& GetSourceFiles() const |
| { |
| return this->SourceFiles; |
| } |
| |
| std::vector<cmTarget*> const& GetOrderedTargets() const |
| { |
| return this->OrderedTargets; |
| } |
| |
| //! Add a new cmTest to the list of tests for this makefile. |
| cmTest* CreateTest(const std::string& testName); |
| |
| /** Get a cmTest pointer for a given test name, if the name is |
| * not found, then a null pointer is returned. |
| */ |
| cmTest* GetTest(const std::string& testName) const; |
| |
| /** |
| * Get all tests that run under the given configuration. |
| */ |
| void GetTests(const std::string& config, std::vector<cmTest*>& tests) const; |
| |
| /** |
| * Return a location of a file in cmake or custom modules directory |
| */ |
| std::string GetModulesFile(const std::string& name) const |
| { |
| bool system; |
| std::string debugBuffer; |
| return this->GetModulesFile(name, system, false, debugBuffer); |
| } |
| |
| /** |
| * Return a location of a file in cmake or custom modules directory |
| */ |
| std::string GetModulesFile(const std::string& name, bool& system) const |
| { |
| std::string debugBuffer; |
| return this->GetModulesFile(name, system, false, debugBuffer); |
| } |
| |
| std::string GetModulesFile(const std::string& name, bool& system, bool debug, |
| std::string& debugBuffer) const; |
| |
| //! Set/Get a property of this directory |
| void SetProperty(const std::string& prop, cmValue value); |
| void SetProperty(const std::string& prop, std::nullptr_t) |
| { |
| this->SetProperty(prop, cmValue{ nullptr }); |
| } |
| void SetProperty(const std::string& prop, const std::string& value) |
| { |
| this->SetProperty(prop, cmValue(value)); |
| } |
| void AppendProperty(const std::string& prop, const std::string& value, |
| bool asString = false); |
| cmValue GetProperty(const std::string& prop) const; |
| cmValue GetProperty(const std::string& prop, bool chain) const; |
| bool GetPropertyAsBool(const std::string& prop) const; |
| std::vector<std::string> GetPropertyKeys() const; |
| |
| //! Initialize a makefile from its parent |
| void InitializeFromParent(cmMakefile* parent); |
| |
| void AddInstallGenerator(std::unique_ptr<cmInstallGenerator> g); |
| |
| std::vector<std::unique_ptr<cmInstallGenerator>>& GetInstallGenerators() |
| { |
| return this->InstallGenerators; |
| } |
| const std::vector<std::unique_ptr<cmInstallGenerator>>& |
| GetInstallGenerators() const |
| { |
| return this->InstallGenerators; |
| } |
| |
| void AddTestGenerator(std::unique_ptr<cmTestGenerator> g); |
| |
| const std::vector<std::unique_ptr<cmTestGenerator>>& GetTestGenerators() |
| const |
| { |
| return this->TestGenerators; |
| } |
| |
| class FunctionPushPop |
| { |
| public: |
| FunctionPushPop(cmMakefile* mf, std::string const& fileName, |
| cmPolicies::PolicyMap const& pm); |
| ~FunctionPushPop(); |
| |
| FunctionPushPop(const FunctionPushPop&) = delete; |
| FunctionPushPop& operator=(const FunctionPushPop&) = delete; |
| |
| void Quiet() { this->ReportError = false; } |
| |
| private: |
| cmMakefile* Makefile; |
| bool ReportError = true; |
| }; |
| |
| class MacroPushPop |
| { |
| public: |
| MacroPushPop(cmMakefile* mf, std::string const& fileName, |
| cmPolicies::PolicyMap const& pm); |
| ~MacroPushPop(); |
| |
| MacroPushPop(const MacroPushPop&) = delete; |
| MacroPushPop& operator=(const MacroPushPop&) = delete; |
| |
| void Quiet() { this->ReportError = false; } |
| |
| private: |
| cmMakefile* Makefile; |
| bool ReportError = true; |
| }; |
| |
| void PushFunctionScope(std::string const& fileName, |
| cmPolicies::PolicyMap const& pm); |
| void PopFunctionScope(bool reportError); |
| void PushMacroScope(std::string const& fileName, |
| cmPolicies::PolicyMap const& pm); |
| void PopMacroScope(bool reportError); |
| void PushScope(); |
| void PopScope(); |
| void RaiseScope(const std::string& var, const char* value); |
| void RaiseScope(const std::string& var, cmValue value) |
| { |
| this->RaiseScope(var, value.GetCStr()); |
| } |
| void RaiseScope(const std::vector<std::string>& variables); |
| |
| // push and pop loop scopes |
| void PushLoopBlockBarrier(); |
| void PopLoopBlockBarrier(); |
| |
| bool IsImportedTargetGlobalScope() const; |
| |
| enum class ImportedTargetScope |
| { |
| Local, |
| Global, |
| }; |
| |
| /** Helper class to manage whether imported packages |
| * should be globally scoped based off the find package command |
| */ |
| class SetGlobalTargetImportScope |
| { |
| public: |
| SetGlobalTargetImportScope(cmMakefile* mk, ImportedTargetScope const scope) |
| : Makefile(mk) |
| { |
| if (scope == ImportedTargetScope::Global && |
| !this->Makefile->IsImportedTargetGlobalScope()) { |
| this->Makefile->CurrentImportedTargetScope = scope; |
| this->Set = true; |
| } else { |
| this->Set = false; |
| } |
| } |
| ~SetGlobalTargetImportScope() |
| { |
| if (this->Set) { |
| this->Makefile->CurrentImportedTargetScope = |
| ImportedTargetScope::Local; |
| } |
| } |
| |
| private: |
| cmMakefile* Makefile; |
| bool Set; |
| }; |
| |
| /** Helper class to push and pop scopes automatically. */ |
| class ScopePushPop |
| { |
| public: |
| ScopePushPop(cmMakefile* m) |
| : Makefile(m) |
| { |
| this->Makefile->PushScope(); |
| } |
| |
| ~ScopePushPop() { this->Makefile->PopScope(); } |
| |
| ScopePushPop(ScopePushPop const&) = delete; |
| ScopePushPop& operator=(ScopePushPop const&) = delete; |
| |
| private: |
| cmMakefile* Makefile; |
| }; |
| |
| void IssueMessage(MessageType t, std::string const& text) const; |
| Message::LogLevel GetCurrentLogLevel() const; |
| |
| /** Set whether or not to report a CMP0000 violation. */ |
| void SetCheckCMP0000(bool b) { this->CheckCMP0000 = b; } |
| |
| bool CheckCMP0037(std::string const& targetName, |
| cmStateEnums::TargetType targetType) const; |
| |
| cmBTStringRange GetIncludeDirectoriesEntries() const; |
| cmBTStringRange GetCompileOptionsEntries() const; |
| cmBTStringRange GetCompileDefinitionsEntries() const; |
| cmBTStringRange GetLinkOptionsEntries() const; |
| cmBTStringRange GetLinkDirectoriesEntries() const; |
| |
| std::set<std::string> const& GetSystemIncludeDirectories() const |
| { |
| return this->SystemIncludeDirectories; |
| } |
| |
| bool PolicyOptionalWarningEnabled(std::string const& var) const; |
| |
| void PushLoopBlock(); |
| void PopLoopBlock(); |
| bool IsLoopBlock() const; |
| |
| void ClearMatches(); |
| void StoreMatches(cmsys::RegularExpression& re); |
| |
| cmStateSnapshot GetStateSnapshot() const; |
| |
| const char* GetDefineFlagsCMP0059() const; |
| |
| void EnforceDirectoryLevelRules() const; |
| |
| void AddEvaluationFile( |
| const std::string& inputFile, const std::string& targetName, |
| std::unique_ptr<cmCompiledGeneratorExpression> outputName, |
| std::unique_ptr<cmCompiledGeneratorExpression> condition, |
| const std::string& newLineCharacter, mode_t permissions, |
| bool inputIsContent); |
| const std::vector<std::unique_ptr<cmGeneratorExpressionEvaluationFile>>& |
| GetEvaluationFiles() const; |
| |
| std::vector<std::unique_ptr<cmExportBuildFileGenerator>> const& |
| GetExportBuildFileGenerators() const; |
| void RemoveExportBuildFileGeneratorCMP0024(cmExportBuildFileGenerator* gen); |
| void AddExportBuildFileGenerator( |
| std::unique_ptr<cmExportBuildFileGenerator> gen); |
| |
| // Maintain a stack of package roots to allow nested PACKAGE_ROOT_PATH |
| // searches |
| std::deque<std::vector<std::string>> FindPackageRootPathStack; |
| |
| class DebugFindPkgRAII |
| { |
| cmMakefile* Makefile; |
| bool OldValue; |
| |
| public: |
| DebugFindPkgRAII(cmMakefile* mf, std::string const& pkg); |
| ~DebugFindPkgRAII(); |
| }; |
| |
| bool GetDebugFindPkgMode() const; |
| |
| void MaybeWarnCMP0074(std::string const& rootVar, cmValue rootDef, |
| cm::optional<std::string> const& rootEnv); |
| void MaybeWarnCMP0144(std::string const& rootVAR, cmValue rootDEF, |
| cm::optional<std::string> const& rootENV); |
| void MaybeWarnUninitialized(std::string const& variable, |
| const char* sourceFilename) const; |
| bool IsProjectFile(const char* filename) const; |
| |
| size_t GetRecursionDepthLimit() const; |
| |
| size_t GetRecursionDepth() const; |
| void SetRecursionDepth(size_t recursionDepth); |
| |
| std::string NewDeferId() const; |
| bool DeferCall(std::string id, std::string fileName, cmListFileFunction lff); |
| bool DeferCancelCall(std::string const& id); |
| cm::optional<std::string> DeferGetCallIds() const; |
| cm::optional<std::string> DeferGetCall(std::string const& id) const; |
| |
| protected: |
| // add link libraries and directories to the target |
| void AddGlobalLinkInformation(cmTarget& target); |
| |
| mutable std::set<cmListFileContext> CMP0054ReportedIds; |
| |
| // libraries, classes, and executables |
| mutable cmTargetMap Targets; |
| std::map<std::string, std::string> AliasTargets; |
| |
| std::vector<cmTarget*> OrderedTargets; |
| |
| std::vector<std::unique_ptr<cmSourceFile>> SourceFiles; |
| |
| // Because cmSourceFile names are compared in a fuzzy way (see |
| // cmSourceFileLocation::Match()) we can't have a straight mapping from |
| // filename to cmSourceFile. To make lookups more efficient we store the |
| // Name portion of the cmSourceFileLocation and then compare on the list of |
| // cmSourceFiles that might match that name. Note that on platforms which |
| // have a case-insensitive filesystem we store the key in all lowercase. |
| using SourceFileMap = |
| std::unordered_map<std::string, std::vector<cmSourceFile*>>; |
| SourceFileMap SourceFileSearchIndex; |
| |
| // For "Known" paths we can store a direct filename to cmSourceFile map |
| std::unordered_map<std::string, cmSourceFile*> KnownFileSearchIndex; |
| |
| // Tests |
| std::map<std::string, std::unique_ptr<cmTest>> Tests; |
| |
| // The set of include directories that are marked as system include |
| // directories. |
| std::set<std::string> SystemIncludeDirectories; |
| |
| std::vector<std::string> ListFiles; |
| std::vector<std::string> OutputFiles; |
| |
| std::vector<std::unique_ptr<cmInstallGenerator>> InstallGenerators; |
| std::vector<std::unique_ptr<cmTestGenerator>> TestGenerators; |
| |
| std::string ComplainFileRegularExpression; |
| std::string DefineFlags; |
| |
| // Track the value of the computed DEFINITIONS property. |
| std::string DefineFlagsOrig; |
| |
| #if !defined(CMAKE_BOOTSTRAP) |
| std::vector<cmSourceGroup> SourceGroups; |
| size_t ObjectLibrariesSourceGroupIndex; |
| #endif |
| |
| cmGlobalGenerator* GlobalGenerator; |
| bool IsFunctionBlocked(const cmListFileFunction& lff, |
| cmExecutionStatus& status); |
| |
| private: |
| cmStateSnapshot StateSnapshot; |
| cmListFileBacktrace Backtrace; |
| size_t RecursionDepth = 0; |
| |
| struct DeferCommand |
| { |
| // Id is empty for an already-executed or canceled operation. |
| std::string Id; |
| std::string FilePath; |
| cmListFileFunction Command; |
| }; |
| struct DeferCommands |
| { |
| std::vector<DeferCommand> Commands; |
| }; |
| std::unique_ptr<DeferCommands> Defer; |
| bool DeferRunning = false; |
| |
| void DoGenerate(cmLocalGenerator& lg); |
| |
| void RunListFile(cmListFile const& listFile, |
| const std::string& filenametoread, |
| DeferCommands* defer = nullptr); |
| |
| bool ParseDefineFlag(std::string const& definition, bool remove); |
| |
| bool EnforceUniqueDir(const std::string& srcPath, |
| const std::string& binPath) const; |
| |
| std::function<void()> ExecuteCommandCallback; |
| using FunctionBlockerPtr = std::unique_ptr<cmFunctionBlocker>; |
| using FunctionBlockersType = |
| std::stack<FunctionBlockerPtr, std::vector<FunctionBlockerPtr>>; |
| FunctionBlockersType FunctionBlockers; |
| std::vector<FunctionBlockersType::size_type> FunctionBlockerBarriers; |
| void PushFunctionBlockerBarrier(); |
| void PopFunctionBlockerBarrier(bool reportError = true); |
| |
| std::stack<int> LoopBlockCounter; |
| |
| mutable cmsys::RegularExpression cmDefineRegex; |
| mutable cmsys::RegularExpression cmDefine01Regex; |
| mutable cmsys::RegularExpression cmAtVarRegex; |
| mutable cmsys::RegularExpression cmNamedCurly; |
| |
| std::vector<cmMakefile*> UnConfiguredDirectories; |
| std::vector<std::unique_ptr<cmExportBuildFileGenerator>> |
| ExportBuildFileGenerators; |
| |
| std::vector<std::unique_ptr<cmGeneratorExpressionEvaluationFile>> |
| EvaluationFiles; |
| |
| std::vector<cmExecutionStatus*> ExecutionStatusStack; |
| friend class cmMakefileCall; |
| friend class cmParseFileScope; |
| |
| std::vector<std::unique_ptr<cmTarget>> ImportedTargetsOwned; |
| using TargetMap = std::unordered_map<std::string, cmTarget*>; |
| TargetMap ImportedTargets; |
| |
| // Internal policy stack management. |
| void PushPolicy(bool weak = false, |
| cmPolicies::PolicyMap const& pm = cmPolicies::PolicyMap()); |
| void PopPolicy(); |
| void PopSnapshot(bool reportError = true); |
| friend bool cmCMakePolicyCommand(std::vector<std::string> const& args, |
| cmExecutionStatus& status); |
| class IncludeScope; |
| friend class IncludeScope; |
| |
| class ListFileScope; |
| friend class ListFileScope; |
| |
| class DeferScope; |
| friend class DeferScope; |
| |
| class DeferCallScope; |
| friend class DeferCallScope; |
| |
| class BuildsystemFileScope; |
| friend class BuildsystemFileScope; |
| |
| // CMP0053 == old |
| MessageType ExpandVariablesInStringOld(std::string& errorstr, |
| std::string& source, |
| bool escapeQuotes, bool noEscapes, |
| bool atOnly, const char* filename, |
| long line, bool removeEmpty, |
| bool replaceAt) const; |
| // CMP0053 == new |
| MessageType ExpandVariablesInStringNew(std::string& errorstr, |
| std::string& source, |
| bool escapeQuotes, bool noEscapes, |
| bool atOnly, const char* filename, |
| long line, bool replaceAt) const; |
| |
| bool ValidateCustomCommand(const cmCustomCommandLines& commandLines) const; |
| |
| void CreateGeneratedOutputs(const std::vector<std::string>& outputs); |
| |
| std::vector<BT<GeneratorAction>> GeneratorActions; |
| bool GeneratorActionsInvoked = false; |
| |
| bool DebugFindPkg = false; |
| |
| bool CheckSystemVars; |
| bool CheckCMP0000; |
| std::set<std::string> WarnedCMP0074; |
| std::set<std::string> WarnedCMP0144; |
| bool IsSourceFileTryCompile; |
| mutable bool SuppressSideEffects; |
| ImportedTargetScope CurrentImportedTargetScope = ImportedTargetScope::Local; |
| }; |