Exemple #1
0
        /// <summary>
        /// Discover and fill in the project info
        /// </summary>
        public static void FillProjectInfo()
        {
            DateTime StartTime = DateTime.Now;

            List <DirectoryReference> DirectoriesToSearch = new List <DirectoryReference>();

            // Find all the .uprojectdirs files contained in the root folder and add their entries to the search array
            string EngineSourceDirectory = Path.GetFullPath(Path.Combine(RootDirectory, "Engine", "Source"));

            foreach (FileReference ProjectDirsFile in DirectoryReference.EnumerateFiles(UnrealBuildTool.RootDirectory, "*.uprojectdirs", SearchOption.TopDirectoryOnly))
            {
                Log.TraceVerbose("\tFound uprojectdirs file {0}", ProjectDirsFile.FullName);
                foreach (string Line in File.ReadAllLines(ProjectDirsFile.FullName))
                {
                    string TrimLine = Line.Trim();
                    if (!TrimLine.StartsWith(";"))
                    {
                        DirectoryReference BaseProjectDir = DirectoryReference.Combine(UnrealBuildTool.RootDirectory, TrimLine);
                        if (BaseProjectDir.IsUnderDirectory(UnrealBuildTool.RootDirectory))
                        {
                            DirectoriesToSearch.Add(BaseProjectDir);
                        }
                        else
                        {
                            Log.TraceWarning("Project search path '{0}' is not under root directory, ignoring.", TrimLine);
                        }
                    }
                }
            }

            Log.TraceVerbose("\tFound {0} directories to search", DirectoriesToSearch.Count);

            foreach (DirectoryReference DirToSearch in DirectoriesToSearch)
            {
                Log.TraceVerbose("\t\tSearching {0}", DirToSearch.FullName);
                if (DirectoryReference.Exists(DirToSearch))
                {
                    foreach (DirectoryReference SubDir in DirectoryReference.EnumerateDirectories(DirToSearch, "*", SearchOption.TopDirectoryOnly))
                    {
                        Log.TraceVerbose("\t\t\tFound subdir {0}", SubDir.FullName);
                        foreach (FileReference UProjFile in DirectoryReference.EnumerateFiles(SubDir, "*.uproject", SearchOption.TopDirectoryOnly))
                        {
                            Log.TraceVerbose("\t\t\t\t{0}", UProjFile.FullName);
                            AddProject(UProjFile);
                        }
                    }
                }
                else
                {
                    Log.TraceVerbose("ProjectInfo: Skipping directory {0} from .uprojectdirs file as it doesn't exist.", DirToSearch);
                }
            }

            DateTime StopTime = DateTime.Now;

            if (UnrealBuildTool.bPrintPerformanceInfo)
            {
                TimeSpan TotalProjectInfoTime = StopTime - StartTime;
                Log.TraceInformation("FillProjectInfo took {0} milliseconds", TotalProjectInfoTime.TotalMilliseconds);
            }
        }
Exemple #2
0
        /// <summary>
        /// Sets the Visual C++ INCLUDE environment variable
        /// </summary>
        static List <string> GetVisualCppIncludePaths(WindowsCompiler Compiler, DirectoryReference VisualCppDir, DirectoryReference VisualCppToolchainDir, string UniversalCRTDir, string UniversalCRTVersion, string NetFXSDKDir, string WindowsSDKDir, string WindowsSDKLibVersion)
        {
            List <string> IncludePaths = new List <string>();

            // Add the standard Visual C++ include paths
            if (Compiler == WindowsCompiler.VisualStudio2017)
            {
                DirectoryReference StdIncludeDir = DirectoryReference.Combine(VisualCppToolchainDir, "INCLUDE");
                if (DirectoryReference.Exists(StdIncludeDir))
                {
                    IncludePaths.Add(StdIncludeDir.FullName);
                }
                DirectoryReference AtlMfcIncludeDir = DirectoryReference.Combine(VisualCppToolchainDir, "ATLMFC", "INCLUDE");
                if (DirectoryReference.Exists(AtlMfcIncludeDir))
                {
                    IncludePaths.Add(AtlMfcIncludeDir.FullName);
                }
            }
            else
            {
                DirectoryReference StdIncludeDir = DirectoryReference.Combine(VisualCppDir, "INCLUDE");
                if (DirectoryReference.Exists(StdIncludeDir))
                {
                    IncludePaths.Add(StdIncludeDir.FullName);
                }
                DirectoryReference AtlMfcIncludeDir = DirectoryReference.Combine(VisualCppDir, "ATLMFC", "INCLUDE");
                if (DirectoryReference.Exists(AtlMfcIncludeDir))
                {
                    IncludePaths.Add(AtlMfcIncludeDir.FullName);
                }
            }

            // Add the universal CRT paths
            if (!String.IsNullOrEmpty(UniversalCRTDir) && !String.IsNullOrEmpty(UniversalCRTVersion))
            {
                IncludePaths.Add(Path.Combine(UniversalCRTDir, "include", UniversalCRTVersion, "ucrt"));
            }

            // Add the NETFXSDK include path
            if (!String.IsNullOrEmpty(NetFXSDKDir))
            {
                IncludePaths.Add(Path.Combine(NetFXSDKDir, "include", "um"));                 // 2015
            }

            // Add the Windows SDK paths
            if (Compiler >= WindowsCompiler.VisualStudio2015 && WindowsPlatform.bUseWindowsSDK10)
            {
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", WindowsSDKLibVersion, "shared"));
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", WindowsSDKLibVersion, "um"));
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", WindowsSDKLibVersion, "winrt"));
            }
            else
            {
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", "shared"));
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", "um"));
                IncludePaths.Add(Path.Combine(WindowsSDKDir, "include", "winrt"));
            }

            // Add the existing include paths
            string ExistingIncludePaths = Environment.GetEnvironmentVariable("INCLUDE");

            if (ExistingIncludePaths != null)
            {
                IncludePaths.AddRange(ExistingIncludePaths.Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries));
            }

            // Set the environment variable
            return(IncludePaths);
        }
Exemple #3
0
        /// <summary>
        /// Sets the Visual C++ LIB environment variable
        /// </summary>
        static List <string> GetVisualCppLibraryPaths(WindowsCompiler Compiler, DirectoryReference VisualCppDir, DirectoryReference VisualCppToolchainDir, string UniversalCRTDir, string UniversalCRTVersion, string NetFXSDKDir, string WindowsSDKDir, string WindowsSDKLibVersion, CppPlatform Platform)
        {
            List <string> LibraryPaths = new List <string>();

            // Add the standard Visual C++ library paths
            if (Compiler == WindowsCompiler.VisualStudio2017)
            {
                if (Platform == CppPlatform.Win32)
                {
                    DirectoryReference StdLibraryDir = DirectoryReference.Combine(VisualCppToolchainDir, "lib", "x86");
                    if (DirectoryReference.Exists(StdLibraryDir))
                    {
                        LibraryPaths.Add(StdLibraryDir.FullName);
                    }
                }
                else
                {
                    DirectoryReference StdLibraryDir = DirectoryReference.Combine(VisualCppToolchainDir, "lib", "x64");
                    if (DirectoryReference.Exists(StdLibraryDir))
                    {
                        LibraryPaths.Add(StdLibraryDir.FullName);
                    }
                }
            }
            else
            {
                if (Platform == CppPlatform.Win32)
                {
                    DirectoryReference StdLibraryDir = DirectoryReference.Combine(VisualCppDir, "LIB");
                    if (DirectoryReference.Exists(StdLibraryDir))
                    {
                        LibraryPaths.Add(StdLibraryDir.FullName);
                    }
                    DirectoryReference AtlMfcLibraryDir = DirectoryReference.Combine(VisualCppDir, "ATLMFC", "LIB");
                    if (DirectoryReference.Exists(AtlMfcLibraryDir))
                    {
                        LibraryPaths.Add(AtlMfcLibraryDir.FullName);
                    }
                }
                else
                {
                    DirectoryReference StdLibraryDir = DirectoryReference.Combine(VisualCppDir, "LIB", "amd64");
                    if (DirectoryReference.Exists(StdLibraryDir))
                    {
                        LibraryPaths.Add(StdLibraryDir.FullName);
                    }
                    DirectoryReference AtlMfcLibraryDir = DirectoryReference.Combine(VisualCppDir, "ATLMFC", "LIB", "amd64");
                    if (DirectoryReference.Exists(AtlMfcLibraryDir))
                    {
                        LibraryPaths.Add(AtlMfcLibraryDir.FullName);
                    }
                }
            }

            // Add the Universal CRT
            if (!String.IsNullOrEmpty(UniversalCRTDir) && !String.IsNullOrEmpty(UniversalCRTVersion))
            {
                if (Platform == CppPlatform.Win32)
                {
                    LibraryPaths.Add(Path.Combine(UniversalCRTDir, "lib", UniversalCRTVersion, "ucrt", "x86"));
                }
                else
                {
                    LibraryPaths.Add(Path.Combine(UniversalCRTDir, "lib", UniversalCRTVersion, "ucrt", "x64"));
                }
            }

            // Add the NETFXSDK include path
            if (!String.IsNullOrEmpty(NetFXSDKDir))
            {
                if (Platform == CppPlatform.Win32)
                {
                    LibraryPaths.Add(Path.Combine(NetFXSDKDir, "lib", "um", "x86"));
                }
                else
                {
                    LibraryPaths.Add(Path.Combine(NetFXSDKDir, "lib", "um", "x64"));
                }
            }

            // Add the standard Windows SDK paths
            if (Platform == CppPlatform.Win32)
            {
                LibraryPaths.Add(Path.Combine(WindowsSDKDir, "lib", WindowsSDKLibVersion, "um", "x86"));
            }
            else
            {
                LibraryPaths.Add(Path.Combine(WindowsSDKDir, "lib", WindowsSDKLibVersion, "um", "x64"));
            }

            // Add the existing library paths
            string ExistingLibraryPaths = Environment.GetEnvironmentVariable("LIB");

            if (ExistingLibraryPaths != null)
            {
                LibraryPaths.AddRange(ExistingLibraryPaths.Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries));
            }

            return(LibraryPaths);
        }
        /// <summary>
        ///
        /// </summary>
        /// <param name="RulesFileType"></param>
        /// <param name="GameFolders"></param>
        /// <param name="ForeignPlugins"></param>
        /// <param name="AdditionalSearchPaths"></param>
        /// <param name="bIncludeEngine"></param>
        /// <param name="bIncludeEnterprise"></param>
        /// <returns></returns>
        public static List <FileReference> FindAllRulesSourceFiles(RulesFileType RulesFileType, List <DirectoryReference> GameFolders, List <FileReference> ForeignPlugins, List <DirectoryReference> AdditionalSearchPaths, bool bIncludeEngine = true, bool bIncludeEnterprise = true)
        {
            List <DirectoryReference> Folders = new List <DirectoryReference>();

            // Add all engine source (including third party source)
            if (bIncludeEngine)
            {
                Folders.Add(UnrealBuildTool.EngineSourceDirectory);
            }
            if (bIncludeEnterprise)
            {
                Folders.Add(UnrealBuildTool.EnterpriseSourceDirectory);
            }

            // @todo plugin: Disallow modules from including plugin modules as dependency modules? (except when the module is part of that plugin)

            // Get all the root folders for plugins
            List <DirectoryReference> RootFolders = new List <DirectoryReference>();

            if (bIncludeEngine)
            {
                RootFolders.Add(UnrealBuildTool.EngineDirectory);
            }
            if (bIncludeEnterprise)
            {
                RootFolders.Add(UnrealBuildTool.EnterpriseDirectory);
            }
            if (GameFolders != null)
            {
                RootFolders.AddRange(GameFolders);
            }

            // Find all the plugin source directories
            foreach (DirectoryReference RootFolder in RootFolders)
            {
                DirectoryReference PluginsFolder = DirectoryReference.Combine(RootFolder, "Plugins");
                foreach (FileReference PluginFile in Plugins.EnumeratePlugins(PluginsFolder))
                {
                    Folders.Add(DirectoryReference.Combine(PluginFile.Directory, "Source"));
                }
            }

            // Add all the extra plugin folders
            if (ForeignPlugins != null)
            {
                foreach (FileReference ForeignPlugin in ForeignPlugins)
                {
                    Folders.Add(DirectoryReference.Combine(ForeignPlugin.Directory, "Source"));
                }
            }

            // Add in the game folders to search
            if (GameFolders != null)
            {
                foreach (DirectoryReference GameFolder in GameFolders)
                {
                    DirectoryReference GameSourceFolder = DirectoryReference.Combine(GameFolder, "Source");
                    Folders.Add(GameSourceFolder);
                    DirectoryReference GameIntermediateSourceFolder = DirectoryReference.Combine(GameFolder, "Intermediate", "Source");
                    Folders.Add(GameIntermediateSourceFolder);
                }
            }

            // Process the additional search path, if sent in
            if (AdditionalSearchPaths != null)
            {
                foreach (DirectoryReference AdditionalSearchPath in AdditionalSearchPaths)
                {
                    if (AdditionalSearchPath != null)
                    {
                        if (DirectoryReference.Exists(AdditionalSearchPath))
                        {
                            Folders.Add(AdditionalSearchPath);
                        }
                        else
                        {
                            throw new BuildException("Couldn't find AdditionalSearchPath for rules source files '{0}'", AdditionalSearchPath);
                        }
                    }
                }
            }

            // Iterate over all the folders to check
            List <FileReference>    SourceFiles       = new List <FileReference>();
            HashSet <FileReference> UniqueSourceFiles = new HashSet <FileReference>();

            foreach (DirectoryReference Folder in Folders)
            {
                IReadOnlyList <FileReference> SourceFilesForFolder = FindAllRulesFiles(Folder, RulesFileType);
                foreach (FileReference SourceFile in SourceFilesForFolder)
                {
                    if (UniqueSourceFiles.Add(SourceFile))
                    {
                        SourceFiles.Add(SourceFile);
                    }
                }
            }
            return(SourceFiles);
        }
Exemple #5
0
        /// <summary>
        /// Checks if the editor is currently running and this is a hot-reload
        /// </summary>
        public static bool ShouldDoHotReloadFromIDE(BuildConfiguration BuildConfiguration, TargetDescriptor TargetDesc)
        {
            // Check if Hot-reload is disabled globally for this project
            ConfigHierarchy Hierarchy = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(TargetDesc.ProjectFile), TargetDesc.Platform);
            bool            bAllowHotReloadFromIDE;

            if (Hierarchy.TryGetValue("BuildConfiguration", "bAllowHotReloadFromIDE", out bAllowHotReloadFromIDE) && !bAllowHotReloadFromIDE)
            {
                return(false);
            }

            if (!BuildConfiguration.bAllowHotReloadFromIDE)
            {
                return(false);
            }

            // Check if we're using LiveCode instead
            ConfigHierarchy EditorPerProjectHierarchy = ConfigCache.ReadHierarchy(ConfigHierarchyType.EditorPerProjectUserSettings, DirectoryReference.FromFile(TargetDesc.ProjectFile), TargetDesc.Platform);
            bool            bEnableLiveCode;

            if (EditorPerProjectHierarchy.GetBool("/Script/LiveCoding.LiveCodingSettings", "bEnabled", out bEnableLiveCode) && bEnableLiveCode)
            {
                return(false);
            }

            bool bIsRunning = false;

            // @todo ubtmake: Kind of cheating here to figure out if an editor target.  At this point we don't have access to the actual target description, and
            // this code must be able to execute before we create or load module rules DLLs so that hot reload can work with bUseUBTMakefiles
            if (TargetDesc.Name.EndsWith("Editor", StringComparison.OrdinalIgnoreCase))
            {
                string EditorBaseFileName = "UE4Editor";
                if (TargetDesc.Configuration != UnrealTargetConfiguration.Development)
                {
                    EditorBaseFileName = String.Format("{0}-{1}-{2}", EditorBaseFileName, TargetDesc.Platform, TargetDesc.Configuration);
                }

                FileReference EditorLocation;
                if (TargetDesc.Platform == UnrealTargetPlatform.Win64)
                {
                    EditorLocation = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Binaries", "Win64", String.Format("{0}.exe", EditorBaseFileName));
                }
                else if (TargetDesc.Platform == UnrealTargetPlatform.Mac)
                {
                    EditorLocation = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Binaries", "Mac", String.Format("{0}.app/Contents/MacOS/{0}", EditorBaseFileName));
                }
                else if (TargetDesc.Platform == UnrealTargetPlatform.Linux)
                {
                    EditorLocation = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Binaries", "Linux", EditorBaseFileName);
                }
                else
                {
                    throw new BuildException("Unknown editor filename for this platform");
                }

                using (Timeline.ScopeEvent("Finding editor processes for hot-reload"))
                {
                    DirectoryReference EditorRunsDir = DirectoryReference.Combine(UnrealBuildTool.EngineDirectory, "Intermediate", "EditorRuns");
                    if (!DirectoryReference.Exists(EditorRunsDir))
                    {
                        return(false);
                    }

                    if (BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Win64)
                    {
                        foreach (FileReference EditorInstanceFile in DirectoryReference.EnumerateFiles(EditorRunsDir))
                        {
                            int ProcessId;
                            if (!Int32.TryParse(EditorInstanceFile.GetFileName(), out ProcessId))
                            {
                                FileReference.Delete(EditorInstanceFile);
                                continue;
                            }

                            Process RunningProcess;
                            try
                            {
                                RunningProcess = Process.GetProcessById(ProcessId);
                            }
                            catch
                            {
                                RunningProcess = null;
                            }

                            if (RunningProcess == null)
                            {
                                FileReference.Delete(EditorInstanceFile);
                                continue;
                            }

                            FileReference MainModuleFile;
                            try
                            {
                                MainModuleFile = new FileReference(RunningProcess.MainModule.FileName);
                            }
                            catch
                            {
                                MainModuleFile = null;
                            }

                            if (!bIsRunning && EditorLocation == MainModuleFile)
                            {
                                bIsRunning = true;
                            }
                        }
                    }
                    else
                    {
                        FileInfo[] EditorRunsFiles = new DirectoryInfo(EditorRunsDir.FullName).GetFiles();
                        BuildHostPlatform.ProcessInfo[] Processes = BuildHostPlatform.Current.GetProcesses();

                        foreach (FileInfo File in EditorRunsFiles)
                        {
                            int PID;
                            BuildHostPlatform.ProcessInfo Proc = null;
                            if (!Int32.TryParse(File.Name, out PID) || (Proc = Processes.FirstOrDefault(P => P.PID == PID)) == default(BuildHostPlatform.ProcessInfo))
                            {
                                // Delete stale files (it may happen if editor crashes).
                                File.Delete();
                                continue;
                            }

                            // Don't break here to allow clean-up of other stale files.
                            if (!bIsRunning)
                            {
                                // Otherwise check if the path matches.
                                bIsRunning = new FileReference(Proc.Filename) == EditorLocation;
                            }
                        }
                    }
                }
            }
            return(bIsRunning);
        }
Exemple #6
0
        public override bool ExecuteActions(List <Action> Actions, bool bLogDetailedActionStats)
        {
            if (Actions.Count == 0)
            {
                return(true);
            }

            // Clean the intermediate directory in case there are any leftovers from previous builds
            if (DirectoryReference.Exists(IntermediateDir))
            {
                DirectoryReference.Delete(IntermediateDir, true);
            }

            DirectoryReference.CreateDirectory(IntermediateDir);
            if (!DirectoryReference.Exists(IntermediateDir))
            {
                throw new BuildException($"Failed to create directory \"{IntermediateDir}\".");
            }

            // Build the json script file to describe all the actions and their dependencies
            var ActionIds = Actions.ToDictionary(a => a, a => Guid.NewGuid().ToString());

            File.WriteAllText(ScriptFile.FullName, Json.Serialize(new Dictionary <string, object>()
            {
                ["jobs"] = Actions.ToDictionary(a => ActionIds[a], a =>
                {
                    var Job = new Dictionary <string, object>()
                    {
                        ["title"]             = a.StatusDescription,
                        ["command"]           = $"\"{a.CommandPath}\" {a.CommandArguments}",
                        ["working_directory"] = a.WorkingDirectory.FullName,
                        ["dependencies"]      = a.PrerequisiteActions.Select(p => ActionIds[p]).ToArray(),
                        ["run_locally"]       = !(a.bCanExecuteRemotely && a.bCanExecuteRemotelyWithSNDBS)
                    };

                    if (a.PrerequisiteItems.Count > 0)
                    {
                        Job["explicit_input_files"] = a.PrerequisiteItems.Select(i => new Dictionary <string, object>()
                        {
                            ["filename"] = i.AbsolutePath
                        }).ToList();
                    }

                    if (EnableEcho)
                    {
                        var EchoString = string.Join(" ", string.IsNullOrWhiteSpace(a.CommandDescription) ? string.Empty : $"[{a.CommandDescription}]", a.StatusDescription);
                        if (!string.IsNullOrWhiteSpace(EchoString))
                        {
                            Job["echo"] = EchoString;
                        }
                    }

                    return(Job);
                })
            }));

            PrepareToolTemplates();
            bool bHasRewrites = GenerateSNDBSIncludeRewriteRules();

            var LocalProcess = new Process();

            LocalProcess.StartInfo           = new ProcessStartInfo(SNDBSExecutable, $"-q -p \"Unreal Engine Tasks\" -s \"{ScriptFile}\" -templates \"{IntermediateDir}\"{(bHasRewrites ? $" --include-rewrite-rules \"{IncludeRewriteRulesFile}\"" : "")}");
            LocalProcess.OutputDataReceived += (Sender, Args) => Log.TraceInformation("{0}", Args.Data);
            LocalProcess.ErrorDataReceived  += (Sender, Args) => Log.TraceInformation("{0}", Args.Data);
            return(Utils.RunLocalProcess(LocalProcess) == 0);
        }
Exemple #7
0
        /// <summary>
        /// Creates an environment with the given settings
        /// </summary>
        /// <param name="Compiler">The compiler version to use</param>
        /// <param name="Platform">The platform to target</param>
        /// <param name="Architecture">The Architecture to target</param>
        /// <param name="CompilerVersion">The specific toolchain version to use</param>
        /// <param name="WindowsSdkVersion">Version of the Windows SDK to use</param>
        /// <param name="SuppliedSdkDirectoryForVersion">If specified, this is the SDK directory to use, otherwise, attempt to look up via registry. If specified, the WindowsSdkVersion is used directly</param>
        /// <returns>New environment object with paths for the given settings</returns>
        public static VCEnvironment Create(WindowsCompiler Compiler, UnrealTargetPlatform Platform, WindowsArchitecture Architecture, string CompilerVersion, string WindowsSdkVersion, string SuppliedSdkDirectoryForVersion)
        {
            // Get the compiler version info
            VersionNumber      SelectedCompilerVersion;
            DirectoryReference SelectedCompilerDir;

            if (!WindowsPlatform.TryGetToolChainDir(Compiler, CompilerVersion, out SelectedCompilerVersion, out SelectedCompilerDir))
            {
                throw new BuildException("{0}{1} must be installed in order to build this target.", WindowsPlatform.GetCompilerName(Compiler), String.IsNullOrEmpty(CompilerVersion)? "" : String.Format(" ({0})", CompilerVersion));
            }

            // Get the toolchain info
            WindowsCompiler    ToolChain;
            VersionNumber      SelectedToolChainVersion;
            DirectoryReference SelectedToolChainDir;

            if (Compiler == WindowsCompiler.Clang || Compiler == WindowsCompiler.Intel)
            {
                if (WindowsPlatform.TryGetToolChainDir(WindowsCompiler.VisualStudio2019, null, out SelectedToolChainVersion, out SelectedToolChainDir))
                {
                    ToolChain = WindowsCompiler.VisualStudio2019;
                }
                else if (WindowsPlatform.TryGetToolChainDir(WindowsCompiler.VisualStudio2017, null, out SelectedToolChainVersion, out SelectedToolChainDir))
                {
                    ToolChain = WindowsCompiler.VisualStudio2017;
                }
                else
                {
                    throw new BuildException("{0} or {1} must be installed in order to build this target.", WindowsPlatform.GetCompilerName(WindowsCompiler.VisualStudio2019), WindowsPlatform.GetCompilerName(WindowsCompiler.VisualStudio2017));
                }
            }
            else
            {
                ToolChain = Compiler;
                SelectedToolChainVersion = SelectedCompilerVersion;
                SelectedToolChainDir     = SelectedCompilerDir;
            }

            // Get the actual Windows SDK directory
            VersionNumber      SelectedWindowsSdkVersion;
            DirectoryReference SelectedWindowsSdkDir;

            if (SuppliedSdkDirectoryForVersion != null)
            {
                SelectedWindowsSdkDir     = new DirectoryReference(SuppliedSdkDirectoryForVersion);
                SelectedWindowsSdkVersion = VersionNumber.Parse(WindowsSdkVersion);

                if (!DirectoryReference.Exists(SelectedWindowsSdkDir))
                {
                    throw new BuildException("Windows SDK{0} must be installed at {1}.", String.IsNullOrEmpty(WindowsSdkVersion) ? "" : String.Format(" ({0})", WindowsSdkVersion), SuppliedSdkDirectoryForVersion);
                }
            }
            else
            {
                if (!WindowsPlatform.TryGetWindowsSdkDir(WindowsSdkVersion, out SelectedWindowsSdkVersion, out SelectedWindowsSdkDir))
                {
                    throw new BuildException("Windows SDK{0} must be installed in order to build this target.", String.IsNullOrEmpty(WindowsSdkVersion) ? "" : String.Format(" ({0})", WindowsSdkVersion));
                }
            }

            return(new VCEnvironment(Platform, Compiler, SelectedCompilerDir, SelectedCompilerVersion, Architecture, ToolChain, SelectedToolChainDir, SelectedToolChainVersion, SelectedWindowsSdkDir, SelectedWindowsSdkVersion));
        }
Exemple #8
0
        /// <summary>
        /// Gets all build products produced by this binary
        /// </summary>
        /// <param name="Target">The target being built</param>
        /// <param name="ToolChain">The platform toolchain</param>
        /// <param name="BuildProducts">Mapping of produced build product to type</param>
        /// <param name="bCreateDebugInfo">Whether debug info is enabled for this binary</param>
        public void GetBuildProducts(ReadOnlyTargetRules Target, UEToolChain ToolChain, Dictionary <FileReference, BuildProductType> BuildProducts, bool bCreateDebugInfo)
        {
            // Add all the precompiled outputs
            foreach (UEBuildModuleCPP Module in Modules.OfType <UEBuildModuleCPP>())
            {
                if (Module.Rules.bPrecompile)
                {
                    if (Module.GeneratedCodeDirectory != null && DirectoryReference.Exists(Module.GeneratedCodeDirectory))
                    {
                        foreach (FileReference GeneratedCodeFile in DirectoryReference.EnumerateFiles(Module.GeneratedCodeDirectory))
                        {
                            // Exclude timestamp files, since they're always updated and cause collisions between builds
                            if (!GeneratedCodeFile.GetFileName().Equals("Timestamp", StringComparison.OrdinalIgnoreCase) && !GeneratedCodeFile.HasExtension(".cpp"))
                            {
                                BuildProducts.Add(GeneratedCodeFile, BuildProductType.BuildResource);
                            }
                        }
                    }
                    if (Target.LinkType == TargetLinkType.Monolithic)
                    {
                        FileReference PrecompiledManifestLocation = Module.PrecompiledManifestLocation;
                        BuildProducts.Add(PrecompiledManifestLocation, BuildProductType.BuildResource);

                        PrecompiledManifest ModuleManifest = PrecompiledManifest.Read(PrecompiledManifestLocation);
                        foreach (FileReference OutputFile in ModuleManifest.OutputFiles)
                        {
                            if (!BuildProducts.ContainsKey(OutputFile))
                            {
                                BuildProducts.Add(OutputFile, BuildProductType.BuildResource);
                            }
                        }
                    }
                }
            }

            // Add all the binary outputs
            if (!Target.bDisableLinking)
            {
                // Get the type of build products we're creating
                BuildProductType OutputType = BuildProductType.RequiredResource;
                switch (Type)
                {
                case UEBuildBinaryType.Executable:
                    OutputType = BuildProductType.Executable;
                    break;

                case UEBuildBinaryType.DynamicLinkLibrary:
                    OutputType = BuildProductType.DynamicLibrary;
                    break;

                case UEBuildBinaryType.StaticLibrary:
                    OutputType = BuildProductType.BuildResource;
                    break;
                }

                // Add the primary build products
                string[] DebugExtensions = UEBuildPlatform.GetBuildPlatform(Target.Platform).GetDebugInfoExtensions(Target, Type);
                foreach (FileReference OutputFilePath in OutputFilePaths)
                {
                    AddBuildProductAndDebugFiles(OutputFilePath, OutputType, DebugExtensions, BuildProducts, ToolChain, bCreateDebugInfo);
                }

                // Add the console app, if there is one
                if (Type == UEBuildBinaryType.Executable && bBuildAdditionalConsoleApp)
                {
                    foreach (FileReference OutputFilePath in OutputFilePaths)
                    {
                        AddBuildProductAndDebugFiles(GetAdditionalConsoleAppPath(OutputFilePath), OutputType, DebugExtensions, BuildProducts, ToolChain, bCreateDebugInfo);
                    }
                }

                // Add any additional build products from the modules in this binary, including additional bundle resources/dylibs on Mac.
                List <string> Libraries = new List <string>();
                List <UEBuildBundleResource> BundleResources = new List <UEBuildBundleResource>();
                GatherAdditionalResources(Libraries, BundleResources);

                // Add any extra files from the toolchain
                ToolChain.ModifyBuildProducts(Target, this, Libraries, BundleResources, BuildProducts);
            }
        }
Exemple #9
0
        /// <summary>
        /// Main entry point
        /// </summary>
        /// <param name="Arguments">Command-line arguments</param>
        /// <returns>One of the values of ECompilationResult</returns>
        public override int Execute(CommandLineArguments Arguments)
        {
            Arguments.ApplyTo(this);

            // Create the build configuration object, and read the settings
            BuildConfiguration BuildConfiguration = new BuildConfiguration();

            XmlConfig.ApplyTo(BuildConfiguration);
            Arguments.ApplyTo(BuildConfiguration);

            // Parse all the targets being built
            List <TargetDescriptor> TargetDescriptors = TargetDescriptor.ParseCommandLine(Arguments, BuildConfiguration.bUsePrecompiled, bSkipRulesCompile);

            if (TargetDescriptors.Count == 0)
            {
                throw new BuildException("No targets specified to clean");
            }

            // Also add implicit descriptors for cleaning UnrealBuildTool
            if (!BuildConfiguration.bDoNotBuildUHT)
            {
                const string UnrealHeaderToolTarget = "UnrealHeaderTool";

                // Get a list of project files to clean UHT for
                List <FileReference> ProjectFiles = new List <FileReference>();
                foreach (TargetDescriptor TargetDesc in TargetDescriptors)
                {
                    if (TargetDesc.Name != UnrealHeaderToolTarget && !RemoteMac.HandlesTargetPlatform(TargetDesc.Platform))
                    {
                        if (ProjectFiles.Count == 0)
                        {
                            ProjectFiles.Add(null);
                        }
                        if (TargetDesc.ProjectFile != null && !ProjectFiles.Contains(TargetDesc.ProjectFile))
                        {
                            ProjectFiles.Add(TargetDesc.ProjectFile);
                        }
                    }
                }

                // Add descriptors for cleaning UHT with all these projects
                if (ProjectFiles.Count > 0)
                {
                    UnrealTargetConfiguration Configuration = BuildConfiguration.bForceDebugUnrealHeaderTool ? UnrealTargetConfiguration.Debug : UnrealTargetConfiguration.Development;
                    string Architecture = UEBuildPlatform.GetBuildPlatform(BuildHostPlatform.Current.Platform).GetDefaultArchitecture(null);
                    foreach (FileReference ProjectFile in ProjectFiles)
                    {
                        TargetDescriptors.Add(new TargetDescriptor(ProjectFile, UnrealHeaderToolTarget, BuildHostPlatform.Current.Platform, Configuration, Architecture, null));
                    }
                }
            }

            // Output the list of targets that we're cleaning
            Log.TraceInformation("Cleaning {0} binaries...", StringUtils.FormatList(TargetDescriptors.Select(x => x.Name).Distinct()));

            // Loop through all the targets, and clean them all
            HashSet <FileReference>      FilesToDelete       = new HashSet <FileReference>();
            HashSet <DirectoryReference> DirectoriesToDelete = new HashSet <DirectoryReference>();

            foreach (TargetDescriptor TargetDescriptor in TargetDescriptors)
            {
                // Create the rules assembly
                RulesAssembly RulesAssembly = RulesCompiler.CreateTargetRulesAssembly(TargetDescriptor.ProjectFile, TargetDescriptor.Name, bSkipRulesCompile, BuildConfiguration.bUsePrecompiled, TargetDescriptor.ForeignPlugin);

                // Create the rules object
                ReadOnlyTargetRules Target = new ReadOnlyTargetRules(RulesAssembly.CreateTargetRules(TargetDescriptor.Name, TargetDescriptor.Platform, TargetDescriptor.Configuration, TargetDescriptor.Architecture, TargetDescriptor.ProjectFile, TargetDescriptor.AdditionalArguments));

                // Find the base folders that can contain binaries
                List <DirectoryReference> BaseDirs = new List <DirectoryReference>();
                BaseDirs.Add(UnrealBuildTool.EngineDirectory);
                BaseDirs.Add(UnrealBuildTool.EnterpriseDirectory);
                foreach (FileReference Plugin in Plugins.EnumeratePlugins(Target.ProjectFile))
                {
                    BaseDirs.Add(Plugin.Directory);
                }
                if (Target.ProjectFile != null)
                {
                    BaseDirs.Add(Target.ProjectFile.Directory);
                }

                // If we're running a precompiled build, remove anything under the engine folder
                BaseDirs.RemoveAll(x => RulesAssembly.IsReadOnly(x));

                // Get all the names which can prefix build products
                List <string> NamePrefixes = new List <string>();
                if (Target.Type != TargetType.Program)
                {
                    NamePrefixes.Add(UEBuildTarget.GetAppNameForTargetType(Target.Type));
                }
                NamePrefixes.Add(Target.Name);

                // Get the suffixes for this configuration
                List <string> NameSuffixes = new List <string>();
                if (Target.Configuration == Target.UndecoratedConfiguration)
                {
                    NameSuffixes.Add("");
                }
                NameSuffixes.Add(String.Format("-{0}-{1}", Target.Platform.ToString(), Target.Configuration.ToString()));
                if (!String.IsNullOrEmpty(Target.Architecture))
                {
                    NameSuffixes.AddRange(NameSuffixes.ToArray().Select(x => x + Target.Architecture));
                }

                // Add all the makefiles and caches to be deleted
                FilesToDelete.Add(TargetMakefile.GetLocation(Target.ProjectFile, Target.Name, Target.Platform, Target.Configuration));
                FilesToDelete.UnionWith(SourceFileMetadataCache.GetFilesToClean(Target.ProjectFile));
                FilesToDelete.UnionWith(ActionHistory.GetFilesToClean(Target.ProjectFile, Target.Name, Target.Platform, Target.Type, Target.Architecture));

                // Add all the intermediate folders to be deleted
                foreach (DirectoryReference BaseDir in BaseDirs)
                {
                    foreach (string NamePrefix in NamePrefixes)
                    {
                        DirectoryReference GeneratedCodeDir = DirectoryReference.Combine(BaseDir, "Intermediate", "Build", Target.Platform.ToString(), NamePrefix, "Inc");
                        if (DirectoryReference.Exists(GeneratedCodeDir))
                        {
                            DirectoriesToDelete.Add(GeneratedCodeDir);
                        }

                        DirectoryReference IntermediateDir = DirectoryReference.Combine(BaseDir, "Intermediate", "Build", Target.Platform.ToString(), NamePrefix, Target.Configuration.ToString());
                        if (DirectoryReference.Exists(IntermediateDir))
                        {
                            DirectoriesToDelete.Add(IntermediateDir);
                        }
                    }
                }

                // List of additional files and directories to clean, specified by the target platform
                List <FileReference>      AdditionalFilesToDelete       = new List <FileReference>();
                List <DirectoryReference> AdditionalDirectoriesToDelete = new List <DirectoryReference>();

                // Add all the build products from this target
                string[] NamePrefixesArray = NamePrefixes.Distinct().ToArray();
                string[] NameSuffixesArray = NameSuffixes.Distinct().ToArray();
                foreach (DirectoryReference BaseDir in BaseDirs)
                {
                    DirectoryReference BinariesDir = DirectoryReference.Combine(BaseDir, "Binaries", Target.Platform.ToString());
                    if (DirectoryReference.Exists(BinariesDir))
                    {
                        UEBuildPlatform.GetBuildPlatform(Target.Platform).FindBuildProductsToClean(BinariesDir, NamePrefixesArray, NameSuffixesArray, AdditionalFilesToDelete, AdditionalDirectoriesToDelete);
                    }
                }

                // Get all the additional intermediate folders created by this platform
                UEBuildPlatform.GetBuildPlatform(Target.Platform).FindAdditionalBuildProductsToClean(Target, AdditionalFilesToDelete, AdditionalDirectoriesToDelete);

                // Add the platform's files and directories to the main list
                FilesToDelete.UnionWith(AdditionalFilesToDelete);
                DirectoriesToDelete.UnionWith(AdditionalDirectoriesToDelete);
            }

            // Delete all the directories, then all the files. By sorting the list of directories before we delete them, we avoid spamming the log if a parent directory is deleted first.
            foreach (DirectoryReference DirectoryToDelete in DirectoriesToDelete.OrderBy(x => x.FullName))
            {
                if (DirectoryReference.Exists(DirectoryToDelete))
                {
                    Log.TraceVerbose("    Deleting {0}{1}...", DirectoryToDelete, Path.DirectorySeparatorChar);
                    try
                    {
                        DirectoryReference.Delete(DirectoryToDelete, true);
                    }
                    catch (Exception Ex)
                    {
                        throw new BuildException(Ex, "Unable to delete {0} ({1})", DirectoryToDelete, Ex.Message.TrimEnd());
                    }
                }
            }

            foreach (FileReference FileToDelete in FilesToDelete.OrderBy(x => x.FullName))
            {
                if (FileReference.Exists(FileToDelete))
                {
                    Log.TraceVerbose("    Deleting " + FileToDelete);
                    try
                    {
                        FileReference.Delete(FileToDelete);
                    }
                    catch (Exception Ex)
                    {
                        throw new BuildException(Ex, "Unable to delete {0} ({1})", FileToDelete, Ex.Message.TrimEnd());
                    }
                }
            }

            // Also clean all the remote targets
            for (int Idx = 0; Idx < TargetDescriptors.Count; Idx++)
            {
                TargetDescriptor TargetDescriptor = TargetDescriptors[Idx];
                if (RemoteMac.HandlesTargetPlatform(TargetDescriptor.Platform))
                {
                    RemoteMac RemoteMac = new RemoteMac(TargetDescriptor.ProjectFile);
                    RemoteMac.Clean(TargetDescriptor);
                }
            }

            return(0);
        }
        /// <summary>
        /// Creates a rules assembly with the given parameters.
        /// </summary>
        /// <param name="ProjectFileName">The project file to create rules for. Null for the engine.</param>
        /// <param name="bUsePrecompiled">Whether to use a precompiled engine</param>
        /// <param name="bSkipCompile">Whether to skip compilation for this assembly</param>
        /// <returns>New rules assembly</returns>
        public static RulesAssembly CreateProjectRulesAssembly(FileReference ProjectFileName, bool bUsePrecompiled, bool bSkipCompile)
        {
            // Check if there's an existing assembly for this project
            RulesAssembly ProjectRulesAssembly;

            if (!LoadedAssemblyMap.TryGetValue(ProjectFileName, out ProjectRulesAssembly))
            {
                ProjectDescriptor Project = ProjectDescriptor.FromFile(ProjectFileName);

                // Create the parent assembly
                RulesAssembly Parent;
                if (Project.IsEnterpriseProject)
                {
                    Parent = CreateEnterpriseRulesAssembly(bUsePrecompiled, bSkipCompile);
                }
                else
                {
                    Parent = CreateEngineRulesAssembly(bUsePrecompiled, bSkipCompile);
                }

                DirectoryReference MainProjectDirectory       = ProjectFileName.Directory;
                DirectoryReference MainProjectSourceDirectory = DirectoryReference.Combine(MainProjectDirectory, "Source");

                // Create a scope for things in this assembly
                RulesScope Scope = new RulesScope("Project", Parent.Scope);

                // Create a new context for modules created by this assembly
                ModuleRulesContext DefaultModuleContext = new ModuleRulesContext(Scope, MainProjectDirectory);
                DefaultModuleContext.bCanBuildDebugGame          = true;
                DefaultModuleContext.bCanHotReload               = true;
                DefaultModuleContext.bClassifyAsGameModuleForUHT = true;
                DefaultModuleContext.bCanUseForSharedPCH         = false;

                // gather modules from project and platforms
                Dictionary <FileReference, ModuleRulesContext> ModuleFiles = new Dictionary <FileReference, ModuleRulesContext>();
                List <FileReference> TargetFiles = new List <FileReference>();

                // Find all the rules/plugins under the project source directories
                foreach (DirectoryReference ProjectDirectory in UnrealBuildTool.GetAllProjectDirectories(ProjectFileName))
                {
                    DirectoryReference ProjectSourceDirectory = DirectoryReference.Combine(ProjectDirectory, "Source");

                    AddModuleRulesWithContext(ProjectSourceDirectory, DefaultModuleContext, ModuleFiles);
                    TargetFiles.AddRange(FindAllRulesFiles(ProjectSourceDirectory, RulesFileType.Target));
                }

                // Find all the project plugins
                List <PluginInfo> ProjectPlugins = new List <PluginInfo>();
                ProjectPlugins.AddRange(Plugins.ReadProjectPlugins(MainProjectDirectory));

                // Add the project's additional plugin directories plugins too
                if (Project.AdditionalPluginDirectories != null)
                {
                    foreach (string AdditionalPluginDirectory in Project.AdditionalPluginDirectories)
                    {
                        ProjectPlugins.AddRange(Plugins.ReadAdditionalPlugins(MainProjectDirectory, AdditionalPluginDirectory));
                    }
                }


                // Find all the plugin module rules
                FindModuleRulesForPlugins(ProjectPlugins, DefaultModuleContext, ModuleFiles);

                // Add the games project's intermediate source folder
                DirectoryReference ProjectIntermediateSourceDirectory = DirectoryReference.Combine(MainProjectDirectory, "Intermediate", "Source");
                if (DirectoryReference.Exists(ProjectIntermediateSourceDirectory))
                {
                    AddModuleRulesWithContext(ProjectIntermediateSourceDirectory, DefaultModuleContext, ModuleFiles);
                    TargetFiles.AddRange(FindAllRulesFiles(ProjectIntermediateSourceDirectory, RulesFileType.Target));
                }

                // Compile the assembly. If there are no module or target files, just use the parent assembly.
                FileReference AssemblyFileName = FileReference.Combine(MainProjectDirectory, "Intermediate", "Build", "BuildRules", ProjectFileName.GetFileNameWithoutExtension() + "ModuleRules" + FrameworkAssemblyExtension);
                if (ModuleFiles.Count == 0 && TargetFiles.Count == 0)
                {
                    ProjectRulesAssembly = Parent;
                }
                else
                {
                    ProjectRulesAssembly = new RulesAssembly(Scope, MainProjectDirectory, ProjectPlugins, ModuleFiles, TargetFiles, AssemblyFileName, bContainsEngineModules: false, DefaultBuildSettings: null, bReadOnly: UnrealBuildTool.IsProjectInstalled(), bSkipCompile: bSkipCompile, Parent: Parent);
                }
                LoadedAssemblyMap.Add(ProjectFileName, ProjectRulesAssembly);
            }
            return(ProjectRulesAssembly);
        }