1 /***************************************************************************************************
2 
3   Zyan Disassembler Library (Zydis)
4 
5   Original Author : Florian Bernd
6 
7  * Permission is hereby granted, free of charge, to any person obtaining a copy
8  * of this software and associated documentation files (the "Software"), to deal
9  * in the Software without restriction, including without limitation the rights
10  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11  * copies of the Software, and to permit persons to whom the Software is
12  * furnished to do so, subject to the following conditions:
13  *
14  * The above copyright notice and this permission notice shall be included in all
15  * copies or substantial portions of the Software.
16  *
17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23  * SOFTWARE.
24 
25 ***************************************************************************************************/
26 
27 /**
28  * @file
29  * @brief   Defines the basic `ZydisDecodedInstruction` and `ZydisDecodedOperand` structs.
30  */
31 
32 #ifndef ZYDIS_INSTRUCTIONINFO_H
33 #define ZYDIS_INSTRUCTIONINFO_H
34 
35 #include <Zycore/Types.h>
36 #include <Zydis/MetaInfo.h>
37 #include <Zydis/Mnemonic.h>
38 #include <Zydis/Register.h>
39 #include <Zydis/SharedTypes.h>
40 
41 #ifdef __cplusplus
42 extern "C" {
43 #endif
44 
45 /* ============================================================================================== */
46 /* Decoded operand                                                                                */
47 /* ============================================================================================== */
48 
49 /* ---------------------------------------------------------------------------------------------- */
50 /* Memory type                                                                                    */
51 /* ---------------------------------------------------------------------------------------------- */
52 
53 /**
54  * @brief   Defines the `ZydisMemoryOperandType` enum.
55  */
56 typedef enum ZydisMemoryOperandType_
57 {
58     ZYDIS_MEMOP_TYPE_INVALID,
59     /**
60      * @brief   Normal memory operand.
61      */
62     ZYDIS_MEMOP_TYPE_MEM,
63     /**
64      * @brief   The memory operand is only used for address-generation. No real memory-access is
65      *          caused.
66      */
67     ZYDIS_MEMOP_TYPE_AGEN,
68     /**
69      * @brief   A memory operand using `SIB` addressing form, where the index register is not used
70      *          in address calculation and scale is ignored. No real memory-access is caused.
71      */
72     ZYDIS_MEMOP_TYPE_MIB,
73 
74     /**
75      * @brief   Maximum value of this enum.
76      */
77     ZYDIS_MEMOP_TYPE_MAX_VALUE = ZYDIS_MEMOP_TYPE_MIB,
78     /**
79      * @brief   The minimum number of bits required to represent all values of this enum.
80      */
81     ZYDIS_MEMOP_TYPE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_MEMOP_TYPE_MAX_VALUE)
82 } ZydisMemoryOperandType;
83 
84 /* ---------------------------------------------------------------------------------------------- */
85 /* Decoded operand                                                                                */
86 /* ---------------------------------------------------------------------------------------------- */
87 
88 /**
89  * @brief   Defines the `ZydisDecodedOperand` struct.
90  */
91 typedef struct ZydisDecodedOperand_
92 {
93     /**
94      * @brief   The operand-id.
95      */
96     ZyanU8 id;
97     /**
98      * @brief   The type of the operand.
99      */
100     ZydisOperandType type;
101     /**
102      * @brief   The visibility of the operand.
103      */
104     ZydisOperandVisibility visibility;
105     /**
106      * @brief   The operand-actions.
107      */
108     ZydisOperandActions actions;
109     /**
110      * @brief   The operand-encoding.
111      */
112     ZydisOperandEncoding encoding;
113     /**
114      * @brief   The logical size of the operand (in bits).
115      */
116     ZyanU16 size;
117     /**
118      * @brief   The element-type.
119      */
120     ZydisElementType element_type;
121     /**
122      * @brief   The size of a single element.
123      */
124     ZydisElementSize element_size;
125     /**
126      * @brief   The number of elements.
127      */
128     ZyanU16 element_count;
129     /**
130      * @brief   Extended info for register-operands.
131      */
132     struct ZydisDecodedOperandReg_
133     {
134         /**
135          * @brief   The register value.
136          */
137         ZydisRegister value;
138         // TODO: AVX512_4VNNIW MULTISOURCE registers
139     } reg;
140     /**
141      * @brief   Extended info for memory-operands.
142      */
143     struct ZydisDecodedOperandMem_
144     {
145         /**
146          * @brief   The type of the memory operand.
147          */
148         ZydisMemoryOperandType type;
149         /**
150          * @brief   The segment register.
151          */
152         ZydisRegister segment;
153         /**
154          * @brief   The base register.
155          */
156         ZydisRegister base;
157         /**
158          * @brief   The index register.
159          */
160         ZydisRegister index;
161         /**
162          * @brief   The scale factor.
163          */
164         ZyanU8 scale;
165         /**
166          * @brief   Extended info for memory-operands with displacement.
167          */
168         struct ZydisDecodedOperandMemDisp_
169         {
170             /**
171              * @brief   Signals, if the displacement value is used.
172              */
173             ZyanBool has_displacement;
174             /**
175              * @brief   The displacement value
176              */
177             ZyanI64 value;
178         } disp;
179     } mem;
180     /**
181      * @brief   Extended info for pointer-operands.
182      */
183     struct ZydisDecodedOperandPtr_
184     {
185         ZyanU16 segment;
186         ZyanU32 offset;
187     } ptr;
188     /**
189      * @brief   Extended info for immediate-operands.
190      */
191     struct ZydisDecodedOperandImm_
192     {
193         /**
194          * @brief   Signals, if the immediate value is signed.
195          */
196         ZyanBool is_signed;
197         /**
198          * @brief   Signals, if the immediate value contains a relative offset. You can use
199          *          `ZydisCalcAbsoluteAddress` to determine the absolute address value.
200          */
201         ZyanBool is_relative;
202         /**
203          * @brief   The immediate value.
204          */
205         union ZydisDecodedOperandImmValue_
206         {
207             ZyanU64 u;
208             ZyanI64 s;
209         } value;
210     } imm;
211 } ZydisDecodedOperand;
212 
213 /* ---------------------------------------------------------------------------------------------- */
214 
215 /* ============================================================================================== */
216 /* Decoded instruction                                                                            */
217 /* ============================================================================================== */
218 
219 /* ---------------------------------------------------------------------------------------------- */
220 /* Instruction attributes                                                                         */
221 /* ---------------------------------------------------------------------------------------------- */
222 
223 /**
224  * @brief   Defines the `ZydisInstructionAttributes` data-type.
225  */
226 typedef ZyanU64 ZydisInstructionAttributes;
227 
228 /**
229  * @brief   The instruction has the `ModRM` byte.
230  */
231 #define ZYDIS_ATTRIB_HAS_MODRM                  0x0000000000000001 // (1 <<  0)
232 /**
233  * @brief   The instruction has the `SIB` byte.
234  */
235 #define ZYDIS_ATTRIB_HAS_SIB                    0x0000000000000002 // (1 <<  1)
236 /**
237  * @brief   The instruction has the `REX` prefix.
238  */
239 #define ZYDIS_ATTRIB_HAS_REX                    0x0000000000000004 // (1 <<  2)
240 /**
241  * @brief   The instruction has the `XOP` prefix.
242  */
243 #define ZYDIS_ATTRIB_HAS_XOP                    0x0000000000000008 // (1 <<  3)
244 /**
245  * @brief   The instruction has the `VEX` prefix.
246  */
247 #define ZYDIS_ATTRIB_HAS_VEX                    0x0000000000000010 // (1 <<  4)
248 /**
249  * @brief   The instruction has the `EVEX` prefix.
250  */
251 #define ZYDIS_ATTRIB_HAS_EVEX                   0x0000000000000020 // (1 <<  5)
252 /**
253  * @brief   The instruction has the `MVEX` prefix.
254  */
255 #define ZYDIS_ATTRIB_HAS_MVEX                   0x0000000000000040 // (1 <<  6)
256 /**
257  * @brief   The instruction has one or more operands with position-relative offsets.
258  */
259 #define ZYDIS_ATTRIB_IS_RELATIVE                0x0000000000000080 // (1 <<  7)
260 /**
261  * @brief   The instruction is privileged.
262  *
263  * Privileged instructions are any instructions that require a current ring level below 3.
264  */
265 #define ZYDIS_ATTRIB_IS_PRIVILEGED              0x0000000000000100 // (1 <<  8)
266 
267 /**
268  * @brief   The instruction accesses one or more CPU-flags.
269  */
270 #define ZYDIS_ATTRIB_CPUFLAG_ACCESS             0x0000001000000000 // (1 << 36) // TODO: rebase
271 
272 /**
273  * @brief   The instruction may conditionally read the general CPU state.
274  */
275 #define ZYDIS_ATTRIB_CPU_STATE_CR               0x0000002000000000 // (1 << 37) // TODO: rebase
276 /**
277  * @brief   The instruction may conditionally write the general CPU state.
278  */
279 #define ZYDIS_ATTRIB_CPU_STATE_CW               0x0000004000000000 // (1 << 38) // TODO: rebase
280 /**
281  * @brief   The instruction may conditionally read the FPU state (X87, MMX).
282  */
283 #define ZYDIS_ATTRIB_FPU_STATE_CR               0x0000008000000000 // (1 << 39) // TODO: rebase
284 /**
285  * @brief   The instruction may conditionally write the FPU state (X87, MMX).
286  */
287 #define ZYDIS_ATTRIB_FPU_STATE_CW               0x0000010000000000 // (1 << 40) // TODO: rebase
288 /**
289  * @brief   The instruction may conditionally read the XMM state (AVX, AVX2, AVX-512).
290  */
291 #define ZYDIS_ATTRIB_XMM_STATE_CR               0x0000020000000000 // (1 << 41) // TODO: rebase
292 /**
293  * @brief   The instruction may conditionally write the XMM state (AVX, AVX2, AVX-512).
294  */
295 #define ZYDIS_ATTRIB_XMM_STATE_CW               0x0000040000000000 // (1 << 42) // TODO: rebase
296 
297 /**
298  * @brief   The instruction accepts the `LOCK` prefix (`0xF0`).
299  */
300 #define ZYDIS_ATTRIB_ACCEPTS_LOCK               0x0000000000000200 // (1 <<  9)
301 /**
302  * @brief   The instruction accepts the `REP` prefix (`0xF3`).
303  */
304 #define ZYDIS_ATTRIB_ACCEPTS_REP                0x0000000000000400 // (1 << 10)
305 /**
306  * @brief   The instruction accepts the `REPE`/`REPZ` prefix (`0xF3`).
307  */
308 #define ZYDIS_ATTRIB_ACCEPTS_REPE               0x0000000000000800 // (1 << 11)
309 /**
310  * @brief   The instruction accepts the `REPE`/`REPZ` prefix (`0xF3`).
311  */
312 #define ZYDIS_ATTRIB_ACCEPTS_REPZ               0x0000000000000800 // (1 << 11)
313 /**
314  * @brief   The instruction accepts the `REPNE`/`REPNZ` prefix (`0xF2`).
315  */
316 #define ZYDIS_ATTRIB_ACCEPTS_REPNE              0x0000000000001000 // (1 << 12)
317 /**
318  * @brief   The instruction accepts the `REPNE`/`REPNZ` prefix (`0xF2`).
319  */
320 #define ZYDIS_ATTRIB_ACCEPTS_REPNZ              0x0000000000001000 // (1 << 12)
321 /**
322  * @brief   The instruction accepts the `BND` prefix (`0xF2`).
323  */
324 #define ZYDIS_ATTRIB_ACCEPTS_BND                0x0000000000002000 // (1 << 13)
325 /**
326  * @brief   The instruction accepts the `XACQUIRE` prefix (`0xF2`).
327  */
328 #define ZYDIS_ATTRIB_ACCEPTS_XACQUIRE           0x0000000000004000 // (1 << 14)
329 /**
330  * @brief   The instruction accepts the `XRELEASE` prefix (`0xF3`).
331  */
332 #define ZYDIS_ATTRIB_ACCEPTS_XRELEASE           0x0000000000008000 // (1 << 15)
333 /**
334  * @brief   The instruction accepts the `XACQUIRE`/`XRELEASE` prefixes (`0xF2`, `0xF3`) without
335  *          the `LOCK` prefix (`0x0F`).
336  */
337 #define ZYDIS_ATTRIB_ACCEPTS_HLE_WITHOUT_LOCK   0x0000000000010000 // (1 << 16)
338 /**
339  * @brief   The instruction accepts branch hints (0x2E, 0x3E).
340  */
341 #define ZYDIS_ATTRIB_ACCEPTS_BRANCH_HINTS       0x0000000000020000 // (1 << 17)
342 /**
343  * @brief   The instruction accepts segment prefixes (`0x2E`, `0x36`, `0x3E`, `0x26`, `0x64`,
344  *          `0x65`).
345  */
346 #define ZYDIS_ATTRIB_ACCEPTS_SEGMENT            0x0000000000040000 // (1 << 18)
347 /**
348  * @brief   The instruction has the `LOCK` prefix (`0xF0`).
349  */
350 #define ZYDIS_ATTRIB_HAS_LOCK                   0x0000000000080000 // (1 << 19)
351 /**
352  * @brief   The instruction has the `REP` prefix (`0xF3`).
353  */
354 #define ZYDIS_ATTRIB_HAS_REP                    0x0000000000100000 // (1 << 20)
355 /**
356  * @brief   The instruction has the `REPE`/`REPZ` prefix (`0xF3`).
357  */
358 #define ZYDIS_ATTRIB_HAS_REPE                   0x0000000000200000 // (1 << 21)
359 /**
360  * @brief   The instruction has the `REPE`/`REPZ` prefix (`0xF3`).
361  */
362 #define ZYDIS_ATTRIB_HAS_REPZ                   0x0000000000200000 // (1 << 21)
363 /**
364  * @brief   The instruction has the `REPNE`/`REPNZ` prefix (`0xF2`).
365  */
366 #define ZYDIS_ATTRIB_HAS_REPNE                  0x0000000000400000 // (1 << 22)
367 /**
368  * @brief   The instruction has the `REPNE`/`REPNZ` prefix (`0xF2`).
369  */
370 #define ZYDIS_ATTRIB_HAS_REPNZ                  0x0000000000400000 // (1 << 22)
371 /**
372  * @brief   The instruction has the `BND` prefix (`0xF2`).
373  */
374 #define ZYDIS_ATTRIB_HAS_BND                    0x0000000000800000 // (1 << 23)
375 /**
376  * @brief   The instruction has the `XACQUIRE` prefix (`0xF2`).
377  */
378 #define ZYDIS_ATTRIB_HAS_XACQUIRE               0x0000000001000000 // (1 << 24)
379 /**
380  * @brief   The instruction has the `XRELEASE` prefix (`0xF3`).
381  */
382 #define ZYDIS_ATTRIB_HAS_XRELEASE               0x0000000002000000 // (1 << 25)
383 /**
384  * @brief   The instruction has the branch-not-taken hint (`0x2E`).
385  */
386 #define ZYDIS_ATTRIB_HAS_BRANCH_NOT_TAKEN       0x0000000004000000 // (1 << 26)
387 /**
388  * @brief   The instruction has the branch-taken hint (`0x3E`).
389  */
390 #define ZYDIS_ATTRIB_HAS_BRANCH_TAKEN           0x0000000008000000 // (1 << 27)
391 /**
392  * @brief   The instruction has a segment modifier.
393  */
394 #define ZYDIS_ATTRIB_HAS_SEGMENT                0x00000003F0000000
395 /**
396  * @brief   The instruction has the `CS` segment modifier (`0x2E`).
397  */
398 #define ZYDIS_ATTRIB_HAS_SEGMENT_CS             0x0000000010000000 // (1 << 28)
399 /**
400  * @brief   The instruction has the `SS` segment modifier (`0x36`).
401  */
402 #define ZYDIS_ATTRIB_HAS_SEGMENT_SS             0x0000000020000000 // (1 << 29)
403 /**
404  * @brief   The instruction has the `DS` segment modifier (`0x3E`).
405  */
406 #define ZYDIS_ATTRIB_HAS_SEGMENT_DS             0x0000000040000000 // (1 << 30)
407 /**
408  * @brief   The instruction has the `ES` segment modifier (`0x26`).
409  */
410 #define ZYDIS_ATTRIB_HAS_SEGMENT_ES             0x0000000080000000 // (1 << 31)
411 /**
412  * @brief   The instruction has the `FS` segment modifier (`0x64`).
413  */
414 #define ZYDIS_ATTRIB_HAS_SEGMENT_FS             0x0000000100000000 // (1 << 32)
415 /**
416  * @brief   The instruction has the `GS` segment modifier (`0x65`).
417  */
418 #define ZYDIS_ATTRIB_HAS_SEGMENT_GS             0x0000000200000000 // (1 << 33)
419 /**
420  * @brief   The instruction has the operand-size override prefix (`0x66`).
421  */
422 #define ZYDIS_ATTRIB_HAS_OPERANDSIZE            0x0000000400000000 // (1 << 34) // TODO: rename
423 /**
424  * @brief   The instruction has the address-size override prefix (`0x67`).
425  */
426 #define ZYDIS_ATTRIB_HAS_ADDRESSSIZE            0x0000000800000000 // (1 << 35) // TODO: rename
427 
428 /* ---------------------------------------------------------------------------------------------- */
429 /* R/E/FLAGS info                                                                                 */
430 /* ---------------------------------------------------------------------------------------------- */
431 
432 /**
433  * @brief   Defines the `ZydisCPUFlags` data-type.
434  */
435 typedef ZyanU32 ZydisCPUFlags;
436 
437 /**
438  * @brief   Defines the `ZydisCPUFlag` enum.
439  */
440 typedef enum ZydisCPUFlag_
441 {
442     /**
443      * @brief   Carry flag.
444      */
445     ZYDIS_CPUFLAG_CF,
446     /**
447      * @brief   Parity flag.
448      */
449     ZYDIS_CPUFLAG_PF,
450     /**
451      * @brief   Adjust flag.
452      */
453     ZYDIS_CPUFLAG_AF,
454     /**
455      * @brief   Zero flag.
456      */
457     ZYDIS_CPUFLAG_ZF,
458     /**
459      * @brief   Sign flag.
460      */
461     ZYDIS_CPUFLAG_SF,
462     /**
463      * @brief   Trap flag.
464      */
465     ZYDIS_CPUFLAG_TF,
466     /**
467      * @brief   Interrupt enable flag.
468      */
469     ZYDIS_CPUFLAG_IF,
470     /**
471      * @brief   Direction flag.
472      */
473     ZYDIS_CPUFLAG_DF,
474     /**
475      * @brief   Overflow flag.
476      */
477     ZYDIS_CPUFLAG_OF,
478     /**
479      * @brief   I/O privilege level flag.
480      */
481     ZYDIS_CPUFLAG_IOPL,
482     /**
483      * @brief   Nested task flag.
484      */
485     ZYDIS_CPUFLAG_NT,
486     /**
487      * @brief   Resume flag.
488      */
489     ZYDIS_CPUFLAG_RF,
490     /**
491      * @brief   Virtual 8086 mode flag.
492      */
493     ZYDIS_CPUFLAG_VM,
494     /**
495      * @brief   Alignment check.
496      */
497     ZYDIS_CPUFLAG_AC,
498     /**
499      * @brief   Virtual interrupt flag.
500      */
501     ZYDIS_CPUFLAG_VIF,
502     /**
503      * @brief   Virtual interrupt pending.
504      */
505     ZYDIS_CPUFLAG_VIP,
506     /**
507      * @brief   Able to use CPUID instruction.
508      */
509     ZYDIS_CPUFLAG_ID,
510     /**
511      * @brief   FPU condition-code flag 0.
512      */
513     ZYDIS_CPUFLAG_C0,
514     /**
515      * @brief   FPU condition-code flag 1.
516      */
517     ZYDIS_CPUFLAG_C1,
518     /**
519      * @brief   FPU condition-code flag 2.
520      */
521     ZYDIS_CPUFLAG_C2,
522     /**
523      * @brief   FPU condition-code flag 3.
524      */
525     ZYDIS_CPUFLAG_C3,
526 
527     /**
528      * @brief   Maximum value of this enum.
529      */
530     ZYDIS_CPUFLAG_MAX_VALUE = ZYDIS_CPUFLAG_C3,
531     /**
532      * @brief   The minimum number of bits required to represent all values of this enum.
533      */
534     ZYDIS_CPUFLAG_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_CPUFLAG_MAX_VALUE)
535 } ZydisCPUFlag;
536 
537 /**
538  * @brief   Defines the `ZydisCPUFlagAction` enum.
539  */
540 typedef enum ZydisCPUFlagAction_
541 {
542     /**
543      * @brief   The CPU flag is not touched by the instruction.
544      */
545     ZYDIS_CPUFLAG_ACTION_NONE,
546     /**
547      * @brief   The CPU flag is tested (read).
548      */
549     ZYDIS_CPUFLAG_ACTION_TESTED,
550     /**
551      * @brief   The CPU flag is tested and modified afterwards (read-write).
552      */
553     ZYDIS_CPUFLAG_ACTION_TESTED_MODIFIED,
554     /**
555      * @brief   The CPU flag is modified (write).
556      */
557     ZYDIS_CPUFLAG_ACTION_MODIFIED,
558     /**
559      * @brief   The CPU flag is set to 0 (write).
560      */
561     ZYDIS_CPUFLAG_ACTION_SET_0,
562     /**
563      * @brief   The CPU flag is set to 1 (write).
564      */
565     ZYDIS_CPUFLAG_ACTION_SET_1,
566     /**
567      * @brief   The CPU flag is undefined (write).
568      */
569     ZYDIS_CPUFLAG_ACTION_UNDEFINED,
570 
571     /**
572      * @brief   Maximum value of this enum.
573      */
574     ZYDIS_CPUFLAG_ACTION_MAX_VALUE = ZYDIS_CPUFLAG_ACTION_UNDEFINED,
575     /**
576      * @brief   The minimum number of bits required to represent all values of this enum.
577      */
578     ZYDIS_CPUFLAG_ACTION_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_CPUFLAG_ACTION_MAX_VALUE)
579 } ZydisCPUFlagAction;
580 
581 /* ---------------------------------------------------------------------------------------------- */
582 /* Branch types                                                                                   */
583 /* ---------------------------------------------------------------------------------------------- */
584 
585 /**
586  * @brief   Defines the `ZydisBranchType` enum.
587  */
588 typedef enum ZydisBranchType_
589 {
590     /**
591      * @brief   The instruction is not a branch instruction.
592      */
593     ZYDIS_BRANCH_TYPE_NONE,
594     /**
595      * @brief   The instruction is a short (8-bit) branch instruction.
596      */
597     ZYDIS_BRANCH_TYPE_SHORT,
598     /**
599      * @brief   The instruction is a near (16-bit or 32-bit) branch instruction.
600      */
601     ZYDIS_BRANCH_TYPE_NEAR,
602     /**
603      * @brief   The instruction is a far (inter-segment) branch instruction.
604      */
605     ZYDIS_BRANCH_TYPE_FAR,
606 
607     /**
608      * @brief   Maximum value of this enum.
609      */
610     ZYDIS_BRANCH_TYPE_MAX_VALUE = ZYDIS_BRANCH_TYPE_FAR,
611     /**
612      * @brief   The minimum number of bits required to represent all values of this enum.
613      */
614     ZYDIS_BRANCH_TYPE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_BRANCH_TYPE_MAX_VALUE)
615 } ZydisBranchType;
616 
617 /* ---------------------------------------------------------------------------------------------- */
618 /* SSE/AVX exception-class                                                                        */
619 /* ---------------------------------------------------------------------------------------------- */
620 
621 /**
622  * @brief   Defines the `ZydisExceptionClass` enum.
623  */
624 typedef enum ZydisExceptionClass_
625 {
626     ZYDIS_EXCEPTION_CLASS_NONE,
627     // TODO: FP Exceptions
628     ZYDIS_EXCEPTION_CLASS_SSE1,
629     ZYDIS_EXCEPTION_CLASS_SSE2,
630     ZYDIS_EXCEPTION_CLASS_SSE3,
631     ZYDIS_EXCEPTION_CLASS_SSE4,
632     ZYDIS_EXCEPTION_CLASS_SSE5,
633     ZYDIS_EXCEPTION_CLASS_SSE7,
634     ZYDIS_EXCEPTION_CLASS_AVX1,
635     ZYDIS_EXCEPTION_CLASS_AVX2,
636     ZYDIS_EXCEPTION_CLASS_AVX3,
637     ZYDIS_EXCEPTION_CLASS_AVX4,
638     ZYDIS_EXCEPTION_CLASS_AVX5,
639     ZYDIS_EXCEPTION_CLASS_AVX6,
640     ZYDIS_EXCEPTION_CLASS_AVX7,
641     ZYDIS_EXCEPTION_CLASS_AVX8,
642     ZYDIS_EXCEPTION_CLASS_AVX11,
643     ZYDIS_EXCEPTION_CLASS_AVX12,
644     ZYDIS_EXCEPTION_CLASS_E1,
645     ZYDIS_EXCEPTION_CLASS_E1NF,
646     ZYDIS_EXCEPTION_CLASS_E2,
647     ZYDIS_EXCEPTION_CLASS_E2NF,
648     ZYDIS_EXCEPTION_CLASS_E3,
649     ZYDIS_EXCEPTION_CLASS_E3NF,
650     ZYDIS_EXCEPTION_CLASS_E4,
651     ZYDIS_EXCEPTION_CLASS_E4NF,
652     ZYDIS_EXCEPTION_CLASS_E5,
653     ZYDIS_EXCEPTION_CLASS_E5NF,
654     ZYDIS_EXCEPTION_CLASS_E6,
655     ZYDIS_EXCEPTION_CLASS_E6NF,
656     ZYDIS_EXCEPTION_CLASS_E7NM,
657     ZYDIS_EXCEPTION_CLASS_E7NM128,
658     ZYDIS_EXCEPTION_CLASS_E9NF,
659     ZYDIS_EXCEPTION_CLASS_E10,
660     ZYDIS_EXCEPTION_CLASS_E10NF,
661     ZYDIS_EXCEPTION_CLASS_E11,
662     ZYDIS_EXCEPTION_CLASS_E11NF,
663     ZYDIS_EXCEPTION_CLASS_E12,
664     ZYDIS_EXCEPTION_CLASS_E12NP,
665     ZYDIS_EXCEPTION_CLASS_K20,
666     ZYDIS_EXCEPTION_CLASS_K21,
667 
668     /**
669      * @brief   Maximum value of this enum.
670      */
671     ZYDIS_EXCEPTION_CLASS_MAX_VALUE = ZYDIS_EXCEPTION_CLASS_K21,
672     /**
673      * @brief   The minimum number of bits required to represent all values of this enum.
674      */
675     ZYDIS_EXCEPTION_CLASS_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_EXCEPTION_CLASS_MAX_VALUE)
676 } ZydisExceptionClass;
677 
678 /* ---------------------------------------------------------------------------------------------- */
679 /* AVX mask mode                                                                                  */
680 /* ---------------------------------------------------------------------------------------------- */
681 
682 /**
683  * @brief   Defines the `ZydisMaskMode` enum.
684  */
685 typedef enum ZydisMaskMode_
686 {
687     ZYDIS_MASK_MODE_INVALID,
688     /**
689      * @brief   Masking is disabled for the current instruction (`K0` register is used).
690      */
691     ZYDIS_MASK_MODE_DISABLED,
692     /**
693      * @brief   The embedded mask register is used as a merge-mask.
694      */
695     ZYDIS_MASK_MODE_MERGING,
696     /**
697      * @brief   The embedded mask register is used as a zero-mask.
698      */
699     ZYDIS_MASK_MODE_ZEROING,
700     /**
701      * @brief   The embedded mask register is used as a control-mask (element selector).
702      */
703     ZYDIS_MASK_MODE_CONTROL,
704     /**
705      * @brief   The embedded mask register is used as a zeroing control-mask (element selector).
706      */
707     ZYDIS_MASK_MODE_CONTROL_ZEROING,
708 
709     /**
710      * @brief   Maximum value of this enum.
711      */
712     ZYDIS_MASK_MODE_MAX_VALUE = ZYDIS_MASK_MODE_CONTROL_ZEROING,
713     /**
714      * @brief   The minimum number of bits required to represent all values of this enum.
715      */
716     ZYDIS_MASK_MODE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_MASK_MODE_MAX_VALUE)
717 } ZydisMaskMode;
718 
719 /* ---------------------------------------------------------------------------------------------- */
720 /* AVX broadcast-mode                                                                             */
721 /* ---------------------------------------------------------------------------------------------- */
722 
723 /**
724  * @brief   Defines the `ZydisBroadcastMode` enum.
725  */
726 typedef enum ZydisBroadcastMode_
727 {
728     ZYDIS_BROADCAST_MODE_INVALID,
729     ZYDIS_BROADCAST_MODE_1_TO_2,
730     ZYDIS_BROADCAST_MODE_1_TO_4,
731     ZYDIS_BROADCAST_MODE_1_TO_8,
732     ZYDIS_BROADCAST_MODE_1_TO_16,
733     ZYDIS_BROADCAST_MODE_1_TO_32,
734     ZYDIS_BROADCAST_MODE_1_TO_64,
735     ZYDIS_BROADCAST_MODE_2_TO_4,
736     ZYDIS_BROADCAST_MODE_2_TO_8,
737     ZYDIS_BROADCAST_MODE_2_TO_16,
738     ZYDIS_BROADCAST_MODE_4_TO_8,
739     ZYDIS_BROADCAST_MODE_4_TO_16,
740     ZYDIS_BROADCAST_MODE_8_TO_16,
741 
742     /**
743      * @brief   Maximum value of this enum.
744      */
745     ZYDIS_BROADCAST_MODE_MAX_VALUE = ZYDIS_BROADCAST_MODE_8_TO_16,
746     /**
747      * @brief   The minimum number of bits required to represent all values of this enum.
748      */
749     ZYDIS_BROADCAST_MODE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_BROADCAST_MODE_MAX_VALUE)
750 } ZydisBroadcastMode;
751 
752 /* ---------------------------------------------------------------------------------------------- */
753 /* AVX rounding-mode                                                                              */
754 /* ---------------------------------------------------------------------------------------------- */
755 
756 /**
757  * @brief   Defines the `ZydisRoundingMode` enum.
758  */
759 typedef enum ZydisRoundingMode_
760 {
761     ZYDIS_ROUNDING_MODE_INVALID,
762     /**
763      * @brief   Round to nearest.
764      */
765     ZYDIS_ROUNDING_MODE_RN,
766     /**
767      * @brief   Round down.
768      */
769     ZYDIS_ROUNDING_MODE_RD,
770     /**
771      * @brief   Round up.
772      */
773     ZYDIS_ROUNDING_MODE_RU,
774     /**
775      * @brief   Round towards zero.
776      */
777     ZYDIS_ROUNDING_MODE_RZ,
778 
779     /**
780      * @brief   Maximum value of this enum.
781      */
782     ZYDIS_ROUNDING_MODE_MAX_VALUE = ZYDIS_ROUNDING_MODE_RZ,
783     /**
784      * @brief   The minimum number of bits required to represent all values of this enum.
785      */
786     ZYDIS_ROUNDING_MODE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_ROUNDING_MODE_MAX_VALUE)
787 } ZydisRoundingMode;
788 
789 /* ---------------------------------------------------------------------------------------------- */
790 /* KNC swizzle-mode                                                                               */
791 /* ---------------------------------------------------------------------------------------------- */
792 
793 /**
794  * @brief   Defines the `ZydisSwizzleMode` enum.
795  */
796 typedef enum ZydisSwizzleMode_
797 {
798     ZYDIS_SWIZZLE_MODE_INVALID,
799     ZYDIS_SWIZZLE_MODE_DCBA,
800     ZYDIS_SWIZZLE_MODE_CDAB,
801     ZYDIS_SWIZZLE_MODE_BADC,
802     ZYDIS_SWIZZLE_MODE_DACB,
803     ZYDIS_SWIZZLE_MODE_AAAA,
804     ZYDIS_SWIZZLE_MODE_BBBB,
805     ZYDIS_SWIZZLE_MODE_CCCC,
806     ZYDIS_SWIZZLE_MODE_DDDD,
807 
808     /**
809      * @brief   Maximum value of this enum.
810      */
811     ZYDIS_SWIZZLE_MODE_MAX_VALUE = ZYDIS_SWIZZLE_MODE_DDDD,
812     /**
813      * @brief   The minimum number of bits required to represent all values of this enum.
814      */
815     ZYDIS_SWIZZLE_MODE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_SWIZZLE_MODE_MAX_VALUE)
816 } ZydisSwizzleMode;
817 
818 /* ---------------------------------------------------------------------------------------------- */
819 /* KNC conversion-mode                                                                            */
820 /* ---------------------------------------------------------------------------------------------- */
821 
822 /**
823  * @brief   Defines the `ZydisConversionMode` enum.
824  */
825 typedef enum ZydisConversionMode_
826 {
827     ZYDIS_CONVERSION_MODE_INVALID,
828     ZYDIS_CONVERSION_MODE_FLOAT16,
829     ZYDIS_CONVERSION_MODE_SINT8,
830     ZYDIS_CONVERSION_MODE_UINT8,
831     ZYDIS_CONVERSION_MODE_SINT16,
832     ZYDIS_CONVERSION_MODE_UINT16,
833 
834     /**
835      * @brief   Maximum value of this enum.
836      */
837     ZYDIS_CONVERSION_MODE_MAX_VALUE = ZYDIS_CONVERSION_MODE_UINT16,
838     /**
839      * @brief   The minimum number of bits required to represent all values of this enum.
840      */
841     ZYDIS_CONVERSION_MODE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_CONVERSION_MODE_MAX_VALUE)
842 } ZydisConversionMode;
843 
844 /* ---------------------------------------------------------------------------------------------- */
845 /* Legacy prefix type                                                                             */
846 /* ---------------------------------------------------------------------------------------------- */
847 
848 /**
849  * @brief   Defines the `ZydisPrefixType` enum.
850  */
851 typedef enum ZydisPrefixType_
852 {
853     /**
854      * @brief   The prefix is ignored by the instruction.
855      *
856      * This applies to all prefixes that are not accepted by the instruction in general or the
857      * ones that are overwritten by a prefix of the same group closer to the instruction opcode.
858      */
859     ZYDIS_PREFIX_TYPE_IGNORED,
860     /**
861      * @brief   The prefix is effectively used by the instruction.
862      */
863     ZYDIS_PREFIX_TYPE_EFFECTIVE,
864     /**
865      * @brief   The prefix is used as a mandatory prefix.
866      *
867      * A mandatory prefix is interpreted as an opcode extension and has no further effect on the
868      * instruction.
869      */
870     ZYDIS_PREFIX_TYPE_MANDATORY,
871 
872     /**
873      * @brief   Maximum value of this enum.
874      */
875     ZYDIS_PREFIX_TYPE_MAX_VALUE = ZYDIS_PREFIX_TYPE_MANDATORY,
876     /**
877      * @brief   The minimum number of bits required to represent all values of this enum.
878      */
879     ZYDIS_PREFIX_TYPE_REQUIRED_BITS = ZYAN_BITS_TO_REPRESENT(ZYDIS_PREFIX_TYPE_MAX_VALUE)
880 } ZydisPrefixType;
881 
882 // TODO: Check effective for 66/67 prefixes (currently defaults to EFFECTIVE)
883 
884 /* ---------------------------------------------------------------------------------------------- */
885 /* Decoded instruction                                                                            */
886 /* ---------------------------------------------------------------------------------------------- */
887 
888 /**
889  * @brief   Defines the `ZydisDecodedInstruction` struct.
890  */
891 typedef struct ZydisDecodedInstruction_
892 {
893     /**
894      * @brief   The machine mode used to decode this instruction.
895      */
896     ZydisMachineMode machine_mode;
897     /**
898      * @brief   The instruction-mnemonic.
899      */
900     ZydisMnemonic mnemonic;
901     /**
902      * @brief   The length of the decoded instruction.
903      */
904     ZyanU8 length;
905     /**
906      * @brief   The instruction-encoding (`LEGACY`, `3DNOW`, `VEX`, `EVEX`, `XOP`).
907      */
908     ZydisInstructionEncoding encoding;
909     /**
910      * @brief   The opcode-map.
911      */
912     ZydisOpcodeMap opcode_map;
913     /**
914      * @brief   The instruction-opcode.
915      */
916     ZyanU8 opcode;
917     /**
918      * @brief   The stack width.
919      */
920     ZyanU8 stack_width;
921     /**
922      * @brief   The effective operand width.
923      */
924     ZyanU8 operand_width;
925     /**
926      * @brief   The effective address width.
927      */
928     ZyanU8 address_width;
929     /**
930      * @brief   The number of instruction-operands.
931      */
932     ZyanU8 operand_count;
933     /**
934      * @brief   Detailed info for all instruction operands.
935      *
936      * Explicit operands are guaranteed to be in the front and ordered as they are printed
937      * by the formatter in Intel mode. No assumptions can be made about the order of hidden
938      * operands, except that they always located behind the explicit operands.
939      */
940     ZydisDecodedOperand operands[ZYDIS_MAX_OPERAND_COUNT];
941     /**
942      * @brief  Instruction attributes.
943      */
944     ZydisInstructionAttributes attributes;
945     /**
946      * @brief   Information about accessed CPU flags.
947      */
948     struct ZydisDecodedInstructionAccessedFlags_
949     {
950         /**
951          * @brief   The CPU-flag action.
952          *
953          * Use `ZydisGetAccessedFlagsByAction` to get a mask with all flags matching a specific
954          * action.
955          */
956         ZydisCPUFlagAction action;
957     } accessed_flags[ZYDIS_CPUFLAG_MAX_VALUE + 1];
958     /**
959      * @brief   Extended info for `AVX` instructions.
960      */
961     struct ZydisDecodedInstructionAvx_
962     {
963         /**
964          * @brief   The `AVX` vector-length.
965          */
966         ZyanU16 vector_length;
967         /**
968          * @brief   Info about the embedded writemask-register (`AVX-512` and `KNC` only).
969          */
970         struct ZydisDecodedInstructionAvxMask_
971         {
972             /**
973              * @brief   The masking mode.
974              */
975             ZydisMaskMode mode;
976             /**
977              * @brief   The mask register.
978              */
979             ZydisRegister reg;
980         } mask;
981         /**
982          * @brief   Contains info about the `AVX` broadcast.
983          */
984         struct ZydisDecodedInstructionAvxBroadcast_
985         {
986             /**
987              * @brief   Signals, if the broadcast is a static broadcast.
988              *
989              * This is the case for instructions with inbuilt broadcast functionality, which is
990              * always active and not controlled by the `EVEX/MVEX.RC` bits.
991              */
992             ZyanBool is_static;
993             /**
994              * @brief   The `AVX` broadcast-mode.
995              */
996             ZydisBroadcastMode mode;
997         } broadcast;
998         /**
999          * @brief   Contains info about the `AVX` rounding.
1000          */
1001         struct ZydisDecodedInstructionAvxRounding_
1002         {
1003             /**
1004              * @brief   The `AVX` rounding-mode.
1005              */
1006             ZydisRoundingMode mode;
1007         } rounding;
1008         /**
1009          * @brief   Contains info about the `AVX` register-swizzle (`KNC` only).
1010          */
1011         struct ZydisDecodedInstructionAvxSwizzle_
1012         {
1013             /**
1014              * @brief   The `AVX` register-swizzle mode.
1015              */
1016             ZydisSwizzleMode mode;
1017         } swizzle;
1018         /**
1019          * @brief   Contains info about the `AVX` data-conversion (`KNC` only).
1020          */
1021         struct ZydisDecodedInstructionAvxConversion_
1022         {
1023             /**
1024              * @brief   The `AVX` data-conversion mode.
1025              */
1026             ZydisConversionMode mode;
1027         } conversion;
1028         /**
1029          * @brief   Signals, if the `SAE` (suppress-all-exceptions) functionality is enabled for
1030          *          the instruction.
1031          */
1032         ZyanBool has_sae;
1033         /**
1034          * @brief   Signals, if the instruction has a memory-eviction-hint (`KNC` only).
1035          */
1036         ZyanBool has_eviction_hint;
1037         // TODO: publish EVEX tuple-type and MVEX functionality
1038     } avx;
1039     /**
1040      * @brief   Meta info.
1041      */
1042     struct ZydisDecodedInstructionMeta_
1043     {
1044         /**
1045          * @brief   The instruction category.
1046          */
1047         ZydisInstructionCategory category;
1048         /**
1049          * @brief   The ISA-set.
1050          */
1051         ZydisISASet isa_set;
1052         /**
1053          * @brief   The ISA-set extension.
1054          */
1055         ZydisISAExt isa_ext;
1056         /**
1057          * @brief   The branch type.
1058          */
1059         ZydisBranchType branch_type;
1060         /**
1061          * @brief   The exception class.
1062          */
1063         ZydisExceptionClass exception_class;
1064     } meta;
1065     /**
1066      * @brief   Detailed info about different instruction-parts like `ModRM`, `SIB` or
1067      *          encoding-prefixes.
1068      */
1069     struct ZydisDecodedInstructionRaw_
1070     {
1071         /**
1072          * @brief   The number of legacy prefixes.
1073          */
1074         ZyanU8 prefix_count;
1075         /**
1076          * @brief   Detailed info about the legacy prefixes (including `REX`).
1077          */
1078         struct ZydisDecodedInstructionRawPrefixes_
1079         {
1080             /**
1081              * @brief   The prefix type.
1082              */
1083             ZydisPrefixType type;
1084             /**
1085              * @brief   The prefix byte.
1086              */
1087             ZyanU8 value;
1088         } prefixes[ZYDIS_MAX_INSTRUCTION_LENGTH];
1089         /**
1090          * @brief   Detailed info about the `REX` prefix.
1091          */
1092         struct ZydisDecodedInstructionRawRex_
1093         {
1094             /**
1095              * @brief   64-bit operand-size promotion.
1096              */
1097             ZyanU8 W;
1098             /**
1099              * @brief   Extension of the `ModRM.reg` field.
1100              */
1101             ZyanU8 R;
1102             /**
1103              * @brief   Extension of the `SIB.index` field.
1104              */
1105             ZyanU8 X;
1106             /**
1107              * @brief   Extension of the `ModRM.rm`, `SIB.base`, or `opcode.reg` field.
1108              */
1109             ZyanU8 B;
1110             /**
1111              * @brief   The offset of the effective `REX` byte, relative to the beginning of the
1112              *          instruction, in bytes.
1113              *
1114              * This offset always points to the "effective" `REX` prefix (the one closest to the
1115              * instruction opcode), if multiple `REX` prefixes are present.
1116              *
1117              * Note that the `REX` byte can be the first byte of the instruction, which would lead
1118              * to an offset of `0`. Please refer to the instruction attributes to check for the
1119              * presence of the `REX` prefix.
1120              */
1121             ZyanU8 offset;
1122         } rex;
1123         /**
1124          * @brief   Detailed info about the `XOP` prefix.
1125          */
1126         struct ZydisDecodedInstructionRawXop_
1127         {
1128             /**
1129              * @brief   Extension of the `ModRM.reg` field (inverted).
1130              */
1131             ZyanU8 R;
1132             /**
1133              * @brief   Extension of the `SIB.index` field (inverted).
1134              */
1135             ZyanU8 X;
1136             /**
1137              * @brief   Extension of the `ModRM.rm`, `SIB.base`, or `opcode.reg` field (inverted).
1138              */
1139             ZyanU8 B;
1140             /**
1141              * @brief   Opcode-map specifier.
1142              */
1143             ZyanU8 m_mmmm;
1144             /**
1145              * @brief   64-bit operand-size promotion or opcode-extension.
1146              */
1147             ZyanU8 W;
1148             /**
1149              * @brief   `NDS`/`NDD` (non-destructive-source/destination) register specifier
1150              *          (inverted).
1151              */
1152             ZyanU8 vvvv;
1153             /**
1154              * @brief   Vector-length specifier.
1155              */
1156             ZyanU8 L;
1157             /**
1158              * @brief   Compressed legacy prefix.
1159              */
1160             ZyanU8 pp;
1161             /**
1162              * @brief   The offset of the first xop byte, relative to the beginning of the
1163              *          instruction, in bytes.
1164              */
1165             ZyanU8 offset;
1166         } xop;
1167         /**
1168          * @brief   Detailed info about the `VEX` prefix.
1169          */
1170         struct ZydisDecodedInstructionRawVex_
1171         {
1172             /**
1173              * @brief   Extension of the `ModRM.reg` field (inverted).
1174              */
1175             ZyanU8 R;
1176             /**
1177              * @brief   Extension of the `SIB.index` field (inverted).
1178              */
1179             ZyanU8 X;
1180             /**
1181              * @brief   Extension of the `ModRM.rm`, `SIB.base`, or `opcode.reg` field (inverted).
1182              */
1183             ZyanU8 B;
1184             /**
1185              * @brief   Opcode-map specifier.
1186              */
1187             ZyanU8 m_mmmm;
1188             /**
1189              * @brief   64-bit operand-size promotion or opcode-extension.
1190              */
1191             ZyanU8 W;
1192             /**
1193              * @brief   `NDS`/`NDD` (non-destructive-source/destination) register specifier
1194              *          (inverted).
1195              */
1196             ZyanU8 vvvv;
1197             /**
1198              * @brief   Vector-length specifier.
1199              */
1200             ZyanU8 L;
1201             /**
1202              * @brief   Compressed legacy prefix.
1203              */
1204             ZyanU8 pp;
1205             /**
1206              * @brief   The offset of the first `VEX` byte, relative to the beginning of the
1207              *          instruction, in bytes.
1208              */
1209             ZyanU8 offset;
1210             /**
1211              * @brief   The size of the `VEX` prefix, in bytes.
1212              */
1213             ZyanU8 size;
1214         } vex;
1215         /**
1216          * @brief   Detailed info about the `EVEX` prefix.
1217          */
1218         struct ZydisDecodedInstructionRawEvex_
1219         {
1220             /**
1221              * @brief   Extension of the `ModRM.reg` field (inverted).
1222              */
1223             ZyanU8 R;
1224             /**
1225              * @brief   Extension of the `SIB.index/vidx` field (inverted).
1226              */
1227             ZyanU8 X;
1228             /**
1229              * @brief   Extension of the `ModRM.rm` or `SIB.base` field (inverted).
1230              */
1231             ZyanU8 B;
1232             /**
1233              * @brief   High-16 register specifier modifier (inverted).
1234              */
1235             ZyanU8 R2;
1236             /**
1237              * @brief   Opcode-map specifier.
1238              */
1239             ZyanU8 mm;
1240             /**
1241              * @brief   64-bit operand-size promotion or opcode-extension.
1242              */
1243             ZyanU8 W;
1244             /**
1245              * @brief   `NDS`/`NDD` (non-destructive-source/destination) register specifier
1246              *          (inverted).
1247              */
1248             ZyanU8 vvvv;
1249             /**
1250              * @brief   Compressed legacy prefix.
1251              */
1252             ZyanU8 pp;
1253             /**
1254              * @brief   Zeroing/Merging.
1255              */
1256             ZyanU8 z;
1257             /**
1258              * @brief   Vector-length specifier or rounding-control (most significant bit).
1259              */
1260             ZyanU8 L2;
1261             /**
1262              * @brief   Vector-length specifier or rounding-control (least significant bit).
1263              */
1264             ZyanU8 L;
1265             /**
1266              * @brief   Broadcast/RC/SAE context.
1267              */
1268             ZyanU8 b;
1269             /**
1270              * @brief   High-16 `NDS`/`VIDX` register specifier.
1271              */
1272             ZyanU8 V2;
1273             /**
1274              * @brief   Embedded opmask register specifier.
1275              */
1276             ZyanU8 aaa;
1277             /**
1278              * @brief   The offset of the first evex byte, relative to the beginning of the
1279              *          instruction, in bytes.
1280              */
1281             ZyanU8 offset;
1282         } evex;
1283         /**
1284         * @brief    Detailed info about the `MVEX` prefix.
1285         */
1286         struct ZydisDecodedInstructionRawMvex_
1287         {
1288             /**
1289              * @brief   Extension of the `ModRM.reg` field (inverted).
1290              */
1291             ZyanU8 R;
1292             /**
1293              * @brief   Extension of the `SIB.index/vidx` field (inverted).
1294              */
1295             ZyanU8 X;
1296             /**
1297              * @brief   Extension of the `ModRM.rm` or `SIB.base` field (inverted).
1298              */
1299             ZyanU8 B;
1300             /**
1301              * @brief   High-16 register specifier modifier (inverted).
1302              */
1303             ZyanU8 R2;
1304             /**
1305              * @brief   Opcode-map specifier.
1306              */
1307             ZyanU8 mmmm;
1308             /**
1309              * @brief   64-bit operand-size promotion or opcode-extension.
1310              */
1311             ZyanU8 W;
1312             /**
1313              * @brief   `NDS`/`NDD` (non-destructive-source/destination) register specifier
1314              *          (inverted).
1315              */
1316             ZyanU8 vvvv;
1317             /**
1318              * @brief   Compressed legacy prefix.
1319              */
1320             ZyanU8 pp;
1321             /**
1322              * @brief   Non-temporal/eviction hint.
1323              */
1324             ZyanU8 E;
1325             /**
1326              * @brief   Swizzle/broadcast/up-convert/down-convert/static-rounding controls.
1327              */
1328             ZyanU8 SSS;
1329             /**
1330              * @brief   High-16 `NDS`/`VIDX` register specifier.
1331              */
1332             ZyanU8 V2;
1333             /**
1334              * @brief   Embedded opmask register specifier.
1335              */
1336             ZyanU8 kkk;
1337             /**
1338              * @brief   The offset of the first mvex byte, relative to the beginning of the
1339              *          instruction, in bytes.
1340              */
1341             ZyanU8 offset;
1342         } mvex;
1343         /**
1344          * @brief   Detailed info about the `ModRM` byte.
1345          */
1346         struct ZydisDecodedInstructionModRm_
1347         {
1348             /**
1349              * @brief   The addressing mode.
1350              */
1351             ZyanU8 mod;
1352             /**
1353              * @brief   Register specifier or opcode-extension.
1354              */
1355             ZyanU8 reg;
1356             /**
1357              * @brief   Register specifier or opcode-extension.
1358              */
1359             ZyanU8 rm;
1360             /**
1361              * @brief   The offset of the `ModRM` byte, relative to the beginning of the
1362              *          instruction, in bytes.
1363              */
1364             ZyanU8 offset;
1365         } modrm;
1366         /**
1367          * @brief   Detailed info about the `SIB` byte.
1368          */
1369         struct ZydisDecodedInstructionRawSib_
1370         {
1371             /**
1372              * @brief   The scale factor.
1373              */
1374             ZyanU8 scale;
1375             /**
1376              * @brief   The index-register specifier.
1377              */
1378             ZyanU8 index;
1379             /**
1380              * @brief   The base-register specifier.
1381              */
1382             ZyanU8 base;
1383             /**
1384              * @brief   The offset of the `SIB` byte, relative to the beginning of the instruction,
1385              *          in bytes.
1386              */
1387             ZyanU8 offset;
1388         } sib;
1389         /**
1390          * @brief   Detailed info about displacement-bytes.
1391          */
1392         struct ZydisDecodedInstructionRawDisp_
1393         {
1394             /**
1395              * @brief   The displacement value
1396              */
1397             ZyanI64 value;
1398             /**
1399              * @brief   The physical displacement size, in bits.
1400              */
1401             ZyanU8 size;
1402             // TODO: publish cd8 scale
1403             /**
1404              * @brief   The offset of the displacement data, relative to the beginning of the
1405              *          instruction, in bytes.
1406              */
1407             ZyanU8 offset;
1408         } disp;
1409         /**
1410          * @brief   Detailed info about immediate-bytes.
1411          */
1412         struct ZydisDecodedInstructionRawImm_
1413         {
1414             /**
1415              * @brief   Signals, if the immediate value is signed.
1416              */
1417             ZyanBool is_signed;
1418             /**
1419              * @brief   Signals, if the immediate value contains a relative offset. You can use
1420              *          `ZydisCalcAbsoluteAddress` to determine the absolute address value.
1421              */
1422             ZyanBool is_relative;
1423             /**
1424              * @brief   The immediate value.
1425              */
1426             union ZydisDecodedInstructionRawImmValue_
1427             {
1428                 ZyanU64 u;
1429                 ZyanI64 s;
1430             } value;
1431             /**
1432              * @brief   The physical immediate size, in bits.
1433              */
1434             ZyanU8 size;
1435             /**
1436              * @brief   The offset of the immediate data, relative to the beginning of the
1437              *          instruction, in bytes.
1438              */
1439             ZyanU8 offset;
1440         } imm[2];
1441     } raw;
1442 } ZydisDecodedInstruction;
1443 
1444 /* ---------------------------------------------------------------------------------------------- */
1445 
1446 /* ============================================================================================== */
1447 
1448 #ifdef __cplusplus
1449 }
1450 #endif
1451 
1452 #endif /* ZYDIS_INSTRUCTIONINFO_H */
1453