1 /*BEGIN_LEGAL
2 
3 Copyright (c) 2018 Intel Corporation
4 
5   Licensed under the Apache License, Version 2.0 (the "License");
6   you may not use this file except in compliance with the License.
7   You may obtain a copy of the License at
8 
9       http://www.apache.org/licenses/LICENSE-2.0
10 
11   Unless required by applicable law or agreed to in writing, software
12   distributed under the License is distributed on an "AS IS" BASIS,
13   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   See the License for the specific language governing permissions and
15   limitations under the License.
16 
17 END_LEGAL */
18 /// @file xed-encode.h
19 
20 
21 #ifndef XED_ENCODE_H
22 # define XED_ENCODE_H
23 #include "xed-common-hdrs.h"
24 #include "xed-types.h"
25 #include "xed-error-enum.h"
26 #include "xed-operand-values-interface.h"
27 #include "xed-operand-width-enum.h"
28 #include "xed-encoder-iforms.h" //generated
29 #include "xed-encoder-gen-defs.h" //generated
30 
31 // we now (mostly) share the decode data structure
32 #include "xed-decoded-inst.h"
33 
34 
35 // establish a type equivalence for the xed_encoder_request_t and the
36 // corresponding xed_decoded_inst_t.
37 
38 /// @ingroup ENC
39 typedef struct  xed_decoded_inst_s xed_encoder_request_s;
40 /// @ingroup ENC
41 typedef xed_decoded_inst_t xed_encoder_request_t;
42 
43 
44 
45 /// @ingroup ENC
46 XED_DLL_EXPORT xed_iclass_enum_t
47 xed_encoder_request_get_iclass( const xed_encoder_request_t* p);
48 
49 /////////////////////////////////////////////////////////
50 // set functions
51 
52 /// @ingroup ENC
53 XED_DLL_EXPORT void
54 xed_encoder_request_set_iclass( xed_encoder_request_t* p,
55                                 xed_iclass_enum_t iclass);
56 
57 /// @name Prefixes
58 //@{
59 /// @ingroup ENC
60 /// for  REPNE(F2) prefix on string ops
61 XED_DLL_EXPORT void xed_encoder_request_set_repne(xed_encoder_request_t* p);
62 /// @ingroup ENC
63 /// for REP(F3) prefix on string ops
64 XED_DLL_EXPORT void xed_encoder_request_set_rep(xed_encoder_request_t* p);
65 /// @ingroup ENC
66 /// clear the REP prefix indicator
67 XED_DLL_EXPORT void xed_encoder_request_clear_rep(xed_encoder_request_t* p);
68 //@}
69 
70 /// @name Primary Encode Functions
71 //@{
72 /// @ingroup ENC
73 XED_DLL_EXPORT void
74 xed_encoder_request_set_effective_operand_width( xed_encoder_request_t* p,
75                                                  xed_uint_t width_bits);
76 /// @ingroup ENC
77 XED_DLL_EXPORT void
78 xed_encoder_request_set_effective_address_size( xed_encoder_request_t* p,
79                                                 xed_uint_t width_bits);
80 /*! @ingroup ENC
81  *
82  * Set the operands array element indexed by operand to the actual register
83  * name reg.
84  *
85  * @param[in] p            xed_encoder_request_t
86  * @param[in] operand      indicates which register operand storage field to use
87  * @param[in] reg          the actual register represented (EAX, etc.)  to store.
88  */
89 XED_DLL_EXPORT void xed_encoder_request_set_reg(xed_encoder_request_t* p,
90                                                 xed_operand_enum_t operand,
91                                                 xed_reg_enum_t reg);
92 //@}
93 
94 /// @name Operand Order
95 //@{
96 /*! @ingroup ENC
97  * Specify the name as the n'th operand in the operand order.
98  *
99  * The complication of this function is that the register operand names are
100  * specific to the position of the operand (REG0, REG1, REG2...). One can
101  * use this function for registers or one can use the
102  * xed_encoder_request_set_operand_name_reg() which takes integers instead
103  * of operand names.
104  *
105  * @param[in] p                #xed_encoder_request_t
106  * @param[in] operand_index    xed_uint_t representing n'th operand position
107  * @param[in] name             #xed_operand_enum_t operand name.
108  */
109 XED_DLL_EXPORT void
110 xed_encoder_request_set_operand_order(xed_encoder_request_t* p,
111                                       xed_uint_t operand_index,
112                                       xed_operand_enum_t name);
113 
114 /*! @ingroup ENC
115  * Retrieve the name of the n'th operand in the operand order.
116  *
117  * @param[in] p                #xed_encoder_request_t
118  * @param[in] operand_index    xed_uint_t representing n'th operand position
119  * @return The #xed_operand_enum_t operand name.
120  */
121 XED_DLL_EXPORT xed_operand_enum_t
122 xed_encoder_request_get_operand_order(xed_encoder_request_t* p,
123                                       xed_uint_t operand_index);
124 
125 
126 /// @ingroup ENC
127 /// Retrieve the number of entries in the encoder operand order array
128 /// @return The number of entries in the encoder operand order array
129 static XED_INLINE xed_uint_t
xed_encoder_request_operand_order_entries(xed_encoder_request_t * p)130 xed_encoder_request_operand_order_entries(xed_encoder_request_t* p)
131 {
132     return  p->_n_operand_order;
133 }
134 
135 //@}
136 
137 
138 /// @name branches and far pointers
139 //@{
140 /// @ingroup ENC
141 XED_DLL_EXPORT void xed_encoder_request_set_relbr(xed_encoder_request_t* p);
142 /// @ingroup ENC
143 XED_DLL_EXPORT void
144 xed_encoder_request_set_branch_displacement(xed_encoder_request_t* p,
145                                             xed_int32_t brdisp,
146                                             xed_uint_t nbytes);
147 /// @ingroup ENC
148 XED_DLL_EXPORT void xed_encoder_request_set_ptr(xed_encoder_request_t* p);
149 //@}
150 
151 
152 /// @name Immediates
153 //@{
154 /// @ingroup ENC
155 /// Set the uimm0 using a BYTE  width.
156 XED_DLL_EXPORT void xed_encoder_request_set_uimm0(xed_encoder_request_t* p,
157                                                   xed_uint64_t uimm,
158                                                   xed_uint_t nbytes);
159 /// @ingroup ENC
160 /// Set the uimm0 using a BIT  width.
161 XED_DLL_EXPORT void xed_encoder_request_set_uimm0_bits(xed_encoder_request_t* p,
162                                                        xed_uint64_t uimm,
163                                                        xed_uint_t nbits);
164 /// @ingroup ENC
165 XED_DLL_EXPORT void xed_encoder_request_set_uimm1(xed_encoder_request_t* p,
166                                                   xed_uint8_t uimm);
167 /// @ingroup ENC
168 /// same storage as uimm0
169 XED_DLL_EXPORT void xed_encoder_request_set_simm(xed_encoder_request_t* p,
170                                                  xed_int32_t simm,
171                                                  xed_uint_t nbytes);
172 
173 /// @name Memory
174 //@{
175 /// @ingroup ENC
176 XED_DLL_EXPORT void
177 xed_encoder_request_set_memory_displacement(xed_encoder_request_t* p,
178                                             xed_int64_t memdisp,
179                                             xed_uint_t nbytes);
180 
181 /// @ingroup ENC
182 XED_DLL_EXPORT void xed_encoder_request_set_agen(xed_encoder_request_t* p);
183 /// @ingroup ENC
184 XED_DLL_EXPORT void xed_encoder_request_set_mem0(xed_encoder_request_t* p);
185 /// @ingroup ENC
186 XED_DLL_EXPORT void xed_encoder_request_set_mem1(xed_encoder_request_t* p);
187 /// @ingroup ENC
188 XED_DLL_EXPORT void
189 xed_encoder_request_set_memory_operand_length(xed_encoder_request_t* p,
190                                               xed_uint_t nbytes);
191 /// @ingroup ENC
192 XED_DLL_EXPORT void xed_encoder_request_set_seg0(xed_encoder_request_t* p,
193                                   xed_reg_enum_t seg_reg);
194 /// @ingroup ENC
195 XED_DLL_EXPORT void xed_encoder_request_set_seg1(xed_encoder_request_t* p,
196                                   xed_reg_enum_t seg_reg);
197 /// @ingroup ENC
198 XED_DLL_EXPORT void xed_encoder_request_set_base0(xed_encoder_request_t* p,
199                                    xed_reg_enum_t base_reg);
200 /// @ingroup ENC
201 XED_DLL_EXPORT void xed_encoder_request_set_base1(xed_encoder_request_t* p,
202                                    xed_reg_enum_t base_reg) ;
203 /// @ingroup ENC
204 XED_DLL_EXPORT void xed_encoder_request_set_index(xed_encoder_request_t* p,
205                                    xed_reg_enum_t index_reg);
206 /// @ingroup ENC
207 XED_DLL_EXPORT void
208 xed_encoder_request_set_scale(xed_encoder_request_t* p,
209                               xed_uint_t scale);
210 //@}
211 
212 //////////////////////////////////////////////
213 /// @ingroup ENC
214 XED_DLL_EXPORT const xed_operand_values_t*
215 xed_encoder_request_operands_const(const xed_encoder_request_t* p);
216 /// @ingroup ENC
217 XED_DLL_EXPORT xed_operand_values_t*
218 xed_encoder_request_operands(xed_encoder_request_t* p);
219 
220 /// @name Initialization
221 //@{
222 /*! @ingroup ENC
223  * clear the operand order array
224  * @param[in] p                xed_encoder_request_t
225  */
226 XED_DLL_EXPORT void
227 xed_encoder_request_zero_operand_order(xed_encoder_request_t* p);
228 
229 /// @ingroup ENC
230 XED_DLL_EXPORT void
231 xed_encoder_request_zero_set_mode(xed_encoder_request_t* p,
232                                   const xed_state_t* dstate);
233 /// @ingroup ENC
234 XED_DLL_EXPORT void  xed_encoder_request_zero(xed_encoder_request_t* p) ;
235 //@}
236 
237 struct xed_decoded_inst_s; //fwd decl
238 /// @ingroup ENC
239 /// Converts an decoder request to a valid encoder request.
240 XED_DLL_EXPORT void
241 xed_encoder_request_init_from_decode(struct xed_decoded_inst_s* d);
242 
243 /// @name String Printing
244 //@{
245 /// @ingroup ENC
246 XED_DLL_EXPORT void xed_encode_request_print(const xed_encoder_request_t* p,
247                                              char* buf, xed_uint_t buflen);
248 //@}
249 
250 
251 
252 
253 /// @name Encoding
254 //@{
255 ///   This is the main interface to the encoder. The array should be
256 ///   at most 15 bytes long. The ilen parameter should indicate
257 ///   this length. If the array is too short, the encoder may fail to
258 ///   encode the request.  Failure is indicated by a return value of
259 ///   type #xed_error_enum_t that is not equal to
260 ///   #XED_ERROR_NONE. Otherwise, #XED_ERROR_NONE is returned and the
261 ///   length of the encoded instruction is returned in olen.
262 ///
263 /// @param r encoder request description (#xed_encoder_request_t), includes mode info
264 /// @param array the encoded instruction bytes are stored here
265 /// @param ilen the input length of array.
266 /// @param olen the actual  length of array used for encoding
267 /// @return success/failure as a #xed_error_enum_t
268 /// @ingroup ENC
269 XED_DLL_EXPORT xed_error_enum_t
270 xed_encode(xed_encoder_request_t* r,
271            xed_uint8_t* array,
272            const unsigned int ilen,
273            unsigned int* olen);
274 
275 /// This function will attempt to encode a NOP of exactly ilen
276 /// bytes. If such a NOP is not encodeable, then false will be returned.
277 ///
278 /// @param array the encoded instruction bytes are stored here
279 /// @param  ilen the input length array.
280 /// @return success/failure as a #xed_error_enum_t
281 /// @ingroup ENC
282 XED_DLL_EXPORT xed_error_enum_t
283 xed_encode_nop(xed_uint8_t* array,
284                const unsigned int ilen);
285 //@}
286 
287 #endif
288