autd3_firmware_emulator/fpga/emulator/stm/
mod.rs

1mod foci;
2mod gain;
3
4use autd3_core::firmware::{Drive, Phase, Segment, transition_mode::TransitionModeParams};
5
6use super::{super::params::*, FPGAEmulator};
7
8impl FPGAEmulator {
9    #[must_use]
10    pub fn is_stm_gain_mode(&self, segment: Segment) -> bool {
11        self.mem
12            .controller_bram
13            .read(ADDR_STM_MODE0 + segment as usize)
14            == STM_MODE_GAIN
15    }
16
17    #[must_use]
18    pub fn stm_freq_divide(&self, segment: Segment) -> u16 {
19        self.mem
20            .controller_bram
21            .read(ADDR_STM_FREQ_DIV0 + segment as usize)
22    }
23
24    #[must_use]
25    pub fn stm_cycle(&self, segment: Segment) -> usize {
26        self.mem
27            .controller_bram
28            .read(ADDR_STM_CYCLE0 + segment as usize) as usize
29            + 1
30    }
31
32    #[must_use]
33    pub fn stm_loop_count(&self, segment: Segment) -> u16 {
34        self.mem
35            .controller_bram
36            .read(ADDR_STM_REP0 + segment as usize)
37    }
38
39    #[must_use]
40    pub fn stm_transition_mode(&self) -> TransitionModeParams {
41        TransitionModeParams {
42            mode: self.mem.controller_bram.read(ADDR_STM_TRANSITION_MODE) as u8,
43            value: self
44                .mem
45                .controller_bram
46                .read_bram_as::<u64>(ADDR_STM_TRANSITION_VALUE_0),
47        }
48    }
49
50    #[must_use]
51    pub fn req_stm_segment(&self) -> Segment {
52        match self.mem.controller_bram.read(ADDR_STM_REQ_RD_SEGMENT) {
53            0 => Segment::S0,
54            1 => Segment::S1,
55            _ => unreachable!(),
56        }
57    }
58
59    #[must_use]
60    pub fn drives(&self) -> Vec<Drive> {
61        self.drives_at(self.current_stm_segment(), self.current_stm_idx())
62    }
63
64    #[must_use]
65    pub fn drives_at(&self, segment: Segment, idx: usize) -> Vec<Drive> {
66        let len = self.mem.num_transducers;
67        let mut phase_corr = Vec::<Phase>::with_capacity(len);
68        let mut output_mask = Vec::<bool>::with_capacity(len);
69        let mut buffer = Vec::with_capacity(len);
70        unsafe {
71            self.drives_at_inplace(
72                segment,
73                idx,
74                phase_corr.as_mut_ptr(),
75                output_mask.as_mut_ptr(),
76                buffer.as_mut_ptr(),
77            );
78            buffer.set_len(len);
79        }
80        buffer
81    }
82
83    pub unsafe fn drives_at_inplace(
84        &self,
85        segment: Segment,
86        idx: usize,
87        phase_corr_buf: *mut Phase,
88        output_mask_buf: *mut bool,
89        dst: *mut Drive,
90    ) {
91        if self.is_stm_gain_mode(segment) {
92            self.gain_stm_drives_inplace(segment, idx, phase_corr_buf, output_mask_buf, dst)
93        } else {
94            self.foci_stm_drives_inplace(segment, idx, phase_corr_buf, output_mask_buf, dst)
95        }
96    }
97}