/// <summary> /// Reads the next instruction /// </summary> Instruction ReadOneInstruction() { var instr = new Instruction(); instr.Offset = currentOffset; instr.OpCode = ReadOpCode(); instr.Operand = ReadOperand(instr); if (instr.OpCode.Code == Code.Switch) { var targets = (IList <uint>)instr.Operand; currentOffset += (uint)(instr.OpCode.Size + 4 + 4 * targets.Count); } else { currentOffset += (uint)instr.GetSize(); } if (currentOffset < instr.Offset) { reader.Position = codeEndOffs; } return(instr); }
private static int ResolveOffset(CilBody body, Instruction instruction) { if (instruction == null) { instruction = body.Instructions[body.Instructions.Count - 1]; return (int)(instruction.Offset + instruction.GetSize()); } else return (int)instruction.Offset; }
/// <summary> /// Reads a <see cref="OperandType.ShortInlineBrTarget"/> operand /// </summary> /// <param name="instr">The current instruction</param> /// <returns>The operand</returns> protected virtual uint ReadShortInlineBrTarget(Instruction instr) { return(instr.Offset + (uint)instr.GetSize() + (uint)reader.ReadSByte()); }
/// <summary> /// Reads a <see cref="OperandType.InlineBrTarget"/> operand /// </summary> /// <param name="instr">The current instruction</param> /// <returns>The operand</returns> protected virtual uint ReadInlineBrTarget(Instruction instr) { return(instr.Offset + (uint)instr.GetSize() + reader.ReadUInt32()); }
protected Instruction ReadOneInstruction_Special(VirtualOpCode virtualInstruction) { //this.Logger.Verbose(this, "Special Opcode ({0}, delegate MDToken = 0x{1:X8})", // virtualInstruction.SpecialOpCode.ToString(), // virtualInstruction.DelegateMethod.MDToken.Raw //); // Have a method for this? OpCode opcode = null; switch(virtualInstruction.SpecialOpCode) { case SpecialCode.Eaz_Call: opcode = Code.Call.ToOpCode(); // Or Callvirt? break; } if(opcode == null) { throw new Exception(String.Format( "Cannot convert SpecialOpCode to CIL OpCode: {0}", virtualInstruction.SpecialOpCode )); } Object operand = this.ReadSpecialOperand(virtualInstruction); Instruction instruction = new Instruction(opcode); instruction.Offset = this.CurrentILOffset; instruction.OpCode = opcode; instruction.Operand = operand; // this.ReadOperand(instruction); this.CurrentILOffset += (UInt32)instruction.GetSize(); this.CurrentVirtualOffset += (UInt32)virtualInstruction.GetSize(instruction.Operand); this.CurrentInstructionOffset++; return instruction; }
protected static int GetInstructionSize(Instruction instr) { var opcode = instr.OpCode; if (opcode == null) return 5; // Load store/field var op = instr.Operand as SwitchTargetDisplOperand; if (op == null) return instr.GetSize(); return instr.OpCode.Size + (op.TargetDisplacements.Length + 1) * 4; }
protected Instruction ReadOneInstruction_CIL(VirtualOpCode virtualInstruction) { OpCode opcode = virtualInstruction.OpCode.ToOpCode(); Instruction instruction = new Instruction(opcode); instruction.Offset = this.CurrentILOffset; instruction.OpCode = opcode; instruction.Operand = this.ReadOperand(instruction); if (instruction.OpCode.Code == Code.Switch) { var targets = (IList<UInt32>)instruction.Operand; this.CurrentILOffset += (UInt32)(instruction.OpCode.Size + 4 + (4 * targets.Count)); this.CurrentVirtualOffset += (UInt32)(4 + 4 + (4 * targets.Count)); } else { this.CurrentILOffset += (UInt32)instruction.GetSize(); this.CurrentVirtualOffset += (UInt32)virtualInstruction.GetSize(instruction.Operand); } this.CurrentInstructionOffset++; return instruction; }
/// <summary> /// Reads a <see cref="OperandType.ShortInlineBrTarget"/> operand /// </summary> /// <param name="instr">The current instruction</param> /// <returns>The operand</returns> protected virtual uint ReadShortInlineBrTarget(Instruction instr) { return instr.Offset + (uint)instr.GetSize() + (uint)reader.ReadSByte(); }
/// <summary> /// Reads a <see cref="OperandType.InlineBrTarget"/> operand /// </summary> /// <param name="instr">The current instruction</param> /// <returns>The operand</returns> protected virtual uint ReadInlineBrTarget(Instruction instr) { return instr.Offset + (uint)instr.GetSize() + reader.ReadUInt32(); }
/// <summary> /// Reads the next instruction /// </summary> Instruction ReadOneInstruction() { var instr = new Instruction(); instr.Offset = currentOffset; instr.OpCode = ReadOpCode(); instr.Operand = ReadOperand(instr); if (instr.OpCode.Code == Code.Switch) { var targets = (IList<uint>)instr.Operand; currentOffset += (uint)(instr.OpCode.Size + 4 + 4 * targets.Count); } else currentOffset += (uint)instr.GetSize(); if (currentOffset < instr.Offset) reader.Position = codeEndOffs; return instr; }
/// <summary> /// Get the size of this virtual instruction. Requires that the instruction be identified /// with a CIL opcode. /// </summary> /// <param name="operand">Instruction operand</param> /// <returns>Size of instruction when serialized</returns> /// <exception cref="System.Exception">Thrown if virtual instruction not identified</exception> public Int32 GetSize(Object operand) { if (!this.IsIdentified) throw new Exception("Cannot get a virtual instruction's size if not identified"); if (this.HasCILOpCode) { // Instruction instruction = this.OpCode.ToOpCode().ToInstruction(); Instruction instruction = new Instruction(this.OpCode.ToOpCode(), operand); return (instruction.GetSize() - instruction.OpCode.Size) + 4; } else { switch(this.SpecialOpCode) { case SpecialCode.Eaz_Call: return 8; } throw new Exception(String.Format( "Cannot get size of virtual instruction: {0}", this.Name)); } }
/// <summary> /// Gets the size of an instruction /// </summary> /// <param name="instr">The instruction</param> /// <returns>Size of the instruction in bytes</returns> protected virtual uint GetSizeOfInstruction(Instruction instr) { return (uint)instr.GetSize(); }