本文整理汇总了C#中dnlib.DotNet.Emit.Instruction.CalculateStackUsage方法的典型用法代码示例。如果您正苦于以下问题:C# Instruction.CalculateStackUsage方法的具体用法?C# Instruction.CalculateStackUsage怎么用?C# Instruction.CalculateStackUsage使用的例子?那么恭喜您, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类dnlib.DotNet.Emit.Instruction
的用法示例。
在下文中一共展示了Instruction.CalculateStackUsage方法的6个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C#代码示例。
示例1: CalculateStackUsage
static void CalculateStackUsage(Instruction instr, bool methodHasReturnValue, out int pushes, out int pops) {
instr.CalculateStackUsage(false, out pushes, out pops);
}
示例2: EmulateToReturn
bool EmulateToReturn(int index, Instruction lastInstr) {
int pushes, pops;
lastInstr.CalculateStackUsage(false, out pushes, out pops);
instructionEmulator.Pop(pops);
returnValue = null;
if (pushes != 0) {
returnValue = new UnknownValue();
instructionEmulator.SetProtected(returnValue);
instructionEmulator.Push(returnValue);
}
if (!EmulateInstructions(ref index, true))
return false;
if (index >= methodToInline.Body.Instructions.Count)
return false;
if (methodToInline.Body.Instructions[index].OpCode.Code != Code.Ret)
return false;
if (returnValue != null) {
if (instructionEmulator.Pop() != returnValue)
return false;
}
return instructionEmulator.StackSize() == 0;
}
示例3: TraceArguments
/// <summary>
/// Traces the arguments of the specified call instruction.
/// </summary>
/// <param name="instr">The call instruction.</param>
/// <returns>The indexes of the begin instruction of arguments.</returns>
/// <exception cref="System.ArgumentException">The specified call instruction is invalid.</exception>
/// <exception cref="InvalidMethodException">The method body is invalid.</exception>
public int[] TraceArguments(Instruction instr) {
if (instr.OpCode.Code != Code.Call && instr.OpCode.Code != Code.Callvirt && instr.OpCode.Code != Code.Newobj)
throw new ArgumentException("Invalid call instruction.", "instr");
int push, pop;
instr.CalculateStackUsage(out push, out pop); // pop is number of arguments
if (pop == 0)
return new int[0];
int instrIndex = offset2index[instr.Offset];
int argCount = pop;
int targetStack = BeforeStackDepths[instrIndex] - argCount;
// Find the begin instruction of method call
int beginInstrIndex = -1;
var seen = new HashSet<uint>();
var working = new Queue<int>();
working.Enqueue(offset2index[instr.Offset] - 1);
while (working.Count > 0) {
int index = working.Dequeue();
while (index >= 0) {
if (BeforeStackDepths[index] == targetStack)
break;
if (fromInstrs.ContainsKey(index))
foreach (Instruction fromInstr in fromInstrs[index]) {
if (!seen.Contains(fromInstr.Offset)) {
seen.Add(fromInstr.Offset);
working.Enqueue(offset2index[fromInstr.Offset]);
}
}
index--;
}
if (index < 0)
return null;
if (beginInstrIndex == -1)
beginInstrIndex = index;
else if (beginInstrIndex != index)
return null;
}
// Trace the index of arguments
seen.Clear();
var working2 = new Queue<Tuple<int, Stack<int>>>();
working2.Clear();
working2.Enqueue(Tuple.Create(beginInstrIndex, new Stack<int>()));
int[] ret = null;
while (working2.Count > 0) {
Tuple<int, Stack<int>> tuple = working2.Dequeue();
int index = tuple.Item1;
Stack<int> evalStack = tuple.Item2;
while (index != instrIndex && index < method.Body.Instructions.Count) {
Instruction currentInstr = Instructions[index];
currentInstr.CalculateStackUsage(out push, out pop);
int stackUsage = pop - push;
if (stackUsage < 0) {
Debug.Assert(stackUsage == -1); // i.e. push
evalStack.Push(index);
}
else {
if (evalStack.Count < stackUsage)
return null;
for (int i = 0; i < stackUsage; i++)
evalStack.Pop();
}
object instrOperand = currentInstr.Operand;
if (currentInstr.Operand is Instruction) {
int targetIndex = offset2index[((Instruction)currentInstr.Operand).Offset];
if (currentInstr.OpCode.FlowControl == FlowControl.Branch)
index = targetIndex;
else {
working2.Enqueue(Tuple.Create(targetIndex, new Stack<int>(evalStack)));
index++;
}
}
else if (currentInstr.Operand is Instruction[]) {
foreach (Instruction targetInstr in (Instruction[])currentInstr.Operand)
working2.Enqueue(Tuple.Create(offset2index[targetInstr.Offset], new Stack<int>(evalStack)));
index++;
}
else
index++;
}
if (evalStack.Count != argCount)
return null;
if (ret != null && !evalStack.SequenceEqual(ret))
return null;
ret = evalStack.ToArray();
//.........这里部分代码省略.........
示例4: VerifyValidArgs
bool VerifyValidArgs(Instruction instr)
{
int pushes, pops;
instr.CalculateStackUsage(out pushes, out pops);
if (pops < 0)
return false;
bool retVal;
Value val2, val1;
switch (pops) {
case 0:
return true;
case 1:
val1 = instructionEmulator.Pop();
retVal = VerifyValidArg(val1);
instructionEmulator.Push(val1);
return retVal;
case 2:
val2 = instructionEmulator.Pop();
val1 = instructionEmulator.Pop();
retVal = VerifyValidArg(val2) && VerifyValidArg(val1);
instructionEmulator.Push(val1);
instructionEmulator.Push(val2);
return retVal;
}
return false;
}
示例5: UpdateStack
void UpdateStack(Instruction instr) {
int pushes, pops;
instr.CalculateStackUsage(out pushes, out pops);
if (pops == -1)
valueStack.Clear();
else {
valueStack.Pop(pops);
valueStack.Push(pushes);
}
}
示例6: Emulate_Call
void Emulate_Call(Instruction instr, IMethod method) {
int pushes, pops;
instr.CalculateStackUsage(out pushes, out pops);
valueStack.Pop(pops);
if (pushes == 1)
valueStack.Push(GetUnknownValue(method.MethodSig.GetRetType()));
else
valueStack.Push(pushes);
}