Please disclose if your mod was created primarily using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of Network Behaviour Event Injector v1.0.0
BepInEx/patchers/Daydream.NetworkBehaviourEvents.dll
Decompiled 2 years agousing System; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using BepInEx; using BepInEx.Logging; using HarmonyLib; using Mono.Cecil; using Mono.Cecil.Cil; using Mono.Collections.Generic; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: AssemblyTitle("Daydream.NetworkBehaviourEvents")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("Daydream.NetworkBehaviourEvents")] [assembly: AssemblyCopyright("Copyright © 2024")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("8D6B7A3E-C51F-4A44-8D6F-59A3565273B8")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyVersion("1.0.0.0")] namespace Daydream.NetworkBehaviourEvents; public class Test { public virtual void OnTest() { } } public class Tester : Test { public override void OnTest() { base.OnTest(); } } public static class Preloader { private const string NetworkBehaviourFullName = "Unity.Netcode.NetworkBehaviour"; private static ManualLogSource Logger { get; set; } private static TypeReference NetworkBehaviourRef { get; set; } private static MethodReference[] NetworkBehaviourEvents { get; set; } public static IEnumerable<string> TargetDLLs { get; } = new string[1] { "Assembly-CSharp.dll" }; public static void Patch(AssemblyDefinition assemblyDefinition) { Logger.LogInfo((object)"Patching NetworkBehaviour's sub-classes to always contain implementations of virtual methods.."); NetworkBehaviourRef = assemblyDefinition.MainModule.GetTypeReferences().FirstOrDefault((Func<TypeReference, bool>)((TypeReference typeRef) => ((MemberReference)typeRef).FullName == "Unity.Netcode.NetworkBehaviour")); if (NetworkBehaviourRef == null) { Logger.LogError((object)"The game doesn't contain a reference to Unity.Netcode.NetworkBehaviour"); return; } NetworkBehaviourEvents = (from methodDef in (IEnumerable<MethodDefinition>)NetworkBehaviourRef.Resolve().Methods where methodDef.IsVirtual && !((MethodReference)methodDef).HasGenericParameters && ((MemberReference)methodDef).Name.StartsWith("On") select assemblyDefinition.MainModule.ImportReference((MethodReference)(object)methodDef)).ToArray(); CollectionExtensions.Do<TypeDefinition>(from typeDef in assemblyDefinition.MainModule.GetTypes() where typeDef.IsSubclassOf("Unity.Netcode.NetworkBehaviour") select typeDef, (Action<TypeDefinition>)delegate(TypeDefinition typeDef) { foreach (MethodReference item in NetworkBehaviourEvents.Where((MethodReference methodRef) => ((IEnumerable<MethodDefinition>)typeDef.Methods).All((MethodDefinition methodDef) => ((MemberReference)methodDef).Name != ((MemberReference)methodRef).Name))) { CreateEventMethod(assemblyDefinition, item, typeDef); } }); assemblyDefinition.Write(Path.Combine(Paths.CachePath, "Assembly-CSharp.dll")); } private static void CreateEventMethod(AssemblyDefinition assemblyDefinition, MethodReference methodReference, TypeDefinition typeDef) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0044: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Unknown result type (might be due to invalid IL or missing references) //IL_0096: Unknown result type (might be due to invalid IL or missing references) //IL_00ba: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Unknown result type (might be due to invalid IL or missing references) MethodDefinition val = new MethodDefinition(((MemberReference)methodReference).Name, (MethodAttributes)198, assemblyDefinition.MainModule.TypeSystem.Void); typeDef.Methods.Add(val); val.Body.InitLocals = true; Enumerator<ParameterDefinition> enumerator = methodReference.Parameters.GetEnumerator(); try { while (enumerator.MoveNext()) { ParameterDefinition current = enumerator.Current; ((MethodReference)val).Parameters.Add(((ParameterReference)current).Resolve()); } } finally { ((IDisposable)enumerator).Dispose(); } ILProcessor iLProcessor = val.Body.GetILProcessor(); iLProcessor.Emit(OpCodes.Ldarg_0); for (int i = 0; i < methodReference.Parameters.Count; i++) { iLProcessor.Emit(OpCodes.Ldarg, i + 1); } iLProcessor.Emit(OpCodes.Call, methodReference); iLProcessor.Emit(OpCodes.Ret); } private static void Initialize() { Logger = Logger.CreateLogSource("DayDream.NetworkBehaviourEvents"); } public static void Finish() { Logger.LogInfo((object)("Patching complete! Verifying types contain {" + string.Join(", ", NetworkBehaviourEvents.Select((MethodReference evt) => ((MemberReference)evt).Name).ToArray()) + "}...")); Assembly assembly2 = AppDomain.CurrentDomain.GetAssemblies().FirstOrDefault((Assembly assembly) => assembly.FullName.StartsWith("Assembly-CSharp")); if ((object)assembly2 == null) { Logger.LogError((object)"Couldn't find Assembly-CSharp within the AppDomain! Was it even patched?!"); } else { if (NetworkBehaviourRef == null || NetworkBehaviourEvents == null) { return; } Type[] array = (from type in assembly2.GetTypes() where type.IsSubclassOf("Unity.Netcode.NetworkBehaviour") select type).ToArray(); int num = 0; Type[] array2 = array; foreach (Type allType in array2) { if (NetworkBehaviourEvents.Aggregate(0, (int i, MethodReference reference) => i + (((object)allType.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic).FirstOrDefault((MethodInfo methodInfo) => methodInfo.Name == ((MemberReference)reference).Name) != null) ? 1 : 0)) == NetworkBehaviourEvents.Length) { num++; } } Logger.LogInfo((object)(num + "/" + array.Length + " NetworkBehaviour Sub-Classes are now in compliance! Useless reference dll can be found in /BepInEx/cache/.")); } } private static bool IsSubclassOf(this Type type, string fullClassName) { if (type.FullName == fullClassName) { return false; } while ((object)type != null) { if (type.FullName == fullClassName) { return true; } type = type.BaseType; } return false; } private static bool IsSubclassOf(this TypeDefinition typeDefinition, string fullClassName) { if (((MemberReference)typeDefinition).FullName == fullClassName) { return false; } while (typeDefinition != null) { if (((MemberReference)typeDefinition).FullName == fullClassName) { return true; } TypeReference baseType = typeDefinition.BaseType; typeDefinition = ((baseType != null) ? baseType.Resolve() : null); } return false; } }