コード例 #1
0
        // relative jump
        private static bool jb(uint u, Tlcs90Disassembler dasm)
        {
            if (!dasm.rdr.TryReadByte(out byte b))
            {
                return(false);
            }
            var dest = dasm.rdr.Address + (sbyte)b;

            dasm.ops.Add(AddressOperand.Create(dest));
            return(true);
        }
コード例 #2
0
ファイル: Avr8Disassembler.cs プロジェクト: xiaobo996/reko
        // Branch offset
        private static bool o(uint wInstr, Avr8Disassembler dasm)
        {
            short offset;

            offset = (short)wInstr;
            offset = (short)(offset << 6);
            offset = (short)(offset >> 8);
            offset = (short)(offset & ~1);
            dasm.ops.Add(AddressOperand.Create(dasm.addr + offset + 2));
            return(true);
        }
コード例 #3
0
        private static bool jw(uint b, Tlcs90Disassembler dasm)
        {
            if (!dasm.rdr.TryReadLeInt16(out short off))
            {
                return(false);
            }
            var dest = dasm.rdr.Address + off;

            dasm.ops.Add(AddressOperand.Create(dest));
            return(true);
        }
コード例 #4
0
        private static bool PCb(uint wInstr, M6809Disassembler dasm)
        {
            if (!dasm.rdr.TryReadByte(out byte b))
            {
                return(false);
            }
            var addr = dasm.rdr.Address + (sbyte)b;

            dasm.ops.Add(AddressOperand.Create(addr));
            return(true);
        }
コード例 #5
0
        private static Mutator <LatticeMico32Disassembler> PcRel(int bitpos, int bitsize)
        {
            var field = new Bitfield(bitpos, bitsize);

            return((u, d) =>
            {
                var offset = field.ReadSigned(u) << 2;
                d.ops.Add(AddressOperand.Create(d.addr + offset));
                return true;
            });
        }
コード例 #6
0
ファイル: YmpDisassembler.cs プロジェクト: qcyb/reko
        internal static bool Jijkm(uint uInstr, YmpDisassembler dasm)
        {
            if (!dasm.rdr.TryReadBeUInt16(out ushort n))
            {
                return(false);
            }
            var uAddr = ((uInstr & 0x1FF) << 16) | n;

            dasm.ops.Add(AddressOperand.Ptr32(uAddr));
            return(true);
        }
コード例 #7
0
        private static bool PCw(uint wInstr, M6809Disassembler dasm)
        {
            if (!dasm.rdr.TryReadBeInt16(out short d))
            {
                return(false);
            }
            var addr = dasm.rdr.Address + d;

            dasm.ops.Add(AddressOperand.Create(addr));
            return(true);
        }
コード例 #8
0
ファイル: Tlcs90Disassembler.cs プロジェクト: qcyb/reko
 // Absolute jump.
 private static Mutator <Tlcs90Disassembler> J(PrimitiveType size)
 {
     return((b, dasm) =>
     {
         if (!dasm.rdr.TryReadLe(size, out var c))
         {
             return false;
         }
         dasm.ops.Add(AddressOperand.Ptr16(c.ToUInt16()));
         return true;
     });
 }
コード例 #9
0
ファイル: AAOprec.cs プロジェクト: melbcat/reko
 public AArch64Instruction Decode(AArch64Disassembler dasm, uint instr, string fmt)
 {
     AA64Opcode opcode = this.opcode;
     List<MachineOperand> ops = new List<MachineOperand>();
     MachineOperand op = null;
     int i = 0;
     int off;
     while (i < fmt.Length)
     {
         switch (fmt[i++])
         {
         default: throw new InvalidOperationException(string.Format("Bad format character {0}.", fmt[i - 1]));
         case ',':
             continue;
         case 'B':   // Logical Bitmask
             op = LogicalBitmask(dasm, instr, fmt[i++] == 'x');
             break;
         case 'H':   // 16-bit Immediate constant
             off = GetOffset(fmt, ref i);
             op = ArmImmediateOperand.Word32(GetImm(instr, off, 16));
             break;
         case 'I':   // 12-bit Immediate constant
             off = GetOffset(fmt, ref i);
             op = ArmImmediateOperand.Word32(GetImm(instr, off, 12));
             break;
         case 'J':   // long relative branch
             int offset = (((int) instr) << 6) >> 4;
             op = new AddressOperand(dasm.rdr.Address + offset);
             break;
         case 'W':   // (32-bit) W register operand
             op = GetWReg(instr, GetOffset(fmt, ref i));
             break;
         case 'X':   // (64-bit) X register operand 
             op = GetXReg(instr, GetOffset(fmt, ref i));
             break;
         case 's':   // Shift operand by 12
             off = GetOffset(fmt, ref i);
             op = ops[ops.Count - 1];
             ops.RemoveAt(ops.Count - 1);
             uint shiftCode = GetImm(instr, off, 2);
             switch (shiftCode)
             {
             case 0: break;
             case 1:
                 op = new ShiftOperand(op, Opcode.lsl, 12); break;
             default: throw new FormatException("Reserved value for shift code.");
             }
             break;
         }
         ops.Add(op);
     }
     return AArch64Instruction.Create(opcode, ops);
 }
コード例 #10
0
        private static Mutator <MCoreDisassembler> Disp(int bitlen, int shift)
        {
            var dispField = new Bitfield(0, bitlen);

            return((u, d) =>
            {
                var disp = dispField.ReadSigned(u) << shift;
                var addr = Address.Ptr32((uint)(d.addr.ToUInt32() + (2 + disp)) & ~3u);
                d.ops.Add(AddressOperand.Create(addr));
                return true;
            });
        }
コード例 #11
0
        /// <summary>
        /// PC-relative jump displacement.
        /// </summary>
        private static Mutator <MCoreDisassembler> Disp(int bitlen)
        {
            var dispField = new Bitfield(0, bitlen);

            return((u, d) =>
            {
                var disp = dispField.ReadSigned(u) << 1;
                var addr = d.addr + (2 + disp);
                d.ops.Add(AddressOperand.Create(addr));
                return true;
            });
        }
コード例 #12
0
 // absolute address used by jump and call.
 private static bool Q(uint wInstr, Avr8Disassembler dasm)
 {
     if (!dasm.rdr.TryReadLeUInt16(out ushort w2))
     {
         return(false);
     }
     dasm.ops.Add(AddressOperand.Ptr32(
                      (uint)(((wInstr >> 4) & 0x1F) << 18) |
                      (uint)((wInstr & 1) << 17) |
                      (uint)(w2 << 1)));
     return(true);
 }
コード例 #13
0
        private static Mutator <OpenRISCDisassembler> Pc(int bitPos, int bitLength)
        {
            var field = new Bitfield(bitPos, bitLength);

            return((u, d) =>
            {
                var displacement = field.ReadSigned(u) << 2;
                var addrDest = d.addr + displacement;
                d.ops.Add(AddressOperand.Create(addrDest));
                return true;
            });
        }
コード例 #14
0
        public AvrInstruction Decode(ushort wInstr, Opcode opcode, string fmt)
        {
            var ops = new List <MachineOperand>();

            for (int i = 0; i < fmt.Length; ++i)
            {
                MachineOperand op;
                switch (fmt[i++])
                {
                case ',':
                    continue;

                case 'A': // I/O location
                    op = ImmediateOperand.Byte((byte)(((wInstr >> 5) & 0x30) | (wInstr & 0xF)));
                    break;

                case 'J': // Relative jump
                    int offset = ((wInstr & 0xFFF) << 4) >> 3;
                    op = AddressOperand.Create(this.addr + 2 + offset);
                    break;

                case 'D': // Destination register
                    op = Register((wInstr >> 4) & 0x1F);
                    break;

                case 'd': // Destination register (r16-r31)
                    op = Register(0x10 | (wInstr >> 4) & 0x1F);
                    break;

                case 'R': // source register
                    op = Register((wInstr >> 5) & 0x10 | (wInstr >> 4) & 0x0F);
                    break;

                case 'r': // source register
                    op = Register((wInstr >> 4) & 0x10 | (wInstr >> 4) & 0x0F);
                    break;

                case 'K':
                    op = ImmediateOperand.Byte((byte)(((wInstr >> 4) & 0xF0) | (wInstr & 0xF)));
                    break;

                default:
                    throw new NotImplementedException();
                }
                ops.Add(op);
            }
            return(new AvrInstruction
            {
                opcode = opcode,
                operands = ops.ToArray(),
            });
        }
コード例 #15
0
 private int GetHashCode(MachineOperand op)
 {
     return(op switch
     {
         RegisterOperand regOp => base.GetRegisterHash(regOp.Register),
         ImmediateOperand immOp => base.GetConstantHash(immOp.Value),
         AddressOperand addrOp => base.NormalizeConstants
                 ? 1
                 : addrOp.Address.GetHashCode(),
         MemoryOperand memOp => GetMemoryOperandHash(memOp),
         FpuOperand fpuOp => 59 * fpuOp.StNumber.GetHashCode(),
         _ => throw new NotImplementedException("Unhandled operand type: " + op.GetType().FullName)
     });
コード例 #16
0
 // An 11-bit address destination. This argument is used by ACALL and AJMP instructions. The target of the CALL or JMP must lie within the same 2K page as the first byte of the following instruction.
 private static bool j(uint uInstr, i8051Disassembler dasm)
 {
     if (!dasm.rdr.TryReadByte(out byte b))
     {
         return(false);
     }
     dasm.ops.Add(AddressOperand.Ptr16(
                      (ushort)(
                          (dasm.rdr.Address.ToLinear() & ~0x7Ful) |
                          (uInstr & 0xE0u) << 3 |
                              b)));
     return(true);
 }
コード例 #17
0
ファイル: VaxDisassembler.cs プロジェクト: ghmole/reko
 private static Mutator b(PrimitiveType width)
 {
     return((u, d) =>
     {
         if (!d.rdr.TryReadLeSigned(width, out long jOffset))
         {
             return false;
         }
         uint uAddr = (uint)((long)d.rdr.Address.Offset + jOffset);
         d.ops.Add(AddressOperand.Ptr32(uAddr));
         return true;
     });
 }
コード例 #18
0
        /// <summary>
        /// 8 bit signed displacement from the low byte of the instruction.
        /// </summary>
        private static bool disp8(uint uInstr, H8Disassembler dasm)
        {
            var disp = (sbyte)uInstr;

            if ((disp & 1) != 0)
            {
                return(false);       // Branch destination must be even.
            }
            var addrTarget = dasm.rdr.Address + disp;

            dasm.ops.Add(AddressOperand.Create(addrTarget));
            return(true);
        }
コード例 #19
0
ファイル: MicroMipsDisassembler.cs プロジェクト: Seabreg/reko
        // pcRel - short PC-relative
        private static Mutator <MicroMipsDisassembler> pcRel(int bitLength)
        {
            var field = new Bitfield(0, bitLength);

            return((u, d) =>
            {
                var offset = field.ReadSigned(u);
                offset <<= 1;
                var addrDst = d.rdr.Address + offset;
                d.ops.Add(AddressOperand.Create(addrDst));
                return true;
            });
        }
コード例 #20
0
            public override AlphaInstruction Decode(uint uInstr, AlphaDisassembler dasm)
            {
                int offset = ((int)uInstr << 11) >> 9;
                var op1    = dasm.FpuRegister(uInstr >> 21);
                var op2    = AddressOperand.Create(dasm.rdr.Address + offset);

                return(new AlphaInstruction
                {
                    Opcode = this.opcode,
                    op1 = op1,
                    op2 = op2,
                });
            }
コード例 #21
0
            public override AlphaInstruction Decode(uint uInstr, AlphaDisassembler dasm)
            {
                int offset = ((int)uInstr << 11) >> 9;
                var op1    = dasm.FpuRegister(uInstr >> 21);
                var op2    = AddressOperand.Create(dasm.rdr.Address + offset);

                return(new AlphaInstruction
                {
                    Mnemonic = this.opcode,
                    InstructionClass = InstrClass.ConditionalTransfer,
                    Operands = new MachineOperand[] { op1, op2 }
                });
            }
コード例 #22
0
        private void RewritePush()
        {
            if (instrCur.Operands[0] is RegisterOperand reg && reg.Register == Registers.cs)
            {
                // Is it a 'push cs;call near XXXX' sequence that simulates a far call?
                X86Instruction?p1 = dasm.Peek(1);
                if (p1 is not null &&
                    p1.Mnemonic == Mnemonic.call &&
                    p1.Operands[0].Width.BitSize == 16)
                {
                    dasm.MoveNext();
                    MachineOperand targetOperand = dasm.Current.Operands[0];

                    if (targetOperand is ImmediateOperand immOperand)
                    {
                        targetOperand = AddressOperand.Create(orw.ImmediateAsAddress(instrCur.Address, immOperand));
                    }
                    else
                    {
                        m.Assign(StackPointer(), m.ISubS(StackPointer(), reg.Register.DataType.Size));
                    }

                    RewriteCall(targetOperand, targetOperand.Width);
                    this.len = (byte)(this.len + dasm.Current.Length);
                    return;
                }

                X86Instruction?p2 = dasm.Peek(2);
                X86Instruction?p3 = dasm.Peek(3);
                if (p1 is not null && p2 is not null && p3 is not null &&
                    (p1.Mnemonic == Mnemonic.push && (p1.Operands[0] is ImmediateOperand)) &&
                    (p2.Mnemonic == Mnemonic.push && (p2.Operands[0] is ImmediateOperand)) &&
                    (p3.Mnemonic == Mnemonic.jmp && (p3.Operands[0] is AddressOperand)))
                {
                    // That's actually a far call, but the callee thinks its a near call.
                    RewriteCall(p3.Operands[0], instrCur.Operands[0].Width);
                    dasm.MoveNext();
                    dasm.MoveNext();
                    dasm.MoveNext();
                    return;
                }
            }
            var value = SrcOp(0, instrCur.dataWidth);

            Debug.Assert(
                value.DataType.BitSize == 16 ||
                value.DataType.BitSize == 32 ||
                value.DataType.BitSize == 64,
                $"Unexpected size {dasm.Current.dataWidth}");
            RewritePush(PrimitiveType.CreateWord(value.DataType.BitSize), value);
        }
コード例 #23
0
 private MachineOperand DisplacementOperand(PrimitiveType width, RegisterStorage reg, Constant c, byte bSpecifier)
 {
     if (reg.Number == 15)
     {
         return(AddressOperand.Ptr32(
                    (uint)((int)rdr.Address.ToLinear() + c.ToInt32())));
     }
     return(new MemoryOperand(width)
     {
         Base = reg,
         Offset = c,
         Deferred = (bSpecifier >> 4) > 0xC
     });
 }
コード例 #24
0
 private MachineOperand CreateAccess(
     RegisterStorage baseReg,
     int offset)
 {
     if (baseReg == null || baseReg.Number == 0)
     {
         return(AddressOperand.Ptr32((uint)offset));
     }
     return(new MemoryOperand(PrimitiveType.Word32)
     {
         Base = baseReg,
         Offset = offset
     });
 }
コード例 #25
0
        //Register with 6-bit immediate subtracted from PC
        private static bool ru6_m_pc(uint uInstr, XCore200Disassembler dasm)
        {
            var iReg = (uInstr >> 6) & 0xF;
            var imm  = uInstr & 0x3F;

            if ((imm & 1) != 0)
            {
                return(false);       // Illegal address.
            }
            var addr = dasm.addr - imm;

            dasm.ops.Add(new RegisterOperand(Registers.GpRegs[iReg]));
            dasm.ops.Add(AddressOperand.Create(addr));
            return(true);
        }
コード例 #26
0
ファイル: V850Disassembler.cs プロジェクト: ghmole/reko
        private static bool disp32(uint uInstr, V850Disassembler dasm)
        {
            if (!dasm.rdr.TryReadUInt16(out ushort dispLo))
            {
                return(false);
            }
            if (!dasm.rdr.TryReadUInt16(out ushort dispHi))
            {
                return(false);
            }
            var disp = (uint)(dispHi << 16) | dispLo;

            dasm.ops.Add(AddressOperand.Create(dasm.addr + (int)disp));
            return(true);
        }
コード例 #27
0
ファイル: YmpDisassembler.cs プロジェクト: qcyb/reko
        internal static bool Jnm(uint uInstr, YmpDisassembler dasm)
        {
            if (!dasm.rdr.TryReadBeUInt16(out ushort m))
            {
                return(false);
            }
            if (!dasm.rdr.TryReadBeUInt16(out ushort n))
            {
                return(false);
            }
            uint nm = n;

            nm = nm << 16 | m;
            dasm.ops.Add(AddressOperand.Ptr32(nm));
            return(true);
        }
コード例 #28
0
ファイル: Tlcs900Disassembler.cs プロジェクト: erenes/reko
        private MachineOperand AbsoluteDestination(int addrBytes)
        {
            uint uAddr = 0;
            int  sh    = 0;

            while (--addrBytes >= 0)
            {
                if (!rdr.TryReadByte(out byte b))
                {
                    return(null);
                }
                uAddr |= (uint)b << sh;
                sh    += 8;
            }
            return(AddressOperand.Ptr32(uAddr));
        }
コード例 #29
0
        private static Mutator <OpenRISCDisassembler> Page(int bitLen)
        {
            var offsetField = new Bitfield(0, bitLen);

            return((u, d) =>
            {
                long pageOffset = offsetField.ReadSigned(u) << 13;
                long lAddr = (long)(d.addr.ToLinear() & ~8192ul) + pageOffset;
                ulong uAddr = (ulong)lAddr;
                var aOp = d.arch.WordWidth.BitSize == 64
                    ? AddressOperand.Ptr64(uAddr)
                    : AddressOperand.Ptr32((uint)uAddr);
                d.ops.Add(aOp);
                return true;
            });
        }
コード例 #30
0
        public Address OperandAsCodeAddress(MachineOperand op)
        {
            AddressOperand ado = op as AddressOperand;

            if (ado != null)
            {
                return(ado.Address);
            }
            ImmediateOperand imm = op as ImmediateOperand;

            if (imm != null)
            {
                return(orw.ImmediateAsAddress(instrCur.Address, imm));
            }
            return(null);
        }
コード例 #31
0
            public override AArch32Instruction Decode(uint wInstr, T32Disassembler dasm)
            {
                var s   = SBitfield(wInstr, 10 + 16, 1);
                var i1  = 1 & ~(SBitfield(wInstr, 13, 1) ^ s);
                var i2  = 1 & ~(SBitfield(wInstr, 11, 1) ^ s);
                var off = (int)Bits.SignExtend((uint)s, 1);

                off   = (off << 2) | (i1 << 1) | i2;
                off   = (off << 10) | SBitfield(wInstr, 16, 10);
                off   = (off << 11) | SBitfield(wInstr, 0, 11);
                off <<= 1;
                return(new T32Instruction
                {
                    Mnemonic = Mnemonic.bl,
                    Operands = new MachineOperand[] { AddressOperand.Create(dasm.addr + (off + 4)) }
                });
            }