EverestAPI / Everest

Everest - Celeste Mod Loader / Mod API
https://everestapi.github.io/
MIT License
367 stars 80 forks source link

Game crash when ilhook Level.TransitionRoutine #371

Open DemoJameson opened 3 years ago

DemoJameson commented 3 years ago
public void OnLoad() {
    new ILHook(typeof(Level).GetMethod("TransitionRoutine", BindingFlags.Instance | BindingFlags.NonPublic).GetStateMachineTarget(), il => {});
}
Ver 1.4.0.0-xna [Everest: 3014-azure-106d7]
08/27/2021 15:24:16
System.TypeLoadException: Could not load type 'Celeste.patch_Level+<TransitionRoutine>d__25' from assembly 'Celeste, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null'.
   at System.Reflection.CustomAttribute._CreateCaObject(RuntimeModule pModule, IRuntimeMethodInfo pCtor, Byte** ppBlob, Byte* pEndBlob, Int32* pcNamedArgs)
   at System.Reflection.CustomAttribute.CreateCaObject(RuntimeModule module, IRuntimeMethodInfo ctor, IntPtr& blob, IntPtr blobEnd, Int32& namedArgs)
   at System.Reflection.CustomAttribute.GetCustomAttributes(RuntimeModule decoratedModule, Int32 decoratedMetadataToken, Int32 pcaCount, RuntimeType attributeFilterType, Boolean mustBeInheritable, IList derivedAttributes, Boolean isDecoratedTargetSecurityTransparent)
   at System.Reflection.CustomAttribute.GetCustomAttributes(RuntimeMethodInfo method, RuntimeType caType, Boolean inherit)
   at System.Reflection.RuntimeMethodInfo.GetCustomAttributes(Boolean inherit)
   at MonoMod.Utils.Extensions.GetStateMachineTarget(MethodInfo method)
   at Celeste.Mod.SpeedrunTool.SaveLoad.StateManager.OnLoad()
WEGFan commented 3 years ago

I guess it's because MonoMod didn't relink IteratorStateMachine and causing the parameter still refers to patch_ class so the game failed to load it when trying to get the MoveNext() method. It will be fixed in #351.

For now, you can try first get the instructions of TransitionRoutine and get the state machine class from the operand of IL_0001, then just hook the MoveNext() method of the class:

IL_0000: ldc.i4.0
IL_0001: newobj instance void Celeste.Level/'<TransitionRoutine>d__25'::.ctor(int32)

Or you can try https://www.pastery.net/jzvbdv/ (only tested with a console application, not guaranteed to work)

Kalobi commented 2 years ago

Tested now that #351 is merged, still crashes

WEGFan commented 2 years ago
  • [ ] Correct multiple IteratorStateMachine attributes on a single iterator method It will break a lot of mods, so it's better to only include this after we have a solution to migrate.

The patch didn't get merged eventually, I forgot to edit the comment in this issue. 😅