public void ValidateStackOrThrow()
{
var stacksize = StackSizOneEnter;
var startstacksize = stacksize;
var ins = StartInstruction;
while (true)
{
var popcount = ins.GetPopCount(MethodBody.Method, stacksize);
stacksize -= popcount;
// exception handlers pushes one value to stack
if (MethodBody.HasExceptionHandlers && MethodBody.ExceptionHandlers.Any(eh => eh.HandlerStart == ins))
stacksize++;
if (stacksize < 0)
throw new Exception(
$"instruction {ins} pops {popcount} values from stack." + Environment.NewLine +
$"but there are only {stacksize + popcount} values on stack. at:" + Environment.NewLine +
ListInstructions(ins)); // todo: print full instruction list
stacksize += ins.GetPushCount();
if (stacksize != 0 && ins.OpCode.FlowControl == FlowControl.Return && ins.OpCode != OpCodes.Endfinally)
throw new Exception("stacksize on return is not zero. at: " + Environment.NewLine +
ListInstructions(EndInstruction)); // todo: print full instruction list
if (ins == EndInstruction)
break;
ins = ins.Next;
};
_stackDelta = stacksize - startstacksize;
}