/// <summary>Applies all registered patches</summary> /// <returns>The generated replacement method</returns> /// public MethodInfo Patch() { if (original == null) { throw new NullReferenceException($"Null method for {instance.Id}"); } if (original.IsDeclaredMember() == false) { var declaredMember = original.GetDeclaredMember(); throw new ArgumentException($"You can only patch implemented methods/constructors. Path the declared method {declaredMember.FullDescription()} instead."); } lock (locker) { var patchInfo = HarmonySharedState.GetPatchInfo(original); if (patchInfo == null) { patchInfo = new PatchInfo(); } PatchFunctions.AddPrefix(patchInfo, instance.Id, prefix); PatchFunctions.AddPostfix(patchInfo, instance.Id, postfix); PatchFunctions.AddTranspiler(patchInfo, instance.Id, transpiler); PatchFunctions.AddFinalizer(patchInfo, instance.Id, finalizer); var replacement = PatchFunctions.UpdateWrapper(original, patchInfo); HarmonySharedState.UpdatePatchInfo(original, patchInfo); return(replacement); } }
/// <summary>Applies the patch</summary> /// <returns>A list of all created dynamic methods</returns> /// public List <DynamicMethod> Patch() { lock (locker) { var dynamicMethods = new List <DynamicMethod>(); foreach (var original in originals) { if (original == null) { throw new NullReferenceException("Null method for " + instance.Id); } var individualPrepareResult = RunMethod <HarmonyPrepare, bool>(true, original); if (individualPrepareResult) { var patchInfo = HarmonySharedState.GetPatchInfo(original); if (patchInfo == null) { patchInfo = new PatchInfo(); } PatchFunctions.AddPrefix(patchInfo, instance.Id, prefix); PatchFunctions.AddPostfix(patchInfo, instance.Id, postfix); PatchFunctions.AddTranspiler(patchInfo, instance.Id, transpiler); PatchFunctions.AddFinalizer(patchInfo, instance.Id, finalizer); dynamicMethods.Add(PatchFunctions.UpdateWrapper(original, patchInfo, instance.Id)); HarmonySharedState.UpdatePatchInfo(original, patchInfo); RunMethod <HarmonyCleanup>(original); } } return(dynamicMethods); } }
void ProcessPatchJob(PatchJobs <MethodInfo> .Job job) { MethodInfo replacement = default; var individualPrepareResult = RunMethod <HarmonyPrepare, bool>(true, false, null, job.original); Exception exception = null; if (individualPrepareResult) { lock (PatchProcessor.locker) { try { var patchInfo = HarmonySharedState.GetPatchInfo(job.original); if (patchInfo == null) { patchInfo = new PatchInfo(); } foreach (var prefix in job.prefixes) { PatchFunctions.AddPrefix(patchInfo, instance.Id, prefix); } foreach (var postfix in job.postfixes) { PatchFunctions.AddPostfix(patchInfo, instance.Id, postfix); } foreach (var transpiler in job.transpilers) { PatchFunctions.AddTranspiler(patchInfo, instance.Id, transpiler); } foreach (var finalizer in job.finalizers) { PatchFunctions.AddFinalizer(patchInfo, instance.Id, finalizer); } replacement = PatchFunctions.UpdateWrapper(job.original, patchInfo); HarmonySharedState.UpdatePatchInfo(job.original, patchInfo); } catch (Exception ex) { exception = ex; } } } RunMethod <HarmonyCleanup>(ref exception, job.original, exception); if (exception != null) { ReportException(exception, job.original); } job.replacement = replacement; }