public static void WriteInstruction (TextWriter writer, Instruction instruction)
		{
			writer.Write (FormatLabel (instruction.Offset));
			writer.Write (": ");
			writer.Write (instruction.OpCode.Name);
			WriteOperand (writer, instruction);
		}
Ejemplo n.º 2
0
 public ProcessorState(Stack<Address> stack, VariableInfo[] locals, IList<Address> args, Instruction instruction,
    Instruction last = null, IDictionary<FieldInfo, Address> delegates = null)
 {
     Delegates = delegates ?? new Dictionary<FieldInfo, Address>();
     Stack = stack;
     Locals = locals;
     Args = args;
     Instruction = instruction;
     Last = last;
 }
Ejemplo n.º 3
0
        public Expression Process(Instruction instruction, Type returnType)
        {
            var ex = AdjustType(Process(instruction), returnType);

            if (ex.Type != returnType && returnType != typeof(void))
            {
                return Expression.Convert(ex, returnType);
            }

            return ex;
        }
Ejemplo n.º 4
0
        private static OpCode OpCodeFor(MR.Instruction instruction)
        {
            foreach (var opcode in _opcodes)
            {
                if (opcode.Value == instruction.OpCode.Value)
                {
                    return(opcode);
                }
            }

            throw new NotSupportedException("OpCode not found: " + instruction.OpCode.Name);
        }
Ejemplo n.º 5
0
        public static Expression Process(VariableInfo[] locals, IList<Address> args, Instruction instruction, Type returnType)
        {
            Processor processor = new Processor();
            processor.states.Push(new ProcessorState(new Stack<Address>(), locals, args, instruction));

            var ex = AdjustType(processor.Process(), returnType);

            if (ex.Type != returnType && returnType != typeof(void))
            {
                return Expression.Convert(ex, returnType);
            }

            return ex;
        }
Ejemplo n.º 6
0
 public ProcessorState Clone(Instruction instruction, Instruction last = null)
 {
     var state = new ProcessorState(null, new VariableInfo[Locals.Length], Args.ToArray(), instruction, last, Delegates);
     var addressMap = new Dictionary<Address, Address>();
     var buffer = new List<Address>();
     foreach (var address in Stack)
     {
         buffer.Add(address.Clone(addressMap));
     }
     state.Stack = new Stack<Address>(Enumerable.Reverse(buffer));
     for (int i = 0; i < Locals.Length; i++)
     {
         state.Locals[i] = new VariableInfo(Locals[i].Type);
         state.Locals[i].Address = Locals[i].Address.Clone(addressMap);
     }
     return state;
 }
Ejemplo n.º 7
0
        void ReadOperand(Instruction instruction)
        {
            switch (instruction.OpCode.OperandType)
            {
                case OperandType.InlineNone:
                    break;
                case OperandType.InlineSwitch:
                    int length = il.ReadInt32();
                    int base_offset = il.position + (4 * length);
                    int[] branches = new int[length];
                    for (int i = 0; i < length; i++)
                        branches[i] = il.ReadInt32() + base_offset;

                    instruction.Operand = branches;
                    break;
                case OperandType.ShortInlineBrTarget:
                    instruction.Operand = (((sbyte)il.ReadByte()) + il.position);
                    break;
                case OperandType.InlineBrTarget:
                    instruction.Operand = il.ReadInt32() + il.position;
                    break;
                case OperandType.ShortInlineI:
                    if (instruction.OpCode == OpCodes.Ldc_I4_S)
                        instruction.Operand = (sbyte)il.ReadByte();
                    else
                        instruction.Operand = il.ReadByte();
                    break;
                case OperandType.InlineI:
                    instruction.Operand = il.ReadInt32();
                    break;
                case OperandType.ShortInlineR:
                    instruction.Operand = il.ReadSingle();
                    break;
                case OperandType.InlineR:
                    instruction.Operand = il.ReadDouble();
                    break;
                case OperandType.InlineI8:
                    instruction.Operand = il.ReadInt64();
                    break;
                case OperandType.InlineSig:
                    instruction.Operand = module.ResolveSignature(il.ReadInt32());
                    break;
                case OperandType.InlineString:
                    instruction.Operand = module.ResolveString(il.ReadInt32());
                    break;
                case OperandType.InlineTok:
                case OperandType.InlineType:
                case OperandType.InlineMethod:
                case OperandType.InlineField:
                    instruction.Operand = module.ResolveMember(il.ReadInt32(), type_arguments, method_arguments);
                    break;
                case OperandType.ShortInlineVar:
                    instruction.Operand = GetVariable(instruction, il.ReadByte());
                    break;
                case OperandType.InlineVar:
                    instruction.Operand = GetVariable(instruction, il.ReadInt16());
                    break;
                default:
                    throw new NotSupportedException();
            }
        }
		static string FormatLabel (Instruction instruction)
		{
			return FormatLabel (instruction.Offset);
		}
Ejemplo n.º 9
0
        private void ReadOperand(Instruction instruction)
        {
            switch (instruction.OpCode.OperandType)
            {
                case OperandType.InlineNone:
                    break;
                case OperandType.InlineSwitch:
                    int length = il.ReadInt32();
                    int[] branches = new int[length];
                    int[] offsets = new int[length];
                    for (int i = 0; i < length; i++)
                        offsets[i] = il.ReadInt32();
                    for (int i = 0; i < length; i++)
                        branches[i] = il.position + offsets[i];

                    instruction.Operand = branches;
                    break;
                case OperandType.ShortInlineBrTarget:
                    instruction.Operand = (sbyte) (il.ReadByte() + il.position);
                    break;
                case OperandType.InlineBrTarget:
                    instruction.Operand = il.ReadInt32() + il.position;
                    break;
                case OperandType.ShortInlineI:
                    if (instruction.OpCode == OpCodes.Ldc_I4_S)
                        instruction.Operand = (sbyte) il.ReadByte();
                    else
                        instruction.Operand = il.ReadByte();
                    break;
                case OperandType.InlineI:
                    instruction.Operand = il.ReadInt32();
                    break;
                case OperandType.ShortInlineR:
                    instruction.Operand = il.ReadSingle();
                    break;
                case OperandType.InlineR:
                    instruction.Operand = il.ReadDouble();
                    break;
                case OperandType.InlineI8:
                    instruction.Operand = il.ReadInt64();
                    break;
                case OperandType.InlineSig:
                    byte[] resolveSignature = module.ResolveSignature(il.ReadInt32());
                    instruction.Operand = resolveSignature;
                    break;
                case OperandType.InlineString:
                    string resolveString = module.ResolveString(il.ReadInt32());
                    instruction.Operand = resolveString;
                    break;
                case OperandType.InlineTok:
                    MemberInfo resolveMember = module.ResolveMember(il.ReadInt32(), generic_type_arguments, method_arguments);
                    instruction.Operand = resolveMember;
                    break;
                case OperandType.InlineType:
                    Type resolveType = module.ResolveType(il.ReadInt32(), generic_type_arguments, method_arguments);
                    instruction.Operand = resolveType;
                    break;
                case OperandType.InlineMethod:
                    MethodBase resolveMethod = module.ResolveMethod(il.ReadInt32(), generic_type_arguments, method_arguments);
                    instruction.Operand = resolveMethod;
                    break;
                case OperandType.InlineField:
                    FieldInfo resolveField = module.ResolveField(il.ReadInt32(), generic_type_arguments, method_arguments);
                    instruction.Operand = resolveField;
                    break;
                case OperandType.ShortInlineVar:
                    object variable = GetVariable(instruction, il.ReadByte());
                    instruction.Operand = variable;
                    break;
                case OperandType.InlineVar:
                    object operand = GetVariable(instruction, il.ReadInt16());
                    instruction.Operand = operand;
                    break;
                default:
                    throw new NotSupportedException();
            }
        }
Ejemplo n.º 10
0
		internal void Advance () {
			instruction = instruction.Next;
		}
Ejemplo n.º 11
0
		internal MatchContext (Instruction instruction) {
			Reset(instruction);
		}
Ejemplo n.º 12
0
 public JoinPointState(Instruction left, Instruction right)
 {
     Left = left;
     Right = right;
     LeftInstructions = new Stack<Instruction>();
     RightInstructions = new Stack<Instruction>();
 }
Ejemplo n.º 13
0
		internal void Advance ()
		{
			this.instruction = this.instruction.Next;
		}
Ejemplo n.º 14
0
        Instruction ConditionalBranch(Instruction instruction, Func<Expression, BinaryExpression> condition)
        {
            var val1 = stack.Pop();
            var test = condition(val1);

            var left = (Instruction)instruction.Operand;
            var right = instruction.Next;

            Instruction common = GetJoinPoint(left, right);

            var rightExpression = Clone().Process(right, common);
            var leftExpression = AdjustType(Clone().Process(left, common), rightExpression.Type);

            var expression = BuildConditionalBranch(test, val1, leftExpression, rightExpression);
            stack.Push(expression);
            return common;
        }
Ejemplo n.º 15
0
 static Instruction GetJoinPoint(Instruction left, Instruction right)
 {
     return GetCommon(GetFlow(left), GetFlow(right));
 }
Ejemplo n.º 16
0
        static Stack<Instruction> GetFlow(Instruction instruction)
        {
            var instructions = new Stack<Instruction>();
            while (instruction != null)
            {
                instructions.Push(instruction);

                if (instruction.OpCode.FlowControl == FlowControl.Return)
                    break;

                if (instruction.OpCode.FlowControl == FlowControl.Branch)
                {
                    instruction = (Instruction) instruction.Operand;
                }
                else if (instruction.OpCode.FlowControl == FlowControl.Cond_Branch)
                {
                    instruction = GetJoinPoint((Instruction) instruction.Operand, instruction.Next);
                }
                else
                {
                    instruction = instruction.Next;
                }
            }
            return instructions;
        }
Ejemplo n.º 17
0
        public Expression Process(Instruction instruction, Instruction last = null)
        {
            while(instruction != null && instruction != last)
            {
                Debug.WriteLine(instruction);

                if (instruction.OpCode == OpCodes.Nop || instruction.OpCode == OpCodes.Break)
                {
                    //do nothing;
                }
                else if (instruction.OpCode == OpCodes.Ldarg_0)
                {
                    LdArg(0);
                }
                else if (instruction.OpCode == OpCodes.Ldarg_1)
                {
                    LdArg(1);
                }
                else if (instruction.OpCode == OpCodes.Ldarg_2)
                {
                    LdArg(2);
                }
                else if (instruction.OpCode == OpCodes.Ldarg_3)
                {
                    LdArg(3);
                }
                else if (instruction.OpCode == OpCodes.Ldarg_S)
                {
                    LdArg((short) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldarg)
                {
                    LdArg((int) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldarga || instruction.OpCode == OpCodes.Ldarga_S)
                {
                    var operand = (ParameterInfo) instruction.Operand;
                    stack.Push(args.Single(x => x.Name == operand.Name));
                }
                else if (instruction.OpCode == OpCodes.Ldlen)
                {
                    var array = stack.Pop();
                    stack.Push(Expression.ArrayLength(array));
                }
                else if (instruction.OpCode == OpCodes.Ldelem ||
                         instruction.OpCode == OpCodes.Ldelem_I ||
                         instruction.OpCode == OpCodes.Ldelem_I1 ||
                         instruction.OpCode == OpCodes.Ldelem_I2 ||
                         instruction.OpCode == OpCodes.Ldelem_I4 ||
                         instruction.OpCode == OpCodes.Ldelem_I8 ||
                         instruction.OpCode == OpCodes.Ldelem_U1 ||
                         instruction.OpCode == OpCodes.Ldelem_U2 ||
                         instruction.OpCode == OpCodes.Ldelem_U4 ||
                         instruction.OpCode == OpCodes.Ldelem_R4 ||
                         instruction.OpCode == OpCodes.Ldelem_R8 ||
                         instruction.OpCode == OpCodes.Ldelem_Ref)
                {
                    var index = stack.Pop();
                    var array = stack.Pop();
                    stack.Push(Expression.ArrayIndex(array, index));
                }
                else if (instruction.OpCode == OpCodes.Stloc_0)
                {
                    StLoc(0);
                }
                else if (instruction.OpCode == OpCodes.Stloc_1)
                {
                    StLoc(1);
                }
                else if (instruction.OpCode == OpCodes.Stloc_2)
                {
                    StLoc(2);
                }
                else if (instruction.OpCode == OpCodes.Stloc_3)
                {
                    StLoc(3);
                }
                else if (instruction.OpCode == OpCodes.Stloc_S)
                {
                    StLoc((byte) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Stloc)
                {
                    StLoc((int) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Stelem ||
                         instruction.OpCode == OpCodes.Stelem_I ||
                         instruction.OpCode == OpCodes.Stelem_I1 ||
                         instruction.OpCode == OpCodes.Stelem_I2 ||
                         instruction.OpCode == OpCodes.Stelem_I4 ||
                         instruction.OpCode == OpCodes.Stelem_I8 ||
                         instruction.OpCode == OpCodes.Stelem_R4 ||
                         instruction.OpCode == OpCodes.Stelem_R8 ||
                         instruction.OpCode == OpCodes.Stelem_Ref)
                {
                    StElem();
                }
                else if (instruction.OpCode == OpCodes.Ldnull)
                {
                    stack.Push(Expression.Constant(null));
                }
                else if (instruction.OpCode == OpCodes.Ldfld || instruction.OpCode == OpCodes.Ldflda)
                {
                    var instance = stack.Pop();
                    stack.Push(Expression.Field(instance, (FieldInfo) instruction.Operand));
                }
                else if (instruction.OpCode == OpCodes.Ldsfld)
                {
                    var targetField = instruction.Operand as FieldInfo;

                    if (IsCachedAnonymousMethodDelegate(targetField))
                    {
                        // do nothing.
                    }
                    else
                    {
                        stack.Push(Expression.Field(null, (FieldInfo) instruction.Operand));
                    }
                }
                else if (instruction.OpCode == OpCodes.Ldloc_0)
                {
                    LdLoc(0);
                }
                else if (instruction.OpCode == OpCodes.Ldloc_1)
                {
                    LdLoc(1);
                }
                else if (instruction.OpCode == OpCodes.Ldloc_2)
                {
                    LdLoc(2);
                }
                else if (instruction.OpCode == OpCodes.Ldloc_3)
                {
                    LdLoc(3);
                }
                else if (instruction.OpCode == OpCodes.Ldloc_S)
                {
                    LdLoc((byte) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldloc)
                {
                    LdLoc((int) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldloca || instruction.OpCode == OpCodes.Ldloca_S)
                {
                    var operand = (LocalVariableInfo) instruction.Operand;
                    LdLoc(operand.LocalIndex);
                }
                else if (instruction.OpCode == OpCodes.Ldstr)
                {
                    stack.Push(Expression.Constant((string) instruction.Operand));
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_0)
                {
                    LdC(0);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_1)
                {
                    LdC(1);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_2)
                {
                    LdC(2);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_3)
                {
                    LdC(3);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_4)
                {
                    LdC(4);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_5)
                {
                    LdC(5);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_6)
                {
                    LdC(6);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_7)
                {
                    LdC(7);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_8)
                {
                    LdC(8);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_S)
                {
                    LdC((sbyte) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4_M1)
                {
                    LdC(-1);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I4)
                {
                    LdC((int) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldc_I8)
                {
                    LdC((long) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldc_R4)
                {
                    LdC((float) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ldc_R8)
                {
                    LdC((double) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Br_S || instruction.OpCode == OpCodes.Br)
                {
                    instruction = (Instruction) instruction.Operand;
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Brfalse ||
                         instruction.OpCode == OpCodes.Brfalse_S)
                {
                    instruction = ConditionalBranch(instruction, val => Expression.Equal(val, Default(val.Type)));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Brtrue ||
                         instruction.OpCode == OpCodes.Brtrue_S)
                {
                    var target = ((Instruction) instruction.Operand);

                    if (target.OpCode == OpCodes.Ldsfld && IsCachedAnonymousMethodDelegate(target.Operand as FieldInfo))
                    {
                        stack.Push(((MethodInfo) instruction.Next.Next.Operand).Decompile());
                        instruction = (Instruction) instruction.Operand;
                    }
                    else
                    {
                        instruction = ConditionalBranch(instruction, val => Expression.NotEqual(val, Default(val.Type)));
                    }

                    continue;
                }
                else if (instruction.OpCode == OpCodes.Bgt ||
                         instruction.OpCode == OpCodes.Bgt_S ||
                         instruction.OpCode == OpCodes.Bgt_Un ||
                         instruction.OpCode == OpCodes.Bgt_Un_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => Expression.GreaterThan(val, val1));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Bge ||
                         instruction.OpCode == OpCodes.Bge_S ||
                         instruction.OpCode == OpCodes.Bge_Un ||
                         instruction.OpCode == OpCodes.Bge_Un_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => Expression.GreaterThanOrEqual(val, val1));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Blt ||
                         instruction.OpCode == OpCodes.Blt_S ||
                         instruction.OpCode == OpCodes.Blt_Un ||
                         instruction.OpCode == OpCodes.Blt_Un_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => Expression.LessThan(val, val1));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Ble ||
                         instruction.OpCode == OpCodes.Ble_S ||
                         instruction.OpCode == OpCodes.Ble_Un ||
                         instruction.OpCode == OpCodes.Ble_Un_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => Expression.LessThanOrEqual(val, val1));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Beq ||
                         instruction.OpCode == OpCodes.Beq_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => AdjustedBinaryExpression(val, val1, ExpressionType.Equal));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Bne_Un ||
                         instruction.OpCode == OpCodes.Bne_Un_S)
                {
                    var val1 = stack.Pop();
                    instruction = ConditionalBranch(instruction, val => AdjustedBinaryExpression(val, val1, ExpressionType.NotEqual));
                    continue;
                }
                else if (instruction.OpCode == OpCodes.Dup)
                {
                    stack.Push(stack.Peek());
                }
                else if (instruction.OpCode == OpCodes.Pop)
                {
                    stack.Pop();
                }
                else if (instruction.OpCode == OpCodes.Add)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Add(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Add_Ovf || instruction.OpCode == OpCodes.Add_Ovf_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.AddChecked(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Sub)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Subtract(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Sub_Ovf || instruction.OpCode == OpCodes.Sub_Ovf_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.SubtractChecked(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Mul)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Multiply(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Mul_Ovf || instruction.OpCode == OpCodes.Mul_Ovf_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.MultiplyChecked(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Div || instruction.OpCode == OpCodes.Div_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Divide(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Rem || instruction.OpCode == OpCodes.Rem_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Modulo(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Xor)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.ExclusiveOr(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Shl)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.LeftShift(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Shr || instruction.OpCode == OpCodes.Shr_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.RightShift(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Neg)
                {
                    var val = stack.Pop();
                    stack.Push(Expression.Negate(val));
                }
                else if (instruction.OpCode == OpCodes.Not)
                {
                    var val = stack.Pop();
                    stack.Push(Expression.Not(val));
                }
                else if (instruction.OpCode == OpCodes.Conv_I)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (int))); // Support x64?
                }
                else if (instruction.OpCode == OpCodes.Conv_I1)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (sbyte)));
                }
                else if (instruction.OpCode == OpCodes.Conv_I2)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (short)));
                }
                else if (instruction.OpCode == OpCodes.Conv_I4)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (int)));
                }
                else if (instruction.OpCode == OpCodes.Conv_I8)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (long)));
                }
                else if (instruction.OpCode == OpCodes.Conv_U)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (uint))); // Suppot x64?
                }
                else if (instruction.OpCode == OpCodes.Conv_U1)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (byte)));
                }
                else if (instruction.OpCode == OpCodes.Conv_U2)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (ushort)));
                }
                else if (instruction.OpCode == OpCodes.Conv_U4)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (uint)));
                }
                else if (instruction.OpCode == OpCodes.Conv_U8)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, typeof (ulong)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_I || instruction.OpCode == OpCodes.Conv_Ovf_I_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (int))); // Suppot x64?
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_I1 || instruction.OpCode == OpCodes.Conv_Ovf_I1_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (sbyte)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_I2 || instruction.OpCode == OpCodes.Conv_Ovf_I2_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (short)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_I4 || instruction.OpCode == OpCodes.Conv_Ovf_I4_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (int)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_I8 || instruction.OpCode == OpCodes.Conv_Ovf_I8_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (long)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_U || instruction.OpCode == OpCodes.Conv_Ovf_U_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (uint))); // Suppot x64?
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_U1 || instruction.OpCode == OpCodes.Conv_Ovf_U1_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (byte)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_U2 || instruction.OpCode == OpCodes.Conv_Ovf_U2_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (ushort)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_U4 || instruction.OpCode == OpCodes.Conv_Ovf_U4_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (uint)));
                }
                else if (instruction.OpCode == OpCodes.Conv_Ovf_U8 || instruction.OpCode == OpCodes.Conv_Ovf_U8_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (ulong)));
                }
                else if (instruction.OpCode == OpCodes.Conv_R4 || instruction.OpCode == OpCodes.Conv_R_Un)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (float)));
                }
                else if (instruction.OpCode == OpCodes.Conv_R8)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.ConvertChecked(val1, typeof (double)));
                }
                else if (instruction.OpCode == OpCodes.Castclass)
                {
                    var val1 = stack.Pop();
                    stack.Push(Expression.Convert(val1, (Type) instruction.Operand));
                }
                else if (instruction.OpCode == OpCodes.And)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.And(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Or)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();
                    stack.Push(Expression.Or(val2, val1));
                }
                else if (instruction.OpCode == OpCodes.Newobj)
                {
                    var operand = (ConstructorInfo) instruction.Operand;
                    stack.Push(Expression.New(operand, GetArguments(operand)));
                }
                else if (instruction.OpCode == OpCodes.Newarr)
                {
                    var operand = (Type) instruction.Operand;
                    var expression = stack.Pop();
                    var size = expression as ConstantExpression;
                    if (size != null && (int) size.Value == 0) // optimization
                        stack.Push(Expression.NewArrayInit(operand));
                    else
                        stack.Push(Expression.NewArrayBounds(operand, expression));
                }
                else if (instruction.OpCode == OpCodes.Box)
                {
                    stack.Push(Box(stack.Pop(), (Type) instruction.Operand));
                }
                else if (instruction.OpCode == OpCodes.Call || instruction.OpCode == OpCodes.Callvirt)
                {
                    Call((MethodInfo) instruction.Operand);
                }
                else if (instruction.OpCode == OpCodes.Ceq)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();

                    stack.Push(AdjustedBinaryExpression(val2, AdjustType(val1, val2.Type), ExpressionType.Equal));
                }
                else if (instruction.OpCode == OpCodes.Cgt || instruction.OpCode == OpCodes.Cgt_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();

                    stack.Push(Expression.GreaterThan(val2, AdjustType(val1, val2.Type)));
                }
                else if (instruction.OpCode == OpCodes.Clt || instruction.OpCode == OpCodes.Clt_Un)
                {
                    var val1 = stack.Pop();
                    var val2 = stack.Pop();

                    stack.Push(Expression.LessThan(val2, AdjustType(val1, val2.Type)));
                }
                else if (instruction.OpCode == OpCodes.Ret)
                {
                    break;
                }

                instruction = instruction.Next;
            }

            return stack.Count == 0
                       ? Expression.Empty()
                       : stack.Pop();
        }
		static void WriteLabelList (TextWriter writer, Instruction [] targets)
		{
			writer.Write ("(");

			for (int i = 0; i < targets.Length; i++) {
				if (i != 0) writer.Write (", ");
				writer.Write (FormatLabel (targets [i]));
			}

			writer.Write (")");
		}
        private SourceLocation? FindSourceLocation(Instruction instruction, MethodNode methodNode)
        {
            var sequencePoints = this.symbols.GetSequencePointsForMethod(methodNode);

            return sequencePoints.NearestSequencePoint(instruction).Location;
        }
		static void WriteOperand (TextWriter writer, Instruction instruction)
		{
			var opcode = instruction.OpCode;
			var operand = instruction.Operand;

			if (opcode.OperandType == OperandType.InlineNone)
				return;

			writer.Write (' ');

			switch (opcode.OperandType) {
			case OperandType.ShortInlineBrTarget:
			case OperandType.InlineBrTarget:
				writer.Write (FormatLabel ((Instruction) operand));
				return;
			case OperandType.InlineSwitch:
				WriteLabelList (writer, (Instruction []) operand);
				return;
			case OperandType.InlineString:
				writer.Write ("\"" + operand.ToString () + "\"");
				return;
			case OperandType.ShortInlineVar:
			case OperandType.InlineVar:
				if (TargetsLocalVariable (opcode)) {
					var local = (LocalVariableInfo) operand;
					writer.Write ("V_{0}", local.LocalIndex);
					return;
				}

				var parameter = (ParameterInfo) operand;
				writer.Write (parameter.Name);
				return;
			case OperandType.InlineTok:
			case OperandType.InlineType:
			case OperandType.InlineMethod:
			case OperandType.InlineField:
				var member = (MemberInfo) operand;
				switch (member.MemberType) {
				case MemberTypes.Constructor:
				case MemberTypes.Method:
					WriteMethodReference (writer, (MethodBase) member);
					return;
				case MemberTypes.Field:
					WriteFieldReference (writer, (FieldInfo) member);
					return;
				case MemberTypes.TypeInfo:
				case MemberTypes.NestedType:
					writer.Write (FormatTypeReference ((Type) member));
					return;
				default:
					throw new NotSupportedException ();
				}
			case OperandType.InlineI:
			case OperandType.ShortInlineI:
			case OperandType.InlineR:
			case OperandType.ShortInlineR:
			case OperandType.InlineI8:
				writer.Write (ToInvariantCultureString (operand));
				return;
			default:
				throw new NotSupportedException ();
			}
		}
Ejemplo n.º 21
0
        void ResolveBranches()
        {
            foreach (var instruction in instructions)
            {
                switch (instruction.OpCode.OperandType)
                {
                    case OperandType.ShortInlineBrTarget:
                    case OperandType.InlineBrTarget:
                        instruction.Operand = GetInstruction(instructions, (int)instruction.Operand);
                        break;
                    case OperandType.InlineSwitch:
                        var offsets = (int[])instruction.Operand;
                        var branches = new Instruction[offsets.Length];
                        for (int j = 0; j < offsets.Length; j++)
                            branches[j] = GetInstruction(instructions, offsets[j]);

                        instruction.Operand = branches;
                        break;
                }
            }
        }
Ejemplo n.º 22
0
 object GetVariable(Instruction instruction, int index)
 {
     return TargetsLocalVariable(instruction.OpCode)
         ? (object)GetLocalVariable(index)
         : (object)GetParameter(index);
 }
Ejemplo n.º 23
0
        private static ParameterDefinition ParameterFor(MR.Instruction instruction, MethodDefinition method)
        {
            var parameter = (ParameterInfo)instruction.Operand;

            return(method.Parameters[parameter.Position]);
        }
Ejemplo n.º 24
0
        private static VariableDefinition VariableFor(MR.Instruction instruction, MethodDefinition method)
        {
            var local = (LocalVariableInfo)instruction.Operand;

            return(method.Body.Variables[local.LocalIndex]);
        }
Ejemplo n.º 25
0
		internal void Reset (Instruction instruction)
		{
			this.instruction = instruction;
			this.success = true;
		}
Ejemplo n.º 26
0
        static Instruction GetJoinPoint(Instruction left, Instruction right)
        {
            Stack<JoinPointState> joinPointStates = new Stack<JoinPointState>();
            joinPointStates.Push(new JoinPointState(left, right));
            JoinPointState joinPointState = null;
            while(joinPointStates.Count > 0)
            {
                joinPointState = joinPointStates.Peek();
                               
                // See if both flows have been computed (right goes second) and if so, get the common join point
                if(joinPointState.Right == null)
                {
                    foreach (var leftInstruction in joinPointState.LeftInstructions)
                    {
                        if (joinPointState.RightInstructions.Count <= 0 || leftInstruction != joinPointState.RightInstructions.Pop())
                        {
                            break;
                        }
                        joinPointState.Common = leftInstruction;
                    }
                    joinPointStates.Pop();
                }
                else
                {
                    // Check if we were waiting on a pending operation
                    if (joinPointState.Pending != null)
                    {
                        joinPointState.Current = joinPointState.Pending.Common;
                        joinPointState.Pending = null;
                    }
                    else
                    {

                        joinPointState.CurrentInstructions.Push(joinPointState.Current);

                        if (joinPointState.Current.OpCode.FlowControl == FlowControl.Return)
                        {
                            joinPointState.Current = null;
                        }
                        else if (joinPointState.Current.OpCode.FlowControl == FlowControl.Branch)
                        {
                            joinPointState.Current = (Instruction)joinPointState.Current.Operand;
                        }
                        else if (joinPointState.Current.OpCode.FlowControl == FlowControl.Cond_Branch)
                        {
                            joinPointState.Pending = new JoinPointState((Instruction)joinPointState.Current.Operand, joinPointState.Current.Next);
                            joinPointStates.Push(joinPointState.Pending);
                        }
                        else
                        {
                            joinPointState.Current = joinPointState.Current.Next;
                        }
                    }
                }
            }

            return joinPointState.Common;
        }
        private static bool NextInstructionIsACallToAStep(Instruction instruction)
        {
            Instruction nextInstruction = instruction.Next;

            while(nextInstruction.Next != null)
            {
                if (nextInstruction.OpCode.FlowControl == System.Reflection.Emit.FlowControl.Call)
                {
                    return nextInstruction.Operand.ToString().Contains("TechTalk.SpecFlow");
                }

                nextInstruction = nextInstruction.Next;
            }
            return false;
        }
Ejemplo n.º 28
0
		internal void Reset (Instruction resetInstruction) {
			instruction = resetInstruction;
			success = true;
		}
        private bool GetSpecFlowStepInvocationHasTable(Instruction instruction)
        {
            Instruction nextInstruction = instruction.Next;

            while (nextInstruction != null && nextInstruction.OpCode.FlowControl != System.Reflection.Emit.FlowControl.Call)
            {
                nextInstruction = nextInstruction.Next;
            }

            if (nextInstruction.Operand == null)
            {
                return false;
            }

            return nextInstruction.Operand.ToString().Contains("TechTalk.SpecFlow.Table");
        }
Ejemplo n.º 30
0
        private void ReadInstructions()
        {
            Instruction previous = null;

            while (il.position < il.buffer.Length)
            {
                var instruction = new Instruction(il.position, ReadOpCode());

                ReadOperand(instruction);

                if (previous != null)
                {
                    instruction.Previous = previous;
                    previous.Next = instruction;
                }

                instructions.Add(instruction);
                previous = instruction;
            }
        }
Ejemplo n.º 31
0
		static void AppendLabel (StringBuilder builder, Instruction instruction)
		{
			builder.Append ("IL_");
			builder.Append (instruction.offset.ToString ("x4"));
		}
Ejemplo n.º 32
0
 private object GetVariable(Instruction instruction, int index)
 {
     if (TargetsLocalVariable(instruction.OpCode))
         return GetLocalVariable(index);
     return GetParameter(index);
 }
		public static string FormatInstruction (Instruction instruction)
		{
			var writer = new StringWriter ();
			WriteInstruction (writer, instruction);
			return writer.ToString ();
		}