using System.Collections.ObjectModel; using UnityEngine; namespace BetterAmongUs; class FileChecker { private static bool Enabled = true; private static readonly ReadOnlyCollection UnsupportedBepInExMods = new(new List { "TOHE", "YuAntiCheat" }); // Put BepInEx BepInPlugin name, not dll name here lol. private static readonly ReadOnlyCollection BannedBepInExMods = new(new List { "MalumMenu", "MalumMenu-Yu", "MalumMenuYu", "AUnlocker" }); // Put BepInEx BepInPlugin name, not dll name here lol. private static readonly ReadOnlyCollection KeyWordsInVersionInfo = new(new List { "Malum", "Sicko", "AUM" }); // Banned words for version text public static string UnauthorizedReason = string.Empty; public static List CheatTags = []; // For API report public static bool HasTrySpoofFriendCode = false; public static bool HasUnauthorizedFile = false; public static bool HasShownPopUp = false; // Set up if unauthorized files have been found. public static void UpdateUnauthorizedFiles() { if (Enabled == false) return; if (GameStates.IsDev) { HasTrySpoofFriendCode = false; } GameObject PlayButton = GameObject.Find("Main Buttons/PlayButton"); // Disable play button if (PlayButton != null) { if (EOSManager.Instance.userId == null || HasTrySpoofFriendCode) { PlayButton.GetComponent().enabled = false; GameObject.Find("Main Buttons/PlayButton/Inactive").GetComponent().color = Color.gray; } else { PlayButton.GetComponent().enabled = true; GameObject.Find("Main Buttons/PlayButton/Inactive").GetComponent().color = new Color(1.0f, 1.0f, 1.0f); } } // Unauthorized file or ban detected. if (HasUnauthorizedFile) { GameObject playOnlineButton = GameObject.Find("PlayOnlineButton"); if (playOnlineButton != null) { PassiveButton PassiveButtonComponent = playOnlineButton.GetComponent(); PlayOnlineButtonSprite PlayOnlineButtonSpriteComponent = playOnlineButton.GetComponent(); if (PassiveButtonComponent != null) { if (PassiveButtonComponent != null) PassiveButtonComponent.enabled = false; PlayOnlineButtonSpriteComponent?.SetGreyscale(); } } GameObject SignInStatus = GameObject.Find("SignInStatus"); if (SignInStatus != null) { SignInStatusComponent SignInStatusCom = SignInStatus.GetComponent(); SignInStatusCom?.SetOffline(); GameObject.Find("Account_CTA")?.SetActive(false); GameObject.Find("AccountTab/GameHeader/LeftSide/FriendCode")?.SetActive(false); if (GameObject.Find("Stats_CTA") != null) GameObject.Find("Stats_CTA").transform.position = new Vector2(1.7741f, -0.2442f); } SoundManager.instance?.ChangeMusicVolume(0); return; } if (EOSManager.Instance.editAccountUsername.gameObject.active || EOSManager.Instance.askToMergeAccount.gameObject.active) { HasTrySpoofFriendCode = true; } } private static readonly string UnauthorizedTextDetectedMsg = "Unauthorized {0} Detected"; private static readonly string UnauthorizedFileMsg = "Unauthorized Game Files Detected"; private static readonly string OnlineMsg = "Online access has been temporarily disabled!"; private static readonly string UnsupportedBepInExModMsg = "Unsupported BepInEx Mod Detected"; private static readonly string BannedBepInExModMsg = "Unauthorized BepInEx Mod Detected"; // Check if there's any unauthorized files. public static bool CheckIfUnauthorizedFiles() { if (Enabled == false) return false; // Get user info for later use with API. string ClientUserName = GameObject.Find("AccountTab")?.GetComponent()?.userName.text; string ClientFriendCode = EOSManager.Instance.friendCode; string ClientPUIDHash = Utils.GetHashPuid(EOSManager.Instance.ProductUserId); if (GameStates.IsDev) { Enabled = false; return false; } // Check for Banned BepInEx Mods foreach (var bannedMod in BannedBepInExMods) { if (IsBepInExModLoaded(bannedMod)) { if (!HasUnauthorizedFile) UnauthorizedReason = BannedBepInExModMsg; if (!CheatTags.Contains($"{bannedMod}-BepInEx")) CheatTags.Add($"{bannedMod}-BepInEx"); HasUnauthorizedFile = true; } } // Check for Unsupported BepInEx Mods foreach (var unsupportedMod in UnsupportedBepInExMods) { if (IsBepInExModLoaded(unsupportedMod)) { if (!HasUnauthorizedFile) UnauthorizedReason = UnsupportedBepInExModMsg; HasUnauthorizedFile = true; } } // Check for version.dll if (File.Exists(Path.Combine(Environment.CurrentDirectory, "version.dll"))) { string versiondll = "'version.dll'"; if (!HasUnauthorizedFile) UnauthorizedReason = string.Format(UnauthorizedTextDetectedMsg, versiondll); if (!CheatTags.Contains("version.dll")) CheatTags.Add("version.dll"); HasUnauthorizedFile = true; } // Check for banned words in VersionInfo display. Aka check cheat developers ego foreach (var WordInVersionInfo in KeyWordsInVersionInfo) { if (UnityEngine.Object.FindFirstObjectByType().text.text.ToLower().Contains(WordInVersionInfo.ToLower())) { if (!HasUnauthorizedFile) UnauthorizedReason = UnauthorizedFileMsg; if (!CheatTags.Contains($"{WordInVersionInfo}-VersionInfo")) CheatTags.Add($"{WordInVersionInfo}-VersionInfo"); HasUnauthorizedFile = true; } } // Check for Sicko leftover files if (File.Exists(Path.Combine(Environment.CurrentDirectory, "sicko-settings.json")) || File.Exists(Path.Combine(Environment.CurrentDirectory, "sicko-log.txt")) || File.Exists(Path.Combine(Environment.CurrentDirectory, "sicko-prev-log.txt")) || File.Exists(Path.Combine(Environment.CurrentDirectory, "sicko-config"))) { if (!HasUnauthorizedFile) UnauthorizedReason = UnauthorizedFileMsg; if (!CheatTags.Contains("Sicko-Menu-Files")) CheatTags.Add("Sicko-Menu-Files"); HasUnauthorizedFile = true; } // Check for AUM leftover files if (File.Exists(Path.Combine(Environment.CurrentDirectory, "settings.json")) || File.Exists(Path.Combine(Environment.CurrentDirectory, "aum-log.txt")) || File.Exists(Path.Combine(Environment.CurrentDirectory, "aum-prev-log.txt"))) { if (!HasUnauthorizedFile) UnauthorizedReason = UnauthorizedFileMsg; if (!CheatTags.Contains("AUM-Menu-Files")) CheatTags.Add("AUM-Menu-Files"); HasUnauthorizedFile = true; } // ----------- Unused Until API support is added! ----------- // Combine Player information and Tags string tagsAsString = string.Join(" - ", CheatTags); string playerInfo = $"{ClientUserName}.{ClientFriendCode}.{ClientPUIDHash} - {tagsAsString}"; // If Detection goes off send this information to the API database! // ---------------------------------------------------------- return HasUnauthorizedFile; } // Get all loaded BepInEx mods and check if one is on the ban list. private static bool IsBepInExModLoaded(string modName) { foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies()) { if (assembly.FullName.Contains(modName)) { return true; } } return false; } }