Esempio n. 1
0
 /// <summary>
 ///   Invokes the HCE executable.
 /// </summary>
 private static void InvokeExecutable(Executable executable)
 {
     executable.Start();
 }
Esempio n. 2
0
        /// <summary>
        ///   Invokes the HCE loading procedure.
        /// </summary>
        public static void Bootstrap(Executable executable)
        {
            var configuration = (Configuration)Files.Configuration;

            if (!configuration.Exists())
            {
                configuration.Save(); /* gracefully create new configuration */
            }
            configuration.Load();

            if (!configuration.Kernel.SkipVerifyMainAssets)
            {
                VerifyMainAssets();
            }
            else
            {
                Info("Skipping Kernel.VerifyMainAssets");
            }

            if (!configuration.Kernel.SkipInvokeCoreTweaks)
            {
                InvokeCoreTweaks(executable);
            }
            else
            {
                Info("Skipping Kernel.InvokeCoreTweaks");
            }

            if (!configuration.Kernel.SkipResumeCheckpoint)
            {
                ResumeCheckpoint(executable);
            }
            else
            {
                Info("Skipping Kernel.ResumeCheckpoint");
            }

            if (!configuration.Kernel.SkipSetShadersConfig)
            {
                SetShadersConfig(configuration);
            }
            else
            {
                Info("Skipping Kernel.SkipSetShadersConfig");
            }

            if (!configuration.Kernel.SkipPatchLargeAAware)
            {
                PatchLargeAAware(executable);
            }
            else
            {
                Info("Skipping Kernel.SkipPatchLargeAAware");
            }

            if (!configuration.Kernel.SkipInvokeExecutable)
            {
                InvokeExecutable(executable);
            }
            else
            {
                Info("Skipping Kernel.InvokeExecutable");
            }
        }
Esempio n. 3
0
        /// <summary>
        ///   Console API to the HXE kernel, installer and compiler.
        /// </summary>
        /// <param name="args">
        ///   --config            Opens configuration GUI
        ///   --load              Initiates HCE/SPV3
        ///   --install=VALUE     Installs HCE/SPV3   to destination
        ///   --compile=VALUE     Compiles HCE/SPV3   to destination
        ///   --console           Loads HCE           with console mode
        ///   --devmode           Loads HCE           with developer mode
        ///   --screenshot        Loads HCE           with screenshot ability
        ///   --window            Loads HCE           in window mode
        ///   --nogamma           Loads HCE           without gamma overriding
        ///   --adapter=VALUE     Loads HCE           on monitor X
        ///   --path=VALUE        Loads HCE           with custom profile path
        ///   --vidmode=VALUE     Loads HCE           with video mode
        /// </param>
        private static void InvokeProgram(string[] args)
        {
            Directory.CreateDirectory(Paths.Directory);

            var help       = false;        /* Displays commands list              */
            var config     = false;        /* Opens configuration GUI             */
            var positions  = false;        /* Opens positions GUI                 */
            var install    = string.Empty; /* Installs HCE/SPV3 to destination    */
            var compile    = string.Empty; /* Compiles HCE/SPV3 to destination    */
            var update     = string.Empty; /* Updates directory using manifest    */
            var registry   = string.Empty; /* Write to Windows Registry           */
            var infer      = false;        /* Infer the running Halo executable   */
            var console    = false;        /* Loads HCE with console mode         */
            var devmode    = false;        /* Loads HCE with developer mode       */
            var screenshot = false;        /* Loads HCE with screenshot ability   */
            var window     = false;        /* Loads HCE in window mode            */
            var nogamma    = false;        /* Loads HCE without gamma overriding  */
            var adapter    = string.Empty; /* Loads HCE on monitor X              */
            var path       = string.Empty; /* Loads HCE with custom profile path  */
            var exec       = string.Empty; /* Loads HCE with custom init file     */
            var vidmode    = string.Empty; /* Loads HCE with custom res. and Hz   */
            var refresh    = string.Empty; /* Loads HCE with custom refresh rate  */

            var options = new OptionSet()
                          .Add("help", "Displays commands list", s => help                  = s != null)                 /* hxe command   */
                          .Add("config", "Opens configuration GUI", s => config             = s != null)                 /* hxe command   */
                          .Add("positions", "Opens positions GUI", s => positions           = s != null)                 /* hxe command   */
                          .Add("install=", "Installs HCE/SPV3 to destination", s => install = s)                         /* hxe parameter */
                          .Add("compile=", "Compiles HCE/SPV3 to destination", s => compile = s)                         /* hxe parameter */
                          .Add("update=", "Updates directory using manifest", s => update   = s)                         /* hxe parameter */
                          .Add("registry=", "Create Registry keys for Retail, Custom, Trial, or HEK", s => registry = s) /* hxe parameter */
                          .Add("infer", "Infer the running Halo executable", s => infer           = s != null)           /* hxe parameter */
                          .Add("console", "Loads HCE with console mode", s => console             = s != null)           /* hce parameter */
                          .Add("devmode", "Loads HCE with developer mode", s => devmode           = s != null)           /* hce parameter */
                          .Add("screenshot", "Loads HCE with screenshot ability", s => screenshot = s != null)           /* hce parameter */
                          .Add("window", "Loads HCE in window mode", s => window              = s != null)               /* hce parameter */
                          .Add("nogamma", "Loads HCE without gamma overriding", s => nogamma  = s != null)               /* hce parameter */
                          .Add("adapter=", "Loads HCE on monitor X", s => adapter             = s)                       /* hce parameter */
                          .Add("path=", "Loads HCE with custom profile path", s => path       = s)                       /* hce parameter */
                          .Add("exec=", "Loads HCE with custom init file", s => exec          = s)                       /* hce parameter */
                          .Add("vidmode=", "Loads HCE with custom res. and Hz", s => vidmode  = s)                       /* hce parameter */
                          .Add("refresh=", "Loads HCE with custom refresh rate", s => refresh = s);                      /* hce parameter */

            var input = options.Parse(args);

            foreach (var i in input)
            {
                Info("Discovered CLI command: " + i);
            }

            var hce = new Executable();

            if (help)
            {
                options.WriteOptionDescriptions(Out);
                Exit(0);
            }

            if (config)
            {
                new Application().Run(new Settings());
                Exit(0);
            }

            if (positions)
            {
                new Application().Run(new Positions());
                Exit(0);
            }

            if (infer)
            {
                var descriptions = new Dictionary <Process.Type, string>
                {
                    { Process.Type.Unknown, "N/A" },
                    { Process.Type.Retail, "Halo: Combat Evolved" },
                    { Process.Type.HCE, "Halo: Custom Edition" },
                    { Process.Type.Steam, "Halo: MCC - CEA (Steam)" },
                    { Process.Type.Store, "Halo: MCC - CEA (Store)" },
                };

                Info($"Inferred the following Halo process: {descriptions[Process.Infer()]}");
                Info("Press any key to exit.");
                ReadLine();
                Exit(0);
            }

            if (!string.IsNullOrWhiteSpace(install))
            {
                Run(() =>
                {
                    SFX.Extract(new SFX.Configuration
                    {
                        Target = new DirectoryInfo(install)
                    });
                });
            }

            if (!string.IsNullOrWhiteSpace(compile))
            {
                Run(() =>
                {
                    SFX.Compile(new SFX.Configuration
                    {
                        Source = new DirectoryInfo(CurrentDirectory),
                        Target = new DirectoryInfo(compile)
                    });
                });
            }

            if (!string.IsNullOrWhiteSpace(update))
            {
                Run(() =>
                {
                    var updateModule = new Update();
                    updateModule.Import(update);
                    updateModule.Commit();
                });
            }

            if (!string.IsNullOrWhiteSpace(registry))
            {
            }



            /**
             * Implicit verification for legal HCE installations.
             */

            try
            {
                hce = Executable.Detect();
            }
            catch (Exception e)
            {
                var msg = " -- Legal copy of HCE needs to be installed for loading!\n Error:  " + e.ToString() + "\n";
                var log = (File)Paths.Exception;
                log.AppendAllText(msg);
                Error(msg);
            }

            if (console)
            {
                hce.Debug.Console = true;
            }

            if (devmode)
            {
                hce.Debug.Developer = true;
            }

            if (screenshot)
            {
                hce.Debug.Screenshot = true;
            }

            if (window)
            {
                hce.Video.Window = true;
            }

            if (nogamma)
            {
                hce.Video.NoGamma = true;
            }

            if (!string.IsNullOrWhiteSpace(adapter))
            {
                hce.Video.Adapter = byte.Parse(adapter);
            }

            if (!string.IsNullOrWhiteSpace(path))
            {
                hce.Profile.Path = path;
            }

            if (!string.IsNullOrWhiteSpace(exec))
            {
                hce.Debug.Initiation = exec;
            }

            if (!string.IsNullOrWhiteSpace(vidmode))
            {
                var a = vidmode.Split(',');

                if (a.Length < 2)
                {
                    return;
                }

                hce.Video.DisplayMode = true;
                hce.Video.Width       = ushort.Parse(a[0]);
                hce.Video.Height      = ushort.Parse(a[1]);

                if (a.Length > 2) /* optional refresh rate */
                {
                    hce.Video.Refresh = ushort.Parse(a[2]);
                }
            }

            if (!string.IsNullOrWhiteSpace(refresh))
            {
                hce.Video.Refresh = ushort.Parse(refresh);
            }

            /**
             * Implicitly invoke the HXE kernel with the HCE loading procedure.
             */

            Run(() => { Kernel.Invoke(hce); });

            /**
             * This method is used for running code asynchronously and catching exceptions at the highest level.
             */

            void Run(Action action)
            {
                try
                {
                    Task.Run(action).GetAwaiter().GetResult();
                    WithCode(Code.Success);
                }
                catch (Exception e)
                {
                    var msg = " -- EXEC.START HALTED\n Error:  " + e.ToString() + "\n";
                    var log = (File)Paths.Exception;
                    log.AppendAllText(msg);
                    Error(msg);
                    System.Console.Error.WriteLine("\n\n" + e.StackTrace);
                    WithCode(Code.Exception);
                }
            }
        }
Esempio n. 4
0
        /// <summary>
        ///   Console API to the HXE kernel, installer and compiler.
        /// </summary>
        /// <param name="args">
        ///   --config            Opens configuration GUI
        ///   --load              Initiates HCE/SPV3
        ///   --install=VALUE     Installs HCE/SPV3   to destination
        ///   --compile=VALUE     Compiles HCE/SPV3   to destination
        ///   --console           Loads HCE           with console    mode
        ///   --devmode           Loads HCE           with developer  mode
        ///   --screenshot        Loads HCE           with screenshot ability
        ///   --window            Loads HCE in window mode
        ///   --nogamma           Loads HCE           without gamma overriding
        ///   --adapter=VALUE     Loads HCE           on monitor    X
        ///   --path=VALUE        Loads HCE           with custom   profile path
        ///   --vidmode=VALUE     Loads HCE           with video    mode
        /// </param>
        private static void InvokeProgram(string[] args)
        {
            Directory.CreateDirectory(Paths.Directory);

            var hce = new Executable();

            /**
             * Implicit verification for legal HCE installations.
             */

            try
            {
                hce = Executable.Detect();
            }
            catch (Exception e)
            {
                Error(e.Message + " -- Legal copy of HCE needs to be installed for loading!");
            }

            var options = new OptionSet()
                          .Add("config", "Opens configuration GUI",
                               s =>
            {
                new Application().Run(new Settings());
                Exit(0);
            }
                               )
                          .Add("positions", "Opens positions GUI",
                               s =>
            {
                new Application().Run(new Positions());
                Exit(0);
            })
                          .Add("load", "Initiates HCE/SPV3",
                               s => Run(() => { Kernel.Bootstrap(hce); }))
                          .Add("install=", "Installs HCE/SPV3 to destination",
                               s => Run(() => { Installer.Install(CurrentDirectory, s); }))
                          .Add("compile=", "Compiles HCE/SPV3 to destination",
                               s => Run(() => { Compiler.Compile(CurrentDirectory, s); }))
                          .Add("update=", "Updates directory using manifest",
                               s => Run(() =>
            {
                var update = new Update();
                update.Import(s);
                update.Commit();
            }))
                          .Add("console", "Loads HCE with console mode",
                               s => hce.Debug.Console = true)
                          .Add("devmode", "Loads HCE with developer mode",
                               s => hce.Debug.Developer = true)
                          .Add("screenshot", "Loads HCE with screenshot ability",
                               s => hce.Debug.Screenshot = true)
                          .Add("window", "Loads HCE in window mode",
                               s => hce.Video.Window = true)
                          .Add("nogamma", "Loads HCE without gamma overriding",
                               s => hce.Video.NoGamma = true)
                          .Add("adapter=", "Loads HCE on monitor X",
                               s => hce.Video.Adapter = ushort.Parse(s))
                          .Add("path=", "Loads HCE with custom profile path",
                               s => hce.Profile.Path = s)
                          .Add("vidmode=", "Loads HCE with video mode",
                               s =>
            {
                var a = s.Split(',');

                if (a.Length < 2)
                {
                    return;
                }

                hce.Video.Width  = ushort.Parse(a[0]);
                hce.Video.Height = ushort.Parse(a[1]);

                if (a.Length > 2) /* optional refresh rate */
                {
                    hce.Video.Refresh = ushort.Parse(a[2]);
                }
            });

            var input = options.Parse(args);

            /**
             * Implicitly invoke the HXE kernel when no install/compile/load/update command is passed.
             */

            if (!input.Contains("load") &&
                !input.Contains("install") &&
                !input.Contains("compile") &&
                !input.Contains("update"))
            {
                Run(() => { Kernel.Bootstrap(hce); });
            }

            /**
             * This method is used for running code asynchronously and catching exceptions at the highest level.
             */

            void Run(Action action)
            {
                try
                {
                    Task.Run(action).GetAwaiter().GetResult();
                    WithCode(Code.Success);
                }
                catch (Exception e)
                {
                    Error(e.Message);
                    System.Console.Error.WriteLine("\n\n" + e.StackTrace);
                    WriteAllText(Paths.Exception, e.ToString());
                    WithCode(Code.Exception);
                }
            }
        }
Esempio n. 5
0
        /// <summary>
        ///   Invokes core improvements to the auto-detected profile, such as auto max resolution and gamma fixes. This is
        ///   NOT done when a profile does not exist/cannot be found!
        /// </summary>
        /// <param name="executable"></param>
        private static void InvokeCoreTweaks(Executable executable)
        {
            try
            {
                if (executable.Video.Width == 0 && executable.Video.Height == 0)
                {
                    executable.Video.Width  = (ushort)PrimaryScreen.Bounds.Width;
                    executable.Video.Height = (ushort)PrimaryScreen.Bounds.Height;

                    Info("Dimensions not specified - applied native resolution");
                    Info("Executable -vidmode width  - " + executable.Video.Width);
                    Info("Executable -vidmode height - " + executable.Video.Height);
                }

                var lastprof = (LastProfile)Custom.LastProfile(executable.Profile.Path);

                if (!lastprof.Exists())
                {
                    return;
                }

                lastprof.Load();

                Info("Deserialised found lastprof file");

                var profile = (Profile)Custom.Profile(executable.Profile.Path, lastprof.Profile);

                if (!profile.Exists())
                {
                    return;
                }

                profile.Load();

                Info("Deserialised inferred HCE profile");

                foreach (var availableProfile in Profile.List(executable.Profile.Path))
                {
                    Debug(availableProfile.Details.Name.Equals(profile.Details.Name)
            ? $"Available profile: {availableProfile.Details.Name} << SELECTED PROFILE"
            : $"Available profile: {availableProfile.Details.Name}");
                }

                profile.Video.Resolution.Width  = executable.Video.Width;
                profile.Video.Resolution.Height = executable.Video.Height;
                profile.Video.FrameRate         = VideoFrameRate.VsyncOff; /* ensure no FPS locking */
                profile.Video.Particles         = VideoParticles.High;
                profile.Video.Quality           = VideoQuality.High;
                profile.Video.Effects.Specular  = true;
                profile.Video.Effects.Shadows   = true;
                profile.Video.Effects.Decals    = true;

                Info("Applied profile video patches");

                profile.Audio.Quality = AudioQuality.High;
                profile.Audio.Variety = AudioVariety.High;

                if (Exists(DSOAL) && Exists(DSOUND) && Exists(ALSoft))
                {
                    profile.Audio.HWA = true;
                    profile.Audio.EAX = true;
                }
                else
                {
                    profile.Audio.HWA = false;
                    profile.Audio.EAX = false;
                }

                Info("Applied profile audio patches");

                profile.Save();
                profile.Load();

                Info("Saved profile data to the filesystem");

                Debug("Patched video resolution width  - " + profile.Video.Resolution.Width);
                Debug("Patched video resolution height - " + profile.Video.Resolution.Height);
                Debug("Patched video frame rate        - " + profile.Video.FrameRate);
                Debug("Patched video quality           - " + profile.Video.Particles);
                Debug("Patched video texture           - " + profile.Video.Quality);
                Debug("Patched video effect - specular - " + profile.Video.Effects.Specular);
                Debug("Patched video effect - shadows  - " + profile.Video.Effects.Shadows);
                Debug("Patched video effect - decals   - " + profile.Video.Effects.Decals);
                Debug("Patched audio quality           - " + profile.Audio.Quality);
                Debug("Patched audio variety           - " + profile.Audio.Variety);
            }
            catch (Exception e)
            {
                Error(e.Message + " -- CORE TWEAKS WILL NOT BE APPLIED");
            }
        }
Esempio n. 6
0
        /// <summary>
        ///   Invokes the HCE loading procedure.
        /// </summary>
        public static void Bootstrap(Executable executable)
        {
            var configuration = (Configuration)Paths.Configuration;

            if (!configuration.Exists())
            {
                configuration.Save(); /* gracefully create new configuration */
            }
            configuration.Load();

            if (!configuration.Kernel.SkipVerifyMainAssets)
            {
                VerifyMainAssets();
            }
            else
            {
                Info("Skipped VerifyMainAssets");
            }

            if (configuration.Kernel.EnableSpv3KernelMode)
            {
                if (!configuration.Kernel.SkipInvokeCoreTweaks)
                {
                    InvokeCoreTweaks(executable);
                }
                else
                {
                    Info("Skipped InvokeCoreTweaks");
                }

                if (!configuration.Kernel.SkipResumeCheckpoint)
                {
                    ResumeCheckpoint(executable);
                }
                else
                {
                    Info("Skipped ResumeCheckpoint");
                }
                if (configuration.Kernel.EnableSpv3LegacyMode)
                {
                    SetSpv31InitMode(configuration);
                    Info("Enabled SPV3.1 initiation mode");
                }
                else
                {
                    if (!configuration.Kernel.SkipSetInitcContents)
                    {
                        SetInitcContents(configuration);
                    }
                    else
                    {
                        Info("Skipped SetInitcContents");
                    }
                }
            }
            else
            {
                Info("Skipped EnableSpv3KernelMode");
            }

            if (!configuration.Kernel.SkipPatchLargeAAware)
            {
                PatchLargeAAware(executable);
            }
            else
            {
                Info("Skipped PatchLargeAAware");
            }

            if (!configuration.Kernel.SkipInvokeExecutable)
            {
                InvokeExecutable(executable);
            }
            else
            {
                Info("Skipped InvokeExecutable");
            }
        }
Esempio n. 7
0
        /// <summary>
        ///   Loads inbound HCE executable with the inbound configuration.
        /// </summary>
        /// <param name="executable">
        ///   Object representing a legal HCE executable.
        /// </param>
        /// <param name="configuration">
        ///   Object representing the kernel configuration.
        /// </param>
        public static void Invoke(Executable executable, Configuration configuration)
        {
            /* Clear log file */
            {
                if (Exists(Paths.Exception) && new FileInfo(Paths.Exception).Length > 1048576) // If larger than 1 MiB, ...
                {
                    System.IO.File.WriteAllText(Paths.Exception, "");                          // ...clear log.
                }
            }

            /* Switch to legacy kernel modes */
            {
                if (!Exists(Legacy))
                {
                    configuration.Mode = Configuration.ConfigurationMode.SPV33;
                }
            }

            Init(); /* initc.txt declarations */
            Blam(); /* blam.sav enhancements  */
            Open(); /* opensauce declarations */
            Exec(); /* haloce.exe invocation  */

            Core("CORE.MAIN: Successfully updated the initiation, profile and OS files, and invoked the HCE executable.");

            /**
             * We declare the contents of the initiation file in this method before dealing with the profile enhancements and
             * the executable invocation. It's the most important task, so we have to deal with it first.
             *
             * The values declared by the HXE kernel for the initiation file are categorised into the following sections:
             *
             * -   RESUME: Campaign resuming support for the SPV3 mod, which permits compatibility with SPV3's main UI;
             * -   TWEAKS: Rudimentary tweaks including cinematic bars, and controller enhancements (magnetism & auto-aim);
             * -   SHADER: SPV3 post-processing configurations, including activated shaders & shader intensity levels.
             */

            void Init()
            {
                var init = (Initiation)GetFullPath(executable.Debug.Initiation);

                Resume(); /* spv3 campaign resume with ui.map compatibility */
                Tweaks(); /* hce/spv3 start-up miscellaneous tweaks         */
                Shader(); /* spv3 post-processing toggles & settings        */
                Unlock(); /* spv3.1 legacy maps unlocking mechanism         */

                try
                {
                    init.Save();

                    Core("MAIN.INIT: Initiation data has been successfully applied and saved.");
                }
                catch (Exception e)
                {
                    var msg = " -- MAIN.INIT HALTED.\n Error:  " + e.ToString() + "\n";
                    var log = (File)Paths.Exception;
                    log.AppendAllText(msg);
                    Error(msg);
                }

                /**
                 * Resume the campaign based on the progress of the last used profile. This requires:
                 *
                 * -   a LASTPROF.TXT file to be located in the profile path declared for the inbound executable; and
                 * -   the directory for the profile declared in the aforementioned plaintext file; and
                 * -   the savegame.bin for the respective profile, to infer the campaign progress.
                 */

                void Resume()
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV32 &&
                        configuration.Mode != Configuration.ConfigurationMode.SPV33)
                    {
                        return;
                    }

                    try
                    {
                        var lastprof = (LastProfile)Custom.LastProfile(executable.Profile.Path);

                        /** Check if lastprof.txt exists
                         * If it exists, load its data
                         * Else, create a new one
                         */
                        if (lastprof.Exists())
                        {
                            lastprof.Load();
                        }
                        else
                        {
                            Error("Lastprof.txt does not Exist.");
                            Core("Saving LastProf.txt...");
                            lastprof.Save();
                        }

                        var name = lastprof.Profile;
                        var save = (Progress)Custom.Progress(executable.Profile.Path, name);

                        /** Check for the existence of the blam.sav specified by LastProfile.
                         * If it exists, skip this abomination.
                         * Else, create a new player profile
                         *   or search for existing profiles.
                         */
                        if (!save.Exists())
                        {
                            Error("Player Profile specified in LastProfile not found.");
                            var savegames = Custom.Profiles(executable.Profile.Path);

                            /** Check if the Savegames (profiles) folder exists.
                             * If it exists, search for existing profiles.
                             * Else, create a new player profile.
                             */
                            if (Exists(savegames))
                            {
                                List <Profile> profiles      = Profile.List(savegames);
                                List <Profile> validProfiles = new List <Profile> {
                                };

                                /** Check for any existing profile folders
                                 * If any are found, check if their blam.sav also exists.
                                 *  Select the first valid profile.
                                 * Else, create a new player profile.
                                 */
                                if (profiles.Count != 0)
                                {
                                    foreach (Profile profile in profiles)
                                    {
                                        if (profile.Exists())
                                        {
                                            validProfiles.Add(profile); // todo: implement better validation
                                        }
                                    }
                                    lastprof.Profile = validProfiles[0].Details.Name;
                                    lastprof.Save();
                                }
                                else
                                {
                                    Error("No profiles found in savegames folder.");
                                    Core("Generating new profile");
                                    NewProfile.Generate(executable.Profile.Path, lastprof, new Profile(), false);
                                }
                            }
                            else
                            {
                                Error("Savegames folder does not exist.");
                                Core("Creating savegames folder and a new profile...");
                                NewProfile.Generate(executable.Profile.Path, lastprof, new Profile(), false);;
                            }
                            name = lastprof.Profile;
                            save = (Progress)Custom.Progress(executable.Profile.Path, name);
                        }

                        var campaign = new Campaign(Paths.Campaign(configuration.Mode));

                        campaign.Load();
                        save.Load(campaign);

                        init.Progress = save;
                        init.Resume   = campaign.Resume;

                        Core("INIT.RESUME: Campaign checkpoint information has been applied to the initiation file.");

                        Debug("INIT.RESUME: Mission    - " + init.Progress.Mission.Name);
                        Debug("INIT.RESUME: Difficulty - " + init.Progress.Difficulty.Name);
                    }
                    catch (Exception e)
                    {
                        var msg = " -- INIT.RESUME HALTED\n Error:  " + e.ToString() + "\n";
                        var log = (File)Paths.Exception;
                        log.AppendAllText(msg);
                        Error(e.Message + " -- INIT.RESUME HALTED");
                    }
                }

                /**
                 * Rudimentary tweaks including:
                 *
                 * -   Player Auto-aim
                 * -   Player Magnetism
                 * -   Acceleration
                 *
                 * ... and stuff for SPV3:
                 *
                 * -   Cinematic Bars
                 * -   Motion Sensor
                 */

                void Tweaks()
                {
                    init.PlayerAutoaim     = configuration.Tweaks.AutoAim;
                    init.PlayerMagnetism   = configuration.Tweaks.Magnetism;
                    init.MouseAcceleration = configuration.Tweaks.Acceleration;
                    init.Gamma             = configuration.Video.Gamma;

                    if (configuration.Mode == Configuration.ConfigurationMode.SPV32 ||
                        configuration.Mode == Configuration.ConfigurationMode.SPV33)
                    {
                        init.CinemaBars   = configuration.Tweaks.CinemaBars;
                        init.MotionSensor = configuration.Tweaks.Sensor;
                        init.Unload       = configuration.Tweaks.Unload;

                        Core("INIT.TWEAKS: SPV3 cinematic bars, motion sensor and unload tweaks have been updated.");

                        Debug("INIT.TWEAKS: Cinematic Bars - " + init.CinemaBars);
                        Debug("INIT.TWEAKS: Motion Sensor  - " + init.MotionSensor);
                        Debug("INIT.TWEAKS: Unload         - " + init.Unload);
                    }

                    Core("INIT.TWEAKS: Magnetism, auto-aim, and mouse acceleration tweaks have been updated.");

                    Debug("INIT.TWEAKS: Player Auto-aim    - " + init.PlayerAutoaim);
                    Debug("INIT.TWEAKS: Player Magnetism   - " + init.PlayerMagnetism);
                    Debug("INIT.TWEAKS: Mouse Acceleration - " + init.MouseAcceleration);
                    Debug("INIT.TWEAKS: Gamma              - " + init.Gamma);
                }

                /**
                 * SPV3 shader toggles and configurations.
                 */

                void Shader()
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV32 &&
                        configuration.Mode != Configuration.ConfigurationMode.SPV33)
                    {
                        return;
                    }

                    init.Shaders = configuration.Shaders;

                    Core("INIT.SHADER: SPV3 post-processing effects have been assigned to the initiation file.");
                }

                /**
                 * Indeed, SPV3.1 had some DRM I wasn't quite a fan of. This routine unlocks the 3.1 campaigns. Is this a crack?
                 * I should have a demo screen playing here, along with greetings to friends all over the world.
                 *
                 * Idea: Release 3.2 with an NFO file with ANSI art.
                 */

                void Unlock()
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV32)
                    {
                        return;
                    }

                    init.Unlock = true;

                    Core("INIT.UNLOCK: SPV3.1 campaign has been unlocked for subsequent invocation.");
                }
            }

            /**
             * We enhance the player's profile by applying the highest video & audio quality settings, along with forcing the
             * resolution declared in video parameters of the inbound executable.
             *
             * The enhancements are applied based on the provided configuration and the successful inference
             * the last used profile in the specified profiles directory.
             */

            void Blam()
            {
                Profile blam;

                try
                {
                    blam = Profile.Detect(executable.Profile.Path);

                    Video();
                    Audio();
                    Input();

                    blam.Save();

                    Core("MAIN.BLAM: Profile enhancements have been successfully applied and saved.");
                }
                catch (FileNotFoundException)
                {
                    var lastprof = (LastProfile)Custom.LastProfile(executable.Profile.Path);
                    var scaffold = lastprof.Exists() && System.IO.File.Exists(Custom.Profile(executable.Profile.Path, lastprof.Profile));

                    if (!lastprof.Exists())
                    {
                        Core("Lastprof.txt does not exist.");
                    }

                    if (!scaffold)
                    {
                        Debug("Savegames scaffold doesn't exist.");
                    }
                    else
                    {
                        Debug("Savegames scaffold detected.");
                    }

                    Core("Calling LastProfile.Generate()...");
                    NewProfile.Generate(executable.Profile.Path, lastprof, blam = new Profile(), scaffold);
                }
                catch (Exception e)
                {
                    var msg = " -- MAIN.BLAM HALTED\n Error:  " + e.ToString() + "\n";
                    var log = (File)Paths.Exception;
                    log.AppendAllText(msg);
                    Error(msg);
                }

                /**
                 * Apply the resolution specified in video parameters of the inbound executable OR apply the primary screen's
                 * current resolution. This enforces HCE to run at the desired or native resolution, and also obsoletes Ecran.
                 *
                 * Additionally, effects and qualities are enabled and set to the maximum level, respectively. Of course, this
                 * also depends on the provided configuration.
                 */

                void Video()
                {
                    if (!configuration.Video.ResolutionEnabled)
                    {
                        // infer from resolution if Native Resoluton preferred.
                        if (executable.Video.Width == 0 || executable.Video.Height == 0)
                        {
                            executable.Video.Width  = (ushort)PrimaryScreen.Bounds.Width;
                            executable.Video.Height = (ushort)PrimaryScreen.Bounds.Height;

                            Core("BLAM.VIDEO.RESOLUTION: No resolution provided. Applied native resolution to executable.");
                        }
                        else if (executable.Video.Width > (ushort)PrimaryScreen.Bounds.Width ||
                                 executable.Video.Height > (ushort)PrimaryScreen.Bounds.Height)
                        {
                            executable.Video.Width  = (ushort)PrimaryScreen.Bounds.Width;
                            executable.Video.Height = (ushort)PrimaryScreen.Bounds.Height;

                            Core("BLAM.VIDEO.RESOLUTION: Resolution out of bounds. Applied native resolution to executable.");
                        }

                        blam.Video.Resolution.Width  = executable.Video.Width;
                        blam.Video.Resolution.Height = executable.Video.Height;

                        Core("BLAM.VIDEO.RESOLUTION: Executable resolution has been assigned to the inferred profile.");

                        Debug("BLAM.VIDEO.RESOLUTION: Width  - " + blam.Video.Resolution.Width);
                        Debug("BLAM.VIDEO.RESOLUTION: Height - " + blam.Video.Resolution.Height);
                    }

                    if (configuration.Video.Bless)
                    {
                        executable.Video.Width  -= 10;
                        executable.Video.Height -= 10;
                        Core("BLAM.VIDEO.BLESS: Tweaked executable resolution for border-less support.");
                    }

                    if (configuration.Video.Quality)
                    {
                        blam.Video.Effects.Specular = true;
                        blam.Video.Effects.Shadows  = true;
                        blam.Video.Effects.Decals   = true;

                        blam.Video.Quality   = VideoQuality.High;
                        blam.Video.Particles = VideoParticles.High;

                        Core("BLAM.VIDEO.QUALITY: Patched effects and quality to the highest levels.");

                        Debug("BLAM.VIDEO.QUALITY: Specular  - " + blam.Video.Effects.Specular);
                        Debug("BLAM.VIDEO.QUALITY: Shadows   - " + blam.Video.Effects.Shadows);
                        Debug("BLAM.VIDEO.QUALITY: Decals    - " + blam.Video.Effects.Decals);
                        Debug("BLAM.VIDEO.QUALITY: Quality   - " + blam.Video.Quality);
                        Debug("BLAM.VIDEO.QUALITY: Particles - " + blam.Video.Particles);
                    }

                    if (configuration.Video.Uncap)
                    {
                        blam.Video.FrameRate = VideoFrameRate.VsyncOff;

                        Core("BLAM.VIDEO.UNCAP: Applied V-Sync off for framerate uncap.");

                        Debug("BLAM.VIDEO.UNCAP: Framerate - " + blam.Video.FrameRate);
                    }

                    Core("BLAM.VIDEO: Video enhancements have been applied accordingly.");
                }

                /**
                 * Apply the highest audio settings and toggle Hardware Acceleration & EAX. The latter will require a compatible
                 * library such as DSOAL for it to actually work.
                 */

                void Audio()
                {
                    if (configuration.Audio.Quality)
                    {
                        blam.Audio.Quality = AudioQuality.High;
                        blam.Audio.Variety = AudioVariety.High;

                        Core("BLAM.AUDIO.QUALITY: Patched audio quality to the highest level.");

                        Debug("BLAM.AUDIO.QUALITY: Quality - " + blam.Audio.Quality);
                        Debug("BLAM.AUDIO.QUALITY: Variety - " + blam.Audio.Variety);
                    }

                    if (configuration.Audio.Enhancements)
                    {
                        if (System.IO.File.Exists(DSOAL))
                        {
                            blam.Audio.HWA = true;
                            blam.Audio.EAX = true;

                            Core("BLAM.AUDIO.ENHANCEMENTS: Enabled Hardware Acceleration & EAX.");
                        }
                        else
                        {
                            blam.Audio.HWA = false;
                            blam.Audio.EAX = false;

                            Core("BLAM.AUDIO.ENHANCEMENTS: DSOAL not found. Refusing to enable HWA & EAX..");
                        }

                        Debug("BLAM.AUDIO.ENHANCEMENTS: HWA - " + blam.Audio.HWA);
                        Debug("BLAM.AUDIO.ENHANCEMENTS: EAX - " + blam.Audio.EAX);
                    }

                    Core("BLAM.AUDIO: Audio enhancements have been applied accordingly.");
                }

                /**
                 * Apply SPV3's preset input to the controller.
                 */

                void Input()
                {
                    if (!configuration.Input.Override)
                    {
                        return;
                    }

                    blam.Input.Mapping = new Dictionary <Profile.ProfileInput.Action, Profile.ProfileInput.Button>
                    {
                        { Profile.ProfileInput.Action.MoveForward, Profile.ProfileInput.Button.LSU },
                        { Profile.ProfileInput.Action.MoveBackward, Profile.ProfileInput.Button.LSD },
                        { Profile.ProfileInput.Action.MoveLeft, Profile.ProfileInput.Button.LSL },
                        { Profile.ProfileInput.Action.MoveRight, Profile.ProfileInput.Button.LSR },
                        { Profile.ProfileInput.Action.Crouch, Profile.ProfileInput.Button.LSM },
                        { Profile.ProfileInput.Action.Reload, Profile.ProfileInput.Button.DPU },
                        { Profile.ProfileInput.Action.Jump, Profile.ProfileInput.Button.A },
                        { Profile.ProfileInput.Action.SwitchGrenade, Profile.ProfileInput.Button.B },
                        { Profile.ProfileInput.Action.Action, Profile.ProfileInput.Button.X },
                        { Profile.ProfileInput.Action.SwitchWeapon, Profile.ProfileInput.Button.Y },
                        { Profile.ProfileInput.Action.LookUp, Profile.ProfileInput.Button.RSU },
                        { Profile.ProfileInput.Action.LookDown, Profile.ProfileInput.Button.RSD },
                        { Profile.ProfileInput.Action.LookLeft, Profile.ProfileInput.Button.RSL },
                        { Profile.ProfileInput.Action.LookRight, Profile.ProfileInput.Button.RSR },
                        { Profile.ProfileInput.Action.ScopeZoom, Profile.ProfileInput.Button.RSM },
                        { Profile.ProfileInput.Action.ThrowGrenade, Profile.ProfileInput.Button.LB },
                        { Profile.ProfileInput.Action.Flashlight, Profile.ProfileInput.Button.LT },
                        { Profile.ProfileInput.Action.MeleeAttack, Profile.ProfileInput.Button.RB },
                        { Profile.ProfileInput.Action.FireWeapon, Profile.ProfileInput.Button.RT }
                    };

                    blam.Input.BitBinding = new Dictionary <Profile.ProfileInput.OddValues, Profile.ProfileInput.OddOffsets>
                    {
                        { Profile.ProfileInput.OddValues.Button1, Profile.ProfileInput.OddOffsets.MenuAccept },
                        { Profile.ProfileInput.OddValues.Button2, Profile.ProfileInput.OddOffsets.MenuBack }
                    };

                    Core("BLAM.INPUT: Input overrides have been applied accordingly.");
                }
            }

            /**
             * For SPV3.2+, we will tweak the OpenSauce settings to ensure full compatibility with 3.2+'s specifications and
             * post-processing effects.
             */

            void Open()
            {
                var open = (OpenSauce)Custom.OpenSauce(executable.Profile.Path);
                var mod  = System.IO.File.Exists("./dinput8.dll") ||
                           System.IO.File.Exists("./mods/opensauce.dll");

                if (System.IO.File.Exists("./dinput8.dll"))
                {
                    Debug("dinput8.dll exists");
                }
                else
                {
                    Debug("dinput8 not found");
                }

                if (System.IO.File.Exists("./mods/opensauce.dll"))
                {
                    Debug("opensauce.dll exists");
                }
                else
                {
                    Debug("opensauce.dll not found");
                }

                if (!mod)
                {
                    Debug("Open Sauce not found");
                }

                if (open.Exists() && mod)
                {
                    open.Load();
                }
                else if (mod)
                {
                    open.Save();
                    open.Load();
                }


                try
                {
                    if (configuration.Mode == Configuration.ConfigurationMode.HCE)
                    {
                        return;
                    }

                    open.Rasterizer.PostProcessing.MotionBlur.Enabled = (configuration.Shaders & PP.MOTION_BLUR_BUILT_IN) != 0;
                    open.HUD.ScaleHUD = true;                                 /* fixes user interface    */
                    open.Camera.IgnoreFOVChangeInCinematics           = true; /* fixes user interface    */
                    open.Camera.IgnoreFOVChangeInMainMenu             = true; /* fixes user interface    */
                    open.Rasterizer.ShaderExtensions.Effect.DepthFade = true; /* shader optimisations    */

                    open.Save();

                    Core("MAIN.OPEN: Conditionally applied SPV3 fixes - enabled HUD scaling, FOV ignoreing, and depth fade.");

                    Debug("MAIN.OPEN: Motion Blur          - " + open.Rasterizer.PostProcessing.MotionBlur.Enabled);
                    Debug("MAIN.OPEN: HUD Scaling          - " + open.HUD.ScaleHUD);
                    Debug("MAIN.OPEN: Cinematic FOV Ignore - " + open.Camera.IgnoreFOVChangeInCinematics);
                    Debug("MAIN.OPEN: Main Menu FOV Ignore - " + open.Camera.IgnoreFOVChangeInMainMenu);
                    Debug("MAIN.OPEN: Depth Fade Effects   - " + open.Rasterizer.ShaderExtensions.Effect.DepthFade);
                }
                catch (Exception e)
                {
                    var msg = " -- MAIN.OPEN\n Error:  " + e.ToString() + "\n";
                    var log = (File)Paths.Exception;
                    log.AppendAllText(msg);
                    Error(msg);
                }
            }

            /**
             * Gracefully halt any potentially hanging HCE processes, conditionally patch the HCE executable with LAA flag,
             * and start the executable.
             */

            void Exec()
            {
                Reset();
                Patch();
                Start();
                Bless();

                Core("MAIN.EXEC: All HCE execution routines have been successfully resolved.");

                /**
                 * This method encourages the kernel to wait for a potential HCE process to end before proceeding with any
                 * subsequent routines. For some odd reason, there are cases where HCE runs in the background after the end-user
                 * exits it, thus prohibiting any additional processes from being invoked. To mitigate that, we gracefully kill
                 * any existing ones.
                 */

                void Reset()
                {
                    Info("Killing existing HCE processes");

                    try
                    {
                        foreach (var process in GetProcessesByName("haloce"))
                        {
                            process.Kill();
                        }
                    }
                    catch (Exception e)
                    {
                        var msg = " -- MAIN.BLAM HALTED\n Error:  " + e.ToString() + "\n";
                        var log = (File)Paths.Exception;
                        log.AppendAllText(msg);
                        Info(msg);
                    }

                    var tries = 0;

                    Wait("Waiting for existing HCE process to end ");

                    while (GetProcessesByName("haloce").Length > 0 && tries <= 25)
                    {
                        System.Console.Write(Resources.Progress);
                        tries++;
                    }

                    if (tries == 25)
                    {
                        Error("Could not kill HCE process. Process initiation errors may occur.");
                    }

                    Core("EXEC.RESET: Finalised attempts of killing potential HCE processes.");
                }

                /**
                 * If the HCE executable is not already patched with the LAA flag, this method will take care of modifying the
                 * byte's value to enable the respective LAA flag.
                 */

                void Patch()
                {
                    if (configuration.Tweaks.Acceleration)
                    {
                        configuration.Tweaks.Patches |= Patcher.EXEP.DISABLE_MOUSE_ACCELERATION;
                    }
                    if (configuration.Video.GammaOn == false)
                    {
                        configuration.Tweaks.Patches |= Patcher.EXEP.DISABLE_SYSTEM_GAMMA;
                    }

                    try
                    {
                        new Patcher().Write(configuration.Tweaks.Patches, executable.Path);
                        Core("EXEC.PATCH: Conditional patching has been handled.");
                    }
                    catch (Exception e)
                    {
                        var msg = " -- EXEC.PATCH HALTED\n Error:  " + e.ToString() + "\n";
                        var log = (File)Paths.Exception;
                        log.AppendAllText(msg);
                        Error(msg);
                    }
                }

                /**
                 * God is on my side if this method actually gets called.
                 */

                void Start()
                {
                    try
                    {
                        executable.Start(configuration.Main.Elevated);

                        Core("EXEC.START: Successfully started the inferred HCE executable.");
                    }
                    catch (Exception e)
                    {
                        var msg = " -- EXEC.START HALTED\n Error:  " + e.ToString() + "\n";
                        var log = (File)Paths.Exception;
                        log.AppendAllText(msg);
                        Error(msg);
                    }
                }

                /**
                 * Bless for border-less!
                 */

                void Bless()
                {
                    if (!configuration.Video.Bless)
                    {
                        return;
                    }

                    const int LOADED_OFFSET   = 0x0064533B; /* 0x6B4051 could also be used, according to github.com/gbMichelle */
                    const int PROCESS_WM_READ = 0x0010;
                    const int GWL_STYLE       = -16;
                    const int SWP_NOMOVE      = 0X2;
                    const int SWP_NOSIZE      = 1;
                    const int SWP_NOZORDER    = 0X4;
                    const int SWP_SHOWWINDOW  = 0x0040;
                    const int WS_SYSMENU      = 0x00080000;
                    const int WS_MAXIMIZEBOX  = 0x00010000;
                    const int WS_MINIMIZEBOX  = 0x00020000;
                    const int WS_SIZEBOX      = 0x00040000;
                    const int WS_BORDER       = 0x00800000;
                    const int WS_DLGFRAME     = 0x00400000;
                    const int WS_CAPTION      =
                        SWP_NOMOVE | WS_SYSMENU | WS_MAXIMIZEBOX | WS_MINIMIZEBOX | WS_BORDER | WS_DLGFRAME | WS_SIZEBOX;

                    try
                    {
                        var processes = GetProcesses();

                        foreach (var process in processes)
                        {
                            if (!process.ProcessName.StartsWith("haloce"))
                            {
                                continue;
                            }

                            /**
                             * The bless hack is applied only when HCE has been loaded. HXE deems HCE as loaded when the main menu has
                             * been initiated.
                             *
                             * This is determined by checking the value declared at LOADED_OFFSET. The value changes from 0 to 1 the
                             * moment HCE has loaded.
                             *
                             * The reason we apply the hack then is for robustness: the HCE window becomes responsive around that time
                             * after the loading sequence.
                             */

                            var processHandle = OpenProcess(PROCESS_WM_READ, false, process.Id);

                            var bytesRead = 0;
                            var buffer    = new byte[1];
                            var loaded    = false;

                            while (!loaded && process.HasExited != true)
                            {
                                ReadProcessMemory((int)processHandle, LOADED_OFFSET, buffer, buffer.Length, ref bytesRead);
                                loaded = buffer[0] == 1;
                            }

                            /**
                             * The hack attempts to hide any window controls and also move the window to the top left of the current
                             * display. In most circumstances, this should work just fine. If people are applying border-less mode and
                             * use a resolution lower than their screen resolution, then, err... why?
                             */

                            var pFoundWindow = process.MainWindowHandle;
                            var style        = GetWindowLong(pFoundWindow, GWL_STYLE);
                            SetWindowLong(pFoundWindow, GWL_STYLE, style & ~WS_CAPTION);
                            SetWindowPos(pFoundWindow, 0, 0, 0, 0, 0, SWP_NOZORDER | SWP_NOSIZE | SWP_SHOWWINDOW);
                            Core("EXEC.BLESS: Applied border-less hack to the HCE process window.");
                        }
                    }
                    catch (Exception e)
                    {
                        var msg = " -- EXEC.START HALTED\n Error:  " + e.ToString() + "\n";
                        var log = (File)Paths.Exception;
                        log.AppendAllText(msg);
                        Error(msg);
                    }
                }
            }
        }
Esempio n. 8
0
 /// <summary>
 ///   Loads inbound HCE executable with the default configuration.
 /// </summary>
 /// <param name="executable">
 ///   Object representing a legal HCE executable.
 /// </param>
 public static void Invoke(Executable executable)
 {
     Invoke(executable, new Configuration().Load());
 }
Esempio n. 9
0
    /// <summary>
    ///   Console API to the HXE kernel, installer and compiler.
    /// </summary>
    /// <param name="args">
    ///   --config            Opens configuration GUI
    ///   --load              Initiates HCE/SPV3
    ///   --install=VALUE     Installs HCE/SPV3   to destination
    ///   --compile=VALUE     Compiles HCE/SPV3   to destination
    ///   --console           Loads HCE           with console mode
    ///   --devmode           Loads HCE           with developer mode
    ///   --screenshot        Loads HCE           with screenshot ability
    ///   --window            Loads HCE           in window mode
    ///   --nogamma           Loads HCE           without gamma overriding
    ///   --adapter=VALUE     Loads HCE           on monitor X
    ///   --path=VALUE        Loads HCE           with custom profile path
    ///   --vidmode=VALUE     Loads HCE           with video mode
    /// </param>
    private static void InvokeProgram(string[] args)
    {
      Directory.CreateDirectory(Paths.Directory);

      var help       = false;        /* Displays commands list              */
      var config     = false;        /* Opens configuration GUI             */
      var positions  = false;        /* Opens positions GUI                 */
      var install    = string.Empty; /* Installs HCE/SPV3 to destination    */
      var compile    = string.Empty; /* Compiles HCE/SPV3 to destination    */
      var update     = string.Empty; /* Updates directory using manifest    */
      var console    = false;        /* Loads HCE with console mode         */
      var devmode    = false;        /* Loads HCE with developer mode       */
      var screenshot = false;        /* Loads HCE with screenshot ability   */
      var window     = false;        /* Loads HCE in window mode            */
      var nogamma    = false;        /* Loads HCE without gamma overriding  */
      var adapter    = string.Empty; /* Loads HCE on monitor X              */
      var path       = string.Empty; /* Loads HCE with custom profile path  */
      var exec       = string.Empty; /* Loads HCE with custom init file     */
      var vidmode    = string.Empty; /* Loads HCE with custom res. and Hz   */

      var options = new OptionSet()
        .Add("help",       "Displays commands list",             s => help = s       != null) /* hxe command   */
        .Add("config",     "Opens configuration GUI",            s => config = s     != null) /* hxe command   */
        .Add("positions",  "Opens positions GUI",                s => positions = s  != null) /* hxe command   */
        .Add("install=",   "Installs HCE/SPV3 to destination",   s => install = s)            /* hxe parameter */
        .Add("compile=",   "Compiles HCE/SPV3 to destination",   s => compile = s)            /* hxe parameter */
        .Add("update=",    "Updates directory using manifest",   s => update = s)             /* hxe parameter */
        .Add("console",    "Loads HCE with console mode",        s => console = s    != null) /* hce parameter */
        .Add("devmode",    "Loads HCE with developer mode",      s => devmode = s    != null) /* hce parameter */
        .Add("screenshot", "Loads HCE with screenshot ability",  s => screenshot = s != null) /* hce parameter */
        .Add("window",     "Loads HCE in window mode",           s => window = s     != null) /* hce parameter */
        .Add("nogamma",    "Loads HCE without gamma overriding", s => nogamma = s    != null) /* hce parameter */
        .Add("adapter=",   "Loads HCE on monitor X",             s => adapter = s)            /* hce parameter */
        .Add("path=",      "Loads HCE with custom profile path", s => path = s)               /* hce parameter */
        .Add("exec=",      "Loads HCE with custom init file",    s => exec = s)               /* hce parameter */
        .Add("vidmode=",   "Loads HCE with custom res. and Hz",  s => vidmode = s);           /* hce parameter */

      var input = options.Parse(args);

      foreach (var i in input)
        Info("Discovered CLI command: " + i);

      var hce = new Executable();

      if (help)
      {
        options.WriteOptionDescriptions(Out);
        Exit(0);
      }

      if (config)
      {
        new Application().Run(new Settings());
        Exit(0);
      }

      if (positions)
      {
        new Application().Run(new Positions());
        Exit(0);
      }

      if (!string.IsNullOrWhiteSpace(install))
        Run(() => { Installer.Install(CurrentDirectory, Path.GetFullPath(install)); });

      if (!string.IsNullOrWhiteSpace(compile))
        Run(() => { Compiler.Compile(CurrentDirectory, Path.GetFullPath(compile)); });

      if (!string.IsNullOrWhiteSpace(update))
        Run(() =>
        {
          var updateModule = new Update();
          updateModule.Import(update);
          updateModule.Commit();
        });

      /**
       * Implicit verification for legal HCE installations.
       */

      try
      {
        hce = Executable.Detect();
      }
      catch (Exception e)
      {
        Error(e.Message + " -- Legal copy of HCE needs to be installed for loading!");
      }

      if (console)
        hce.Debug.Console = true;

      if (devmode)
        hce.Debug.Developer = true;

      if (screenshot)
        hce.Debug.Screenshot = true;

      if (window)
        hce.Video.Window = true;

      if (nogamma)
        hce.Video.NoGamma = true;

      if (!string.IsNullOrWhiteSpace(adapter))
        hce.Video.Adapter = byte.Parse(adapter);

      if (!string.IsNullOrWhiteSpace(path))
        hce.Profile.Path = path;

      if (!string.IsNullOrWhiteSpace(exec))
        hce.Debug.Initiation = exec;

      if (!string.IsNullOrWhiteSpace(vidmode))
      {
        var a = vidmode.Split(',');

        if (a.Length < 2) return;

        hce.Video.Mode   = true;
        hce.Video.Width  = ushort.Parse(a[0]);
        hce.Video.Height = ushort.Parse(a[1]);

        if (a.Length > 2) /* optional refresh rate */
          hce.Video.Refresh = ushort.Parse(a[2]);
      }

      /**
       * Implicitly invoke the HXE kernel with the HCE loading procedure.
       */

      Run(() => { Kernel.Invoke(hce); });

      /**
       * This method is used for running code asynchronously and catching exceptions at the highest level.
       */

      void Run(Action action)
      {
        try
        {
          Task.Run(action).GetAwaiter().GetResult();
          WithCode(Code.Success);
        }
        catch (Exception e)
        {
          Error(e.Message);
          System.Console.Error.WriteLine("\n\n" + e.StackTrace);
          WriteAllText(Paths.Exception, e.ToString());
          WithCode(Code.Exception);
        }
      }
    }
Esempio n. 10
0
        /// <summary>
        ///   Loads inbound HCE executable with the inbound configuration.
        /// </summary>
        /// <param name="executable">
        ///   Object representing a legal HCE executable.
        /// </param>
        /// <param name="configuration">
        ///   Object representing the kernel configuration.
        /// </param>
        public static void Invoke(Executable executable, Configuration configuration)
        {
            Init(); /* initc.txt declarations */
            Blam(); /* blam.sav enhancements  */
            Open(); /* opensauce declarations */
            Exec(); /* haloce.exe invocation  */

            Core("CORE.MAIN: Successfully updated the initiation, profile and OS files, and invoked the HCE executable.");

            /**
             * We declare the contents of the initiation file in this method before dealing with the profile enhancements and
             * the executable invocation. It's the most important task, so we have to deal with it first.
             *
             * The values declared by the HXE kernel for the initiation file are categorised into the following sections:
             *
             * -   RESUME: Campaign resuming support for the SPV3 mod, which permits compatibility with SPV3's main UI;
             * -   TWEAKS: Rudimentary tweaks including cinematic bars, and controller enhancements (magnetism & auto-aim);
             * -   SHADER: SPV3 post-processing configurations, including activated shaders & shader intensity levels.
             */

            void Init()
            {
                var init = (Initiation)GetFullPath(executable.Debug.Initiation);

                Resume(); /* spv3 campaign resume with ui.map compatibility */
                Tweaks(); /* hce/spv3 start-up miscellaneous tweaks         */
                Shader(); /* spv3 post-processing toggles & settings        */
                Unlock(); /* spv3.1 legacy maps unlocking mechanism         */

                try
                {
                    init.Save();

                    Core("MAIN.INIT: Initiation data has been successfully applied and saved.");
                }
                catch (Exception e)
                {
                    Error(e.Message + " -- MAIN.INIT HALTED");
                }

                /**
                 * Resume the campaign based on the progress of the last used profile. This requires:
                 *
                 * -   a LASTPROF.TXT file to be located in the profile path declared for the inbound executable; and
                 * -   the directory for the profile declared in the aforementioned plaintext file; and
                 * -   the savegame.bin for the respective profile, to infer the campaign progress.
                 */

                void Resume()
                {
                    try
                    {
                        var prof = (LastProfile)Custom.LastProfile(executable.Profile.Path);

                        if (!prof.Exists())
                        {
                            return;
                        }

                        prof.Load();

                        var name = prof.Profile;
                        var save = (Progress)Custom.Progress(executable.Profile.Path, name);

                        if (!save.Exists())
                        {
                            return;
                        }

                        save.Load();

                        init.Mission    = save.Mission;
                        init.Difficulty = save.Difficulty;

                        Core("INIT.RESUME: Campaign checkpoint information has been applied to the initiation file.");

                        Debug("INIT.RESUME: Mission    - " + init.Mission);
                        Debug("INIT.RESUME: Difficulty - " + init.Difficulty);
                    }
                    catch (Exception e)
                    {
                        Error(e.Message + " -- INIT.RESUME HALTED");
                    }
                }

                /**
                 * Rudimentary tweaks including:
                 *
                 * -   Player Auto-aim
                 * -   Player Magnetism
                 * -   Execution speed
                 * -   Acceleration
                 *
                 * ... and stuff for SPV3:
                 *
                 * -   Cinematic Bars
                 * -   Motion Sensor
                 */

                void Tweaks()
                {
                    init.PlayerAutoaim     = configuration.Tweaks.AutoAim;
                    init.PlayerMagnetism   = configuration.Tweaks.Magnetism;
                    init.Speed             = configuration.Tweaks.Speed;
                    init.MouseAcceleration = configuration.Tweaks.Acceleration;
                    init.Gamma             = configuration.Video.Gamma;

                    if (configuration.Mode == Configuration.ConfigurationMode.SPV32)
                    {
                        init.CinematicBars = configuration.Tweaks.Cinematic;
                        init.MotionSensor  = configuration.Tweaks.Sensor;
                        init.Unload        = configuration.Tweaks.Unload;

                        Core("INIT.TWEAKS: SPV3.2 cinematic bars, motion sensor and unload tweaks have been updated.");

                        Debug("INIT.TWEAKS: Cinematic Bars - " + init.CinematicBars);
                        Debug("INIT.TWEAKS: Motion Sensor  - " + init.MotionSensor);
                        Debug("INIT.TWEAKS: Unload         - " + init.Unload);
                    }

                    Core("INIT.TWEAKS: Magnetism, auto-aim, speed and mouse acceleration tweaks have been updated.");

                    Debug("INIT.TWEAKS: Player Auto-aim    - " + init.PlayerAutoaim);
                    Debug("INIT.TWEAKS: Player Magnetism   - " + init.PlayerMagnetism);
                    Debug("INIT.TWEAKS: Speed              - " + init.Speed);
                    Debug("INIT.TWEAKS: Mouse Acceleration - " + init.MouseAcceleration);
                    Debug("INIT.TWEAKS: Gamma              - " + init.Gamma);
                }

                /**
                 * SPV3.2 shader toggles and configurations.
                 */

                void Shader()
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV32)
                    {
                        return;
                    }

                    init.PostProcessing.Internal           = configuration.Shaders.Internal;
                    init.PostProcessing.External           = configuration.Shaders.External;
                    init.PostProcessing.GBuffer            = configuration.Shaders.GBuffer;
                    init.PostProcessing.DepthFade          = configuration.Shaders.DepthFade;
                    init.PostProcessing.Bloom              = configuration.Shaders.Bloom;
                    init.PostProcessing.LensDirt           = configuration.Shaders.LensDirt;
                    init.PostProcessing.DynamicLensFlares  = configuration.Shaders.DynamicLensFlares;
                    init.PostProcessing.VolumetricLighting = configuration.Shaders.VolumetricLighting;
                    init.PostProcessing.AntiAliasing       = configuration.Shaders.AntiAliasing;
                    init.PostProcessing.HudVisor           = configuration.Shaders.HudVisor;
                    init.PostProcessing.FilmGrain          = configuration.Shaders.FilmGrain;
                    init.PostProcessing.MotionBlur         = configuration.Shaders.MotionBlur;
                    init.PostProcessing.MXAO = configuration.Shaders.MXAO;
                    init.PostProcessing.DOF  = configuration.Shaders.DOF;

                    Core("INIT.SHADER: SPV3.2 post-processing effects have been assigned to the initiation file.");

                    Debug("INIT.SHADER: Internal            - " + init.PostProcessing.Internal);
                    Debug("INIT.SHADER: External            - " + init.PostProcessing.External);
                    Debug("INIT.SHADER: GBuffer             - " + init.PostProcessing.GBuffer);
                    Debug("INIT.SHADER: DepthFade           - " + init.PostProcessing.DepthFade);
                    Debug("INIT.SHADER: Bloom               - " + init.PostProcessing.Bloom);
                    Debug("INIT.SHADER: LensDirt            - " + init.PostProcessing.LensDirt);
                    Debug("INIT.SHADER: Dynamic Lens Flares - " + init.PostProcessing.DynamicLensFlares);
                    Debug("INIT.SHADER: Volumetric Lighting - " + init.PostProcessing.VolumetricLighting);
                    Debug("INIT.SHADER: Anti Aliasing       - " + init.PostProcessing.AntiAliasing);
                    Debug("INIT.SHADER: HUD Visor           - " + init.PostProcessing.HudVisor);
                    Debug("INIT.SHADER: Film Grain          - " + init.PostProcessing.FilmGrain);
                    Debug("INIT.SHADER: Motion Blur         - " + init.PostProcessing.MotionBlur);
                    Debug("INIT.SHADER: MXAO                - " + init.PostProcessing.MXAO);
                    Debug("INIT.SHADER: DOF                 - " + init.PostProcessing.DOF);
                }

                /**
                 * Indeed, SPV3.1 had some DRM I wasn't quite a fan of. This routine unlocks the 3.1 campaigns. Is this a crack?
                 * I should have a demo screen playing here, along with greetings to friends all over the world.
                 *
                 * Idea: Release 3.2 with an NFO file with ANSI art.
                 */

                void Unlock()
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV31)
                    {
                        return;
                    }

                    init.Unlock = true;

                    Core("INIT.UNLOCK: SPV3.1 campaign has been unlocked for subsequent invocation.");
                }
            }

            /**
             * We enhance the player's profile by applying the highest video & audio quality settings, along with forcing the
             * resolution declared in video parameters of the inbound executable.
             *
             * The enhancements are applied based on the provided configuration, and also the on the success rate of inferring
             * the last used profile in the specified profiles directory.
             */

            void Blam()
            {
                Profile blam;

                try
                {
                    blam = Profile.Detect(executable.Profile.Path);

                    Video();
                    Audio();
                    Input();

                    blam.Save();

                    Core("MAIN.BLAM: Profile enhancements have been successfully applied and saved.");
                }
                catch (Exception e)
                {
                    Error(e.Message + " -- MAIN.BLAM HALTED");
                }

                /**
                 * Apply the resolution specified in video parameters of the inbound executable OR apply the primary screen's
                 * current resolution. This enforces HCE to run at the desired or native resolution, and also obsoletes Ecran.
                 *
                 * Additionally, effects and qualities are enabled and set to the maximum level, respectively. Of course, this
                 * also depends on the provided configuration.
                 */

                void Video()
                {
                    if (configuration.Video.Resolution)
                    {
                        if (executable.Video.Width == 0 || executable.Video.Height == 0)
                        {
                            executable.Video.Width  = (ushort)PrimaryScreen.Bounds.Width;
                            executable.Video.Height = (ushort)PrimaryScreen.Bounds.Height;

                            Core("BLAM.VIDEO.RESOLUTION: No resolution provided. Applied native resolution to executable.");
                        }

                        if (executable.Video.Width > (ushort)PrimaryScreen.Bounds.Width ||
                            executable.Video.Height > (ushort)PrimaryScreen.Bounds.Height)
                        {
                            executable.Video.Width  = (ushort)PrimaryScreen.Bounds.Width;
                            executable.Video.Height = (ushort)PrimaryScreen.Bounds.Height;

                            Core("BLAM.VIDEO.RESOLUTION: Resolution out of bounds. Applied native resolution to executable.");
                        }

                        blam.Video.Resolution.Width  = executable.Video.Width;
                        blam.Video.Resolution.Height = executable.Video.Height;

                        Core("BLAM.VIDEO.RESOLUTION: Executable resolution has been assigned to the inferred profile.");

                        Debug("BLAM.VIDEO.RESOLUTION: Width  - " + blam.Video.Resolution.Width);
                        Debug("BLAM.VIDEO.RESOLUTION: Height - " + blam.Video.Resolution.Height);
                    }

                    if (configuration.Video.Bless)
                    {
                        executable.Video.Width  -= 10;
                        executable.Video.Height -= 10;
                        Core("BLAM.VIDEO.BLESS: Tweaked executable resolution for border-less support.");
                    }

                    if (configuration.Video.Quality)
                    {
                        blam.Video.Effects.Specular = true;
                        blam.Video.Effects.Shadows  = true;
                        blam.Video.Effects.Decals   = true;

                        blam.Video.Quality   = VideoQuality.High;
                        blam.Video.Particles = VideoParticles.High;

                        Core("BLAM.VIDEO.QUALITY: Patched effects and quality to the highest levels.");

                        Debug("BLAM.VIDEO.QUALITY: Specular  - " + blam.Video.Effects.Specular);
                        Debug("BLAM.VIDEO.QUALITY: Shadows   - " + blam.Video.Effects.Shadows);
                        Debug("BLAM.VIDEO.QUALITY: Decals    - " + blam.Video.Effects.Decals);
                        Debug("BLAM.VIDEO.QUALITY: Quality   - " + blam.Video.Quality);
                        Debug("BLAM.VIDEO.QUALITY: Particles - " + blam.Video.Particles);
                    }

                    if (configuration.Video.Uncap)
                    {
                        blam.Video.FrameRate = VideoFrameRate.VsyncOff;

                        Core("BLAM.VIDEO.UNCAP: Applied V-Sync off for framerate uncap.");

                        Debug("BLAM.VIDEO.UNCAP: Framerate - " + blam.Video.FrameRate);
                    }

                    Core("BLAM.VIDEO: Video enhancements have been applied accordingly.");
                }

                /**
                 * Apply the highest audio settings and toggle Hardware Acceleration & EAX. The latter will require a compatible
                 * library such as DSOAL for it to actually work.
                 */

                void Audio()
                {
                    if (configuration.Audio.Quality)
                    {
                        blam.Audio.Quality = AudioQuality.High;
                        blam.Audio.Variety = AudioVariety.High;

                        Core("BLAM.AUDIO.QUALITY: Patched audio quality to the highest level.");

                        Debug("BLAM.AUDIO.QUALITY: Quality - " + blam.Audio.Quality);
                        Debug("BLAM.AUDIO.QUALITY: Variety - " + blam.Audio.Variety);
                    }

                    if (configuration.Audio.Enhancements)
                    {
                        if (System.IO.File.Exists(DSOAL))
                        {
                            blam.Audio.HWA = true;
                            blam.Audio.EAX = true;

                            Core("BLAM.AUDIO.ENHANCEMENTS: Enabled Hardware Acceleration & EAX.");
                        }
                        else
                        {
                            blam.Audio.HWA = false;
                            blam.Audio.EAX = false;

                            Core("BLAM.AUDIO.ENHANCEMENTS: DSOAL not found. Refusing to enable HWA & EAX..");
                        }

                        Debug("BLAM.AUDIO.ENHANCEMENTS: HWA - " + blam.Audio.HWA);
                        Debug("BLAM.AUDIO.ENHANCEMENTS: EAX - " + blam.Audio.EAX);
                    }

                    Core("BLAM.AUDIO: Audio enhancements have been applied accordingly.");
                }

                /**
                 * Apply SPV3.2's preset input to the controller.
                 */

                void Input()
                {
                    if (!configuration.Input.Override)
                    {
                        return;
                    }

                    blam.Input.Mapping = new Dictionary <Profile.ProfileInput.Action, Profile.ProfileInput.Button>
                    {
                        { Profile.ProfileInput.Action.MoveForward, Profile.ProfileInput.Button.LSU },
                        { Profile.ProfileInput.Action.MoveBackward, Profile.ProfileInput.Button.LSD },
                        { Profile.ProfileInput.Action.MoveLeft, Profile.ProfileInput.Button.LSL },
                        { Profile.ProfileInput.Action.MoveRight, Profile.ProfileInput.Button.LSR },
                        { Profile.ProfileInput.Action.Crouch, Profile.ProfileInput.Button.LSM },
                        { Profile.ProfileInput.Action.Reload, Profile.ProfileInput.Button.DPU },
                        { Profile.ProfileInput.Action.Jump, Profile.ProfileInput.Button.A },
                        { Profile.ProfileInput.Action.SwitchGrenade, Profile.ProfileInput.Button.B },
                        { Profile.ProfileInput.Action.Action, Profile.ProfileInput.Button.X },
                        { Profile.ProfileInput.Action.SwitchWeapon, Profile.ProfileInput.Button.Y },
                        { Profile.ProfileInput.Action.LookUp, Profile.ProfileInput.Button.RSU },
                        { Profile.ProfileInput.Action.LookDown, Profile.ProfileInput.Button.RSD },
                        { Profile.ProfileInput.Action.LookLeft, Profile.ProfileInput.Button.RSL },
                        { Profile.ProfileInput.Action.LookRight, Profile.ProfileInput.Button.RSR },
                        { Profile.ProfileInput.Action.ScopeZoom, Profile.ProfileInput.Button.RSM },
                        { Profile.ProfileInput.Action.ThrowGrenade, Profile.ProfileInput.Button.LB },
                        { Profile.ProfileInput.Action.Flashlight, Profile.ProfileInput.Button.LT },
                        { Profile.ProfileInput.Action.MeleeAttack, Profile.ProfileInput.Button.RB },
                        { Profile.ProfileInput.Action.FireWeapon, Profile.ProfileInput.Button.RT }
                    };

                    Core("BLAM.INPUT: Input overrides have been applied accordingly.");
                }
            }

            /**
             * For SPV3.2, we will tweak the OpenSauce settings to ensure full compatibility with 3.2's specifications and
             * post-processing effects.
             */

            void Open()
            {
                var open = (OpenSauce)Custom.OpenSauce(executable.Profile.Path);

                if (open.Exists())
                {
                    open.Load();
                }

                try
                {
                    if (configuration.Mode != Configuration.ConfigurationMode.SPV32)
                    {
                        return;
                    }

                    open.Rasterizer.PostProcessing.MotionBlur.Enabled = configuration.Shaders.MotionBlur == BuiltIn;
                    open.HUD.ScaleHUD = true;                                 /* fixes user interface    */
                    open.Camera.IgnoreFOVChangeInCinematics           = true; /* fixes user interface    */
                    open.Camera.IgnoreFOVChangeInMainMenu             = true; /* fixes user interface    */
                    open.Rasterizer.ShaderExtensions.Effect.DepthFade = true; /* shader optimisations    */

                    open.Save();

                    Core("MAIN.OPEN: Conditionally applied SPV3.2 fixes - enabled HUD scaling, FOV ignoreing, and depth fade.");

                    Debug("MAIN.OPEN: Motion Blur          - " + open.Rasterizer.PostProcessing.MotionBlur.Enabled);
                    Debug("MAIN.OPEN: HUD Scaling          - " + open.HUD.ScaleHUD);
                    Debug("MAIN.OPEN: Cinematic FOV Ignore - " + open.Camera.IgnoreFOVChangeInCinematics);
                    Debug("MAIN.OPEN: Main Menu FOV Ignore - " + open.Camera.IgnoreFOVChangeInMainMenu);
                    Debug("MAIN.OPEN: Depth Fade Effects   - " + open.Rasterizer.ShaderExtensions.Effect.DepthFade);
                }
                catch (Exception e)
                {
                    Error(e.Message + " -- MAIN.OPEN HALTED");
                }
            }

            /**
             * Gracefully halt any potentially hanging HCE processes, conditionally patch the HCE executable with LAA flag,
             * and start the executable.
             */

            void Exec()
            {
                Reset();
                Patch();
                Start();
                Bless();

                Core("MAIN.EXEC: All HCE execution routines have been successfully resolved.");

                /**
                 * This method encourages the kernel to wait for a potential HCE process to end before proceeding with any
                 * subsequent routines. For some odd reason, there are cases where HCE runs in the background after the end-user
                 * exits it, thus prohibiting any additional processes from being invoked. To mitigate that, we gracefully kill
                 * any existing ones.
                 */

                void Reset()
                {
                    Info("Killing existing HCE processes");

                    try
                    {
                        foreach (var process in Process.GetProcessesByName("haloce"))
                        {
                            process.Kill();
                        }
                    }
                    catch (Exception e)
                    {
                        Info(e.Message);
                    }

                    var tries = 0;

                    Wait("Waiting for existing HCE process to end ");

                    while (Process.GetProcessesByName("haloce").Length > 0 && tries <= 25)
                    {
                        System.Console.Write(Resources.Progress);
                        tries++;
                    }

                    if (tries == 25)
                    {
                        Error("Could not kill HCE process. Process initiation errors may occur.");
                    }

                    Core("EXEC.RESET: Finalised attempts of killing potential HCE processes.");
                }

                /**
                 * If the HCE executable is not already patched with the LAA flag, this method will take care of modifying the
                 * byte's value to enable the respective LAA flag.
                 */

                void Patch()
                {
                    const byte value  = 0x2F;  /* LAA flag   */
                    const long offset = 0x136; /* LAA offset */

                    try
                    {
                        using (var fs = new FileStream(executable.Path, FileMode.Open, FileAccess.ReadWrite))
                            using (var ms = new MemoryStream(0x24B000))
                                using (var bw = new BinaryWriter(ms))
                                    using (var br = new BinaryReader(ms))
                                    {
                                        ms.Position = 0;
                                        fs.Position = 0;
                                        fs.CopyTo(ms);

                                        ms.Position = offset;

                                        if (br.ReadByte() != value)
                                        {
                                            ms.Position -= 1; /* restore position */
                                            bw.Write(value);  /* patch LAA flag   */

                                            fs.Position = 0;
                                            ms.Position = 0;
                                            ms.CopyTo(fs);

                                            Info("Applied LAA patch to the HCE executable");
                                        }
                                        else
                                        {
                                            Info("HCE executable already patched with LAA");
                                        }
                                    }

                        Core("EXEC.PATCH: Conditional LAA patching has been handled.");
                    }
                    catch (Exception e)
                    {
                        Error(e.Message + " -- EXEC.PATCH HALTED");
                    }
                }

                /**
                 * God is on my side if this method actually gets called.
                 */

                void Start()
                {
                    try
                    {
                        executable.Start();

                        Core("EXEC.START: Successfully started the inferred HCE executable.");
                    }
                    catch (Exception e)
                    {
                        Error(e.Message + " -- EXEC.START HALTED");
                    }
                }

                /**
                 * Bless for border-less!
                 */

                void Bless()
                {
                    if (!configuration.Video.Bless)
                    {
                        return;
                    }

                    const int GWL_STYLE      = -16;
                    const int SWP_NOMOVE     = 0X2;
                    const int SWP_NOSIZE     = 1;
                    const int SWP_NOZORDER   = 0X4;
                    const int SWP_SHOWWINDOW = 0x0040;
                    const int WS_SYSMENU     = 0x00080000;
                    const int WS_MAXIMIZEBOX = 0x00010000;
                    const int WS_MINIMIZEBOX = 0x00020000;
                    const int WS_SIZEBOX     = 0x00040000;
                    const int WS_BORDER      = 0x00800000;
                    const int WS_DLGFRAME    = 0x00400000;
                    const int WS_CAPTION     =
                        SWP_NOMOVE | WS_SYSMENU | WS_MAXIMIZEBOX | WS_MINIMIZEBOX | WS_BORDER | WS_DLGFRAME | WS_SIZEBOX;

                    Thread.Sleep(5000);

                    try
                    {
                        var processes = Process.GetProcesses();

                        foreach (var process in processes)
                        {
                            if (!process.ProcessName.StartsWith("haloce"))
                            {
                                continue;
                            }
                            process.WaitForInputIdle();
                            var pFoundWindow = process.MainWindowHandle;
                            var style        = GetWindowLong(pFoundWindow, GWL_STYLE);
                            SetWindowLong(pFoundWindow, GWL_STYLE, style & ~WS_CAPTION);
                            SetWindowPos(pFoundWindow, 0, 0, 0, 0, 0, SWP_NOZORDER | SWP_NOSIZE | SWP_SHOWWINDOW);
                            Core("EXEC.BLESS: Applied border-less hack to the HCE process window.");
                        }
                    }
                    catch (Exception e)
                    {
                        Error(e.Message + " -- EXEC.BLESS HALTED");
                    }
                }
            }
        }
Esempio n. 11
0
        /// <summary>
        ///   HXE entry.
        /// </summary>
        /// <param name="args">
        ///   Arguments for HXE.
        /// </param>
        public static void Main(string[] args)
        {
            var bn = Assembly.GetEntryAssembly().GetName().Version.Major.ToString("D4");

            ForegroundColor = ConsoleColor.Green;
            WriteLine(@" _    ___   ________ ");
            WriteLine(@"| |  | \ \ / /  ____|");
            WriteLine(@"| |__| |\ V /| |__   ");
            WriteLine(@"|  __  | > < |  __|  ");
            WriteLine(@"| |  | |/ . \| |____ ");
            WriteLine(@"|_|  |_/_/ \_\______| :: Halo XE");
            WriteLine(@"================================");
            WriteLine(@"A HCE wrapper and SPV3.2 loader.");
            WriteLine(@"--------------------------------");
            WriteLine(@"src: https://cgit.n2.network/hxe");
            WriteLine(@"bin: https://dist.n2.network/hxe");
            WriteLine(@"--------------------------------");
            WriteLine($"Current binary build number {bn}");
            WriteLine(@"--------------------------------");
            ForegroundColor = ConsoleColor.White;

            Directory.CreateDirectory(Paths.Directories.HXE);

            var hce = Executable.Detect();

            var options = new OptionSet()
                          .Add("load", "Initiates HCE/SPV3",
                               s => Run(() => { Kernel.Bootstrap(hce); }))
                          .Add("install=", "Installs HCE/SPV3 to destination",
                               s => Run(() => { Installer.Install(CurrentDirectory, s); }))
                          .Add("compile=", "Compiles HCE/SPV3 to destination",
                               s => Run(() => { Compiler.Compile(CurrentDirectory, s); }))
                          .Add("console", "Loads HCE with console mode",
                               s => hce.Debug.Console = true)
                          .Add("devmode", "Loads HCE with developer mode",
                               s => hce.Debug.Developer = true)
                          .Add("screenshot", "Loads HCE with screenshot ability",
                               s => hce.Debug.Screenshot = true)
                          .Add("window", "Loads HCE in window mode",
                               s => hce.Video.Window = true)
                          .Add("adapter=", "Loads HCE on monitor X",
                               s => hce.Video.Adapter = int.Parse(s))
                          .Add("path=", "Loads HCE with custom profile path",
                               s => hce.Profile.Path = s)
                          .Add("vidmode=", "Loads HCE with video mode",
                               s =>
            {
                var a = s.Split(',');

                if (a.Length != 3)
                {
                    return;
                }

                hce.Video.Width   = int.Parse(a[0]);
                hce.Video.Height  = int.Parse(a[1]);
                hce.Video.Refresh = int.Parse(a[2]);
            });

            options.WriteOptionDescriptions(Out);
            var input = options.Parse(args);

            if (!input.Contains("load") &&
                !input.Contains("install") &&
                !input.Contains("compile"))
            {
                Run(() => { Kernel.Bootstrap(hce); });
            }
        }