diff --git a/CommonHelpers/AntiCheatSettings.cs b/CommonHelpers/AntiCheatSettings.cs new file mode 100644 index 0000000..6d53a7b --- /dev/null +++ b/CommonHelpers/AntiCheatSettings.cs @@ -0,0 +1,116 @@ +using Microsoft.Win32; + +namespace CommonHelpers +{ + public class AntiCheatSettings : BaseSettings + { + public const String HelpURL = "https://steam-deck-tools.ayufan.dev/#anti-cheat-and-antivirus-software"; + + public static readonly AntiCheatSettings Default = new AntiCheatSettings(); + + public enum AckState + { + NotYet, + Always, + Session, + Never + } + + public bool SessionAcked { get; set; } + + public AckState Acked + { + get => Get("Acked", AckState.NotYet); + set => Set("Acked", value); + } + + public bool NotYet + { + get { return Acked == AckState.NotYet; } + } + + public bool Dismissed + { + get { return Acked == AckState.Never || Acked == AckState.Session && SessionAcked; } + } + + public AntiCheatSettings() : base("AntiCheat") + { + Microsoft.Win32.SystemEvents.PowerModeChanged += SystemEvents_PowerModeChanged; + } + + ~AntiCheatSettings() + { + Microsoft.Win32.SystemEvents.PowerModeChanged -= SystemEvents_PowerModeChanged; + } + + private void SystemEvents_PowerModeChanged(object sender, PowerModeChangedEventArgs e) + { + if (e.Mode == PowerModes.Resume) + { + SessionAcked = false; + } + } + + public bool AckAntiCheat(String title, String? message, String? footnote = null, bool allowDismiss = true) + { + if (Dismissed) + return true; + + Application.DoEvents(); + + var page = new TaskDialogPage(); + + page.Caption = title; + page.AllowCancel = true; + + var alwaysShow = page.RadioButtons.Add("Always show Anti-Cheat warnings"); + var dismissSession = page.RadioButtons.Add("Hide Anti-Cheat warnings for current session"); + var neverShow = page.RadioButtons.Add("Never show Anti-Cheat warnings"); + + alwaysShow.Checked = (Acked == AckState.Always || Acked == AckState.NotYet); + dismissSession.Checked = (Acked == AckState.Session); + neverShow.Checked = (Acked == AckState.Never); + + var continueButton = new TaskDialogButton("Continue") { ShowShieldIcon = true }; + var abortButton = new TaskDialogButton("Abort"); + + page.Buttons.Add(continueButton); + page.Buttons.Add(abortButton); + page.Buttons.Add(TaskDialogButton.Help); + page.Icon = TaskDialogIcon.ShieldWarningYellowBar; + page.Heading = "Anti-Cheat Protection"; + page.Text = message; + page.Footnote = new TaskDialogFootnote("This might result in kicking from the game or even be banned."); + page.Footnote.Icon = TaskDialogIcon.Information; + if (footnote is not null) + page.Footnote.Text += "\n" + footnote; + + page.HelpRequest += delegate + { + try { System.Diagnostics.Process.Start("explorer.exe", HelpURL); } + catch { } + }; + + var result = TaskDialog.ShowDialog(new Form { TopMost = true }, page, TaskDialogStartupLocation.CenterScreen); + if (result != continueButton) + return false; + + if (alwaysShow.Checked) + { + Acked = AckState.Always; + } + else if (dismissSession.Checked) + { + Acked = AckState.Session; + if (allowDismiss) + SessionAcked = true; + } + else if (neverShow.Checked) + { + Acked = AckState.Never; + } + return true; + } + } +} \ No newline at end of file diff --git a/CommonHelpers/BaseSettings.cs b/CommonHelpers/BaseSettings.cs index bd4ba57..1ec9454 100644 --- a/CommonHelpers/BaseSettings.cs +++ b/CommonHelpers/BaseSettings.cs @@ -31,6 +31,7 @@ namespace CommonHelpers this.SettingChanged += delegate { }; } + [Browsable(false)] public bool Exists { get { return File.Exists(this.ConfigFile); } @@ -60,7 +61,7 @@ namespace CommonHelpers return false; SettingChanging(key); - if (!SetString(key, valueString)) + if (!SetProfileString(key, valueString)) return false; cachedValues[key] = value; @@ -83,7 +84,7 @@ namespace CommonHelpers try { - var valueString = GetString(key, defaultString); + var valueString = GetProfileString(key, defaultString); var value = (T?)typeConverter.ConvertFromString(valueString); if (value is null) { @@ -94,7 +95,7 @@ namespace CommonHelpers if ((TouchSettings || touchSettings) && valueString == defaultString) { // Persist current value on a first access - SetString(key, valueString); + SetProfileString(key, valueString); } cachedValues[key] = value; @@ -108,7 +109,7 @@ namespace CommonHelpers } } - protected string GetString(string key, string defaultValue) + private string GetProfileString(string key, string defaultValue) { StringBuilder sb = new StringBuilder(500); uint res = GetPrivateProfileString(SettingsKey, key, defaultValue, sb, (uint)sb.Capacity, ConfigFile); @@ -117,7 +118,7 @@ namespace CommonHelpers return defaultValue; } - protected bool SetString(string key, string value) + private bool SetProfileString(string key, string value) { lock (this) { diff --git a/FanControl/FanControlForm.cs b/FanControl/FanControlForm.cs index a165b8b..ff79842 100644 --- a/FanControl/FanControlForm.cs +++ b/FanControl/FanControlForm.cs @@ -66,7 +66,7 @@ namespace FanControl protected override void OnLoad(EventArgs e) { base.OnLoad(e); - setFanMode(Settings.Default.FanMode, !Settings.Default.AckAntiCheat); + setFanMode(Settings.Default.FanMode, AntiCheatSettings.Default.NotYet); notifyIcon.ShowBalloonTip(3000, Text, "Fan Control Started", ToolTipIcon.Info); } @@ -79,38 +79,10 @@ namespace FanControl private bool AckAntiCheat() { - if (Settings.Default.AckAntiCheat && Settings.Default.EnableExperimentalFeatures) - return true; - - Application.DoEvents(); - - var result = MessageBox.Show( - new Form { TopMost = true }, - String.Join("\n", - "WARNING!!!!", - "", - "Usage of SteamOS or Max Fan Curve might trigger anti-cheat protection in some games.", - "This might result in kicking from the application or even be banned.", - "", - "Ensure that you USE DEFAULT FAN when playing games with ANTI-CHEAT PROTECTION.", - "", - "CLICK YES TO ACKNOWLEDGE?", - "CLICK NO TO LEARN MORE." - ), Text, - MessageBoxButtons.YesNo, - MessageBoxIcon.Warning, - MessageBoxDefaultButton.Button2 - ); - - if (result == DialogResult.Yes) - { - Settings.Default.AckAntiCheat = true; - return true; - } - - try { System.Diagnostics.Process.Start("explorer.exe", "https://steam-deck-tools.ayufan.dev/#anti-cheat-and-antivirus-software"); } - catch { } - return false; + return AntiCheatSettings.Default.AckAntiCheat( + Text, + "Usage of SteamOS or Max Fan Curve might trigger anti-cheat protection in some games.", + "Ensure that you USE DEFAULT FAN when playing games with ANTI-CHEAT PROTECTION."); } private void SystemEvents_PowerModeChanged(object sender, Microsoft.Win32.PowerModeChangedEventArgs e) diff --git a/FanControl/FanController.cs b/FanControl/FanController.cs index d0b1f6a..905c1e2 100644 --- a/FanControl/FanController.cs +++ b/FanControl/FanController.cs @@ -95,7 +95,7 @@ namespace FanControl try { - if (!Settings.Default.AckAntiCheat || Mode == FanMode.Default && !showForDefault) + if (AntiCheatSettings.Default.NotYet || Mode == FanMode.Default && !showForDefault) { Instance.UseKernelDrivers = false; CurrentRPM = null; diff --git a/FanControl/Settings.cs b/FanControl/Settings.cs index 776f67e..0dc4af8 100644 --- a/FanControl/Settings.cs +++ b/FanControl/Settings.cs @@ -27,11 +27,5 @@ namespace FanControl { get { return Instance.IsDEBUG; } } - - public bool AckAntiCheat - { - get { return Get("AckAntiCheat", false); } - set { Set("AckAntiCheat", value); } - } } } diff --git a/PerformanceOverlay/Controller.cs b/PerformanceOverlay/Controller.cs index 811cb1c..77f584e 100644 --- a/PerformanceOverlay/Controller.cs +++ b/PerformanceOverlay/Controller.cs @@ -165,38 +165,11 @@ namespace PerformanceOverlay private bool AckAntiCheat() { - if (Settings.Default.AckAntiCheat && Settings.Default.EnableExperimentalFeatures) - return true; - - Application.DoEvents(); - - var result = MessageBox.Show( - new Form { TopMost = true }, - String.Join("\n", - "WARNING!!!!", - "", - "Usage of OSD Kernel Drivers might trigger anti-cheat protection in some games.", - "This might result in kicking from the application or even be banned.", - "", - "Ensure that you set it to DISABLED when playing games with ANTI-CHEAT PROTECTION.", - "", - "CLICK YES TO ACKNOWLEDGE?", - "CLICK NO TO LEARN MORE." - ), TitleWithVersion, - MessageBoxButtons.YesNo, - MessageBoxIcon.Warning, - MessageBoxDefaultButton.Button2 + return AntiCheatSettings.Default.AckAntiCheat( + TitleWithVersion, + "Usage of OSD Kernel Drivers might trigger anti-cheat protection in some games.", + "Ensure that you set it to DISABLED when playing games with ANTI-CHEAT PROTECTION." ); - - if (result == DialogResult.Yes) - { - Settings.Default.AckAntiCheat = true; - return true; - } - - try { System.Diagnostics.Process.Start("explorer.exe", "https://steam-deck-tools.ayufan.dev/#anti-cheat-and-antivirus-software"); } - catch { } - return false; } private void setKernelDrivers(bool value) diff --git a/PerformanceOverlay/Settings.cs b/PerformanceOverlay/Settings.cs index f5478d2..b573f2a 100644 --- a/PerformanceOverlay/Settings.cs +++ b/PerformanceOverlay/Settings.cs @@ -51,11 +51,5 @@ namespace PerformanceOverlay { get { return Instance.IsDEBUG; } } - - public bool AckAntiCheat - { - get { return Get("AckAntiCheat", false); } - set { Set("AckAntiCheat", value); } - } } } diff --git a/PowerControl/Options/CPUFrequency.cs b/PowerControl/Options/CPUFrequency.cs index 9bd7f99..cfaf91a 100644 --- a/PowerControl/Options/CPUFrequency.cs +++ b/PowerControl/Options/CPUFrequency.cs @@ -1,3 +1,4 @@ +using CommonHelpers; using PowerControl.Helpers.AMD; namespace PowerControl.Options @@ -16,11 +17,10 @@ namespace PowerControl.Options ResetValue = () => { return "Default"; }, ApplyValue = (selected) => { - if (!Settings.Default.AckAntiCheat( + if (!AntiCheatSettings.Default.AckAntiCheat( Controller.TitleWithVersion, - "CPU", - "Changing GPU frequency requires kernel access for a short period. Leave the game if it uses anti-cheat protection.") - ) + "Changing CPU frequency requires kernel access for a short period.", + "Leave the game if it uses anti-cheat protection.")) return null; return CommonHelpers.Instance.WithGlobalMutex(200, () => diff --git a/PowerControl/Options/GPUFrequency.cs b/PowerControl/Options/GPUFrequency.cs index 5716c47..2ea04ba 100644 --- a/PowerControl/Options/GPUFrequency.cs +++ b/PowerControl/Options/GPUFrequency.cs @@ -1,3 +1,4 @@ +using CommonHelpers; using PowerControl.Helpers.AMD; namespace PowerControl.Options @@ -16,11 +17,10 @@ namespace PowerControl.Options ResetValue = () => { return "Default"; }, ApplyValue = (selected) => { - if (!Settings.Default.AckAntiCheat( + if (!AntiCheatSettings.Default.AckAntiCheat( Controller.TitleWithVersion, - "GPU", - "Changing GPU frequency requires kernel access for a short period. Leave the game if it uses anti-cheat protection.") - ) + "Changing GPU frequency requires kernel access for a short period.", + "Leave the game if it uses anti-cheat protection.")) return null; return CommonHelpers.Instance.WithGlobalMutex(200, () => diff --git a/PowerControl/Options/TDP.cs b/PowerControl/Options/TDP.cs index 548481d..6d85e21 100644 --- a/PowerControl/Options/TDP.cs +++ b/PowerControl/Options/TDP.cs @@ -1,4 +1,5 @@ using System.Diagnostics; +using CommonHelpers; using PowerControl.Helpers.AMD; namespace PowerControl.Options @@ -16,11 +17,10 @@ namespace PowerControl.Options ActiveOption = "?", ApplyValue = (selected) => { - if (!Settings.Default.AckAntiCheat( + if (!AntiCheatSettings.Default.AckAntiCheat( Controller.TitleWithVersion, - "TDP", - "Changing TDP requires kernel access for a short period. Leave the game if it uses anti-cheat protection.") - ) + "Changing TDP requires kernel access for a short period.", + "Leave the game if it uses anti-cheat protection.")) return null; uint mW = uint.Parse(selected.Replace("W", "")) * 1000; diff --git a/PowerControl/Program.cs b/PowerControl/Program.cs index 2c331d4..1f90549 100644 --- a/PowerControl/Program.cs +++ b/PowerControl/Program.cs @@ -18,28 +18,27 @@ namespace PowerControl { Instance.WithSentry(() => { - if (Settings.Default.EnableExperimentalFeatures) - { - if (!Settings.Default.AckAntiCheat( - Controller.TitleWithVersion, - "ExperimentalFeatures", - "You are running EXPERIMENTAL build.")) - return; - - for (int i = 0; !VangoghGPU.IsSupported && i < MAX_GPU_RETRIES; i++) - { - var status = Instance.WithGlobalMutex(1000, () => VangoghGPU.Detect()); - if (status != VangoghGPU.DetectionStatus.Retryable) - break; - - Thread.Sleep(300); - } - } - // To customize application configuration such as set high DPI settings or default font, // see https://aka.ms/applicationconfiguration. ApplicationConfiguration.Initialize(); + if (Settings.Default.EnableExperimentalFeatures) + { + if (!AntiCheatSettings.Default.AckAntiCheat( + Controller.TitleWithVersion, + "You are running EXPERIMENTAL build.", null, false)) + return; + } + + for (int i = 0; !VangoghGPU.IsSupported && i < MAX_GPU_RETRIES; i++) + { + var status = Instance.WithGlobalMutex(1000, () => VangoghGPU.Detect()); + if (status != VangoghGPU.DetectionStatus.Retryable) + break; + + Thread.Sleep(300); + } + using (var controller = new Controller()) { Application.Run(); diff --git a/PowerControl/Settings.cs b/PowerControl/Settings.cs index 696c2d7..00502e4 100644 --- a/PowerControl/Settings.cs +++ b/PowerControl/Settings.cs @@ -58,38 +58,5 @@ namespace PowerControl get { return Instance.IsDEBUG; } } - public bool AckAntiCheat(String title, String name, String message) - { - if (Get("AckAntiCheat" + name, false) && Settings.Default.EnableExperimentalFeatures) - return true; - - Application.DoEvents(); - - var result = MessageBox.Show( - new Form { TopMost = true }, - String.Join("\n", - "WARNING!!!!", - "", - message, - "This might result in kicking from the application or even be banned.", - "", - "CLICK YES TO ACKNOWLEDGE?", - "CLICK NO TO LEARN MORE." - ), title, - MessageBoxButtons.YesNo, - MessageBoxIcon.Warning, - MessageBoxDefaultButton.Button2 - ); - - if (result == DialogResult.Yes) - { - Set("AckAntiCheat" + name, true); - return true; - } - - try { System.Diagnostics.Process.Start("explorer.exe", "https://steam-deck-tools.ayufan.dev/#anti-cheat-and-antivirus-software"); } - catch { } - return false; - } } } diff --git a/RELEASE.md b/RELEASE.md index 9ff4d63..300f6a3 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -9,6 +9,7 @@ ## 0.6.x +- All: Improve Anti-Cheat protection to allow to dismiss it - SteamController: Fix `STEAM+DPadUp` not working - PowerControl/SteamController: Improve RTSS detection to ignore processes not generating frames for over 5s - PowerControl: Expose all in `GameProfiles`, and fix `GPU Scaling`, `Refresh Rate` and `FPS Limit` interwork diff --git a/docs/README.md b/docs/README.md index 56ebcfb..36187a5 100644 --- a/docs/README.md +++ b/docs/README.md @@ -69,6 +69,8 @@ or issues in games that use anti-cheat technology (including the possibility of Application by default does not use any kernel-level features. If you request a change that might trigger anti-cheat detection application does require to acknowledge this. + + ### Safe settings If you play online games application needs to disable kernel-features. diff --git a/docs/images/anti_cheat_protection.png b/docs/images/anti_cheat_protection.png new file mode 100644 index 0000000..e0e446d Binary files /dev/null and b/docs/images/anti_cheat_protection.png differ