asmkit/x86/features/SHA.rs
1use crate::x86::assembler::*;
2use crate::x86::operands::*;
3use super::super::opcodes::*;
4use crate::core::emitter::*;
5use crate::core::operand::*;
6
7/// A dummy operand that represents no register. Here just for simplicity.
8const NOREG: Operand = Operand::new();
9
10/// `SHA1MSG1` (SHA1MSG1).
11/// The SHA1MSG1 instruction is one of two SHA1 message scheduling instructions. The instruction performs an intermediate calculation for the next four SHA1 message dwords.
12///
13///
14/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1MSG1.html).
15///
16/// Supported operand variants:
17///
18/// ```text
19/// +---+----------+
20/// | # | Operands |
21/// +---+----------+
22/// | 1 | Xmm, Mem |
23/// | 2 | Xmm, Xmm |
24/// +---+----------+
25/// ```
26pub trait Sha1msg1Emitter<A, B> {
27 fn sha1msg1(&mut self, op0: A, op1: B);
28}
29
30impl<'a> Sha1msg1Emitter<Xmm, Xmm> for Assembler<'a> {
31 fn sha1msg1(&mut self, op0: Xmm, op1: Xmm) {
32 self.emit(SHA1MSG1RR, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
33 }
34}
35
36impl<'a> Sha1msg1Emitter<Xmm, Mem> for Assembler<'a> {
37 fn sha1msg1(&mut self, op0: Xmm, op1: Mem) {
38 self.emit(SHA1MSG1RM, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
39 }
40}
41
42/// `SHA1MSG2` (SHA1MSG2).
43/// The SHA1MSG2 instruction is one of two SHA1 message scheduling instructions. The instruction performs the final calculation to derive the next four SHA1 message dwords.
44///
45///
46/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1MSG2.html).
47///
48/// Supported operand variants:
49///
50/// ```text
51/// +---+----------+
52/// | # | Operands |
53/// +---+----------+
54/// | 1 | Xmm, Mem |
55/// | 2 | Xmm, Xmm |
56/// +---+----------+
57/// ```
58pub trait Sha1msg2Emitter<A, B> {
59 fn sha1msg2(&mut self, op0: A, op1: B);
60}
61
62impl<'a> Sha1msg2Emitter<Xmm, Xmm> for Assembler<'a> {
63 fn sha1msg2(&mut self, op0: Xmm, op1: Xmm) {
64 self.emit(SHA1MSG2RR, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
65 }
66}
67
68impl<'a> Sha1msg2Emitter<Xmm, Mem> for Assembler<'a> {
69 fn sha1msg2(&mut self, op0: Xmm, op1: Mem) {
70 self.emit(SHA1MSG2RM, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
71 }
72}
73
74/// `SHA1NEXTE` (SHA1NEXTE).
75/// The SHA1NEXTE calculates the SHA1 state variable E after four rounds of operation from the current SHA1 state variable A in the destination operand. The calculated value of the SHA1 state variable E is added to the source operand, which contains the scheduled dwords.
76///
77///
78/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1NEXTE.html).
79///
80/// Supported operand variants:
81///
82/// ```text
83/// +---+----------+
84/// | # | Operands |
85/// +---+----------+
86/// | 1 | Xmm, Mem |
87/// | 2 | Xmm, Xmm |
88/// +---+----------+
89/// ```
90pub trait Sha1nexteEmitter<A, B> {
91 fn sha1nexte(&mut self, op0: A, op1: B);
92}
93
94impl<'a> Sha1nexteEmitter<Xmm, Xmm> for Assembler<'a> {
95 fn sha1nexte(&mut self, op0: Xmm, op1: Xmm) {
96 self.emit(SHA1NEXTERR, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
97 }
98}
99
100impl<'a> Sha1nexteEmitter<Xmm, Mem> for Assembler<'a> {
101 fn sha1nexte(&mut self, op0: Xmm, op1: Mem) {
102 self.emit(SHA1NEXTERM, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
103 }
104}
105
106/// `SHA1RNDS4` (SHA1RNDS4).
107/// The SHA1RNDS4 instruction performs four rounds of SHA1 operation using an initial SHA1 state (A,B,C,D) from the first operand (which is a source operand and the destination operand) and some pre-computed sum of the next 4 round message dwords, and state variable E from the second operand (a source operand). The updated SHA1 state (A,B,C,D) after four rounds of processing is stored in the destination operand.
108///
109///
110/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1RNDS4.html).
111///
112/// Supported operand variants:
113///
114/// ```text
115/// +---+---------------+
116/// | # | Operands |
117/// +---+---------------+
118/// | 1 | Xmm, Mem, Imm |
119/// | 2 | Xmm, Xmm, Imm |
120/// +---+---------------+
121/// ```
122pub trait Sha1rnds4Emitter<A, B, C> {
123 fn sha1rnds4(&mut self, op0: A, op1: B, op2: C);
124}
125
126impl<'a> Sha1rnds4Emitter<Xmm, Xmm, Imm> for Assembler<'a> {
127 fn sha1rnds4(&mut self, op0: Xmm, op1: Xmm, op2: Imm) {
128 self.emit(SHA1RNDS4RRI, op0.as_operand(), op1.as_operand(), op2.as_operand(), &NOREG);
129 }
130}
131
132impl<'a> Sha1rnds4Emitter<Xmm, Mem, Imm> for Assembler<'a> {
133 fn sha1rnds4(&mut self, op0: Xmm, op1: Mem, op2: Imm) {
134 self.emit(SHA1RNDS4RMI, op0.as_operand(), op1.as_operand(), op2.as_operand(), &NOREG);
135 }
136}
137
138/// `SHA256MSG1` (SHA256MSG1).
139/// The SHA256MSG1 instruction is one of two SHA256 message scheduling instructions. The instruction performs an intermediate calculation for the next four SHA256 message dwords.
140///
141///
142/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256MSG1.html).
143///
144/// Supported operand variants:
145///
146/// ```text
147/// +---+----------+
148/// | # | Operands |
149/// +---+----------+
150/// | 1 | Xmm, Mem |
151/// | 2 | Xmm, Xmm |
152/// +---+----------+
153/// ```
154pub trait Sha256msg1Emitter<A, B> {
155 fn sha256msg1(&mut self, op0: A, op1: B);
156}
157
158impl<'a> Sha256msg1Emitter<Xmm, Xmm> for Assembler<'a> {
159 fn sha256msg1(&mut self, op0: Xmm, op1: Xmm) {
160 self.emit(SHA256MSG1RR, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
161 }
162}
163
164impl<'a> Sha256msg1Emitter<Xmm, Mem> for Assembler<'a> {
165 fn sha256msg1(&mut self, op0: Xmm, op1: Mem) {
166 self.emit(SHA256MSG1RM, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
167 }
168}
169
170/// `SHA256MSG2` (SHA256MSG2).
171/// The SHA256MSG2 instruction is one of two SHA2 message scheduling instructions. The instruction performs the final calculation for the next four SHA256 message dwords.
172///
173///
174/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256MSG2.html).
175///
176/// Supported operand variants:
177///
178/// ```text
179/// +---+----------+
180/// | # | Operands |
181/// +---+----------+
182/// | 1 | Xmm, Mem |
183/// | 2 | Xmm, Xmm |
184/// +---+----------+
185/// ```
186pub trait Sha256msg2Emitter<A, B> {
187 fn sha256msg2(&mut self, op0: A, op1: B);
188}
189
190impl<'a> Sha256msg2Emitter<Xmm, Xmm> for Assembler<'a> {
191 fn sha256msg2(&mut self, op0: Xmm, op1: Xmm) {
192 self.emit(SHA256MSG2RR, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
193 }
194}
195
196impl<'a> Sha256msg2Emitter<Xmm, Mem> for Assembler<'a> {
197 fn sha256msg2(&mut self, op0: Xmm, op1: Mem) {
198 self.emit(SHA256MSG2RM, op0.as_operand(), op1.as_operand(), &NOREG, &NOREG);
199 }
200}
201
202/// `SHA256RNDS2` (SHA256RNDS2).
203/// The SHA256RNDS2 instruction performs 2 rounds of SHA256 operation using an initial SHA256 state (C,D,G,H) from the first operand, an initial SHA256 state (A,B,E,F) from the second operand, and a pre-computed sum of the next 2 round message dwords and the corresponding round constants from the implicit operand xmm0. Note that only the two lower dwords of XMM0 are used by the instruction.
204///
205///
206/// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256RNDS2.html).
207///
208/// Supported operand variants:
209///
210/// ```text
211/// +---+---------------+
212/// | # | Operands |
213/// +---+---------------+
214/// | 1 | Xmm, Mem, Xmm |
215/// | 2 | Xmm, Xmm, Xmm |
216/// +---+---------------+
217/// ```
218pub trait Sha256rnds2Emitter<A, B, C> {
219 fn sha256rnds2(&mut self, op0: A, op1: B, op2: C);
220}
221
222impl<'a> Sha256rnds2Emitter<Xmm, Xmm, Xmm> for Assembler<'a> {
223 fn sha256rnds2(&mut self, op0: Xmm, op1: Xmm, op2: Xmm) {
224 self.emit(SHA256RNDS2RRR, op0.as_operand(), op1.as_operand(), op2.as_operand(), &NOREG);
225 }
226}
227
228impl<'a> Sha256rnds2Emitter<Xmm, Mem, Xmm> for Assembler<'a> {
229 fn sha256rnds2(&mut self, op0: Xmm, op1: Mem, op2: Xmm) {
230 self.emit(SHA256RNDS2RMR, op0.as_operand(), op1.as_operand(), op2.as_operand(), &NOREG);
231 }
232}
233
234
235impl<'a> Assembler<'a> {
236 /// `SHA1MSG1` (SHA1MSG1).
237 /// The SHA1MSG1 instruction is one of two SHA1 message scheduling instructions. The instruction performs an intermediate calculation for the next four SHA1 message dwords.
238 ///
239 ///
240 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1MSG1.html).
241 ///
242 /// Supported operand variants:
243 ///
244 /// ```text
245 /// +---+----------+
246 /// | # | Operands |
247 /// +---+----------+
248 /// | 1 | Xmm, Mem |
249 /// | 2 | Xmm, Xmm |
250 /// +---+----------+
251 /// ```
252 #[inline]
253 pub fn sha1msg1<A, B>(&mut self, op0: A, op1: B)
254 where Assembler<'a>: Sha1msg1Emitter<A, B> {
255 <Self as Sha1msg1Emitter<A, B>>::sha1msg1(self, op0, op1);
256 }
257 /// `SHA1MSG2` (SHA1MSG2).
258 /// The SHA1MSG2 instruction is one of two SHA1 message scheduling instructions. The instruction performs the final calculation to derive the next four SHA1 message dwords.
259 ///
260 ///
261 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1MSG2.html).
262 ///
263 /// Supported operand variants:
264 ///
265 /// ```text
266 /// +---+----------+
267 /// | # | Operands |
268 /// +---+----------+
269 /// | 1 | Xmm, Mem |
270 /// | 2 | Xmm, Xmm |
271 /// +---+----------+
272 /// ```
273 #[inline]
274 pub fn sha1msg2<A, B>(&mut self, op0: A, op1: B)
275 where Assembler<'a>: Sha1msg2Emitter<A, B> {
276 <Self as Sha1msg2Emitter<A, B>>::sha1msg2(self, op0, op1);
277 }
278 /// `SHA1NEXTE` (SHA1NEXTE).
279 /// The SHA1NEXTE calculates the SHA1 state variable E after four rounds of operation from the current SHA1 state variable A in the destination operand. The calculated value of the SHA1 state variable E is added to the source operand, which contains the scheduled dwords.
280 ///
281 ///
282 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1NEXTE.html).
283 ///
284 /// Supported operand variants:
285 ///
286 /// ```text
287 /// +---+----------+
288 /// | # | Operands |
289 /// +---+----------+
290 /// | 1 | Xmm, Mem |
291 /// | 2 | Xmm, Xmm |
292 /// +---+----------+
293 /// ```
294 #[inline]
295 pub fn sha1nexte<A, B>(&mut self, op0: A, op1: B)
296 where Assembler<'a>: Sha1nexteEmitter<A, B> {
297 <Self as Sha1nexteEmitter<A, B>>::sha1nexte(self, op0, op1);
298 }
299 /// `SHA1RNDS4` (SHA1RNDS4).
300 /// The SHA1RNDS4 instruction performs four rounds of SHA1 operation using an initial SHA1 state (A,B,C,D) from the first operand (which is a source operand and the destination operand) and some pre-computed sum of the next 4 round message dwords, and state variable E from the second operand (a source operand). The updated SHA1 state (A,B,C,D) after four rounds of processing is stored in the destination operand.
301 ///
302 ///
303 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA1RNDS4.html).
304 ///
305 /// Supported operand variants:
306 ///
307 /// ```text
308 /// +---+---------------+
309 /// | # | Operands |
310 /// +---+---------------+
311 /// | 1 | Xmm, Mem, Imm |
312 /// | 2 | Xmm, Xmm, Imm |
313 /// +---+---------------+
314 /// ```
315 #[inline]
316 pub fn sha1rnds4<A, B, C>(&mut self, op0: A, op1: B, op2: C)
317 where Assembler<'a>: Sha1rnds4Emitter<A, B, C> {
318 <Self as Sha1rnds4Emitter<A, B, C>>::sha1rnds4(self, op0, op1, op2);
319 }
320 /// `SHA256MSG1` (SHA256MSG1).
321 /// The SHA256MSG1 instruction is one of two SHA256 message scheduling instructions. The instruction performs an intermediate calculation for the next four SHA256 message dwords.
322 ///
323 ///
324 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256MSG1.html).
325 ///
326 /// Supported operand variants:
327 ///
328 /// ```text
329 /// +---+----------+
330 /// | # | Operands |
331 /// +---+----------+
332 /// | 1 | Xmm, Mem |
333 /// | 2 | Xmm, Xmm |
334 /// +---+----------+
335 /// ```
336 #[inline]
337 pub fn sha256msg1<A, B>(&mut self, op0: A, op1: B)
338 where Assembler<'a>: Sha256msg1Emitter<A, B> {
339 <Self as Sha256msg1Emitter<A, B>>::sha256msg1(self, op0, op1);
340 }
341 /// `SHA256MSG2` (SHA256MSG2).
342 /// The SHA256MSG2 instruction is one of two SHA2 message scheduling instructions. The instruction performs the final calculation for the next four SHA256 message dwords.
343 ///
344 ///
345 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256MSG2.html).
346 ///
347 /// Supported operand variants:
348 ///
349 /// ```text
350 /// +---+----------+
351 /// | # | Operands |
352 /// +---+----------+
353 /// | 1 | Xmm, Mem |
354 /// | 2 | Xmm, Xmm |
355 /// +---+----------+
356 /// ```
357 #[inline]
358 pub fn sha256msg2<A, B>(&mut self, op0: A, op1: B)
359 where Assembler<'a>: Sha256msg2Emitter<A, B> {
360 <Self as Sha256msg2Emitter<A, B>>::sha256msg2(self, op0, op1);
361 }
362 /// `SHA256RNDS2` (SHA256RNDS2).
363 /// The SHA256RNDS2 instruction performs 2 rounds of SHA256 operation using an initial SHA256 state (C,D,G,H) from the first operand, an initial SHA256 state (A,B,E,F) from the second operand, and a pre-computed sum of the next 2 round message dwords and the corresponding round constants from the implicit operand xmm0. Note that only the two lower dwords of XMM0 are used by the instruction.
364 ///
365 ///
366 /// For more details, see the [Intel manual](https://www.felixcloutier.com/x86/SHA256RNDS2.html).
367 ///
368 /// Supported operand variants:
369 ///
370 /// ```text
371 /// +---+---------------+
372 /// | # | Operands |
373 /// +---+---------------+
374 /// | 1 | Xmm, Mem, Xmm |
375 /// | 2 | Xmm, Xmm, Xmm |
376 /// +---+---------------+
377 /// ```
378 #[inline]
379 pub fn sha256rnds2<A, B, C>(&mut self, op0: A, op1: B, op2: C)
380 where Assembler<'a>: Sha256rnds2Emitter<A, B, C> {
381 <Self as Sha256rnds2Emitter<A, B, C>>::sha256rnds2(self, op0, op1, op2);
382 }
383}