1use super::helpers::encode_package_len;
8
9pub trait OperationObject {
11 fn append_to_vec(&self, byte_stream: &mut Vec<u8>);
12
13 fn to_bytes(&self) -> Vec<u8> {
14 let mut byte_stream = Vec::new();
15 self.append_to_vec(&mut byte_stream);
16 byte_stream
17 }
18}
19
20pub struct AndOp {
22 pub operand1: Vec<u8>,
23 pub operand2: Vec<u8>,
24 pub target_name: Vec<u8>,
25}
26
27impl OperationObject for AndOp {
28 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
29 byte_stream.push(0x7b);
30 byte_stream.extend_from_slice(&self.operand1);
31 byte_stream.extend_from_slice(&self.operand2);
32 byte_stream.extend_from_slice(&self.target_name);
33 }
34}
35
36pub struct OrOp {
38 pub operand1: Vec<u8>,
39 pub operand2: Vec<u8>,
40 pub target_name: Vec<u8>,
41}
42
43impl OperationObject for OrOp {
44 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
45 byte_stream.push(0x7d);
46 byte_stream.extend_from_slice(&self.operand1);
47 byte_stream.extend_from_slice(&self.operand2);
48 byte_stream.extend_from_slice(&self.target_name);
49 }
50}
51
52pub struct IfOp {
54 pub predicate: Vec<u8>,
56 pub body: Vec<u8>,
58}
59
60impl OperationObject for IfOp {
61 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
62 byte_stream.push(0xa0); let inner_len = self.predicate.len() + self.body.len();
64 byte_stream.extend_from_slice(&encode_package_len(inner_len));
65 byte_stream.extend_from_slice(&self.predicate);
66 byte_stream.extend_from_slice(&self.body);
67 }
68}
69
70pub struct ElseOp {
72 pub body: Vec<u8>,
74}
75
76impl OperationObject for ElseOp {
77 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
78 byte_stream.push(0xa1); byte_stream.extend_from_slice(&encode_package_len(self.body.len()));
80 byte_stream.extend_from_slice(&self.body);
81 }
82}
83
84pub struct StoreOp {
86 pub source: Vec<u8>,
88 pub destination: Vec<u8>,
90}
91
92impl OperationObject for StoreOp {
93 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
94 byte_stream.push(0x70); byte_stream.extend_from_slice(&self.source);
96 byte_stream.extend_from_slice(&self.destination);
97 }
98}
99
100pub struct LEqualOp {
102 pub left: Vec<u8>,
104 pub right: Vec<u8>,
106}
107
108impl OperationObject for LEqualOp {
109 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
110 byte_stream.push(0x93); byte_stream.extend_from_slice(&self.left);
112 byte_stream.extend_from_slice(&self.right);
113 }
114}
115
116pub struct CreateDWordFieldOp {
118 pub source_buffer: Vec<u8>,
120 pub byte_index: Vec<u8>,
122 pub field_name: [u8; 4],
124}
125
126impl OperationObject for CreateDWordFieldOp {
127 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
128 byte_stream.push(0x8a); byte_stream.extend_from_slice(&self.source_buffer);
130 byte_stream.extend_from_slice(&self.byte_index);
131 byte_stream.extend_from_slice(&self.field_name);
132 }
133}
134
135pub struct ReturnOp {
137 pub result: Vec<u8>,
138}
139
140impl OperationObject for ReturnOp {
141 fn append_to_vec(&self, byte_stream: &mut Vec<u8>) {
142 byte_stream.push(0xa4);
143 byte_stream.extend_from_slice(&self.result);
144 }
145}
146
147#[cfg(test)]
148mod tests {
149 use super::*;
150 use crate::aml::encode_integer;
151 use crate::aml::test_helpers::verify_expected_bytes;
152
153 #[test]
154 fn verify_and_operation() {
155 let op = AndOp {
156 operand1: vec![b'S', b'T', b'A', b'_'],
157 operand2: encode_integer(13),
158 target_name: vec![b'S', b'T', b'A', b'_'],
159 };
160 let bytes = op.to_bytes();
161 verify_expected_bytes(
162 &bytes,
163 &[
164 0x7b, b'S', b'T', b'A', b'_', 0x0a, 0x0d, b'S', b'T', b'A', b'_',
165 ],
166 );
167 }
168
169 #[test]
170 fn verify_or_operation() {
171 let op = OrOp {
172 operand1: vec![b'S', b'T', b'A', b'_'],
173 operand2: encode_integer(13),
174 target_name: vec![b'S', b'T', b'A', b'_'],
175 };
176 let bytes = op.to_bytes();
177 verify_expected_bytes(
178 &bytes,
179 &[
180 0x7d, b'S', b'T', b'A', b'_', 0x0a, 0x0d, b'S', b'T', b'A', b'_',
181 ],
182 );
183 }
184
185 #[test]
186 fn verify_return_operation() {
187 let op = ReturnOp {
188 result: vec![b'S', b'T', b'A', b'_'],
189 };
190 let bytes = op.to_bytes();
191 verify_expected_bytes(&bytes, &[0xa4, b'S', b'T', b'A', b'_']);
192 }
193
194 #[test]
195 fn verify_if_operation() {
196 let op = IfOp {
198 predicate: vec![0x01],
199 body: vec![],
200 };
201 let bytes = op.to_bytes();
202 verify_expected_bytes(&bytes, &[0xa0, 0x02, 0x01]);
204 }
205
206 #[test]
207 fn verify_else_operation() {
208 let body = ReturnOp { result: vec![0x01] }.to_bytes();
210 let op = ElseOp { body };
211 let bytes = op.to_bytes();
212 verify_expected_bytes(&bytes, &[0xa1, 0x03, 0xa4, 0x01]);
214 }
215
216 #[test]
217 fn verify_store_operation() {
218 let op = StoreOp {
219 source: encode_integer(0),
220 destination: vec![b'S', b'T', b'S', b'0'],
221 };
222 let bytes = op.to_bytes();
223 verify_expected_bytes(&bytes, &[0x70, 0x00, b'S', b'T', b'S', b'0']);
225 }
226
227 #[test]
228 fn verify_lequal_operation() {
229 let op = LEqualOp {
230 left: vec![0x68], right: vec![0x01], };
233 let bytes = op.to_bytes();
234 verify_expected_bytes(&bytes, &[0x93, 0x68, 0x01]);
236 }
237
238 #[test]
239 fn verify_create_dword_field_operation() {
240 let op = CreateDWordFieldOp {
241 source_buffer: vec![0x6b], byte_index: encode_integer(0),
243 field_name: *b"STS0",
244 };
245 let bytes = op.to_bytes();
246 verify_expected_bytes(&bytes, &[0x8a, 0x6b, 0x00, b'S', b'T', b'S', b'0']);
248 }
249}