Example #1
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     if (!cpu.GetFlags().Has(FlagsRegister.Overflow))
     {
         new JumpRelative().Dispatch(cpu, instruction);
     }
 }
Example #2
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            switch (instruction.Argument1)
            {
            case (int)Register.SP:
            // 8086 has a bug where it pushes SP after it has been modified
            // cpu.registers[(int)Register.SP] -= 2;
            // cpu.WriteU16(SegmentToAddress(cpu.GetRegister(Register.SS), cpu.GetRegister(Register.SP)), cpu.GetRegister(Register.SP));
            // break;
            case (int)Register.AX:
            case (int)Register.CX:
            case (int)Register.DX:
            case (int)Register.BX:
            case (int)Register.BP:
            case (int)Register.SI:
            case (int)Register.DI:
            case (int)Register.IP:
            case (int)Register.CS:
            case (int)Register.DS:
            case (int)Register.ES:
            case (int)Register.SS:
            case unchecked ((int)Register.FLAGS):
                cpu.Push(cpu.GetRegister((Register)instruction.Argument1));
                break;

            case OpCodeManager.ARG_DEREFERENCE:
            case OpCodeManager.ARG_MEMORY:
                var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);
                cpu.Push(cpu.ReadU16(address));
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }
        }
Example #3
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            ushort value1;
            ushort value2;
            byte   size;

            if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                value1 = cpu.GetRegisterU8(Register.AL);
                value2 = cpu.ReadU8(InstructionHelper.SegmentToAddress(cpu.GetRegister(Register.ES), cpu.GetRegister(Register.DI)));
                size   = 1;
            }
            else
            {
                value1 = cpu.GetRegister(Register.AX);
                value2 = cpu.ReadU16(InstructionHelper.SegmentToAddress(cpu.GetRegister(Register.ES), cpu.GetRegister(Register.DI)));
                size   = 2;
            }
            var result = value1 - value2;

            InstructionHelper.CalculateSubFlags(cpu, instruction.Flag, value1, value2, result);

            if (!cpu.GetFlags().Has(FlagsRegister.Direction))
            {
                cpu.IncRegister(Register.DI, size);
            }
            else
            {
                cpu.DecRegister(Register.DI, size);
            }
        }
Example #4
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            switch (instruction.Type)
            {
            case OpCodeManager.InstructionType.Cmps:
                new CompareString().Dispatch(cpu, instruction);
                break;

            case OpCodeManager.InstructionType.Lods:
                new LoadString().Dispatch(cpu, instruction);
                break;

            case OpCodeManager.InstructionType.Movs:
                new MoveString().Dispatch(cpu, instruction);
                break;

            case OpCodeManager.InstructionType.Stos:
                new StoreString().Dispatch(cpu, instruction);
                break;

            case OpCodeManager.InstructionType.Scas:
                new ScanString().Dispatch(cpu, instruction);
                break;

            default:
                throw new NotImplementedException();
            }
        }
Example #5
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     if (cpu.GetRegister(Register.CX) == 0)
     {
         new JumpRelative().Dispatch(cpu, instruction);
     }
 }
Example #6
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            switch (instruction.Argument1)
            {
            case (int)Register.AX:
            case (int)Register.CX:
            case (int)Register.DX:
            case (int)Register.BX:
            case (int)Register.SP:
            case (int)Register.BP:
            case (int)Register.SI:
            case (int)Register.DI:
            case (int)Register.IP:
            case (int)Register.CS:
            case (int)Register.DS:
            case (int)Register.ES:
            case (int)Register.SS:
                cpu.SetRegister((Register)instruction.Argument1, ProcessExchangeSecond(cpu, instruction, cpu.GetRegister((Register)instruction.Argument1)));
                break;

            case OpCodeManager.ARG_BYTE_REGISTER:
                cpu.SetRegister((Register)instruction.Argument1Value, (byte)ProcessExchangeSecond(cpu, instruction, cpu.GetRegisterU8((Register)instruction.Argument1Value)));
                break;

            default:
                throw new NotImplementedException();
            }
        }
Example #7
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var value1 = cpu.GetRegister(Register.AX);
            var value2 = InstructionHelper.GetInstructionValue(cpu, instruction.Flag, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);

            if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                value1 &= 0xFF;
                value2 &= 0xFF;
            }

            uint result;

            switch (instruction.Type)
            {
            case OpCodeManager.InstructionType.Multiply:
                result = (uint)value1 * value2;
                break;

            case OpCodeManager.InstructionType.SignedMultiply:
                result = (uint)(value1 * value2);
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }

            InstructionHelper.CalculateAddFlags(cpu, instruction.Flag, value1, value2, (int)result);

            cpu.SetRegister(Register.AX, (ushort)result);
            if (!instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                cpu.SetRegister(Register.DX, (ushort)(result >> 16));
            }
        }
Example #8
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            switch (instruction.Argument1)
            {
            case (int)Register.AX:
            case (int)Register.CX:
            case (int)Register.DX:
            case (int)Register.BX:
            case (int)Register.SP:
            case (int)Register.BP:
            case (int)Register.SI:
            case (int)Register.DI:
            case (int)Register.IP:
            case (int)Register.CS:
            case (int)Register.DS:
            case (int)Register.ES:
            case (int)Register.SS:
                //case unchecked((int)Register.FLAGS):
                cpu.SetRegister((Register)instruction.Argument1, cpu.Pop());
                break;

            case unchecked ((int)Register.FLAGS):
                cpu.SetRegister((Register)instruction.Argument1, cpu.Pop());
                break;

            case OpCodeManager.ARG_DEREFERENCE:
            case OpCodeManager.ARG_MEMORY:
                var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);
                cpu.WriteU16(address, cpu.Pop());
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }
        }
Example #9
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument2, instruction.Argument2Value, instruction.Argument2Displacement);
            var memory  = cpu.ReadU16(address);
            var segment = cpu.ReadU16(address + 2);

            cpu.SetRegister(_register, segment);
            switch ((Register)instruction.Argument1)
            {
            case Register.AX:
            case Register.CX:
            case Register.DX:
            case Register.BX:
            case Register.SP:
            case Register.BP:
            case Register.SI:
            case Register.DI:
            case Register.IP:
            case Register.CS:
            case Register.DS:
            case Register.ES:
            case Register.SS:
                cpu.SetRegister((Register)instruction.Argument1, memory);
                break;

            default:
                throw new NotImplementedException();
            }
        }
Example #10
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            const FlagsRegister flagsAffected = FlagsRegister.Sign | FlagsRegister.Zero | FlagsRegister.Auxiliary | FlagsRegister.Parity | FlagsRegister.Carry;

            cpu.Flags &= ~flagsAffected;
            cpu.Flags |= (FlagsRegister)(cpu.GetRegister(Register.AH) & (ushort)flagsAffected);
        }
Example #11
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var address = InstructionHelper.GetInstructionAddress(cpu, instruction.Argument2, instruction.Argument2Value, instruction.Argument2Displacement);

            switch ((Register)instruction.Argument1)
            {
            case Register.AX:
            case Register.CX:
            case Register.DX:
            case Register.BX:
            case Register.SP:
            case Register.BP:
            case Register.SI:
            case Register.DI:
            case Register.IP:
            case Register.CS:
            case Register.DS:
            case Register.ES:
            case Register.SS:
                cpu.SetRegister((Register)instruction.Argument1, address);
                break;

            default:
                throw new NotImplementedException();
            }
        }
Example #12
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     cpu.SetRegister(Register.IP, cpu.Pop());
     cpu.SetRegister(Register.CS, cpu.Pop());
     cpu.SetRegister(Register.FLAGS, cpu.Pop());
     //cpu._interruptStack.Pop();
 }
Example #13
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var prefix = instruction.SegmentPrefix;

            if (prefix == Register.Invalid)
            {
                prefix = Register.DS;
            }
            var sourceAddress = InstructionHelper.SegmentToAddress(cpu.GetRegister(prefix), cpu.GetRegister(Register.SI));

            byte size;

            if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                cpu.SetRegisterU8(Register.AL, cpu.ReadU8(sourceAddress));
                size = 1;
            }
            else
            {
                cpu.SetRegister(Register.AX, cpu.ReadU16(sourceAddress));
                size = 2;
            }

            if (!cpu.GetFlags().Has(FlagsRegister.Direction))
            {
                cpu.SetRegister(Register.SI, (ushort)(cpu.GetRegister(Register.SI) + size));
            }
            else
            {
                cpu.SetRegister(Register.SI, (ushort)(cpu.GetRegister(Register.SI) - size));
            }
        }
Example #14
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var address = InstructionHelper.GetInstructionValue(cpu, instruction.Flag, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);

            cpu.Push(cpu.GetRegister(Register.IP));
            cpu.SetRegister(Register.IP, address);
        }
Example #15
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var al    = cpu.GetRegisterU8(Register.AL);
            var flags = cpu.GetFlags();

            if ((al & 0xF) > 9 || flags.Has(FlagsRegister.Auxiliary))
            {
                var ah = cpu.GetRegisterU8(Register.AH);

                al = (byte)((al + 6) & 0x0F);
                ah++;

                cpu.SetRegisterU8(Register.AH, ah);
                flags |= FlagsRegister.Carry | FlagsRegister.Auxiliary;
            }
            else
            {
                al    &= 0x0F;
                flags &= ~(FlagsRegister.Carry | FlagsRegister.Auxiliary);
            }

            flags &= ~(FlagsRegister.Parity | FlagsRegister.Zero | FlagsRegister.Sign);
            flags |= (InstructionHelper.ParityLookup[al] ? FlagsRegister.Parity : 0) |
                     (al == 0 ? FlagsRegister.Zero : 0) |
                     ((al & 0x80) != 0 ? FlagsRegister.Sign : 0);

            cpu.SetFlags(flags);
            cpu.SetRegisterU8(Register.AL, al);
        }
Example #16
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     if (cpu.GetFlags().Has(FlagsRegister.Overflow))
     {
         cpu.Interrupt(4);
     }
 }
Example #17
0
        private static void RunTest([NotNull] string testFile)
        {
            ICpu cpu;

            using (var file = File.OpenRead("CpuBinaries/" + testFile))
                cpu = new Cpu8086(file, 1024 * 1024);
            cpu.WriteBytes(0, new byte[0x100]);

            if (cpu.ProcessInstructions(1000))
            {
                throw new InvalidOperationException("Test case did not complete in the required amount of time.");
            }

            using (var file = File.OpenRead($"CpuBinaries/{testFile}Result"))
            {
                var goodData = new byte[file.Length];
                if (file.Read(goodData, 0, goodData.Length) != goodData.Length)
                {
                    throw new InvalidDataException();
                }

                var testData = cpu.ReadBytes(0, (uint)goodData.Length);

                var result = CompareArrays(goodData, testData);
                if (result.Count > 0)
                {
                    var comparison = result.Select(i => new Tuple <int, byte, byte>(i, goodData[i], testData[i])).ToList();
                    throw new InvalidOperationException("Test case did not produce valid output.");
                }
            }
        }
Example #18
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var al = cpu.GetRegister(Register.AL);

            cpu.SetRegister(Register.AH, (byte)(al / 10));
            cpu.SetRegister(Register.AL, (byte)(al % 10));
            InstructionHelper.CalculateBitwiseFlags(cpu, instruction.Flag, al, 0, cpu.GetRegister(Register.AX));
        }
Example #19
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var flags = cpu.GetFlags();

            if (!flags.Has(FlagsRegister.Carry) && !flags.Has(FlagsRegister.Zero))
            {
                new JumpRelative().Dispatch(cpu, instruction);
            }
        }
Example #20
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var flags = cpu.GetFlags();

            if (flags.Has(FlagsRegister.Zero) || flags.Has(FlagsRegister.Sign) != flags.Has(FlagsRegister.Overflow))
            {
                new JumpRelative().Dispatch(cpu, instruction);
            }
        }
Example #21
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            cpu.DecRegister(Register.CX);
            var counter = cpu.GetRegister(Register.CX);

            if (counter != 0)
            {
                new JumpRelative().Dispatch(cpu, instruction);
            }
        }
Example #22
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
     {
         new Divide8().Dispatch(cpu, instruction);
     }
     else
     {
         new Divide16().Dispatch(cpu, instruction);
     }
 }
Example #23
0
 public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
 {
     cpu.SetRegister(Register.IP, cpu.Pop());
     if (instruction.Argument1 == OpCodeManager.ARG_CONSTANT)
     {
         cpu.SetRegister(Register.SP, (ushort)(cpu.GetRegister(Register.SP) + instruction.Argument1Value));
     }
     else
     {
         Debug.Assert(instruction.Argument1 == OpCodeManager.ARG_NONE);
     }
 }
Example #24
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var al       = cpu.GetRegisterU8(Register.AL);
            var oldAl    = al;
            var flags    = cpu.GetFlags();
            var oldCarry = flags.Has(FlagsRegister.Carry);

            flags &= ~FlagsRegister.Carry;

            if ((al & 0xF) > 9 || flags.Has(FlagsRegister.Auxiliary))
            {
                al -= 6;
                if (oldCarry || (al > oldAl))
                {
                    flags |= FlagsRegister.Carry;
                }
                else
                {
                    flags &= ~FlagsRegister.Carry;
                }
                flags |= FlagsRegister.Auxiliary;
            }
            else
            {
                flags &= ~FlagsRegister.Auxiliary;
            }

            if (oldAl > 0x99 || oldCarry)
            {
                al    -= 0x60;
                flags |= FlagsRegister.Carry;
            }
            else
            {
                flags &= ~FlagsRegister.Carry;
            }

            flags &= ~(FlagsRegister.Parity | FlagsRegister.Zero | FlagsRegister.Sign);
            flags |= (InstructionHelper.ParityLookup[al] ? FlagsRegister.Parity : 0) |
                     (al == 0 ? FlagsRegister.Zero : 0) |
                     ((al & 0x80) != 0 ? FlagsRegister.Sign : 0);

            cpu.SetFlags(flags);
            cpu.SetRegister(Register.AL, al);
        }
Example #25
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var value = InstructionHelper.GetInstructionValue(cpu, instruction.Flag, instruction.SegmentPrefix, instruction.Argument2, instruction.Argument2Value, instruction.Argument2Displacement);

            switch (instruction.Argument1)
            {
            case (int)Register.AX:
            case (int)Register.CX:
            case (int)Register.DX:
            case (int)Register.BX:
            case (int)Register.SP:
            case (int)Register.BP:
            case (int)Register.SI:
            case (int)Register.DI:
            case (int)Register.IP:
            case (int)Register.CS:
            case (int)Register.DS:
            case (int)Register.ES:
            case (int)Register.SS:
                cpu.SetRegister((Register)instruction.Argument1, value);
                break;

            case OpCodeManager.ARG_BYTE_REGISTER:
                cpu.SetRegisterU8((Register)instruction.Argument1Value, (byte)value);
                break;

            case OpCodeManager.ARG_DEREFERENCE:
            case OpCodeManager.ARG_MEMORY:
                var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);
                if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
                {
                    cpu.WriteU8(address, (byte)value);
                }
                else
                {
                    cpu.WriteU16(address, value);
                }
                break;

            default:
                throw new NotImplementedException();
            }
        }
Example #26
0
        public Mini8086Emulator()
        {
            var components = new List <BaseComponent>();

            _memMapper  = new MemoryMapper(512);
            _portMapper = new PortMapper();

            _cpu          = new Cpu8086(_memMapper, _portMapper);
            _disassembler = new Disassembler(_cpu, _memMapper);

            components.Add(_bios = new Rom(Config.BiosMemAddress));
            _memMapper.Register(Config.BiosMemAddress, Config.BiosMemAddress + Config.BiosMemSize - 1, _bios);

            components.Add(_pic = new InterruptController(Config.PicBasePort));
            _portMapper.Register(Config.PicBasePort, Config.PicBasePort + 0x07, _pic);

            components.Add(_timer = new Timer(Config.TimerBasePort, _pic));
            _portMapper.Register(Config.TimerBasePort, Config.TimerBasePort + 0x07, _timer);

            components.Add(_graphicsAdapter = new GraphicsAdapter(Config.VgaBasePort, Config.VgaMemAddress, _pic, @"..\..\..\ROMs\charrom.bin"));
            _portMapper.Register(Config.VgaBasePort, Config.VgaBasePort + 0x07, _graphicsAdapter);
            _memMapper.Register(Config.VgaMemAddress, Config.VgaMemAddress + Config.VgaMemSize - 1, _graphicsAdapter);

            components.Add(_lcd = new Lcd44780(Config.LcdBasePort));
            _portMapper.Register(Config.LcdBasePort, Config.LcdBasePort + 0x07, _lcd);

            //components.Add(_ppi = new Ppi(Config.PpiBasePort));
            //_portMapper.Register(Config.PpiBasePort, Config.PpiBasePort + 0x07, _ppi);

            components.Add(_keybController = new KeybController(Config.KeybControllerBasePort, _pic));
            _portMapper.Register(Config.KeybControllerBasePort, Config.KeybControllerBasePort + 0x07, _keybController);

            components.Add(_sdController = new SdController(Config.SdControllerBasePort, Config.SdImagePath));
            _portMapper.Register(Config.SdControllerBasePort, Config.SdControllerBasePort + 0x07, _sdController);

            _memMapper.FinishRegistration();

            components.ForEach(_ =>
            {
                _.EventTimer     = _cpu;
                _.DoCpuInterrupt = _cpu.DoInterrupt;
            });
        }
Example #27
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            switch (instruction.Argument1)
            {
            case OpCodeManager.ARG_FAR_MEMORY:
                cpu.SetRegister(Register.CS, (ushort)((uint)instruction.Argument1Value >> 16));
                cpu.SetRegister(Register.IP, (ushort)(instruction.Argument1Value & 0xFFFF));
                break;

            case OpCodeManager.ARG_DEREFERENCE:
            case OpCodeManager.ARG_MEMORY:
                var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);
                cpu.SetRegister(Register.CS, cpu.ReadU16(address + 2));
                cpu.SetRegister(Register.IP, cpu.ReadU16(address));
                break;

            default:
                throw new InvalidOperationException();
            }
        }
Example #28
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var port   = InstructionHelper.GetInstructionValue(cpu, instruction.Flag, instruction.SegmentPrefix, instruction.Argument2, instruction.Argument2Value, instruction.Argument2Displacement);
            var device = cpu.GetPortDevice(port);

            if (device == null)
            {
                throw new InvalidOperationException($"Tried to read from port 0x{port.ToString("X")}");
            }

            if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                cpu.SetRegister(Register.AL, device.Read(port));
                //Console.WriteLine($"IN {port.ToString("X")}:{cpu.GetRegister(Register.AL).ToString("X")}");
            }
            else
            {
                cpu.SetRegister(Register.AX, device.Read16(port));
            }
        }
Example #29
0
        public void Dispatch(Cpu8086 cpu, OpCodeManager.Instruction instruction)
        {
            var port = InstructionHelper.GetInstructionValue(cpu, instruction.Flag, instruction.SegmentPrefix, instruction.Argument1, instruction.Argument1Value, instruction.Argument1Displacement);

            var device = cpu.GetPortDevice(port);

            if (device == null)
            {
                throw new InvalidOperationException($"Tried to write to port 0x{port.ToString("X")}");
            }

            if (instruction.Flag.Has(OpCodeManager.OpCodeFlag.Size8))
            {
                //Console.WriteLine($"OUT {port.ToString("X")}:{cpu.GetRegister(Register.AL).ToString("X")}");
                device.Write(port, (byte)cpu.GetRegister(Register.AL));
            }
            else
            {
                device.Write16(port, cpu.GetRegister(Register.AX));
            }
        }
Example #30
0
        private ushort ProcessExchangeSecond(Cpu8086 cpu, OpCodeManager.Instruction instruction, ushort value)
        {
            ushort tmp;

            switch (instruction.Argument2)
            {
            case (int)Register.AX:
            case (int)Register.CX:
            case (int)Register.DX:
            case (int)Register.BX:
            case (int)Register.SP:
            case (int)Register.BP:
            case (int)Register.SI:
            case (int)Register.DI:
            case (int)Register.IP:
            case (int)Register.CS:
            case (int)Register.DS:
            case (int)Register.ES:
            case (int)Register.SS:
                tmp = cpu.GetRegister((Register)instruction.Argument2);
                cpu.SetRegister((Register)instruction.Argument2, (byte)value);
                break;

            case OpCodeManager.ARG_BYTE_REGISTER:
                tmp = cpu.GetRegisterU8((Register)instruction.Argument2Value);
                cpu.SetRegisterU8((Register)instruction.Argument2Value, (byte)value);
                break;

            case OpCodeManager.ARG_DEREFERENCE:
            case OpCodeManager.ARG_MEMORY:
                var address = InstructionHelper.GetInstructionRealAddress(cpu, instruction.SegmentPrefix, instruction.Argument2, instruction.Argument2Value, instruction.Argument2Displacement);
                tmp = cpu.ReadU16(address);
                cpu.WriteU16(address, value);
                break;

            default:
                throw new NotImplementedException();
            }
            return(tmp);
        }