x86emu/emulator/
mov.rs

1// Copyright (c) Microsoft Corporation.
2// Licensed under the MIT License.
3
4use super::AlignmentMode;
5use super::Emulator;
6use super::InternalError;
7use crate::Cpu;
8use crate::Segment;
9use iced_x86::Instruction;
10use iced_x86::OpKind;
11
12impl<T: Cpu> Emulator<'_, T> {
13    pub(super) async fn mov(&mut self, instr: &Instruction) -> Result<(), InternalError<T::Error>> {
14        let value = self.op_value(instr, 1).await?;
15        self.write_op_0(instr, value).await?;
16        Ok(())
17    }
18
19    pub(super) async fn movsx(
20        &mut self,
21        instr: &Instruction,
22    ) -> Result<(), InternalError<T::Error>> {
23        let value = self.op_value_sign_extend(instr, 1).await?;
24        self.write_op_0(instr, value as u64).await?;
25        Ok(())
26    }
27
28    pub(super) async fn mov_sse(
29        &mut self,
30        instr: &Instruction,
31        alignment: AlignmentMode,
32    ) -> Result<(), InternalError<T::Error>> {
33        let value = match instr.op1_kind() {
34            OpKind::Memory => self.read_memory_op(instr, 1, alignment).await?,
35            OpKind::Register => {
36                let reg = instr.op1_register();
37                assert!(reg.is_xmm());
38                self.cpu.xmm(reg.number())
39            }
40            _ => Err(self.unsupported_instruction(instr))?,
41        };
42
43        match instr.op0_kind() {
44            OpKind::Memory => self.write_memory_op(instr, 0, alignment, value).await?,
45            OpKind::Register => {
46                let reg = instr.op0_register();
47                assert!(reg.is_xmm());
48                let xmm_index = reg.number();
49                self.cpu.set_xmm(xmm_index, value)
50            }
51            _ => Err(self.unsupported_instruction(instr))?,
52        };
53
54        Ok(())
55    }
56
57    pub(super) async fn movdir64b(
58        &mut self,
59        instr: &Instruction,
60    ) -> Result<(), InternalError<T::Error>> {
61        let mut buffer = [0; 64];
62        let src = self.memory_op_offset(instr, 1);
63        let dst = self.cpu.gp(instr.op0_register().into());
64
65        self.read_memory(
66            instr.memory_segment().into(),
67            src,
68            AlignmentMode::Unaligned,
69            &mut buffer,
70        )
71        .await?;
72
73        self.write_memory(Segment::ES, dst, AlignmentMode::Aligned(64), &buffer)
74            .await?;
75
76        Ok(())
77    }
78}