| /* Distributed under the OSI-approved BSD 3-Clause License. See accompanying | |
| file LICENSE.rst or https://cmake.org/licensing for details. */ | |
| #pragma once | |
| #include "cmConfigure.h" // IWYU pragma: keep | |
| #include <iosfwd> | |
| #include <map> | |
| #include <memory> | |
| #include <set> | |
| #include <string> | |
| #include <vector> | |
| #include <cm/optional> | |
| #include <cm/string_view> | |
| #include "cmDocumentationEntry.h" | |
| #include "cmGlobalGenerator.h" | |
| #include "cmTransformDepfile.h" | |
| #include "cmValue.h" | |
| #include "cmXCodeObject.h" | |
| class cmCustomCommand; | |
| class cmCustomCommandGenerator; | |
| class cmGeneratorTarget; | |
| class cmGlobalGeneratorFactory; | |
| class cmLocalGenerator; | |
| class cmMakefile; | |
| class cmSourceFile; | |
| class cmSourceGroup; | |
| class cmake; | |
| /** \class cmGlobalXCodeGenerator | |
| * \brief Write a Unix makefiles. | |
| * | |
| * cmGlobalXCodeGenerator manages Xcode build process for a tree | |
| */ | |
| class cmGlobalXCodeGenerator : public cmGlobalGenerator | |
| { | |
| public: | |
| cmGlobalXCodeGenerator(cmake* cm, std::string const& version_string, | |
| unsigned int version_number); | |
| static std::unique_ptr<cmGlobalGeneratorFactory> NewFactory(); | |
| cmGlobalXCodeGenerator(cmGlobalXCodeGenerator const&) = delete; | |
| cmGlobalXCodeGenerator const& operator=(cmGlobalXCodeGenerator const&) = | |
| delete; | |
| //! Get the name for the generator. | |
| std::string GetName() const override | |
| { | |
| return cmGlobalXCodeGenerator::GetActualName(); | |
| } | |
| static std::string GetActualName() { return "Xcode"; } | |
| /** Get the documentation entry for this generator. */ | |
| static cmDocumentationEntry GetDocumentation(); | |
| //! Create a local generator appropriate to this Global Generator | |
| std::unique_ptr<cmLocalGenerator> CreateLocalGenerator( | |
| cmMakefile* mf) override; | |
| /** | |
| * Try to determine system information such as shared library | |
| * extension, pthreads, byte order etc. | |
| */ | |
| void EnableLanguage(std::vector<std::string> const& languages, cmMakefile*, | |
| bool optional) override; | |
| /** | |
| * Open a generated IDE project given the following information. | |
| */ | |
| bool Open(std::string const& bindir, std::string const& projectName, | |
| bool dryRun) override; | |
| /** | |
| * Try running cmake and building a file. This is used for dynalically | |
| * loaded commands, not as part of the usual build process. | |
| */ | |
| std::vector<GeneratedMakeCommand> GenerateBuildCommand( | |
| std::string const& makeProgram, std::string const& projectName, | |
| std::string const& projectDir, std::vector<std::string> const& targetNames, | |
| std::string const& config, int jobs, bool verbose, | |
| cmBuildOptions buildOptions = cmBuildOptions(), | |
| std::vector<std::string> const& makeOptions = std::vector<std::string>(), | |
| BuildTryCompile isInTryCompile = BuildTryCompile::No) override; | |
| /** Append the subdirectory for the given configuration. */ | |
| void AppendDirectoryForConfig(std::string const& prefix, | |
| std::string const& config, | |
| std::string const& suffix, | |
| std::string& dir) override; | |
| bool FindMakeProgram(cmMakefile*) override; | |
| //! What is the configurations directory variable called? | |
| char const* GetCMakeCFGIntDir() const override; | |
| //! expand CFGIntDir | |
| std::string ExpandCFGIntDir(std::string const& str, | |
| std::string const& config) const override; | |
| void SetCurrentLocalGenerator(cmLocalGenerator*); | |
| /** Return true if the generated build tree may contain multiple builds. | |
| i.e. "Can I build Debug and Release in the same tree?" */ | |
| bool IsMultiConfig() const override; | |
| bool IsXcode() const override { return true; } | |
| bool HasKnownObjectFileLocation(cmTarget const&, | |
| std::string* reason) const override; | |
| bool IsIPOSupported() const override { return true; } | |
| bool UseEffectivePlatformName(cmMakefile* mf) const override; | |
| bool ShouldStripResourcePath(cmMakefile*) const override; | |
| bool SupportsCustomObjectNames() const override { return false; } | |
| /** | |
| * Used to determine if this generator supports DEPFILE option. | |
| */ | |
| bool SupportsCustomCommandDepfile() const override { return true; } | |
| cm::optional<cmDepfileFormat> DepfileFormat() const override | |
| { | |
| return this->XcodeBuildSystem == BuildSystem::One | |
| ? cmDepfileFormat::MakeDepfile | |
| : cmDepfileFormat::GccDepfile; | |
| } | |
| bool SetSystemName(std::string const& s, cmMakefile* mf) override; | |
| bool SetGeneratorToolset(std::string const& ts, bool build, | |
| cmMakefile* mf) override; | |
| void AppendFlag(std::string& flags, std::string const& flag) const; | |
| cmValue GetDebuggerWorkingDirectory(cmGeneratorTarget* gt) const override; | |
| enum class BuildSystem | |
| { | |
| One = 1, | |
| Twelve = 12, | |
| }; | |
| protected: | |
| std::string GetTestBuildDependencyPath( | |
| cmGeneratorTarget const* target, std::string const& config) const override; | |
| void AddExtraIDETargets() override; | |
| void Generate() override; | |
| private: | |
| enum EmbedActionFlags | |
| { | |
| NoActionOnCopyByDefault = 0, | |
| CodeSignOnCopyByDefault = 1, | |
| RemoveHeadersOnCopyByDefault = 2, | |
| }; | |
| bool ParseGeneratorToolset(std::string const& ts, cmMakefile* mf); | |
| bool ProcessGeneratorToolsetField(std::string const& key, | |
| std::string const& value, cmMakefile* mf); | |
| bool ParseKnownAttributes(cm::string_view attribute, | |
| cm::string_view attributeValue); | |
| cmXCodeObject* CreateOrGetPBXGroup(cmGeneratorTarget* gtgt, | |
| cmSourceGroup const* sg); | |
| cmXCodeObject* CreatePBXGroup(cmXCodeObject* parent, | |
| std::string const& name); | |
| bool CreateGroups(std::vector<cmLocalGenerator*>& generators); | |
| std::string XCodeEscapePath(std::string const& p); | |
| std::string RelativeToSource(std::string const& p); | |
| std::string RelativeToRootBinary(std::string const& p); | |
| std::string RelativeToBinary(std::string const& p); | |
| void CreateCustomCommands( | |
| cmXCodeObject* buildPhases, cmXCodeObject* sourceBuildPhase, | |
| cmXCodeObject* headerBuildPhase, cmXCodeObject* resourceBuildPhase, | |
| std::vector<cmXCodeObject*> const& contentBuildPhases, | |
| cmXCodeObject* frameworkBuildPhase, cmGeneratorTarget* gtgt); | |
| std::string ComputeInfoPListLocation(cmGeneratorTarget* target); | |
| void AddCommandsToBuildPhase(cmXCodeObject* buildphase, | |
| cmGeneratorTarget* target, | |
| std::vector<cmCustomCommand> const& commands, | |
| char const* commandFileName); | |
| void CreateCustomRulesMakefile(char const* makefileBasename, | |
| cmGeneratorTarget* target, | |
| std::vector<cmCustomCommand> const& commands, | |
| std::string const& configName); | |
| cmXCodeObject* FindXCodeTarget(cmGeneratorTarget const*); | |
| std::string GetObjectId(cmXCodeObject::PBXType ptype, cm::string_view key); | |
| std::string GetOrCreateId(std::string const& name, std::string const& id); | |
| // create cmXCodeObject from these functions so that memory can be managed | |
| // correctly. All objects created are stored in this->XCodeObjects. | |
| cmXCodeObject* CreateObject(cmXCodeObject::PBXType ptype, | |
| cm::string_view key = {}); | |
| cmXCodeObject* CreateObject(cmXCodeObject::Type type); | |
| cmXCodeObject* CreateString(cm::string_view s); | |
| cmXCodeObject* CreateObjectReference(cmXCodeObject*); | |
| cmXCodeObject* CreateFlatClone(cmXCodeObject*); | |
| cmXCodeObject* CreateXCodeTarget(cmGeneratorTarget* gtgt, | |
| cmXCodeObject* buildPhases); | |
| void ForceLinkerLanguages() override; | |
| void ForceLinkerLanguage(cmGeneratorTarget* gtgt); | |
| char const* GetTargetLinkFlagsVar(cmGeneratorTarget const* target) const; | |
| char const* GetTargetFileType(cmGeneratorTarget* target); | |
| cm::string_view GetTargetProductType(cmGeneratorTarget* target); | |
| std::string AddConfigurations(cmXCodeObject* target, | |
| cmGeneratorTarget* gtgt); | |
| void AppendOrAddBuildSetting(cmXCodeObject* settings, char const* attr, | |
| cmXCodeObject* value); | |
| void AppendBuildSettingAttribute(cmXCodeObject* settings, | |
| char const* attribute, cmXCodeObject* attr, | |
| cmXCodeObject* value); | |
| void AppendBuildSettingAttribute(cmXCodeObject* target, char const* attr, | |
| cmXCodeObject* value, | |
| std::string const& configName); | |
| void InheritBuildSettingAttribute(cmXCodeObject* target, | |
| char const* attribute); | |
| cmXCodeObject* CreateUtilityTarget(cmGeneratorTarget* gtgt); | |
| void AddDependAndLinkInformation(cmXCodeObject* target); | |
| void AddEmbeddedObjects(cmXCodeObject* target, | |
| std::string const& copyFilesBuildPhaseName, | |
| std::string const& embedPropertyName, | |
| std::string const& dstSubfolderSpec, | |
| int actionsOnByDefault, | |
| std::string const& defaultDstPath = ""); | |
| void AddEmbeddedFrameworks(cmXCodeObject* target); | |
| void AddEmbeddedPlugIns(cmXCodeObject* target); | |
| void AddEmbeddedAppExtensions(cmXCodeObject* target); | |
| void AddEmbeddedExtensionKitExtensions(cmXCodeObject* target); | |
| void AddEmbeddedResources(cmXCodeObject* target); | |
| void AddEmbeddedXPCServices(cmXCodeObject* target); | |
| void AddPositionIndependentLinkAttribute(cmGeneratorTarget* target, | |
| cmXCodeObject* buildSettings, | |
| std::string const& configName); | |
| void CreateGlobalXCConfigSettings(cmLocalGenerator* root, | |
| cmXCodeObject* config, | |
| std::string const& configName); | |
| void CreateTargetXCConfigSettings(cmGeneratorTarget* target, | |
| cmXCodeObject* config, | |
| std::string const& configName); | |
| void CreateBuildSettings(cmGeneratorTarget* gtgt, | |
| cmXCodeObject* buildSettings, | |
| std::string const& buildType); | |
| std::string ExtractFlag(char const* flag, std::string& flags); | |
| std::string ExtractFlagRegex(char const* exp, int matchIndex, | |
| std::string& flags); | |
| void FilterConfigurationAttribute(std::string const& configName, | |
| std::string& attribute); | |
| void SortXCodeObjects(); | |
| // delete all objects in the this->XCodeObjects vector. | |
| void ClearXCodeObjects(); | |
| bool CreateXCodeObjects(cmLocalGenerator* root, | |
| std::vector<cmLocalGenerator*>& generators); | |
| void OutputXCodeProject(cmLocalGenerator* root, | |
| std::vector<cmLocalGenerator*>& generators); | |
| // Write shared scheme files for all the native targets | |
| // return true if any were written | |
| bool OutputXCodeSharedSchemes(std::string const& xcProjDir, | |
| cmLocalGenerator* root); | |
| void OutputXCodeWorkspaceSettings(std::string const& xcProjDir, | |
| bool hasGeneratedSchemes); | |
| void WriteXCodePBXProj(std::ostream& fout, cmLocalGenerator* root, | |
| std::vector<cmLocalGenerator*>& generators); | |
| cmXCodeObject* CreateXCodeFileReferenceFromPath(std::string const& fullpath, | |
| cmGeneratorTarget* target, | |
| std::string const& lang, | |
| cmSourceFile* sf); | |
| cmXCodeObject* CreateXCodeBuildFileFromPath(std::string const& fullpath, | |
| cmGeneratorTarget* target, | |
| std::string const& lang, | |
| cmSourceFile* sf); | |
| cmXCodeObject* CreateXCodeFileReference(cmSourceFile* sf, | |
| cmGeneratorTarget* target); | |
| cmXCodeObject* CreateXCodeSourceFile(cmLocalGenerator* gen, cmSourceFile* sf, | |
| cmGeneratorTarget* gtgt); | |
| bool TargetHasPrefixHeader(cmGeneratorTarget* gtgt); | |
| void AddXCodeProjBuildRule(cmGeneratorTarget* target, | |
| std::vector<cmSourceFile*>& sources) const; | |
| bool CreateXCodeTargets(cmLocalGenerator* gen, std::vector<cmXCodeObject*>&); | |
| bool CreateXCodeTarget(cmGeneratorTarget* gtgt, | |
| std::vector<cmXCodeObject*>&); | |
| bool IsHeaderFile(cmSourceFile*); | |
| void AddDependTarget(cmXCodeObject* target, cmXCodeObject* dependTarget); | |
| void CreateXCodeDependHackMakefile(std::vector<cmXCodeObject*>& targets); | |
| bool SpecialTargetEmitted(std::string const& tname); | |
| void SetGenerationRoot(cmLocalGenerator* root); | |
| void AddExtraTargets(cmLocalGenerator* root, | |
| std::vector<cmLocalGenerator*>& gens); | |
| cmXCodeObject* CreateLegacyRunScriptBuildPhase( | |
| char const* name, char const* name2, cmGeneratorTarget* target, | |
| std::vector<cmCustomCommand> const&); | |
| void CreateRunScriptBuildPhases(cmXCodeObject* buildPhases, | |
| cmGeneratorTarget const* gt); | |
| void CreateRunScriptBuildPhases(cmXCodeObject* buildPhases, | |
| cmSourceFile const* sf, | |
| cmGeneratorTarget const* gt, | |
| std::set<cmSourceFile const*>& visited); | |
| cmXCodeObject* CreateRunScriptBuildPhase(cmSourceFile const* sf, | |
| cmGeneratorTarget const* gt, | |
| cmCustomCommand const& cc); | |
| cmXCodeObject* CreateRunScriptBuildPhase( | |
| std::string const& name, cmGeneratorTarget const* gt, | |
| std::vector<cmCustomCommand> const& commands, | |
| std::vector<std::string> const& depends = {}); | |
| std::string ConstructScript(cmCustomCommandGenerator const& ccg); | |
| void CreateReRunCMakeFile(cmLocalGenerator* root, | |
| std::vector<cmLocalGenerator*> const& gens); | |
| std::string LookupFlags(std::string const& varNamePrefix, | |
| std::string const& varNameLang, | |
| std::string const& varNameSuffix, | |
| cmGeneratorTarget const* gt); | |
| class Factory; | |
| class BuildObjectListOrString; | |
| friend class BuildObjectListOrString; | |
| void AppendDefines(BuildObjectListOrString& defs, char const* defines_list, | |
| bool dflag = false); | |
| void AppendDefines(BuildObjectListOrString& defs, | |
| std::vector<std::string> const& defines, | |
| bool dflag = false); | |
| void ComputeTargetObjectDirectory(cmGeneratorTarget* gt) const override; | |
| protected: | |
| char const* GetInstallTargetName() const override { return "install"; } | |
| char const* GetPackageTargetName() const override { return "package"; } | |
| unsigned int XcodeVersion; | |
| std::string VersionString; | |
| std::set<std::string> XCodeObjectIDs; | |
| std::vector<std::unique_ptr<cmXCodeObject>> XCodeObjects; | |
| cmXCodeObject* RootObject; | |
| BuildSystem XcodeBuildSystem = BuildSystem::One; | |
| private: | |
| std::string GetAppleSpecificPlatformName(); | |
| std::string const& GetXcodeBuildCommand(); | |
| std::string FindXcodeBuildCommand(); | |
| std::string XcodeBuildCommand; | |
| bool XcodeBuildCommandInitialized; | |
| void PrintCompilerAdvice(std::ostream&, std::string const&, | |
| cmValue) const override | |
| { | |
| } | |
| std::string GetLibraryOrFrameworkPath(std::string const& path) const; | |
| std::string GetSymrootDir() const; | |
| std::string GetTargetTempDir(cmGeneratorTarget const* gt, | |
| std::string const& configName) const; | |
| static std::string GetDeploymentPlatform(cmMakefile const* mf); | |
| void ComputeArchitectures(cmMakefile* mf); | |
| void ComputeObjectDirArch(cmMakefile* mf); | |
| void addObject(std::unique_ptr<cmXCodeObject> obj); | |
| std::string PostBuildMakeTarget(std::string const& tName, | |
| std::string const& configName); | |
| cmXCodeObject* MainGroupChildren; | |
| cmXCodeObject* FrameworkGroup; | |
| cmXCodeObject* ResourcesGroup; | |
| cmMakefile* CurrentMakefile; | |
| cmLocalGenerator* CurrentLocalGenerator; | |
| cmLocalGenerator* CurrentRootGenerator = nullptr; | |
| std::vector<std::string> CurrentConfigurationTypes; | |
| std::string CurrentReRunCMakeMakefile; | |
| std::string CurrentXCodeHackMakefile; | |
| std::string CurrentProject; | |
| std::set<std::string> TargetDoneSet; | |
| std::map<std::string, cmXCodeObject*> GroupMap; | |
| std::map<std::string, cmXCodeObject*> GroupNameMap; | |
| std::map<std::string, cmXCodeObject*> TargetGroup; | |
| std::map<std::string, cmXCodeObject*> FileRefs; | |
| std::map<std::string, cmXCodeObject*> ExternalLibRefs; | |
| std::map<cmGeneratorTarget const*, cmXCodeObject*> XCodeObjectMap; | |
| std::map<cmXCodeObject*, cmXCodeObject*> FileRefToBuildFileMap; | |
| std::vector<std::string> Architectures; | |
| std::string ObjectDirArchDefault; | |
| std::string ObjectDirArch; | |
| std::string SystemName; | |
| std::string GeneratorToolset; | |
| std::vector<std::string> EnabledLangs; | |
| std::map<cmGeneratorTarget const*, std::set<cmSourceFile const*>> | |
| CommandsVisited; | |
| std::map<cmSourceFile const*, std::set<cmGeneratorTarget const*>> | |
| CustomCommandRoots; | |
| std::map<cmGeneratorTarget const*, bool> TargetPrefixHeaderMap; | |
| }; |