private static (string publisher, string game) GetPublisherAndGameTitle() { string appInfoPath = Path.Combine(MelonUtils.GetGameDataDirectory(), "app.info"); string appInfo = File.ReadAllText(appInfoPath); string[] appInfoLines = appInfo.Split('\n'); return(appInfoLines[0], appInfoLines[1]); }
internal override bool Execute() { FixConfig(); if (Execute(new string[] { Core.GameAssemblyPath, Path.Combine(MelonUtils.GetGameDataDirectory(), "il2cpp_data", "Metadata", "global-metadata.dat") })) { return(true); } return(false); }
internal override bool Execute() { FixConfig(); MelonLogger.Msg("Executing Il2CppDumper..."); if (Execute(new string[] { Core.GameAssemblyPath, Path.Combine(MelonUtils.GetGameDataDirectory(), "il2cpp_data", "Metadata", "global-metadata.dat") })) { return(true); } ThrowInternalFailure("Failed to Execute Il2CppDumper!"); return(false); }
public override void OnApplicationStart() { var library = LoadLibrary(MelonUtils.GetGameDataDirectory() + "\\Plugins\\steam_api64.dll"); if (library == IntPtr.Zero) { MelonLogger.LogError("Library load failed"); return; } var names = new[] { "SteamAPI_Init", "SteamAPI_RestartAppIfNecessary", "SteamAPI_GetHSteamUser", "SteamAPI_RegisterCallback", "SteamAPI_UnregisterCallback", "SteamAPI_RunCallbacks", "SteamAPI_Shutdown" }; foreach (var name in names) { unsafe { var address = GetProcAddress(library, name); if (address == IntPtr.Zero) { MelonLogger.LogError($"Procedure {name} not found"); continue; } Imports.Hook((IntPtr)(&address), AccessTools.Method(typeof(NoSteamAtAllMod), nameof(InitFail)).MethodHandle .GetFunctionPointer()); } } }
private static void ReadGameInfo(AssetsManager assetsManager) { string gameDataPath = MelonUtils.GetGameDataDirectory(); AssetsFileInstance instance = null; try { string bundlePath = Path.Combine(gameDataPath, "globalgamemanagers"); if (!File.Exists(bundlePath)) { bundlePath = Path.Combine(gameDataPath, "mainData"); } if (!File.Exists(bundlePath)) { bundlePath = Path.Combine(gameDataPath, "data.unity3d"); if (!File.Exists(bundlePath)) { return; } BundleFileInstance bundleFile = assetsManager.LoadBundleFile(bundlePath); instance = assetsManager.LoadAssetsFileFromBundle(bundleFile, "globalgamemanagers"); } else { instance = assetsManager.LoadAssetsFile(bundlePath, true); } if (instance == null) { return; } assetsManager.LoadIncludedClassPackage(); if (!instance.file.typeTree.hasTypeTree) { assetsManager.LoadClassDatabaseFromPackage(instance.file.typeTree.unityVersion); } EngineVersion = UnityVersion.Parse(instance.file.typeTree.unityVersion); List <AssetFileInfoEx> assetFiles = instance.table.GetAssetsOfType(129); if (assetFiles.Count > 0) { AssetFileInfoEx playerSettings = assetFiles.First(); AssetTypeInstance assetTypeInstance = null; try { assetTypeInstance = assetsManager.GetTypeInstance(instance, playerSettings); } catch (Exception ex) { if (MelonDebug.IsEnabled()) { MelonLogger.Error(ex); MelonLogger.Warning("Attempting to use Large Class Package..."); } assetsManager.LoadIncludedLargeClassPackage(); assetsManager.LoadClassDatabaseFromPackage(instance.file.typeTree.unityVersion); assetTypeInstance = assetsManager.GetTypeInstance(instance, playerSettings); } if (assetTypeInstance != null) { AssetTypeValueField playerSettings_baseField = assetTypeInstance.GetBaseField(); AssetTypeValueField bundleVersion = playerSettings_baseField.Get("bundleVersion"); if (bundleVersion != null) { GameVersion = bundleVersion.GetValue().AsString(); } AssetTypeValueField companyName = playerSettings_baseField.Get("companyName"); if (companyName != null) { GameDeveloper = companyName.GetValue().AsString(); } AssetTypeValueField productName = playerSettings_baseField.Get("productName"); if (productName != null) { GameName = productName.GetValue().AsString(); } } } } catch (Exception ex) { if (MelonDebug.IsEnabled()) { MelonLogger.Error(ex); } MelonLogger.Error("Failed to Initialize Assets Manager!"); } if (instance != null) { instance.file.Close(); } }
public override void OnApplicationStart() { var pluginsPath = MelonUtils.GetGameDataDirectory() + "/Plugins"; var dllName = ShaderFilterApi.DLLName + ".dll"; try { using var resourceStream = Assembly.GetExecutingAssembly() .GetManifestResourceStream(typeof(TrueShaderAntiCrashMod), dllName); using var fileStream = File.Open(pluginsPath + "/" + dllName, FileMode.Create, FileAccess.Write); resourceStream.CopyTo(fileStream); } catch (IOException ex) { MelonLogger.Warning("Failed to write native unity plugin; will attempt loading it anyway. This is normal if you're running multiple instances of VRChat"); MelonDebug.Msg(ex.ToString()); } var process = Process.GetCurrentProcess(); foreach (ProcessModule module in process.Modules) { if (!module.FileName.Contains("UnityPlayer")) { continue; } var loadLibraryAddress = module.BaseAddress + 0x819130; var dg = Marshal.GetDelegateForFunctionPointer <FindAndLoadUnityPlugin>(loadLibraryAddress); var strPtr = Marshal.StringToHGlobalAnsi(ShaderFilterApi.DLLName); dg(strPtr, out var loaded); if (loaded == IntPtr.Zero) { MelonLogger.Error("Module load failed"); return; } ShaderFilterApi.Init(loaded); Marshal.FreeHGlobal(strPtr); break; } var category = MelonPreferences.CreateCategory("True Shader Anticrash"); var loopsEnabled = (MelonPreferences_Entry <bool>)category.CreateEntry("LimitLoops", true, "Limit loops"); var geometryEnabled = (MelonPreferences_Entry <bool>)category.CreateEntry("LimitGeometry", true, "Limit geometry shaders"); var tessEnabled = (MelonPreferences_Entry <bool>)category.CreateEntry("LimitTesselation", true, "Limit tesselation"); MelonPreferences_Entry <bool> enabledInPublicsOnly = null; IEnumerator WaitForRoomManagerAndUpdate() { while (RoomManager.field_Internal_Static_ApiWorldInstance_0 == null) { yield return(null); } UpdateLimiters(); } void UpdateLimiters() { if (enabledInPublicsOnly.Value) { var room = RoomManager.field_Internal_Static_ApiWorldInstance_0; if (room == null) { MelonCoroutines.Start(WaitForRoomManagerAndUpdate()); return; } if (room.GetAccessType() != ApiWorldInstance.AccessType.Public) { ShaderFilterApi.SetFilteringState(false, false, false); return; } } ShaderFilterApi.SetFilteringState(loopsEnabled.Value, geometryEnabled.Value, tessEnabled.Value); } loopsEnabled.OnValueChanged += (_, value) => UpdateLimiters(); geometryEnabled.OnValueChanged += (_, value) => UpdateLimiters(); tessEnabled.OnValueChanged += (_, value) => UpdateLimiters(); var maxLoopIterations = (MelonPreferences_Entry <int>)category.CreateEntry("MaxLoopIterations", 128, "Max loop iterations"); maxLoopIterations.OnValueChanged += (_, value) => ShaderFilterApi.SetLoopLimit(value); var maxGeometry = (MelonPreferences_Entry <int>)category.CreateEntry("MaxGeometryOutputs", 60, "Max geometry shader outputs"); maxGeometry.OnValueChanged += (_, value) => ShaderFilterApi.SetLoopLimit(value); var maxTess = (MelonPreferences_Entry <float>)category.CreateEntry("MaxTesselation", 5f, "Max tesselation power"); maxTess.OnValueChanged += (_, value) => ShaderFilterApi.SetMaxTesselationPower(value); var enabledForWorlds = (MelonPreferences_Entry <bool>)category.CreateEntry("DisableDuringWorldLoad", true, "Try to avoid affecting world shaders"); enabledInPublicsOnly = (MelonPreferences_Entry <bool>)category.CreateEntry("EnabledInPublicsOnly", false, "Only enabled in public instances"); SceneManager.add_sceneLoaded(new Action <Scene, LoadSceneMode>((sc, _) => { if (sc.buildIndex == -1) { UpdateLimiters(); } })); SceneManager.add_sceneUnloaded(new Action <Scene>(_ => { if (enabledForWorlds.Value) { ShaderFilterApi.SetFilteringState(false, false, false); } })); UpdateLimiters(); ShaderFilterApi.SetMaxTesselationPower(maxTess.Value); ShaderFilterApi.SetLoopLimit(maxLoopIterations.Value); ShaderFilterApi.SetGeometryLimit(maxGeometry.Value); if (MelonHandler.Mods.Any(it => it.Assembly.GetName().Name == "UIExpansionKit" && it.Assembly.GetName().Version >= new Version(0, 2, 4))) { AddNewUixProperties(category.Identifier); } }
internal bool Execute() { FixConfig(); MelonLogger.Msg("Executing Il2CppDumper..."); string metadata_path = Path.Combine(Path.Combine(Path.Combine(string.Copy(MelonUtils.GetGameDataDirectory()), "il2cpp_data"), "Metadata"), "global-metadata.dat"); return(Execute(new string[] { Core.GameAssemblyPath, metadata_path })); }