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 #ifndef ZYDIS_INTERNAL_DECODERDATA_H
28 #define ZYDIS_INTERNAL_DECODERDATA_H
29 
30 #include <Zycore/Defines.h>
31 #include <Zydis/DecoderTypes.h>
32 
33 #ifdef __cplusplus
34 extern "C" {
35 #endif
36 
37 /* ============================================================================================== */
38 /* Enums and types                                                                                */
39 /* ============================================================================================== */
40 
41 // MSVC does not like types other than (un-)signed int for bit-fields
42 #ifdef ZYAN_MSVC
43 #   pragma warning(push)
44 #   pragma warning(disable:4214)
45 #endif
46 
47 #pragma pack(push, 1)
48 
49 /* ---------------------------------------------------------------------------------------------- */
50 /* Decoder tree                                                                                   */
51 /* ---------------------------------------------------------------------------------------------- */
52 
53 /**
54  * @brief   Defines the `ZydisDecoderTreeNodeType` data-type.
55  */
56 typedef ZyanU8 ZydisDecoderTreeNodeType;
57 
58 /**
59  * @brief   Values that represent zydis decoder tree node types.
60  */
61 enum ZydisDecoderTreeNodeTypes
62 {
63     ZYDIS_NODETYPE_INVALID                  = 0x00,
64     /**
65      * @brief   Reference to an instruction-definition.
66      */
67     ZYDIS_NODETYPE_DEFINITION_MASK          = 0x80,
68     /**
69      * @brief   Reference to an XOP-map filter.
70      */
71     ZYDIS_NODETYPE_FILTER_XOP               = 0x01,
72     /**
73      * @brief   Reference to an VEX-map filter.
74      */
75     ZYDIS_NODETYPE_FILTER_VEX               = 0x02,
76     /**
77      * @brief   Reference to an EVEX/MVEX-map filter.
78      */
79     ZYDIS_NODETYPE_FILTER_EMVEX             = 0x03,
80     /**
81      * @brief   Reference to an opcode filter.
82      */
83     ZYDIS_NODETYPE_FILTER_OPCODE            = 0x04,
84     /**
85      * @brief   Reference to an instruction-mode filter.
86      */
87     ZYDIS_NODETYPE_FILTER_MODE              = 0x05,
88     /**
89      * @brief   Reference to an compacted instruction-mode filter.
90      */
91     ZYDIS_NODETYPE_FILTER_MODE_COMPACT      = 0x06,
92     /**
93      * @brief   Reference to a ModRM.mod filter.
94      */
95     ZYDIS_NODETYPE_FILTER_MODRM_MOD         = 0x07,
96     /**
97      * @brief   Reference to a compacted ModRM.mod filter.
98      */
99     ZYDIS_NODETYPE_FILTER_MODRM_MOD_COMPACT = 0x08,
100     /**
101      * @brief   Reference to a ModRM.reg filter.
102      */
103     ZYDIS_NODETYPE_FILTER_MODRM_REG         = 0x09,
104     /**
105      * @brief   Reference to a ModRM.rm filter.
106      */
107     ZYDIS_NODETYPE_FILTER_MODRM_RM          = 0x0A,
108     /**
109      * @brief   Reference to a PrefixGroup1 filter.
110      */
111     ZYDIS_NODETYPE_FILTER_PREFIX_GROUP1     = 0x0B,
112     /**
113      * @brief   Reference to a mandatory-prefix filter.
114      */
115     ZYDIS_NODETYPE_FILTER_MANDATORY_PREFIX  = 0x0C,
116     /**
117      * @brief   Reference to an operand-size filter.
118      */
119     ZYDIS_NODETYPE_FILTER_OPERAND_SIZE      = 0x0D,
120     /**
121      * @brief   Reference to an address-size filter.
122      */
123     ZYDIS_NODETYPE_FILTER_ADDRESS_SIZE      = 0x0E,
124     /**
125      * @brief   Reference to a vector-length filter.
126      */
127     ZYDIS_NODETYPE_FILTER_VECTOR_LENGTH     = 0x0F,
128     /**
129      * @brief   Reference to an REX/VEX/EVEX.W filter.
130      */
131     ZYDIS_NODETYPE_FILTER_REX_W             = 0x10,
132     /**
133      * @brief   Reference to an REX/VEX/EVEX.B filter.
134      */
135     ZYDIS_NODETYPE_FILTER_REX_B             = 0x11,
136     /**
137      * @brief   Reference to an EVEX.b filter.
138      */
139     ZYDIS_NODETYPE_FILTER_EVEX_B            = 0x12,
140     /**
141      * @brief   Reference to an MVEX.E filter.
142      */
143     ZYDIS_NODETYPE_FILTER_MVEX_E            = 0x13,
144     /**
145      * @brief   Reference to a AMD-mode filter.
146      */
147     ZYDIS_NODETYPE_FILTER_MODE_AMD          = 0x14,
148     /**
149      * @brief   Reference to a KNC-mode filter.
150      */
151     ZYDIS_NODETYPE_FILTER_MODE_KNC          = 0x15,
152     /**
153      * @brief   Reference to a MPX-mode filter.
154      */
155     ZYDIS_NODETYPE_FILTER_MODE_MPX          = 0x16,
156     /**
157      * @brief   Reference to a CET-mode filter.
158      */
159     ZYDIS_NODETYPE_FILTER_MODE_CET          = 0x17,
160     /**
161      * @brief   Reference to a LZCNT-mode filter.
162      */
163     ZYDIS_NODETYPE_FILTER_MODE_LZCNT        = 0x18,
164     /**
165      * @brief   Reference to a TZCNT-mode filter.
166      */
167     ZYDIS_NODETYPE_FILTER_MODE_TZCNT        = 0x19,
168     /**
169      * @brief   Reference to a WBNOINVD-mode filter.
170      */
171     ZYDIS_NODETYPE_FILTER_MODE_WBNOINVD     = 0x1A,
172     /**
173      * @brief   Reference to a CLDEMOTE-mode filter.
174      */
175     ZYDIS_NODETYPE_FILTER_MODE_CLDEMOTE     = 0x1B
176 };
177 
178 /* ---------------------------------------------------------------------------------------------- */
179 
180 /**
181  * @brief   Defines the `ZydisDecoderTreeNodeValue` data-type.
182  */
183 typedef ZyanU16 ZydisDecoderTreeNodeValue;
184 
185 /* ---------------------------------------------------------------------------------------------- */
186 
187 /**
188  * @brief   Defines the `ZydisDecoderTreeNode` struct.
189  */
190 typedef struct ZydisDecoderTreeNode_
191 {
192     ZydisDecoderTreeNodeType type;
193     ZydisDecoderTreeNodeValue value;
194 } ZydisDecoderTreeNode;
195 
196 /* ---------------------------------------------------------------------------------------------- */
197 
198 #pragma pack(pop)
199 
200 #ifdef ZYAN_MSVC
201 #   pragma warning(pop)
202 #endif
203 
204 /* ---------------------------------------------------------------------------------------------- */
205 /* Physical instruction encoding info                                                             */
206 /* ---------------------------------------------------------------------------------------------- */
207 
208 /**
209  * @brief   Defines the `ZydisInstructionEncodingFlags` data-type.
210  */
211 typedef ZyanU8 ZydisInstructionEncodingFlags;
212 
213 /**
214  * @brief   The instruction has an optional modrm byte.
215  */
216 #define ZYDIS_INSTR_ENC_FLAG_HAS_MODRM      0x01
217 
218 /**
219  * @brief   The instruction has an optional displacement value.
220  */
221 #define ZYDIS_INSTR_ENC_FLAG_HAS_DISP       0x02
222 
223 /**
224  * @brief   The instruction has an optional immediate value.
225  */
226 #define ZYDIS_INSTR_ENC_FLAG_HAS_IMM0       0x04
227 
228 /**
229  * @brief   The instruction has a second optional immediate value.
230  */
231 #define ZYDIS_INSTR_ENC_FLAG_HAS_IMM1       0x08
232 
233 /**
234  * @brief   The instruction ignores the value of `modrm.mod` and always assumes `modrm.mod == 3`
235  *          ("reg, reg" - form).
236  *
237  *          Instructions with this flag can't have a SIB byte or a displacement value.
238  */
239 #define ZYDIS_INSTR_ENC_FLAG_FORCE_REG_FORM 0x10
240 
241 /**
242  * @brief   Defines the `ZydisInstructionEncodingInfo` struct.
243  */
244 typedef struct ZydisInstructionEncodingInfo_
245 {
246     /**
247      * @brief   Contains flags with information about the physical instruction-encoding.
248      */
249     ZydisInstructionEncodingFlags flags;
250     /**
251      * @brief   Displacement info.
252      */
253     struct
254     {
255         /**
256          * @brief   The size of the displacement value.
257          */
258         ZyanU8 size[3];
259     } disp;
260     /**
261      * @brief   Immediate info.
262      */
263     struct
264     {
265         /**
266          * @brief   The size of the immediate value.
267          */
268         ZyanU8 size[3];
269         /**
270          * @brief   Signals, if the value is signed.
271          */
272         ZyanBool is_signed;
273         /**
274          * @brief   Signals, if the value is a relative offset.
275          */
276         ZyanBool is_relative;
277     } imm[2];
278 } ZydisInstructionEncodingInfo;
279 
280 /* ---------------------------------------------------------------------------------------------- */
281 
282 /* ============================================================================================== */
283 /* Functions                                                                                      */
284 /* ============================================================================================== */
285 
286 /* ---------------------------------------------------------------------------------------------- */
287 /* Decoder tree                                                                                   */
288 /* ---------------------------------------------------------------------------------------------- */
289 
290 /**
291  * @brief   Returns the root node of the instruction tree.
292  *
293  * @return  The root node of the instruction tree.
294  */
295 ZYDIS_NO_EXPORT const ZydisDecoderTreeNode* ZydisDecoderTreeGetRootNode(void);
296 
297 /**
298  * @brief   Returns the child node of `parent` specified by `index`.
299  *
300  * @param   parent  The parent node.
301  * @param   index   The index of the child node to retrieve.
302  *
303  * @return  The specified child node.
304  */
305 ZYDIS_NO_EXPORT const ZydisDecoderTreeNode* ZydisDecoderTreeGetChildNode(
306     const ZydisDecoderTreeNode* parent, ZyanU16 index);
307 
308 /**
309  * @brief   Returns information about optional instruction parts (like modrm, displacement or
310  *          immediates) for the instruction that is linked to the given `node`.
311  *
312  * @param   node    The instruction definition node.
313  * @param   info    A pointer to the `ZydisInstructionParts` struct.
314  */
315 ZYDIS_NO_EXPORT void ZydisGetInstructionEncodingInfo(const ZydisDecoderTreeNode* node,
316     const ZydisInstructionEncodingInfo** info);
317 
318 /* ---------------------------------------------------------------------------------------------- */
319 
320 /* ============================================================================================== */
321 
322 #ifdef __cplusplus
323 }
324 #endif
325 
326 #endif /* ZYDIS_INTERNAL_DECODERDATA_H */
327