public HTML5ToolChain(FileReference InProjectFile)
            : base(CppPlatform.HTML5)
        {
            if (!HTML5SDKInfo.IsSDKInstalled())
            {
                throw new BuildException("HTML5 SDK is not installed; cannot use toolchain.");
            }

            // ini configs
            // - normal ConfigCache w/ UnrealBuildTool.ProjectFile takes all game config ini files
            //   (including project config ini files)
            // - but, during packaging, if -remoteini is used -- need to use UnrealBuildTool.GetRemoteIniPath()
            //   (note: ConfigCache can take null ProjectFile)
            string             EngineIniPath = UnrealBuildTool.GetRemoteIniPath();
            DirectoryReference ProjectDir    = !String.IsNullOrEmpty(EngineIniPath) ? new DirectoryReference(EngineIniPath)
                                                                                                : DirectoryReference.FromFile(InProjectFile);
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, ProjectDir, UnrealTargetPlatform.HTML5);

//			Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableSIMD", out enableSIMD);
//			Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableMultithreading", out enableMultithreading);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableTracing", out bEnableTracing);

            // TODO: remove this "fix" when emscripten supports (SIMD & pthreads) + WASM
            enableSIMD = false;
            // TODO: double check Engine/Source/Runtime/Core/Private/HTML5/HTML5PlatformProcess.cpp::SupportsMultithreading()
            enableMultithreading = false;

            Log.TraceInformation("HTML5ToolChain: EnableSIMD = " + enableSIMD);
            Log.TraceInformation("HTML5ToolChain: EnableMultithreading " + enableMultithreading);
            Log.TraceInformation("HTML5ToolChain: EnableTracing = " + bEnableTracing);

            PrintOnce = new VerbosePrint(PrintOnceOn);             // reset
        }
Esempio n. 2
0
        /// <summary>
        /// Checks whether the list of dependencies is still valid
        /// </summary>
        /// <returns></returns>
        public bool IsValid()
        {
            foreach (KeyValuePair <ConfigDependencyKey, IReadOnlyList <string> > Pair in Dependencies)
            {
                // Read the appropriate hierarchy
                ConfigHierarchy Hierarchy = ConfigCache.ReadHierarchy(Pair.Key.Type, Pair.Key.ProjectDir, Pair.Key.Platform);

                // Get the value(s) associated with this key
                IReadOnlyList <string> NewValues;
                Hierarchy.TryGetValues(Pair.Key.SectionName, Pair.Key.KeyName, out NewValues);

                // Check if they're different
                if (Pair.Value == null)
                {
                    if (NewValues != null)
                    {
                        return(false);
                    }
                }
                else
                {
                    if (NewValues == null || !Enumerable.SequenceEqual(Pair.Value, NewValues, StringComparer.Ordinal))
                    {
                        return(false);
                    }
                }
            }
            return(true);
        }
        /// <summary>
        ///
        /// </summary>
        /// <param name="InDirectory"></param>
        /// <param name="InTargetPlatform"></param>
        /// <param name="OutRSAKeys"></param>
        /// <param name="OutAESKey"></param>
        public static void ParseEncryptionIni(DirectoryReference InDirectory, UnrealTargetPlatform InTargetPlatform, out String[] OutRSAKeys, out String OutAESKey)
        {
            OutAESKey  = String.Empty;
            OutRSAKeys = null;

            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Encryption, InDirectory, InTargetPlatform);

            bool bSigningEnabled;

            Ini.GetBool("Core.Encryption", "SignPak", out bSigningEnabled);

            if (bSigningEnabled)
            {
                OutRSAKeys = new string[3];
                Ini.GetString("Core.Encryption", "rsa.privateexp", out OutRSAKeys[0]);
                Ini.GetString("Core.Encryption", "rsa.modulus", out OutRSAKeys[1]);
                Ini.GetString("Core.Encryption", "rsa.publicexp", out OutRSAKeys[2]);

                if (String.IsNullOrEmpty(OutRSAKeys[0]) || String.IsNullOrEmpty(OutRSAKeys[1]) || String.IsNullOrEmpty(OutRSAKeys[2]))
                {
                    OutRSAKeys = null;
                }
            }

            bool bEncryptionEnabled;

            Ini.GetBool("Core.Encryption", "EncryptPak", out bEncryptionEnabled);

            if (bEncryptionEnabled)
            {
                Ini.GetString("Core.Encryption", "aes.key", out OutAESKey);
            }
        }
Esempio n. 4
0
        protected static bool DoProjectSettingsMatchDefault(UnrealTargetPlatform Platform, DirectoryReference ProjectDirectoryName, string Section, string[] BoolKeys, string[] IntKeys, string[] StringKeys)
        {
            ConfigHierarchy ProjIni    = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, ProjectDirectoryName, Platform);
            ConfigHierarchy DefaultIni = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, (DirectoryReference)null, Platform);

            // look at all bool values
            if (BoolKeys != null)
            {
                foreach (string Key in BoolKeys)
                {
                    bool Default = false, Project = false;
                    DefaultIni.GetBool(Section, Key, out Default);
                    ProjIni.GetBool(Section, Key, out Project);
                    if (Default != Project)
                    {
                        Log.TraceInformationOnce(Key + " is not set to default. (" + Default + " vs. " + Project + ")");
                        return(false);
                    }
                }
            }

            // look at all int values
            if (IntKeys != null)
            {
                foreach (string Key in IntKeys)
                {
                    int Default = 0, Project = 0;
                    DefaultIni.GetInt32(Section, Key, out Default);
                    ProjIni.GetInt32(Section, Key, out Project);
                    if (Default != Project)
                    {
                        Log.TraceInformationOnce(Key + " is not set to default. (" + Default + " vs. " + Project + ")");
                        return(false);
                    }
                }
            }

            // look for all string values
            if (StringKeys != null)
            {
                foreach (string Key in StringKeys)
                {
                    string Default = "", Project = "";
                    DefaultIni.GetString(Section, Key, out Default);
                    ProjIni.GetString(Section, Key, out Project);
                    if (Default != Project)
                    {
                        Log.TraceInformationOnce(Key + " is not set to default. (" + Default + " vs. " + Project + ")");
                        return(false);
                    }
                }
            }

            // if we get here, we match all important settings
            return(true);
        }
Esempio n. 5
0
 /// <summary>
 /// Protected constructor. Used by TVOSProjectSettings.
 /// </summary>
 /// <param name="ProjectFile">The project file to read settings for</param>
 /// <param name="Platform">The platform to read settings for</param>
 /// <param name="Bundle">Bundle identifier needed when project file is empty</param>
 protected IOSProjectSettings(FileReference ProjectFile, UnrealTargetPlatform Platform, string Bundle)
 {
     this.ProjectFile = ProjectFile;
     ConfigCache.ReadSettings(DirectoryReference.FromFile(ProjectFile), Platform, this);
     if ((ProjectFile == null || string.IsNullOrEmpty(ProjectFile.FullName)) && !string.IsNullOrEmpty(Bundle))
     {
         BundleIdentifier = Bundle;
     }
     BundleIdentifier = BundleIdentifier.Replace("[PROJECT_NAME]", ((ProjectFile != null) ? ProjectFile.GetFileNameWithoutAnyExtensions() : "UE4Game")).Replace("_", "");
 }
Esempio n. 6
0
        public HTML5ToolChain(FileReference InProjectFile)
            : base(CppPlatform.HTML5)
        {
            if (!HTML5SDKInfo.IsSDKInstalled())
            {
                throw new BuildException("HTML5 SDK is not installed; cannot use toolchain.");
            }

            // ini configs
            // - normal ConfigCache w/ UnrealBuildTool.ProjectFile takes all game config ini files
            //   (including project config ini files)
            // - but, during packaging, if -remoteini is used -- need to use UnrealBuildTool.GetRemoteIniPath()
            //   (note: ConfigCache can take null ProjectFile)
            string             EngineIniPath = UnrealBuildTool.GetRemoteIniPath();
            DirectoryReference ProjectDir    = !String.IsNullOrEmpty(EngineIniPath) ? new DirectoryReference(EngineIniPath)
                                                                                                : DirectoryReference.FromFile(InProjectFile);
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, ProjectDir, UnrealTargetPlatform.HTML5);

//			Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableSIMD", out enableSIMD);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableMultithreading", out enableMultithreading);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "OffscreenCanvas", out bMultithreading_UseOffscreenCanvas);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "LLVMWasmBackend", out useLLVMwasmBackend);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableTracing", out bEnableTracing);

            if (useLLVMwasmBackend)
            {
                libExt = ".a";                  // experimental - LLVMWasmBackend
            }

            // TODO: remove this "fix" when emscripten supports WASM with SIMD
            enableSIMD = false;

            Log.TraceInformation("HTML5ToolChain: EnableSIMD = " + enableSIMD);
            Log.TraceInformation("HTML5ToolChain: EnableMultithreading " + enableMultithreading);
            Log.TraceInformation("HTML5ToolChain: OffscreenCanvas " + bMultithreading_UseOffscreenCanvas);
            Log.TraceInformation("HTML5ToolChain: LLVMWasmBackend " + useLLVMwasmBackend);
            Log.TraceInformation("HTML5ToolChain: EnableTracing = " + bEnableTracing);

            PrintOnce = new VerbosePrint(PrintOnceOn);             // reset

            Log.TraceInformation("Setting Emscripten SDK: located in " + HTML5SDKInfo.EMSCRIPTEN_ROOT);
            string TempDir = HTML5SDKInfo.SetupEmscriptenTemp();

            HTML5SDKInfo.SetUpEmscriptenConfigFile();

            if (Environment.GetEnvironmentVariable("EMSDK") == null)             // If EMSDK is present, Emscripten is already configured by the developer
            {
                // If not using preset emsdk, configure our generated .emscripten config, instead of autogenerating one in the user's home directory.
                Environment.SetEnvironmentVariable("EM_CONFIG", HTML5SDKInfo.DOT_EMSCRIPTEN);
                Environment.SetEnvironmentVariable("EM_CACHE", HTML5SDKInfo.EMSCRIPTEN_CACHE);
                Environment.SetEnvironmentVariable("EMCC_TEMP_DIR", TempDir);
            }

            Log.TraceInformation("*** Emscripten Config File: " + Environment.GetEnvironmentVariable("EM_CONFIG"));
        }
Esempio n. 7
0
        public bool UseVulkan()
        {
            // @todo Lumin: Switch to Lumin once we have sub-platform ini
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(ProjectFile), UnrealTargetPlatform.Android);
            // go by string
            bool bUseVulkan = true;

            Ini.GetBool("/Script/LuminRuntimeSettings.LuminRuntimeSettings", "bUseVulkan", out bUseVulkan);

            return(bUseVulkan);
        }
Esempio n. 8
0
        public bool UseVulkan()
        {
            DirectoryReference DirRef = (!string.IsNullOrEmpty(UnrealBuildTool.GetRemoteIniPath()) ? new DirectoryReference(UnrealBuildTool.GetRemoteIniPath()) : (ProjectFile != null ? ProjectFile.Directory : null));
            ConfigHierarchy    Ini    = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirRef, UnrealTargetPlatform.Lumin);
            // go by string
            bool bUseVulkan = true;

            Ini.GetBool("/Script/LuminRuntimeSettings.LuminRuntimeSettings", "bUseVulkan", out bUseVulkan);

            return(bUseVulkan);
        }
        private InstalledPlatformInfo()
        {
            List <string>   InstalledPlatforms;
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, (DirectoryReference)null, UnrealTargetPlatform.Unknown);

            if (Ini.GetArray("InstalledPlatforms", "InstalledPlatformConfigurations", out InstalledPlatforms))
            {
                foreach (string InstalledPlatform in InstalledPlatforms)
                {
                    ParsePlatformConfiguration(InstalledPlatform);
                }
            }
        }
Esempio n. 10
0
        private string GetElfName(FileReference InNMakeOutputPath)
        {
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, InNMakeOutputPath.Directory.ParentDirectory.ParentDirectory, UnrealTargetPlatform.Lumin);
            bool            bUseMobileRendering = false;

            Ini.GetBool("/Script/LuminRuntimeSettings.LuminRuntimeSettings", "bUseMobileRendering", out bUseMobileRendering);
            bool bUseVulkan = false;

            Ini.GetBool("/Script/LuminRuntimeSettings.LuminRuntimeSettings", "bUseVulkan", out bUseVulkan);

            string OutputFileName = string.Format("{0}-arm64-{1}{2}", InNMakeOutputPath.GetFileNameWithoutExtension(), !(bUseMobileRendering || bUseVulkan) ? "lumingl4" : "lumin", InNMakeOutputPath.GetExtension());

            return(OutputFileName);
        }
        /// <summary>
        /// Find the default architecture for the given project
        /// </summary>
        public override string GetDefaultArchitecture(FileReference ProjectFile)
        {
            string ActiveArchitecture = DefaultArchitecture;

            // read settings from the config
            string EngineIniPath = ProjectFile != null ? ProjectFile.Directory.FullName : null;

            if (String.IsNullOrEmpty(EngineIniPath))
            {
                // If the project file hasn't been specified, try to get the path from -remoteini command line param
                EngineIniPath = UnrealBuildTool.GetRemoteIniPath();
            }
            DirectoryReference EngineIniDir = !String.IsNullOrEmpty(EngineIniPath) ? new DirectoryReference(EngineIniPath) : null;

            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, EngineIniDir, UnrealTargetPlatform.Linux);

            string LinuxArchitectureString;

            if (Ini.GetString("/Script/LinuxTargetPlatform.LinuxTargetSettings", "TargetArchitecture", out LinuxArchitectureString))
            {
                LinuxArchitecture Architecture;
                if (Enum.TryParse(LinuxArchitectureString, out Architecture))
                {
                    switch (Architecture)
                    {
                    default:
                        System.Console.WriteLine("Architecture enum value {0} does not map to a valid triplet.", Architecture);
                        break;

                    case LinuxArchitecture.X86_64UnknownLinuxGnu:
                        ActiveArchitecture = "x86_64-unknown-linux-gnu";
                        break;

                    case LinuxArchitecture.ArmUnknownLinuxGnueabihf:
                        ActiveArchitecture = "arm-unknown-linux-gnueabihf";
                        break;

                    case LinuxArchitecture.AArch64UnknownLinuxGnueabi:
                        ActiveArchitecture = "aarch64-unknown-linux-gnueabi";
                        break;

                    case LinuxArchitecture.I686UnknownLinuxGnu:
                        ActiveArchitecture = "i686-unknown-linux-gnu";
                        break;
                    }
                }
            }

            return(ActiveArchitecture);
        }
Esempio n. 12
0
        /// <summary>
        /// checks if the sdk is installed or has been synced, sets environment variable
        /// </summary>
        /// <returns></returns>
        protected override bool HasAnySDK()
        {
            string EnvVarKey = "MLSDK";
            string IniVarKey = "MLSDKPath";

            string MLSDKPath = Environment.GetEnvironmentVariable(EnvVarKey);

            {
                var configCacheIni = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, (DirectoryReference)null, UnrealTargetPlatform.Unknown);

                string path;
                if (GetPath(configCacheIni, "/Script/LuminPlatformEditor.MagicLeapSDKSettings", IniVarKey, out path) && !string.IsNullOrEmpty(path))
                {
                    // if the folder specified by the config var doesn't exist, fall back to the env var.
                    if (Directory.Exists(path))
                    {
                        MLSDKPath = path;
                    }
                }

                // Set for the process
                Environment.SetEnvironmentVariable(EnvVarKey, MLSDKPath);
            }

            // we don't have an MLSDK directory specified
            if (String.IsNullOrEmpty(MLSDKPath))
            {
                return(false);
            }
            // we don't have the required MLSDK setup
            String DetectedVersion = "Unknown";
            String VersionFile     = string.Format("{0}/include/ml_version.h", MLSDKPath).Replace('/', Path.DirectorySeparatorChar);

            if (File.Exists(VersionFile))
            {
                string[] VersionText = File.ReadAllLines(VersionFile);

                String MajorVersion = FindVersionNumber("MLSDK_VERSION_MAJOR", VersionText);
                String MinorVersion = FindVersionNumber("MLSDK_VERSION_MINOR", VersionText);
                DetectedVersion = string.Format("{0}.{1}", MajorVersion, MinorVersion);
            }
            if (!DetectedVersion.Equals(GetRequiredSDKString()))
            {
                Console.WriteLine("*** Found installed MLSDK version {0} but require {1} ***", DetectedVersion, GetRequiredSDKString());
                return(false);
            }

            return(true);
        }
        static bool bEnableTracing       = false;   // Debug option

        public HTML5ToolChain(FileReference InProjectFile)
            : base(CppPlatform.HTML5, WindowsCompiler.VisualStudio2015)
        {
            if (!HTML5SDKInfo.IsSDKInstalled())
            {
                throw new BuildException("HTML5 SDK is not installed; cannot use toolchain.");
            }

            // ini configs
            // - normal ConfigCache w/ UnrealBuildTool.ProjectFile takes all game config ini files
            //   (including project config ini files)
            // - but, during packaging, if -remoteini is used -- need to use UnrealBuildTool.GetRemoteIniPath()
            //   (note: ConfigCache can take null ProjectFile)
            string             EngineIniPath = UnrealBuildTool.GetRemoteIniPath();
            DirectoryReference ProjectDir    = !String.IsNullOrEmpty(EngineIniPath) ? new DirectoryReference(EngineIniPath)
                                                                                                : DirectoryReference.FromFile(InProjectFile);
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, ProjectDir, UnrealTargetPlatform.HTML5);

            // these will be going away...
            bool targetingAsmjs = false;           // inverted check
            bool targetWebGL1   = false;           // inverted check

            if (Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "TargetAsmjs", out targetingAsmjs))
            {
                targetingWasm = !targetingAsmjs;
            }
            if (Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "TargetWebGL1", out targetWebGL1))
            {
                targetWebGL2 = !targetWebGL1;
            }
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableSIMD", out enableSIMD);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableMultithreading", out enableMultithreading);
            Ini.GetBool("/Script/HTML5PlatformEditor.HTML5TargetSettings", "EnableTracing", out bEnableTracing);
            Log.TraceInformation("HTML5ToolChain: TargetWasm = " + targetingWasm);
            Log.TraceInformation("HTML5ToolChain: TargetWebGL2 = " + targetWebGL2);
            Log.TraceInformation("HTML5ToolChain: EnableSIMD = " + enableSIMD);
            Log.TraceInformation("HTML5ToolChain: EnableMultithreading " + enableMultithreading);
            Log.TraceInformation("HTML5ToolChain: EnableTracing = " + bEnableTracing);

            // TODO: remove this "fix" when emscripten supports (SIMD & pthreads) + WASM
            if (targetingWasm)
            {
                enableSIMD = false;

                // TODO: double check Engine/Source/Runtime/Core/Private/HTML5/HTML5PlatformProcess.cpp::SupportsMultithreading()
                enableMultithreading = false;
            }
        }
Esempio n. 14
0
        /// <summary>
        /// Setup the target environment for building
        /// </summary>
        /// <param name="InBuildTarget"> The target being built</param>
        public override void SetUpEnvironment(UEBuildTarget InBuildTarget)
        {
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("PLATFORM_IOS=1");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("PLATFORM_APPLE=1");

            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_TTS=0");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_SPEECH_RECOGNITION=0");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_DATABASE_SUPPORT=0");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_EDITOR=0");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("USE_NULL_RHI=0");
            InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("REQUIRES_ALIGNED_INT_ACCESS");

            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(ProjectFile), UnrealTargetPlatform.IOS);

            Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bEnableRemoteNotificationsSupport", out bNotificationsEnabled);
            if (bNotificationsEnabled)
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("NOTIFICATIONS_ENABLED=1");
            }
            else
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("NOTIFICATIONS_ENABLED=0");
            }

            if (GetActiveArchitecture() == "-simulator")
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_SIMULATOR=1");
            }
            else
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("WITH_SIMULATOR=0");
            }

            // we assume now we are building with IOS8 or later
            if (UEBuildConfiguration.bCompileAgainstEngine)
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("HAS_METAL=1");
                InBuildTarget.ExtraModuleNames.Add("MetalRHI");
            }
            else
            {
                InBuildTarget.GlobalCompileEnvironment.Config.Definitions.Add("HAS_METAL=0");
            }

            InBuildTarget.GlobalLinkEnvironment.Config.AdditionalFrameworks.Add(new UEBuildFramework("GameKit"));
            InBuildTarget.GlobalLinkEnvironment.Config.AdditionalFrameworks.Add(new UEBuildFramework("StoreKit"));
        }
Esempio n. 15
0
        static InstalledPlatformInfo()
        {
            List <string>   InstalledPlatforms;
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, (DirectoryReference)null, UnrealTargetPlatform.Unknown);

            bool bHasInstalledPlatformInfo;

            if (Ini.TryGetValue("InstalledPlatforms", "HasInstalledPlatformInfo", out bHasInstalledPlatformInfo) && bHasInstalledPlatformInfo)
            {
                InstalledPlatformConfigurations = new List <InstalledPlatformConfiguration>();
                if (Ini.GetArray("InstalledPlatforms", "InstalledPlatformConfigurations", out InstalledPlatforms))
                {
                    foreach (string InstalledPlatform in InstalledPlatforms)
                    {
                        ParsePlatformConfiguration(InstalledPlatform);
                    }
                }
            }
        }
Esempio n. 16
0
        public static bool GeneratePList(string ProjectDirectory, bool bIsUE4Game, string GameName, string ProjectName, string InEngineDir, string ExeName)
        {
            string IntermediateDirectory = (bIsUE4Game ? InEngineDir : ProjectDirectory) + "/Intermediate/Mac";
            string DestPListFile         = IntermediateDirectory + "/" + ExeName + "-Info.plist";
            string SrcPListFile          = (bIsUE4Game ? (InEngineDir + "Source/Programs/") : (ProjectDirectory + "/Source/")) + GameName + "/Resources/Mac/Info.plist";

            if (!File.Exists(SrcPListFile))
            {
                SrcPListFile = InEngineDir + "/Source/Runtime/Launch/Resources/Mac/Info.plist";
            }

            string PListData = null;

            if (File.Exists(SrcPListFile))
            {
                PListData = File.ReadAllText(SrcPListFile);
            }
            else
            {
                return(false);
            }

            // bundle identifier
            // plist replacements
            DirectoryReference DirRef = bIsUE4Game ? (!string.IsNullOrEmpty(UnrealBuildTool.GetRemoteIniPath()) ? new DirectoryReference(UnrealBuildTool.GetRemoteIniPath()) : null) : new DirectoryReference(ProjectDirectory);
            ConfigHierarchy    Ini    = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirRef, UnrealTargetPlatform.IOS);

            string BundleIdentifier;

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "BundleIdentifier", out BundleIdentifier);

            string BundleVersion = MacToolChain.LoadEngineDisplayVersion();

            PListData = PListData.Replace("${EXECUTABLE_NAME}", ExeName).Replace("${APP_NAME}", BundleIdentifier.Replace("[PROJECT_NAME]", ProjectName).Replace("_", "")).Replace("${ICON_NAME}", GameName).Replace("${MACOSX_DEPLOYMENT_TARGET}", MacToolChain.Settings.MinMacOSVersion).Replace("${BUNDLE_VERSION}", BundleVersion);

            if (!Directory.Exists(IntermediateDirectory))
            {
                Directory.CreateDirectory(IntermediateDirectory);
            }
            File.WriteAllText(DestPListFile, PListData);

            return(true);
        }
Esempio n. 17
0
        public override bool HasSpecificDefaultBuildConfig(UnrealTargetPlatform Platform, DirectoryReference ProjectPath)
        {
            ConfigHierarchy Ini        = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, ProjectPath, UnrealTargetPlatform.Lumin);
            bool            bUseVulkan = true;

            Ini.GetBool("/Script/LuminRuntimeSettings.LuminRuntimeSettings", "bUseVulkan", out bUseVulkan);

            List <string> ConfigBoolKeys = new List <string>();

            if (!bUseVulkan)
            {
                ConfigBoolKeys.Add("bUseMobileRendering");
            }

            // look up Android specific settings
            if (!DoProjectSettingsMatchDefault(UnrealTargetPlatform.Lumin, ProjectPath, "/Script/LuminRuntimeSettings.LuminRuntimeSettings", ConfigBoolKeys.ToArray(), null, null))
            {
                return(false);
            }

            return(true);
        }
        private bool SetupGraphicsDebugger(ReadOnlyTargetRules Target, CppCompileEnvironment CompileEnvironment, LinkEnvironment LinkEnvironment)
        {
            string          AndroidGraphicsDebugger;
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(Target.ProjectFile), UnrealTargetPlatform.Android);

            Ini.GetString("/Script/AndroidRuntimeSettings.AndroidRuntimeSettings", "AndroidGraphicsDebugger", out AndroidGraphicsDebugger);

            if (AndroidGraphicsDebugger.ToLower() == "renderdoc")
            {
                string RenderDocPath;
                AndroidPlatformSDK.GetPath(Ini, "/Script/AndroidRuntimeSettings.AndroidRuntimeSettings", "RenderDocPath", out RenderDocPath);
                string RenderDocLibPath = Path.Combine(RenderDocPath, @"android\lib\armeabi-v7a");
                if (Directory.Exists(RenderDocLibPath))
                {
                    LinkEnvironment.LibraryPaths.Add(new DirectoryReference(RenderDocLibPath));
                    LinkEnvironment.AdditionalLibraries.Add("VkLayer_GLES_RenderDoc");
                    return(true);
                }
            }

            return(false);
        }
Esempio n. 19
0
        public static bool UseTegraGraphicsDebugger(FileReference ProjectFile)
        {
            if (!HaveTegraGraphicsDebugger.HasValue)
            {
                string ProgramsDir = Environment.GetEnvironmentVariable("ProgramFiles(x86)");
                string NVDir       = ProgramsDir + "/NVIDIA Corporation";
                try
                {
                    string[] TegraDebuggerDirs = Directory.GetDirectories(NVDir, "Tegra Graphics Debugger *");
                    if (TegraDebuggerDirs.Length > 0)
                    {
                        TegraDebuggerDir          = TegraDebuggerDirs[0].Replace('\\', '/');
                        HaveTegraGraphicsDebugger = true;
                        string[] V = TegraDebuggerDir.Split(' ').Last().Split('.');
                        TegraDebuggerVersion    = new int[2];
                        TegraDebuggerVersion[0] = Int32.Parse(V[0]);
                        TegraDebuggerVersion[1] = Int32.Parse(V[1]);
                    }
                    else
                    {
                        HaveTegraGraphicsDebugger = false;
                    }
                }
                catch (System.IO.IOException)
                {
                    HaveTegraGraphicsDebugger = false;
                }
            }
            bool bBuild = false;
            // TODO: do we need this?
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(ProjectFile), UnrealTargetPlatform.Lumin);

            Ini.GetBool(
                "/Script/LuminRuntimeSettings.LuminRuntimeSettings",
                "bBuildWithNvTegraGfxDebugger",
                out bBuild);
            return(HaveTegraGraphicsDebugger.Value && bBuild);
        }
        public override void GenerateGameProperties(UnrealTargetConfiguration Configuration, StringBuilder VCProjectFileContent, TargetType TargetType, DirectoryReference RootDirectory, FileReference TargetFilePath)
        {
            string          MinVersion       = string.Empty;
            string          MaxTestedVersion = string.Empty;
            ConfigHierarchy EngineIni        = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, RootDirectory, UnrealTargetPlatform.HoloLens);

            if (EngineIni != null)
            {
                EngineIni.GetString("/Script/HoloLensPlatformEditor.HoloLensTargetSettings", "MinimumPlatformVersion", out MinVersion);
                EngineIni.GetString("/Script/HoloLensPlatformEditor.HoloLensTargetSettings", "MaximumPlatformVersionTested", out MaxTestedVersion);
            }
            if (!string.IsNullOrEmpty(MinVersion))
            {
                VCProjectFileContent.Append("		<WindowsTargetPlatformMinVersion>"+ MinVersion + "</WindowsTargetPlatformMinVersion>" + ProjectFileGenerator.NewLine);
            }
            if (!string.IsNullOrEmpty(MaxTestedVersion))
            {
                VCProjectFileContent.Append("		<WindowsTargetPlatformVersion>"+ MaxTestedVersion + "</WindowsTargetPlatformVersion>" + ProjectFileGenerator.NewLine);
            }

            WindowsCompiler    Compiler = WindowsPlatform.GetDefaultCompiler(TargetFilePath);
            DirectoryReference PlatformWinMDLocation = HoloLens.GetCppCXMetadataLocation(Compiler, "Latest");

            if (PlatformWinMDLocation == null || !FileReference.Exists(FileReference.Combine(PlatformWinMDLocation, "platform.winmd")))
            {
                throw new BuildException("Unable to find platform.winmd for {0} toolchain; '{1}' is an invalid version", WindowsPlatform.GetCompilerName(Compiler), "Latest");
            }
            string FoundationWinMDPath = HoloLens.GetLatestMetadataPathForApiContract("Windows.Foundation.FoundationContract", Compiler);
            string UniversalWinMDPath  = HoloLens.GetLatestMetadataPathForApiContract("Windows.Foundation.UniversalApiContract", Compiler);

            VCProjectFileContent.Append("		<AdditionalOptions>/ZW /ZW:nostdlib</AdditionalOptions>"+ ProjectFileGenerator.NewLine);
            VCProjectFileContent.Append("		<NMakePreprocessorDefinitions>$(NMakePreprocessorDefinitions);PLATFORM_HOLOLENS=1;HOLOLENS=1;</NMakePreprocessorDefinitions>"+ ProjectFileGenerator.NewLine);
            if (PlatformWinMDLocation != null)
            {
                VCProjectFileContent.Append("		<NMakeAssemblySearchPath>$(NMakeAssemblySearchPath);"+ PlatformWinMDLocation + "</NMakeAssemblySearchPath>" + ProjectFileGenerator.NewLine);
            }
            VCProjectFileContent.Append("		<NMakeForcedUsingAssemblies>$(NMakeForcedUsingAssemblies);"+ FoundationWinMDPath + ";" + UniversalWinMDPath + ";platform.winmd</NMakeForcedUsingAssemblies>" + ProjectFileGenerator.NewLine);
        }
Esempio n. 21
0
        public static bool GenerateTVOSPList(string ProjectDirectory, bool bIsUE4Game, string GameName, bool bIsClient, string ProjectName, string InEngineDir, string AppDirectory, UnrealPluginLanguage UPL, string BundleID)
        {
            // @todo tvos: THIS!


            // generate the Info.plist for future use
            string BuildDirectory        = ProjectDirectory + "/Build/TVOS";
            bool   bSkipDefaultPNGs      = false;
            string IntermediateDirectory = (bIsUE4Game ? InEngineDir : ProjectDirectory) + "/Intermediate/TVOS";
            string PListFile             = IntermediateDirectory + "/" + GameName + "-Info.plist";

            // @todo tvos: This is really nasty - both IOS and TVOS are setting static vars
            VersionUtilities.BuildDirectory = BuildDirectory;
            VersionUtilities.GameName       = GameName;

            // read the old file
            string OldPListData = File.Exists(PListFile) ? File.ReadAllText(PListFile) : "";

            // determine if there is a launch.xib
            //string LaunchXib = InEngineDir + "/Build/IOS/Resources/Interface/LaunchScreen.xib";
            //if (File.Exists(BuildDirectory + "/Resources/Interface/LaunchScreen.xib"))
            //{
            //	LaunchXib = BuildDirectory + "/Resources/Interface/LaunchScreen.xib";
            //}

            // get the settings from the ini file
            // plist replacements
            // @todo tvos: Are we going to make TVOS specific .ini files?
            DirectoryReference DirRef = bIsUE4Game ? (!string.IsNullOrEmpty(UnrealBuildTool.GetRemoteIniPath()) ? new DirectoryReference(UnrealBuildTool.GetRemoteIniPath()) : null) : new DirectoryReference(ProjectDirectory);
            ConfigHierarchy    Ini    = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirRef, UnrealTargetPlatform.IOS);

            // bundle display name
            string BundleDisplayName;

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "BundleDisplayName", out BundleDisplayName);

            // bundle identifier
            string BundleIdentifier;

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "BundleIdentifier", out BundleIdentifier);
            if (!string.IsNullOrEmpty(BundleID))
            {
                BundleIdentifier = BundleID;
            }

            // bundle name
            string BundleName;

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "BundleName", out BundleName);

            // short version string
            string BundleShortVersion;

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "VersionInfo", out BundleShortVersion);

            // required capabilities
            string RequiredCaps = "\t\t<string>arm64</string>\n";

            // minimum iOS version
            string MinVersion;

            if (Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "MinimumTVOSVersion", out MinVersion))
            {
                switch (MinVersion)
                {
                case "TVOS_9":
                    MinVersion = "9.0";
                    break;
                }
            }
            else
            {
                MinVersion = "9.0";
            }

            // extra plist data
            string ExtraData = "";

            Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "AdditionalPlistData", out ExtraData);

            // create the final display name, including converting all entities for XML use
            string FinalDisplayName = BundleDisplayName.Replace("[PROJECT_NAME]", ProjectName).Replace("_", "");

            FinalDisplayName = FinalDisplayName.Replace("&", "&amp;");
            FinalDisplayName = FinalDisplayName.Replace("\"", "&quot;");
            FinalDisplayName = FinalDisplayName.Replace("\'", "&apos;");
            FinalDisplayName = FinalDisplayName.Replace("<", "&lt;");
            FinalDisplayName = FinalDisplayName.Replace(">", "&gt;");

            // generate the plist file
            StringBuilder Text = new StringBuilder();

            Text.AppendLine("<?xml version=\"1.0\" encoding=\"UTF-8\"?>");
            Text.AppendLine("<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">");
            Text.AppendLine("<plist version=\"1.0\">");
            Text.AppendLine("<dict>");
            Text.AppendLine("\t<key>CFBundleDevelopmentRegion</key>");
            Text.AppendLine("\t<string>en</string>");
            Text.AppendLine("\t<key>CFBundleDisplayName</key>");
            Text.AppendLine(string.Format("\t<string>{0}</string>", EncodeBundleName(BundleDisplayName, ProjectName)));
            Text.AppendLine("\t<key>CFBundleExecutable</key>");
            string BundleExecutable = bIsUE4Game ?
                                      (bIsClient ? "UE4Client" : "UE4Game") :
                                      (bIsClient ? GameName + "Client" : GameName);

            Text.AppendLine(string.Format("\t<string>{0}</string>", BundleExecutable));
            Text.AppendLine("\t<key>CFBundleIdentifier</key>");
            Text.AppendLine(string.Format("\t<string>{0}</string>", BundleIdentifier.Replace("[PROJECT_NAME]", ProjectName).Replace("_", "")));
            Text.AppendLine("\t<key>CFBundleInfoDictionaryVersion</key>");
            Text.AppendLine("\t<string>6.0</string>");
            Text.AppendLine("\t<key>CFBundleName</key>");
            Text.AppendLine(string.Format("\t<string>{0}</string>", EncodeBundleName(BundleName, ProjectName)));
            Text.AppendLine("\t<key>CFBundlePackageType</key>");
            Text.AppendLine("\t<string>APPL</string>");
            Text.AppendLine("\t<key>CFBundleSignature</key>");
            Text.AppendLine("\t<string>????</string>");
            Text.AppendLine("\t<key>CFBundleVersion</key>");
            Text.AppendLine(string.Format("\t<string>{0}</string>", VersionUtilities.UpdateBundleVersion(OldPListData, InEngineDir)));
            Text.AppendLine("\t<key>CFBundleShortVersionString</key>");
            Text.AppendLine(string.Format("\t<string>{0}</string>", BundleShortVersion));
            Text.AppendLine("\t<key>LSRequiresIPhoneOS</key>");
            Text.AppendLine("\t<true/>");
            Text.AppendLine("\t<key>UIRequiredDeviceCapabilities</key>");
            Text.AppendLine("\t<array>");
            foreach (string Line in RequiredCaps.Split("\r\n".ToCharArray()))
            {
                if (!string.IsNullOrWhiteSpace(Line))
                {
                    Text.AppendLine(Line);
                }
            }
            Text.AppendLine("\t</array>");

            Text.AppendLine("\t<key>TVTopShelfImage</key>");
            Text.AppendLine("\t<dict>");
            Text.AppendLine("\t\t<key>TVTopShelfPrimaryImage</key>");
            Text.AppendLine("\t\t<string>Top Shelf Image</string>");
            Text.AppendLine("\t\t<key>TVTopShelfPrimaryImageWide</key>");
            Text.AppendLine("\t\t<string>Top Shelf Image Wide</string>");
            Text.AppendLine("\t</dict>");
            Text.AppendLine("\t<key>UILaunchImages</key>");
            Text.AppendLine("\t<array>");
            Text.AppendLine("\t\t<dict>");
            Text.AppendLine("\t\t\t<key>UILaunchImageSize</key>");
            Text.AppendLine("\t\t\t<string>{1920, 1080}</string>");
            Text.AppendLine("\t\t\t<key>UILaunchImageName</key>");
            Text.AppendLine("\t\t\t<string>Launch Image</string>");
            Text.AppendLine("\t\t\t<key>UILaunchImageMinimumOSVersion</key>");
            Text.AppendLine("\t\t\t<string>9.0</string>");
            Text.AppendLine("\t\t\t<key>UILaunchImageOrientation</key>");
            Text.AppendLine("\t\t\t<string>Landscape</string>");
            Text.AppendLine("\t\t</dict>");
            Text.AppendLine("\t</array>");
            Text.AppendLine("\t<key>CFBundleIcons</key>");
            Text.AppendLine("\t<dict>");
            Text.AppendLine("\t\t<key>CFBundlePrimaryIcon</key>");
            Text.AppendLine("\t\t<string>App Icon</string>");
            Text.AppendLine("\t</dict>");

            /*			Text.AppendLine("\t<key>CFBundleIcons</key>");
             *          Text.AppendLine("\t<dict>");
             *          Text.AppendLine("\t\t<key>CFBundlePrimaryIcon</key>");
             *          Text.AppendLine("\t\t<dict>");
             *          Text.AppendLine("\t\t\t<key>CFBundleIconFiles</key>");
             *          Text.AppendLine("\t\t\t<array>");
             *          Text.AppendLine("\t\t\t\t<string>Icon29.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon40.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon57.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t</array>");
             *          Text.AppendLine("\t\t\t<key>UIPrerenderedIcon</key>");
             *          Text.AppendLine("\t\t\t<true/>");
             *          Text.AppendLine("\t\t</dict>");
             *          Text.AppendLine("\t</dict>");
             *          Text.AppendLine("\t<key>CFBundleIcons~ipad</key>");
             *          Text.AppendLine("\t<dict>");
             *          Text.AppendLine("\t\t<key>CFBundlePrimaryIcon</key>");
             *          Text.AppendLine("\t\t<dict>");
             *          Text.AppendLine("\t\t\t<key>CFBundleIconFiles</key>");
             *          Text.AppendLine("\t\t\t<array>");
             *          Text.AppendLine("\t\t\t\t<string>Icon29.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon40.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon50.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon72.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t\t<string>Icon76.png</string>");
             *          Text.AppendLine("\t\t\t\t<string>[email protected]</string>");
             *          Text.AppendLine("\t\t\t</array>");
             *          Text.AppendLine("\t\t\t<key>UIPrerenderedIcon</key>");
             *          Text.AppendLine("\t\t\t<true/>");
             *          Text.AppendLine("\t\t</dict>");
             *          Text.AppendLine("\t</dict>");
             *          if (File.Exists(LaunchXib))
             *          {
             *              // TODO: compile the xib via remote tool
             *              Text.AppendLine("\t<key>UILaunchStoryboardName</key>");
             *              Text.AppendLine("\t<string>LaunchScreen</string>");
             *              bSkipDefaultPNGs = true;
             *          }
             *          else
             *          {
             *              // this is a temp way to inject the iphone 6 images without needing to upgrade everyone's plist
             *              // eventually we want to generate this based on what the user has set in the project settings
             *              string[] IPhoneConfigs =
             *                  {
             *                      "Default-IPhone6", "Landscape", "{375, 667}",
             *                      "Default-IPhone6", "Portrait", "{375, 667}",
             *                      "Default-IPhone6Plus-Landscape", "Landscape", "{414, 736}",
             *                      "Default-IPhone6Plus-Portrait", "Portrait", "{414, 736}",
             *                      "Default", "Landscape", "{320, 480}",
             *                      "Default", "Portrait", "{320, 480}",
             *                      "Default-568h", "Landscape", "{320, 568}",
             *                      "Default-568h", "Portrait", "{320, 568}",
             *                  };
             *
             *              Text.AppendLine("\t<key>UILaunchImages~iphone</key>");
             *              Text.AppendLine("\t<array>");
             *              for (int ConfigIndex = 0; ConfigIndex < IPhoneConfigs.Length; ConfigIndex += 3)
             *              {
             *                  Text.AppendLine("\t\t<dict>");
             *                  Text.AppendLine("\t\t\t<key>UILaunchImageMinimumOSVersion</key>");
             *                  Text.AppendLine("\t\t\t<string>8.0</string>");
             *                  Text.AppendLine("\t\t\t<key>UILaunchImageName</key>");
             *                  Text.AppendLine(string.Format("\t\t\t<string>{0}</string>", IPhoneConfigs[ConfigIndex + 0]));
             *                  Text.AppendLine("\t\t\t<key>UILaunchImageOrientation</key>");
             *                  Text.AppendLine(string.Format("\t\t\t<string>{0}</string>", IPhoneConfigs[ConfigIndex + 1]));
             *                  Text.AppendLine("\t\t\t<key>UILaunchImageSize</key>");
             *                  Text.AppendLine(string.Format("\t\t\t<string>{0}</string>", IPhoneConfigs[ConfigIndex + 2]));
             *                  Text.AppendLine("\t\t</dict>");
             *              }
             *
             *              // close it out
             *              Text.AppendLine("\t</array>");
             *          }
             *          Text.AppendLine("\t<key>UILaunchImages~ipad</key>");
             *          Text.AppendLine("\t<array>");
             *          Text.AppendLine("\t\t<dict>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageMinimumOSVersion</key>");
             *          Text.AppendLine("\t\t\t<string>7.0</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageName</key>");
             *          Text.AppendLine("\t\t\t<string>Default-Landscape</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageOrientation</key>");
             *          Text.AppendLine("\t\t\t<string>Landscape</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageSize</key>");
             *          Text.AppendLine("\t\t\t<string>{768, 1024}</string>");
             *          Text.AppendLine("\t\t</dict>");
             *          Text.AppendLine("\t\t<dict>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageMinimumOSVersion</key>");
             *          Text.AppendLine("\t\t\t<string>7.0</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageName</key>");
             *          Text.AppendLine("\t\t\t<string>Default-Portrait</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageOrientation</key>");
             *          Text.AppendLine("\t\t\t<string>Portrait</string>");
             *          Text.AppendLine("\t\t\t<key>UILaunchImageSize</key>");
             *          Text.AppendLine("\t\t\t<string>{768, 1024}</string>");
             *          Text.AppendLine("\t\t</dict>");
             *          Text.AppendLine("\t</array>");
             *          Text.AppendLine("\t<key>CFBundleSupportedPlatforms</key>");
             *          Text.AppendLine("\t<array>");
             *          Text.AppendLine("\t\t<string>iPhoneOS</string>");
             *          Text.AppendLine("\t</array>");
             *          Text.AppendLine("\t<key>MinimumOSVersion</key>");
             *          Text.AppendLine(string.Format("\t<string>{0}</string>", MinVersion));
             *          if (!string.IsNullOrEmpty(ExtraData))
             *          {
             *              ExtraData = ExtraData.Replace("\\n", "\n");
             *              foreach (string Line in ExtraData.Split("\r\n".ToCharArray()))
             *              {
             *                  if (!string.IsNullOrWhiteSpace(Line))
             *                  {
             *                      Text.AppendLine("\t" + Line);
             *                  }
             *              }
             *          }*/
            // write the iCloud container identifier, if present in the old file
            if (!string.IsNullOrEmpty(OldPListData))
            {
                int index = OldPListData.IndexOf("ICloudContainerIdentifier");
                if (index > 0)
                {
                    index = OldPListData.IndexOf("<string>", index) + 8;
                    int    length = OldPListData.IndexOf("</string>", index) - index;
                    string ICloudContainerIdentifier = OldPListData.Substring(index, length);
                    Text.AppendLine("\t<key>ICloudContainerIdentifier</key>");
                    Text.AppendLine(string.Format("\t<string>{0}</string>", ICloudContainerIdentifier));
                }
            }

            Text.AppendLine("</dict>");
            Text.AppendLine("</plist>");

            // Create the intermediate directory if needed
            if (!Directory.Exists(IntermediateDirectory))
            {
                Directory.CreateDirectory(IntermediateDirectory);
            }

            if (UPL != null)
            {
                // Allow UPL to modify the plist here
                XDocument XDoc;
                try
                {
                    XDoc = XDocument.Parse(Text.ToString());
                }
                catch (Exception e)
                {
                    throw new BuildException("plist is invalid {0}\n{1}", e, Text.ToString());
                }

                XDoc.DocumentType.InternalSubset = "";
                UPL.ProcessPluginNode("None", "iosPListUpdates", "", ref XDoc);
                string result = XDoc.Declaration.ToString() + "\n" + XDoc.ToString().Replace("<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\"[]>", "<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">");
                File.WriteAllText(PListFile, result);
            }
            else
            {
                File.WriteAllText(PListFile, Text.ToString());
            }

            if (BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac)
            {
                if (!Directory.Exists(AppDirectory))
                {
                    Directory.CreateDirectory(AppDirectory);
                }
                File.WriteAllText(AppDirectory + "/Info.plist", Text.ToString());
            }

            return(bSkipDefaultPNGs);
        }
Esempio n. 22
0
        public override void SetUpProjectEnvironment(UnrealTargetConfiguration Configuration, TargetInfo Target = null)
        {
            if (!bInitializedProject)
            {
                base.SetUpProjectEnvironment(Configuration, Target);

                // update the configuration based on the project file
                // look in ini settings for what platforms to compile for
                ConfigHierarchy Ini        = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(ProjectFile), Platform);
                string          MinVersion = "IOS_8";
                if (Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "MinimumiOSVersion", out MinVersion))
                {
                    switch (MinVersion)
                    {
                    case "IOS_61":
                        Log.TraceWarningOnce("IOS 6 is no longer supported in UE4 as 4.11");
                        RunTimeIOSVersion = "8.0";
                        break;

                    case "IOS_7":
                        Log.TraceWarningOnce("IOS 7 is no longer supported in UE4 as 4.14");
                        RunTimeIOSVersion = "8.0";
                        break;

                    case "IOS_8":
                        RunTimeIOSVersion = "8.0";
                        break;

                    case "IOS_9":
                        RunTimeIOSVersion = "9.0";
                        break;

                    case "IOS_10":
                        RunTimeIOSVersion = "10.0";
                        break;
                    }
                }

                bool biPhoneAllowed = true;
                bool biPadAllowed   = true;
                Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bSupportsIPhone", out biPhoneAllowed);
                Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bSupportsIPad", out biPadAllowed);
                if (biPhoneAllowed && biPadAllowed)
                {
                    RunTimeIOSDevices = "1,2";
                }
                else if (biPadAllowed)
                {
                    RunTimeIOSDevices = "2";
                }
                else if (biPhoneAllowed)
                {
                    RunTimeIOSDevices = "1";
                }

                NonShippingArchitectures = String.Join(",", GetNonShippingArchitectures(Ini));

                ShippingArchitectures = String.Join(",", GetShippingArchitectures(Ini));

                // determine if we need to generate the dsym
                Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bGeneratedSYMFile", out BuildConfiguration.bGeneratedSYMFile);
                Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bGeneratedSYMBundle", out BuildConfiguration.bGeneratedSYMBundle);

                // determie if bitcode should be generated for the shipping code
                Ini.GetBool("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "bShipForBitcode", out bShipForBitcode);

                // @todo tvos: We probably want to handle TVOS versions here
                Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "AdditionalLinkerFlags", out AdditionalLinkerFlags);
                Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "AdditionalShippingLinkerFlags", out AdditionalShippingLinkerFlags);

                Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "MobileProvision", out MobileProvision);
                Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "SigningCertificate", out SigningCertificate);

                // bundle identifier
                Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "BundleIdentifier", out BundleIdentifier);

                bInitializedProject = true;
            }

            ProvisionData Data     = new ProvisionData();
            string        BundleId = BundleIdentifier.Replace("[PROJECT_NAME]", ((ProjectFile != null) ? ProjectFile.GetFileNameWithoutAnyExtensions() : "UE4Game")).Replace("_", "");
            bool          bIsTVOS  = GetCodesignPlatformName() == "appletvos";

            if (!ProvisionCache.ContainsKey(BundleId + " " + bIsTVOS.ToString() + " " + bForDistribtion.ToString()))
            {
                Certificate = SigningCertificate;
                Provision   = MobileProvision;
                if (!string.IsNullOrEmpty(SigningCertificate))
                {
                    // verify the certificate
                    Process IPPProcess = new Process();
                    if (BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac)
                    {
                        string IPPCmd = "\"" + UnrealBuildTool.EngineDirectory + "/Binaries/DotNET/IOS/IPhonePackager.exe\" certificates " + ((ProjectFile != null) ? ("\"" + ProjectFile.ToString() + "\"") : "Engine") + " -bundlename " + BundleId + (bForDistribtion ? " -distribution" : "");
                        IPPProcess.StartInfo.WorkingDirectory = UnrealBuildTool.EngineDirectory.ToString();
                        IPPProcess.StartInfo.FileName         = UnrealBuildTool.EngineDirectory + "/Build/BatchFiles/Mac/RunMono.sh";
                        IPPProcess.StartInfo.Arguments        = IPPCmd;
                        IPPProcess.OutputDataReceived        += new DataReceivedEventHandler(IPPDataReceivedHandler);
                        IPPProcess.ErrorDataReceived         += new DataReceivedEventHandler(IPPDataReceivedHandler);
                    }
                    else
                    {
                        string IPPCmd = "certificates " + ((ProjectFile != null) ? ("\"" + ProjectFile.ToString() + "\"") : "Engine") + " -bundlename " + BundleId + (bForDistribtion ? " -distribution" : "");
                        IPPProcess.StartInfo.WorkingDirectory = UnrealBuildTool.EngineDirectory.ToString();
                        IPPProcess.StartInfo.FileName         = UnrealBuildTool.EngineDirectory + "\\Binaries\\DotNET\\IOS\\IPhonePackager.exe";
                        IPPProcess.StartInfo.Arguments        = IPPCmd;
                        IPPProcess.OutputDataReceived        += new DataReceivedEventHandler(IPPDataReceivedHandler);
                        IPPProcess.ErrorDataReceived         += new DataReceivedEventHandler(IPPDataReceivedHandler);
                    }
                    Utils.RunLocalProcess(IPPProcess);
                }
                else
                {
                    Certificate      = bForDistribtion ? "iPhone Distribution" : "iPhone Developer";
                    bHaveCertificate = true;
                }

                if (string.IsNullOrEmpty(MobileProvision) || // no provision specified
                    !File.Exists((BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac ? (Environment.GetEnvironmentVariable("HOME") + "/Library/MobileDevice/Provisioning Profiles/") : (Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + "/Apple Computer/MobileDevice/Provisioning Profiles/")) + MobileProvision) || // file doesn't exist
                    !bHaveCertificate)    // certificate doesn't exist
                {
                    Certificate = "";
                    Provision   = "";
                    Log.TraceLog("Provision not specified or not found for " + ((ProjectFile != null) ? ProjectFile.GetFileNameWithoutAnyExtensions() : "UE4Game") + ", searching for compatible match...");
                    Process IPPProcess = new Process();
                    if (BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac)
                    {
                        string IPPCmd = "\"" + UnrealBuildTool.EngineDirectory + "/Binaries/DotNET/IOS/IPhonePackager.exe\" signing_match " + ((ProjectFile != null) ? ("\"" + ProjectFile.ToString() + "\"") : "Engine") + " -bundlename " + BundleId + (bIsTVOS ? " -tvos" : "") + (bForDistribtion ? " -distribution" : "");
                        IPPProcess.StartInfo.WorkingDirectory = UnrealBuildTool.EngineDirectory.ToString();
                        IPPProcess.StartInfo.FileName         = UnrealBuildTool.EngineDirectory + "/Build/BatchFiles/Mac/RunMono.sh";
                        IPPProcess.StartInfo.Arguments        = IPPCmd;
                        IPPProcess.OutputDataReceived        += new DataReceivedEventHandler(IPPDataReceivedHandler);
                        IPPProcess.ErrorDataReceived         += new DataReceivedEventHandler(IPPDataReceivedHandler);
                    }
                    else
                    {
                        string IPPCmd = "signing_match " + ((ProjectFile != null) ? ("\"" + ProjectFile.ToString() + "\"") : "Engine") + " -bundlename " + BundleId + (bIsTVOS ? " -tvos" : "") + (bForDistribtion ? " -distribution" : "");
                        IPPProcess.StartInfo.WorkingDirectory = UnrealBuildTool.EngineDirectory.ToString();
                        IPPProcess.StartInfo.FileName         = UnrealBuildTool.EngineDirectory + "\\Binaries\\DotNET\\IOS\\IPhonePackager.exe";
                        IPPProcess.StartInfo.Arguments        = IPPCmd;
                        IPPProcess.OutputDataReceived        += new DataReceivedEventHandler(IPPDataReceivedHandler);
                        IPPProcess.ErrorDataReceived         += new DataReceivedEventHandler(IPPDataReceivedHandler);
                    }
                    Utils.RunLocalProcess(IPPProcess);
                    Log.TraceLog("Provision found for " + ((ProjectFile != null) ? ProjectFile.GetFileNameWithoutAnyExtensions() : "UE4Game") + ", Provision: " + Provision + " Certificate: " + Certificate);
                }
                // add to the dictionary
                Data.MobileProvision = Provision;
                Data.Certificate     = Certificate.Replace("\"", "");

                // read the provision to get the UUID
                string filename = (BuildHostPlatform.Current.Platform == UnrealTargetPlatform.Mac ? (Environment.GetEnvironmentVariable("HOME") + "/Library/MobileDevice/Provisioning Profiles/") : (Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + "/Apple Computer/MobileDevice/Provisioning Profiles/")) + Data.MobileProvision;
                if (File.Exists(filename))
                {
                    string AllText = File.ReadAllText(filename);
                    int    idx     = AllText.IndexOf("<key>UUID</key>");
                    if (idx > 0)
                    {
                        idx = AllText.IndexOf("<string>", idx);
                        if (idx > 0)
                        {
                            idx      += "<string>".Length;
                            Data.UUID = AllText.Substring(idx, AllText.IndexOf("</string>", idx) - idx);
                        }
                    }
                    idx = AllText.IndexOf("<key>com.apple.developer.team-identifier</key>");
                    if (idx > 0)
                    {
                        idx = AllText.IndexOf("<string>", idx);
                        if (idx > 0)
                        {
                            idx          += "<string>".Length;
                            Data.TeamUUID = AllText.Substring(idx, AllText.IndexOf("</string>", idx) - idx);
                        }
                    }
                }
                else
                {
                    Log.TraceLog("No matching provision file was discovered. Please ensure you have a compatible provision installed.");
                }
                ProvisionCache.Add(BundleId + " " + bIsTVOS.ToString() + " " + bForDistribtion.ToString(), Data);
            }
            else
            {
                Data = ProvisionCache[BundleId + " " + bIsTVOS.ToString() + " " + bForDistribtion.ToString()];
            }
            MobileProvision     = Data.MobileProvision;
            SigningCertificate  = Data.Certificate;
            MobileProvisionUUID = Data.UUID;
            TeamUUID            = Data.TeamUUID;
        }
        /// <summary>
        /// checks if the sdk is installed or has been synced
        /// </summary>
        /// <returns></returns>
        private bool HasAnySDK()
        {
            string NDKPath = Environment.GetEnvironmentVariable("NDKROOT");

            {
                ConfigHierarchy             configCacheIni = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, (DirectoryReference)null, UnrealTargetPlatform.Unknown);
                Dictionary <string, string> AndroidEnv     = new Dictionary <string, string>();

                Dictionary <string, string> EnvVarNames = new Dictionary <string, string> {
                    { "ANDROID_HOME", "SDKPath" },
                    { "NDKROOT", "NDKPath" },
                    { "ANT_HOME", "ANTPath" },
                    { "JAVA_HOME", "JavaPath" }
                };

                string path;
                foreach (KeyValuePair <string, string> kvp in EnvVarNames)
                {
                    if (GetPath(configCacheIni, "/Script/AndroidPlatformEditor.AndroidSDKSettings", kvp.Value, out path) && !string.IsNullOrEmpty(path))
                    {
                        AndroidEnv.Add(kvp.Key, path);
                    }
                    else
                    {
                        string envValue = Environment.GetEnvironmentVariable(kvp.Key);
                        if (!String.IsNullOrEmpty(envValue))
                        {
                            AndroidEnv.Add(kvp.Key, envValue);
                        }
                    }
                }

                // If we are on Mono and we are still missing a key then go and find it from the .bash_profile
                if (Utils.IsRunningOnMono && !EnvVarNames.All(s => AndroidEnv.ContainsKey(s.Key)))
                {
                    string BashProfilePath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), ".bash_profile");
                    if (!File.Exists(BashProfilePath))
                    {
                        // Try .bashrc if didn't fine .bash_profile
                        BashProfilePath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), ".bashrc");
                    }
                    if (File.Exists(BashProfilePath))
                    {
                        string[] BashProfileContents = File.ReadAllLines(BashProfilePath);

                        // Walk backwards so we keep the last export setting instead of the first
                        for (int LineIndex = BashProfileContents.Length - 1; LineIndex >= 0; --LineIndex)
                        {
                            foreach (KeyValuePair <string, string> kvp in EnvVarNames)
                            {
                                if (AndroidEnv.ContainsKey(kvp.Key))
                                {
                                    continue;
                                }

                                if (BashProfileContents[LineIndex].StartsWith("export " + kvp.Key + "="))
                                {
                                    string PathVar = BashProfileContents[LineIndex].Split('=')[1].Replace("\"", "");
                                    AndroidEnv.Add(kvp.Key, PathVar);
                                }
                            }
                        }
                    }
                }

                // Set for the process
                foreach (KeyValuePair <string, string> kvp in AndroidEnv)
                {
                    Environment.SetEnvironmentVariable(kvp.Key, kvp.Value);
                }

                // See if we have an NDK path now...
                AndroidEnv.TryGetValue("NDKROOT", out NDKPath);
            }

            // we don't have an NDKROOT specified
            if (String.IsNullOrEmpty(NDKPath))
            {
                return(false);
            }

            NDKPath = NDKPath.Replace("\"", "");

            // need a supported llvm
            if (!Directory.Exists(Path.Combine(NDKPath, @"toolchains/llvm")) &&
                !Directory.Exists(Path.Combine(NDKPath, @"toolchains/llvm-3.6")) &&
                !Directory.Exists(Path.Combine(NDKPath, @"toolchains/llvm-3.5")) &&
                !Directory.Exists(Path.Combine(NDKPath, @"toolchains/llvm-3.3")) &&
                !Directory.Exists(Path.Combine(NDKPath, @"toolchains/llvm-3.1")))
            {
                return(false);
            }
            return(true);
        }
        /// <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);
        }
Esempio n. 25
0
        /// <summary>
        /// Parse crypto settings from INI file
        /// </summary>
        public static CryptoSettings ParseCryptoSettings(DirectoryReference InProjectDirectory, UnrealTargetPlatform InTargetPlatform)
        {
            CryptoSettings Settings = new CryptoSettings();

            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, InProjectDirectory, InTargetPlatform);

            Ini.GetBool("PlatformCrypto", "PlatformRequiresDataCrypto", out Settings.bDataCryptoRequired);

            // For now, we'll just not parse any keys if data crypto is disabled for this platform. In the future, we might want to use
            // these keys for non-data purposes (other general purpose encryption maybe?)
            if (!Settings.bDataCryptoRequired)
            {
                return(Settings);
            }

            {
                // Start by parsing the legacy encryption.ini settings
                Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Encryption, InProjectDirectory, InTargetPlatform);
                Ini.GetBool("Core.Encryption", "SignPak", out Settings.bEnablePakSigning);

                string[] SigningKeyStrings = new string[3];
                Ini.GetString("Core.Encryption", "rsa.privateexp", out SigningKeyStrings[0]);
                Ini.GetString("Core.Encryption", "rsa.modulus", out SigningKeyStrings[1]);
                Ini.GetString("Core.Encryption", "rsa.publicexp", out SigningKeyStrings[2]);

                if (String.IsNullOrEmpty(SigningKeyStrings[0]) || String.IsNullOrEmpty(SigningKeyStrings[1]) || String.IsNullOrEmpty(SigningKeyStrings[2]))
                {
                    SigningKeyStrings = null;
                }
                else
                {
                    Settings.SigningKey = new SigningKeyPair();
                    Settings.SigningKey.PrivateKey.Exponent = ParseHexStringToByteArray(SigningKeyStrings[0]);
                    Settings.SigningKey.PrivateKey.Modulus  = ParseHexStringToByteArray(SigningKeyStrings[1]);
                    Settings.SigningKey.PublicKey.Exponent  = ParseHexStringToByteArray(SigningKeyStrings[2]);
                    Settings.SigningKey.PublicKey.Modulus   = Settings.SigningKey.PrivateKey.Modulus;
                }

                Ini.GetBool("Core.Encryption", "EncryptPak", out Settings.bEnablePakIndexEncryption);
                Settings.bEnablePakFullAssetEncryption = false;
                Settings.bEnablePakUAssetEncryption    = false;
                Settings.bEnablePakIniEncryption       = Settings.bEnablePakIndexEncryption;

                string EncryptionKeyString;
                Ini.GetString("Core.Encryption", "aes.key", out EncryptionKeyString);
                Settings.EncryptionKey     = new EncryptionKey();
                Settings.EncryptionKey.Key = ParseAnsiStringToByteArray(EncryptionKeyString);
            }

            Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Crypto, InProjectDirectory, InTargetPlatform);
            string SectionName = "/Script/CryptoKeys.CryptoKeysSettings";
            ConfigHierarchySection CryptoSection = Ini.FindSection(SectionName);

            // If we have new format crypto keys, read them in over the top of the legacy settings
            if (CryptoSection != null && CryptoSection.KeyNames.Count() > 0)
            {
                Ini.GetBool(SectionName, "bEnablePakSigning", out Settings.bEnablePakSigning);
                Ini.GetBool(SectionName, "bEncryptPakIniFiles", out Settings.bEnablePakIniEncryption);
                Ini.GetBool(SectionName, "bEncryptPakIndex", out Settings.bEnablePakIndexEncryption);
                Ini.GetBool(SectionName, "bEncryptUAssetFiles", out Settings.bEnablePakUAssetEncryption);
                Ini.GetBool(SectionName, "bEncryptAllAssetFiles", out Settings.bEnablePakFullAssetEncryption);

                // Parse encryption key
                string EncryptionKeyString;
                Ini.GetString(SectionName, "EncryptionKey", out EncryptionKeyString);
                if (!string.IsNullOrEmpty(EncryptionKeyString))
                {
                    Settings.EncryptionKey     = new EncryptionKey();
                    Settings.EncryptionKey.Key = System.Convert.FromBase64String(EncryptionKeyString);

                    if (Settings.EncryptionKey.Key.Length != 32)
                    {
                        throw new Exception("The encryption key specified in the crypto config file must be 32 bytes long!");
                    }
                }

                // Parse signing key
                string PrivateExponent, PublicExponent, Modulus;
                Ini.GetString(SectionName, "SigningPrivateExponent", out PrivateExponent);
                Ini.GetString(SectionName, "SigningModulus", out Modulus);
                Ini.GetString(SectionName, "SigningPublicExponent", out PublicExponent);

                if (!String.IsNullOrEmpty(PrivateExponent) && !String.IsNullOrEmpty(PublicExponent) && !String.IsNullOrEmpty(Modulus))
                {
                    Settings.SigningKey = new SigningKeyPair();
                    Settings.SigningKey.PublicKey.Exponent  = System.Convert.FromBase64String(PublicExponent);
                    Settings.SigningKey.PublicKey.Modulus   = System.Convert.FromBase64String(Modulus);
                    Settings.SigningKey.PrivateKey.Exponent = System.Convert.FromBase64String(PrivateExponent);
                    Settings.SigningKey.PrivateKey.Modulus  = Settings.SigningKey.PublicKey.Modulus;
                }
            }

            return(Settings);
        }
Esempio n. 26
0
 private ConfigHierarchy GetConfigCacheIni(ConfigHierarchyType Type)
 {
     return(ConfigCache.ReadHierarchy(Type, DirectoryReference.FromFile(ProjectFile), UnrealTargetPlatform.Lumin));
 }
Esempio n. 27
0
        /// <summary>
        /// Setup the target environment for building
        /// </summary>
        /// <param name="Target">Settings for the target being compiled</param>
        /// <param name="CompileEnvironment">The compile environment for this target</param>
        /// <param name="LinkEnvironment">The link environment for this target</param>
        public override void SetUpEnvironment(ReadOnlyTargetRules Target, CppCompileEnvironment CompileEnvironment, LinkEnvironment LinkEnvironment)
        {
            CompileEnvironment.Definitions.Add("WIN32=1");

            if (WindowsPlatform.bUseWindowsSDK10)
            {
                // Windows 8 or higher required
                CompileEnvironment.Definitions.Add("_WIN32_WINNT=0x0602");
                CompileEnvironment.Definitions.Add("WINVER=0x0602");
            }
            else
            {
                // Windows 7 or higher required
                CompileEnvironment.Definitions.Add("_WIN32_WINNT=0x0601");
                CompileEnvironment.Definitions.Add("WINVER=0x0601");
            }
            CompileEnvironment.Definitions.Add("PLATFORM_WINDOWS=1");

            CompileEnvironment.Definitions.Add("DEPTH_32_BIT_CONVERSION=0");

            FileReference MorpheusShaderPath = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Shaders", "PS4", "PostProcessHMDMorpheus.usf");

            if (FileReference.Exists(MorpheusShaderPath))
            {
                CompileEnvironment.Definitions.Add("HAS_MORPHEUS=1");

                //on PS4 the SDK now handles distortion correction.  On PC we will still have to handle it manually,
                CompileEnvironment.Definitions.Add("MORPHEUS_ENGINE_DISTORTION=1");
            }

            // Add path to Intel math libraries when using ICL based on target platform
            if (WindowsPlatform.bCompileWithICL)
            {
                var Result = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFilesX86), "IntelSWTools", "compilers_and_libraries", "windows", "compiler", "lib", Target.Platform == UnrealTargetPlatform.Win32 ? "ia32" : "intel64");
                if (!Directory.Exists(Result))
                {
                    throw new BuildException("ICL was selected but the required math libraries were not found.  Could not find: " + Result);
                }

                LinkEnvironment.LibraryPaths.Add(Result);
            }

            // Explicitly exclude the MS C++ runtime libraries we're not using, to ensure other libraries we link with use the same
            // runtime library as the engine.
            bool bUseDebugCRT = Target.Configuration == UnrealTargetConfiguration.Debug && Target.bDebugBuildsActuallyUseDebugCRT;

            if (!Target.bUseStaticCRT || bUseDebugCRT)
            {
                LinkEnvironment.ExcludedLibraries.Add("LIBCMT");
                LinkEnvironment.ExcludedLibraries.Add("LIBCPMT");
            }
            if (!Target.bUseStaticCRT || !bUseDebugCRT)
            {
                LinkEnvironment.ExcludedLibraries.Add("LIBCMTD");
                LinkEnvironment.ExcludedLibraries.Add("LIBCPMTD");
            }
            if (Target.bUseStaticCRT || bUseDebugCRT)
            {
                LinkEnvironment.ExcludedLibraries.Add("MSVCRT");
                LinkEnvironment.ExcludedLibraries.Add("MSVCPRT");
            }
            if (Target.bUseStaticCRT || !bUseDebugCRT)
            {
                LinkEnvironment.ExcludedLibraries.Add("MSVCRTD");
                LinkEnvironment.ExcludedLibraries.Add("MSVCPRTD");
            }
            LinkEnvironment.ExcludedLibraries.Add("LIBC");
            LinkEnvironment.ExcludedLibraries.Add("LIBCP");
            LinkEnvironment.ExcludedLibraries.Add("LIBCD");
            LinkEnvironment.ExcludedLibraries.Add("LIBCPD");

            //@todo ATL: Currently, only VSAccessor requires ATL (which is only used in editor builds)
            // When compiling games, we do not want to include ATL - and we can't when compiling games
            // made with Launcher build due to VS 2012 Express not including ATL.
            // If more modules end up requiring ATL, this should be refactored into a BuildTarget flag (bNeedsATL)
            // that is set by the modules the target includes to allow for easier tracking.
            // Alternatively, if VSAccessor is modified to not require ATL than we should always exclude the libraries.
            if (Target.LinkType == TargetLinkType.Monolithic &&
                (Target.Type == TargetType.Game || Target.Type == TargetType.Client || Target.Type == TargetType.Server))
            {
                LinkEnvironment.ExcludedLibraries.Add("atl");
                LinkEnvironment.ExcludedLibraries.Add("atls");
                LinkEnvironment.ExcludedLibraries.Add("atlsd");
                LinkEnvironment.ExcludedLibraries.Add("atlsn");
                LinkEnvironment.ExcludedLibraries.Add("atlsnd");
            }

            // Add the library used for the delayed loading of DLLs.
            LinkEnvironment.AdditionalLibraries.Add("delayimp.lib");

            //@todo - remove once FB implementation uses Http module
            if (Target.bCompileAgainstEngine)
            {
                // link against wininet (used by FBX and Facebook)
                LinkEnvironment.AdditionalLibraries.Add("wininet.lib");
            }

            // Compile and link with Win32 API libraries.
            LinkEnvironment.AdditionalLibraries.Add("rpcrt4.lib");
            //LinkEnvironment.AdditionalLibraries.Add("wsock32.lib");
            LinkEnvironment.AdditionalLibraries.Add("ws2_32.lib");
            LinkEnvironment.AdditionalLibraries.Add("dbghelp.lib");
            LinkEnvironment.AdditionalLibraries.Add("comctl32.lib");
            LinkEnvironment.AdditionalLibraries.Add("Winmm.lib");
            LinkEnvironment.AdditionalLibraries.Add("kernel32.lib");
            LinkEnvironment.AdditionalLibraries.Add("user32.lib");
            LinkEnvironment.AdditionalLibraries.Add("gdi32.lib");
            LinkEnvironment.AdditionalLibraries.Add("winspool.lib");
            LinkEnvironment.AdditionalLibraries.Add("comdlg32.lib");
            LinkEnvironment.AdditionalLibraries.Add("advapi32.lib");
            LinkEnvironment.AdditionalLibraries.Add("shell32.lib");
            LinkEnvironment.AdditionalLibraries.Add("ole32.lib");
            LinkEnvironment.AdditionalLibraries.Add("oleaut32.lib");
            LinkEnvironment.AdditionalLibraries.Add("uuid.lib");
            LinkEnvironment.AdditionalLibraries.Add("odbc32.lib");
            LinkEnvironment.AdditionalLibraries.Add("odbccp32.lib");
            LinkEnvironment.AdditionalLibraries.Add("netapi32.lib");
            LinkEnvironment.AdditionalLibraries.Add("iphlpapi.lib");
            LinkEnvironment.AdditionalLibraries.Add("setupapi.lib");             //  Required for access monitor device enumeration

            // Windows Vista/7 Desktop Windows Manager API for Slate Windows Compliance
            LinkEnvironment.AdditionalLibraries.Add("dwmapi.lib");

            // IME
            LinkEnvironment.AdditionalLibraries.Add("imm32.lib");

            // For 64-bit builds, we'll forcibly ignore a linker warning with DirectInput.  This is
            // Microsoft's recommended solution as they don't have a fixed .lib for us.
            if (Target.Platform == UnrealTargetPlatform.Win64)
            {
                LinkEnvironment.AdditionalArguments += " /ignore:4078";
            }

            if (Target.Type != TargetType.Editor)
            {
                if (!string.IsNullOrEmpty(Target.WindowsPlatform.CompanyName))
                {
                    CompileEnvironment.Definitions.Add(String.Format("PROJECT_COMPANY_NAME={0}", Target.WindowsPlatform.CompanyName));
                }

                if (!string.IsNullOrEmpty(Target.WindowsPlatform.CopyrightNotice))
                {
                    CompileEnvironment.Definitions.Add(String.Format("PROJECT_COPYRIGHT_STRING={0}", Target.WindowsPlatform.CopyrightNotice));
                }

                if (!string.IsNullOrEmpty(Target.WindowsPlatform.ProductName))
                {
                    CompileEnvironment.Definitions.Add(String.Format("PROJECT_PRODUCT_NAME={0}", Target.WindowsPlatform.ProductName));
                }

                if (Target.ProjectFile != null)
                {
                    CompileEnvironment.Definitions.Add(String.Format("PROJECT_PRODUCT_IDENTIFIER={0}", Target.ProjectFile.GetFileNameWithoutExtension()));
                }
            }

            // Set up default stack size
            ConfigHierarchy EngineIni             = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, DirectoryReference.FromFile(Target.ProjectFile), UnrealTargetPlatform.Win64);
            String          TargetSettingsIniPath = "/Script/WindowsTargetPlatform.WindowsTargetSettings";
            int             IniDefaultStackSize   = 0;
            String          StackSizeName         = Target.Type == TargetType.Editor ? "DefaultStackSizeEditor" : "DefaultStackSize";

            if (EngineIni.GetInt32(TargetSettingsIniPath, StackSizeName, out IniDefaultStackSize))
            {
                LinkEnvironment.DefaultStackSize = IniDefaultStackSize;
            }

            int    IniDefaultStackSizeCommit = 0;
            String StackSizeCommitName       = Target.Type == TargetType.Editor ? "DefaultStackSizeCommitEditor" : "DefaultStackSizeCommit";

            if (EngineIni.GetInt32(TargetSettingsIniPath, StackSizeCommitName, out IniDefaultStackSizeCommit))
            {
                LinkEnvironment.DefaultStackSizeCommit = IniDefaultStackSizeCommit;
            }
        }
Esempio n. 28
0
        /// <summary>
        /// Constructor
        /// </summary>
        /// <param name="ProjectFile">Project to read settings from</param>
        public RemoteMac(FileReference ProjectFile)
        {
            this.RsyncExe         = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Extras", "ThirdPartyNotUE", "DeltaCopy", "Binaries", "Rsync.exe");
            this.SshExe           = FileReference.Combine(UnrealBuildTool.EngineDirectory, "Extras", "ThirdPartyNotUE", "DeltaCopy", "Binaries", "Ssh.exe");
            this.ProjectFile      = ProjectFile;
            this.ProjectDirectory = DirectoryReference.FromFile(ProjectFile);

            // Apply settings from the XML file
            XmlConfig.ApplyTo(this);

            // Get the project config file path
            DirectoryReference EngineIniPath = ProjectFile != null ? ProjectFile.Directory : null;

            if (EngineIniPath == null && UnrealBuildTool.GetRemoteIniPath() != null)
            {
                EngineIniPath = new DirectoryReference(UnrealBuildTool.GetRemoteIniPath());
            }
            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, EngineIniPath, UnrealTargetPlatform.IOS);

            // Read the project settings if we don't have anything in the build configuration settings
            if (String.IsNullOrEmpty(ServerName))
            {
                // Read the server name
                string IniServerName;
                if (Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "RemoteServerName", out IniServerName) && !String.IsNullOrEmpty(IniServerName))
                {
                    this.ServerName = IniServerName;
                }
                else
                {
                    throw new BuildException("Remote compiling requires a server name. Use the editor (Project Settings > IOS) to set up your remote compilation settings.");
                }

                // Parse the username
                string IniUserName;
                if (Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "RSyncUsername", out IniUserName) && !String.IsNullOrEmpty(IniUserName))
                {
                    this.UserName = IniUserName;
                }
            }

            // Split port out from the server name
            int PortIdx = ServerName.LastIndexOf(':');

            if (PortIdx != -1)
            {
                string Port = ServerName.Substring(PortIdx + 1);
                if (!int.TryParse(Port, out ServerPort))
                {
                    throw new BuildException("Unable to parse port number from '{0}'", ServerName);
                }
                ServerName = ServerName.Substring(0, PortIdx);
            }

            // If a user name is not set, use the current user
            if (String.IsNullOrEmpty(UserName))
            {
                UserName = Environment.UserName;
            }

            // Print out the server info
            Log.TraceInformation("[Remote] Using remote server '{0}' on port {1} (user '{2}')", ServerName, ServerPort, UserName);

            // Get the path to the SSH private key
            string OverrideSshPrivateKeyPath;

            if (Ini.GetString("/Script/IOSRuntimeSettings.IOSRuntimeSettings", "SSHPrivateKeyOverridePath", out OverrideSshPrivateKeyPath) && !String.IsNullOrEmpty(OverrideSshPrivateKeyPath))
            {
                SshPrivateKey = new FileReference(OverrideSshPrivateKeyPath);
                if (!FileReference.Exists(SshPrivateKey))
                {
                    throw new BuildException("SSH private key specified in config file ({0}) does not exist.", SshPrivateKey);
                }
            }

            // If it's not set, look in the standard locations. If that fails, spawn the batch file to generate one.
            if (SshPrivateKey == null && !TryGetSshPrivateKey(out SshPrivateKey))
            {
                Log.TraceWarning("No SSH private key found for {0}@{1}. Launching SSH to generate one.", UserName, ServerName);

                StringBuilder CommandLine = new StringBuilder();
                CommandLine.AppendFormat("/C \"\"{0}\"", FileReference.Combine(UnrealBuildTool.EngineDirectory, "Build", "BatchFiles", "MakeAndInstallSSHKey.bat"));
                CommandLine.AppendFormat(" \"{0}\"", SshExe);
                CommandLine.AppendFormat(" \"{0}\"", ServerPort);
                CommandLine.AppendFormat(" \"{0}\"", RsyncExe);
                CommandLine.AppendFormat(" \"{0}\"", UserName);
                CommandLine.AppendFormat(" \"{0}\"", ServerName);
                CommandLine.AppendFormat(" \"{0}\"", DirectoryReference.GetSpecialFolder(Environment.SpecialFolder.MyDocuments));
                CommandLine.AppendFormat(" \"{0}\"", GetLocalCygwinPath(DirectoryReference.GetSpecialFolder(Environment.SpecialFolder.MyDocuments)));
                CommandLine.AppendFormat(" \"{0}\"", UnrealBuildTool.EngineDirectory);
                CommandLine.Append("\"");

                using (Process ChildProcess = Process.Start("C:\\Windows\\System32\\Cmd.exe", CommandLine.ToString()))
                {
                    ChildProcess.WaitForExit();
                }

                if (!TryGetSshPrivateKey(out SshPrivateKey))
                {
                    throw new BuildException("Failed to generate SSH private key for {0}@{1}.", UserName, ServerName);
                }
            }

            // resolve the rest of the strings
            RsyncAuthentication = ExpandVariables(RsyncAuthentication);
            SshAuthentication   = ExpandVariables(SshAuthentication);

            // Get the remote base directory
            RemoteBaseDir = String.Format("/Users/{0}/UE4/Builds/{1}", UserName, Environment.MachineName);

            // Build the list of directory mappings between the local and remote machines
            Mappings = new List <RemoteMapping>();
            Mappings.Add(new RemoteMapping(UnrealBuildTool.EngineDirectory, GetRemotePath(UnrealBuildTool.EngineDirectory)));
            if (ProjectFile != null && !ProjectFile.IsUnderDirectory(UnrealBuildTool.EngineDirectory))
            {
                Mappings.Add(new RemoteMapping(ProjectFile.Directory, GetRemotePath(ProjectFile.Directory)));
            }

            // Build a list of arguments for SSH
            CommonSshArguments = new List <string>();
            CommonSshArguments.Add("-o BatchMode=yes");
            CommonSshArguments.Add(SshAuthentication);
            CommonSshArguments.Add(String.Format("-p {0}", ServerPort));
            CommonSshArguments.Add(String.Format("\"{0}@{1}\"", UserName, ServerName));

            // Build a list of arguments for Rsync
            CommonRsyncArguments = new List <string>();
            CommonRsyncArguments.Add("--compress");
            CommonRsyncArguments.Add("--recursive");
            CommonRsyncArguments.Add("--delete");            // Delete anything not in the source directory
            CommonRsyncArguments.Add("--delete-excluded");   // Delete anything not in the source directory
            CommonRsyncArguments.Add("--times");             // Preserve modification times
            CommonRsyncArguments.Add("--verbose");
            CommonRsyncArguments.Add("-m");
            CommonRsyncArguments.Add("--chmod=ug=rwX,o=rxX");
            CommonRsyncArguments.Add(String.Format("--rsh=\"{0} -p {1}\"", RsyncAuthentication, ServerPort));
        }
Esempio n. 29
0
 private ConfigHierarchy GetConfigCacheIni(ConfigHierarchyType Type)
 {
     // @todo Lumin: So - this is the problem with subclassing a platform currently - ini files. Lumin will use Android ini files
     // until I finish and get code over from another branch (key letter Q) that allows for insertion of a subclassed ini platform thing
     return(ConfigCache.ReadHierarchy(Type, DirectoryReference.FromFile(ProjectFile), UnrealTargetPlatform.Android));
 }
        /// <summary>
        /// Parse crypto settings from INI file
        /// </summary>
        public static CryptoSettings ParseCryptoSettings(DirectoryReference InProjectDirectory, UnrealTargetPlatform InTargetPlatform)
        {
            CryptoSettings Settings = new CryptoSettings();

            ConfigHierarchy Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Engine, InProjectDirectory, InTargetPlatform);

            Ini.GetBool("PlatformCrypto", "PlatformRequiresDataCrypto", out Settings.bDataCryptoRequired);
            Ini.GetBool("PlatformCrypto", "PakSigningRequired", out Settings.PakSigningRequired);
            Ini.GetBool("PlatformCrypto", "PakEncryptionRequired", out Settings.PakEncryptionRequired);

            {
                // Start by parsing the legacy encryption.ini settings
                Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Encryption, InProjectDirectory, InTargetPlatform);
                Ini.GetBool("Core.Encryption", "SignPak", out Settings.bEnablePakSigning);

                string[] SigningKeyStrings = new string[3];
                Ini.GetString("Core.Encryption", "rsa.privateexp", out SigningKeyStrings[0]);
                Ini.GetString("Core.Encryption", "rsa.modulus", out SigningKeyStrings[1]);
                Ini.GetString("Core.Encryption", "rsa.publicexp", out SigningKeyStrings[2]);

                if (String.IsNullOrEmpty(SigningKeyStrings[0]) || String.IsNullOrEmpty(SigningKeyStrings[1]) || String.IsNullOrEmpty(SigningKeyStrings[2]))
                {
                    SigningKeyStrings = null;
                }
                else
                {
                    Settings.SigningKey = new SigningKeyPair();
                    Settings.SigningKey.PrivateKey.Exponent = ParseHexStringToByteArray(ProcessSigningKeyInputStrings(SigningKeyStrings[0]), 64);
                    Settings.SigningKey.PrivateKey.Modulus  = ParseHexStringToByteArray(ProcessSigningKeyInputStrings(SigningKeyStrings[1]), 64);
                    Settings.SigningKey.PublicKey.Exponent  = ParseHexStringToByteArray(ProcessSigningKeyInputStrings(SigningKeyStrings[2]), 64);
                    Settings.SigningKey.PublicKey.Modulus   = Settings.SigningKey.PrivateKey.Modulus;

                    if ((Settings.SigningKey.PrivateKey.Exponent.Length > 64) ||
                        (Settings.SigningKey.PrivateKey.Modulus.Length > 64) ||
                        (Settings.SigningKey.PublicKey.Exponent.Length > 64) ||
                        (Settings.SigningKey.PublicKey.Modulus.Length > 64))
                    {
                        throw new Exception(string.Format("[{0}] Signing keys parsed from encryption.ini are too long. They must be a maximum of 64 bytes long!", InProjectDirectory));
                    }
                }

                Ini.GetBool("Core.Encryption", "EncryptPak", out Settings.bEnablePakIndexEncryption);
                Settings.bEnablePakFullAssetEncryption = false;
                Settings.bEnablePakUAssetEncryption    = false;
                Settings.bEnablePakIniEncryption       = Settings.bEnablePakIndexEncryption;

                string EncryptionKeyString;
                Ini.GetString("Core.Encryption", "aes.key", out EncryptionKeyString);
                Settings.EncryptionKey = new EncryptionKey();

                if (EncryptionKeyString.Length > 0)
                {
                    if (EncryptionKeyString.Length < 32)
                    {
                        Log.WriteLine(LogEventType.Warning, "AES key parsed from encryption.ini is too short. It must be 32 bytes, so will be padded with 0s, giving sub-optimal security!");
                    }
                    else if (EncryptionKeyString.Length > 32)
                    {
                        Log.WriteLine(LogEventType.Warning, "AES key parsed from encryption.ini is too long. It must be 32 bytes, so will be truncated!");
                    }

                    Settings.EncryptionKey.Key = ParseAnsiStringToByteArray(EncryptionKeyString, 32);
                }
            }

            Ini = ConfigCache.ReadHierarchy(ConfigHierarchyType.Crypto, InProjectDirectory, InTargetPlatform);
            string SectionName = "/Script/CryptoKeys.CryptoKeysSettings";
            ConfigHierarchySection CryptoSection = Ini.FindSection(SectionName);

            // If we have new format crypto keys, read them in over the top of the legacy settings
            if (CryptoSection != null && CryptoSection.KeyNames.Count() > 0)
            {
                Ini.GetBool(SectionName, "bEnablePakSigning", out Settings.bEnablePakSigning);
                Ini.GetBool(SectionName, "bEncryptPakIniFiles", out Settings.bEnablePakIniEncryption);
                Ini.GetBool(SectionName, "bEncryptPakIndex", out Settings.bEnablePakIndexEncryption);
                Ini.GetBool(SectionName, "bEncryptUAssetFiles", out Settings.bEnablePakUAssetEncryption);
                Ini.GetBool(SectionName, "bEncryptAllAssetFiles", out Settings.bEnablePakFullAssetEncryption);

                // Parse encryption key
                string EncryptionKeyString;
                Ini.GetString(SectionName, "EncryptionKey", out EncryptionKeyString);
                if (!string.IsNullOrEmpty(EncryptionKeyString))
                {
                    Settings.EncryptionKey      = new EncryptionKey();
                    Settings.EncryptionKey.Key  = System.Convert.FromBase64String(EncryptionKeyString);
                    Settings.EncryptionKey.Guid = Guid.Empty.ToString();
                    Settings.EncryptionKey.Name = "Embedded";
                }

                // Parse secondary encryption keys
                List <EncryptionKey> SecondaryEncryptionKeys = new List <EncryptionKey>();
                List <string>        SecondaryEncryptionKeyStrings;

                if (Ini.GetArray(SectionName, "SecondaryEncryptionKeys", out SecondaryEncryptionKeyStrings))
                {
                    foreach (string KeySource in SecondaryEncryptionKeyStrings)
                    {
                        EncryptionKey NewKey = new EncryptionKey();
                        SecondaryEncryptionKeys.Add(NewKey);

                        Regex Search = new Regex("\\(Guid=(?\'Guid\'.*),Name=\\\"(?\'Name\'.*)\\\",Key=\\\"(?\'Key\'.*)\\\"\\)");
                        Match Match  = Search.Match(KeySource);
                        if (Match.Success)
                        {
                            foreach (string GroupName in Search.GetGroupNames())
                            {
                                string Value = Match.Groups[GroupName].Value;
                                if (GroupName == "Guid")
                                {
                                    NewKey.Guid = Value;
                                }
                                else if (GroupName == "Name")
                                {
                                    NewKey.Name = Value;
                                }
                                else if (GroupName == "Key")
                                {
                                    NewKey.Key = System.Convert.FromBase64String(Value);
                                }
                            }
                        }
                    }
                }

                Settings.SecondaryEncryptionKeys = SecondaryEncryptionKeys.ToArray();

                // Parse signing key
                string PrivateExponent, PublicExponent, Modulus;
                Ini.GetString(SectionName, "SigningPrivateExponent", out PrivateExponent);
                Ini.GetString(SectionName, "SigningModulus", out Modulus);
                Ini.GetString(SectionName, "SigningPublicExponent", out PublicExponent);

                if (!String.IsNullOrEmpty(PrivateExponent) && !String.IsNullOrEmpty(PublicExponent) && !String.IsNullOrEmpty(Modulus))
                {
                    Settings.SigningKey = new SigningKeyPair();
                    Settings.SigningKey.PublicKey.Exponent  = System.Convert.FromBase64String(PublicExponent);
                    Settings.SigningKey.PublicKey.Modulus   = System.Convert.FromBase64String(Modulus);
                    Settings.SigningKey.PrivateKey.Exponent = System.Convert.FromBase64String(PrivateExponent);
                    Settings.SigningKey.PrivateKey.Modulus  = Settings.SigningKey.PublicKey.Modulus;
                }
            }

            // Parse project dynamic keychain keys
            if (InProjectDirectory != null)
            {
                ConfigHierarchy GameIni = ConfigCache.ReadHierarchy(ConfigHierarchyType.Game, InProjectDirectory, InTargetPlatform);
                if (GameIni != null)
                {
                    string Filename;
                    if (GameIni.GetString("ContentEncryption", "ProjectKeyChain", out Filename))
                    {
                        FileReference ProjectKeyChainFile = FileReference.Combine(InProjectDirectory, "Content", Filename);
                        if (FileReference.Exists(ProjectKeyChainFile))
                        {
                            List <EncryptionKey> EncryptionKeys = new List <EncryptionKey>();

                            if (Settings.SecondaryEncryptionKeys != null)
                            {
                                EncryptionKeys.AddRange(Settings.SecondaryEncryptionKeys);
                            }

                            string[] Lines = FileReference.ReadAllLines(ProjectKeyChainFile);
                            foreach (string Line in Lines)
                            {
                                string[] KeyParts = Line.Split(':');
                                if (KeyParts.Length == 4)
                                {
                                    EncryptionKey NewKey = new EncryptionKey();

                                    NewKey.Name = KeyParts[0];
                                    NewKey.Guid = KeyParts[2];
                                    NewKey.Key  = System.Convert.FromBase64String(KeyParts[3]);

                                    EncryptionKey ExistingKey = EncryptionKeys.Find((EncryptionKey OtherKey) => { return(OtherKey.Guid == NewKey.Guid); });
                                    if (ExistingKey != null && !CompareKey(ExistingKey.Key, NewKey.Key))
                                    {
                                        throw new Exception("Found multiple encryption keys with the same guid but different AES keys while merging secondary keys from the project key-chain!");
                                    }

                                    EncryptionKeys.Add(NewKey);
                                }
                            }

                            Settings.SecondaryEncryptionKeys = EncryptionKeys.ToArray();
                        }
                    }
                }
            }

            if (!Settings.bDataCryptoRequired)
            {
                CryptoSettings NewSettings = new CryptoSettings();
                NewSettings.SecondaryEncryptionKeys = Settings.SecondaryEncryptionKeys;
                Settings = NewSettings;
            }
            else
            {
                if (!Settings.PakSigningRequired)
                {
                    Settings.bEnablePakSigning = false;
                    Settings.SigningKey        = null;
                }

                if (!Settings.PakEncryptionRequired)
                {
                    Settings.bEnablePakFullAssetEncryption = false;
                    Settings.bEnablePakIndexEncryption     = false;
                    Settings.bEnablePakIniEncryption       = false;
                    Settings.EncryptionKey = null;
                    Settings.SigningKey    = null;
                }
            }

            // Check if we have a valid signing key that is of the old short form
            if (Settings.SigningKey != null && Settings.SigningKey.IsValid() && Settings.SigningKey.IsUnsecureLegacyKey())
            {
                Log.TraceWarningOnce("Project signing keys found in '{0}' are of the old insecure short format. Please regenerate them using the project crypto settings panel in the editor!", InProjectDirectory);
            }

            // Validate the settings we have read
            if (Settings.bDataCryptoRequired && Settings.bEnablePakSigning && (Settings.SigningKey == null || !Settings.SigningKey.IsValid()))
            {
                Log.TraceWarningOnce("Pak signing is enabled, but no valid signing keys were found. Please generate a key in the editor project crypto settings. Signing will be disabled");
                Settings.bEnablePakSigning = false;
            }

            if (Settings.bDataCryptoRequired && Settings.IsAnyEncryptionEnabled() && (Settings.EncryptionKey == null || !Settings.EncryptionKey.IsValid()))
            {
                Log.TraceWarningOnce("Pak encryption is enabled, but no valid encryption key was found. Please generate a key in the editor project crypto settings. Encryption will be disabled");
                Settings.bEnablePakUAssetEncryption    = false;
                Settings.bEnablePakFullAssetEncryption = false;
                Settings.bEnablePakIndexEncryption     = false;
                Settings.bEnablePakIniEncryption       = false;
            }

            return(Settings);
        }