gpt4 book ai didi

.net - Mono.Cecil:注入(inject)try/finally?

转载 作者:行者123 更新时间:2023-12-04 20:01:07 24 4
gpt4 key购买 nike

Mono.Cecil was answered here 中实现 try/catch 的良好概述,但他在一次完整的尝试/捕捉/最后停下来。那么如何使用 Mono.Cecil 实现 try/finally?

最佳答案

这里是如何注入(inject)finally。

首先,您需要修复您的退货声明。你只想要一个。

Instruction FixReturns()
{
if (Method.ReturnType == TypeSystem.Void)
{
var instructions = body.Instructions;
var lastRet = Instruction.Create(OpCodes.Ret);
instructions.Add(lastRet);

for (var index = 0; index < instructions.Count - 1; index++)
{
var instruction = instructions[index];
if (instruction.OpCode == OpCodes.Ret)
{
instructions[index] = Instruction.Create(OpCodes.Leave, lastRet);
}
}
return lastRet;
}
else
{
var instructions = body.Instructions;
var returnVariable = new VariableDefinition("methodTimerReturn", Method.ReturnType);
body.Variables.Add(returnVariable);
var lastLd = Instruction.Create(OpCodes.Ldloc, returnVariable);
instructions.Add(lastLd);
instructions.Add(Instruction.Create(OpCodes.Ret));

for (var index = 0; index < instructions.Count - 2; index++)
{
var instruction = instructions[index];
if (instruction.OpCode == OpCodes.Ret)
{
instructions[index] = Instruction.Create(OpCodes.Leave, lastLd);
instructions.Insert(index, Instruction.Create(OpCodes.Stloc, returnVariable));
index++;
}
}
return lastLd;
}
}

然后找到第一条指令。如果它是实例构造函数,则需要跳过 2。
Instruction FirstInstructionSkipCtor()
{
if (Method.IsConstructor && !Method.IsStatic)
{
return body.Instructions.Skip(2).First();
}
return body.Instructions.First();
}

然后缝合在一起
void InnerProcess()
{
body = Method.Body;
body.SimplifyMacros();
ilProcessor = body.GetILProcessor();

var returnInstruction = FixReturns();

var firstInstruction = FirstInstructionSkipCtor();

var beforeReturn = Instruction.Create(OpCodes.Nop);
ilProcessor.InsertBefore(returnInstruction, beforeReturn);

InjectIlForFinaly(returnInstruction);

var handler = new ExceptionHandler(ExceptionHandlerType.Finally)
{
TryStart = firstInstruction,
TryEnd = beforeReturn,
HandlerStart = beforeReturn,
HandlerEnd = returnInstruction,
};

body.ExceptionHandlers.Add(handler);
body.InitLocals = true;
body.OptimizeMacros();
}

关于.net - Mono.Cecil:注入(inject)try/finally?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12769699/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com