Can now understand basic 4 operand VEX instructions
[dyninst.git] / instructionAPI / src / InstructionDecoder-x86.C
1 /*
2  * See the dyninst/COPYRIGHT file for copyright information.
3  * 
4  * We provide the Paradyn Tools (below described as "Paradyn")
5  * on an AS IS basis, and do not warrant its validity or performance.
6  * We reserve the right to update, modify, or discontinue this
7  * software at any time.  We shall have no obligation to supply such
8  * updates or modifications or any other form of support to you.
9  * 
10  * By your use of Paradyn, you understand and agree that we (or any
11  * other person or entity with proprietary rights in Paradyn) are
12  * under no obligation to provide either maintenance services,
13  * update services, notices of latent defects, or correction of
14  * defects for Paradyn.
15  * 
16  * This library is free software; you can redistribute it and/or
17  * modify it under the terms of the GNU Lesser General Public
18  * License as published by the Free Software Foundation; either
19  * version 2.1 of the License, or (at your option) any later version.
20  * 
21  * This library is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
24  * Lesser General Public License for more details.
25  * 
26  * You should have received a copy of the GNU Lesser General Public
27  * License along with this library; if not, write to the Free Software
28  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
29  */
30
31 #define INSIDE_INSTRUCTION_API
32
33 #include "common/src/Types.h"
34 #include "InstructionDecoder-x86.h"
35 #include "Expression.h"
36 #include "common/src/arch-x86.h"
37 #include "Register.h"
38 #include "Dereference.h"
39 #include "Immediate.h" 
40 #include "BinaryFunction.h"
41 #include "common/src/singleton_object_pool.h"
42
43 using namespace std;
44 using namespace NS_x86;
45 namespace Dyninst
46 {
47     namespace InstructionAPI
48     {
49     
50         bool readsOperand(unsigned int opsema, unsigned int i)
51         {
52             switch(opsema) {
53                 case s1R2R:
54                     return (i == 0 || i == 1);
55                 case s1R:
56                 case s1RW:
57                     return i == 0;
58                 case s1W:
59                     return false;
60                 case s1W2RW:
61                 case s1W2R:   // second operand read, first operand written (e.g. mov)
62                     return i == 1;
63                 case s1RW2R:  // two operands read, first written (e.g. add)
64                 case s1RW2RW: // e.g. xchg
65                 case s1R2RW:
66                     return i == 0 || i == 1;
67                 case s1W2R3R: // e.g. imul
68                 case s1W2RW3R: // some mul
69                 case s1W2R3RW: // (stack) push & pop
70                     return i == 1 || i == 2;
71                 case s1W2W3R: // e.g. les
72                     return i == 2;
73                 case s1RW2R3R: // shld/shrd
74                 case s1RW2RW3R: // [i]div, cmpxch8b
75                 case s1R2R3R:
76                     return i == 0 || i == 1 || i == 2;
77                 case s1W2R3R4R:
78                     return i == 1 || i == 2 || i == 3;
79                 case s1RW2R3R4R:
80                     return i == 0 || i == 1 || i == 2 || i == 3;
81                 case sNONE:
82                 default:
83                     return false;
84             }
85       
86         }
87       
88         bool writesOperand(unsigned int opsema, unsigned int i)
89         {
90             switch(opsema) {
91                 case s1R2R:
92                 case s1R:
93                     return false;
94                 case s1RW:
95                 case s1W:
96                 case s1W2R:   // second operand read, first operand written (e.g. mov)
97                 case s1RW2R:  // two operands read, first written (e.g. add)
98                 case s1W2R3R: // e.g. imul
99                 case s1RW2R3R: // shld/shrd
100                 case s1RW2R3R4R:
101                   return i == 0;
102                 case s1R2RW:
103                   return i == 1;
104                 case s1W2RW:
105                 case s1RW2RW: // e.g. xchg
106                 case s1W2RW3R: // some mul
107                 case s1W2W3R: // e.g. les
108                 case s1RW2RW3R: // [i]div, cmpxch8b
109                   return i == 0 || i == 1;
110                 case s1W2R3RW: // (stack) push & pop
111                   return i == 0 || i == 2;
112                 case sNONE:
113                 default:
114                     return false;
115             }
116         }
117
118
119     
120     INSTRUCTION_EXPORT InstructionDecoder_x86::InstructionDecoder_x86(Architecture a) :
121       InstructionDecoderImpl(a),
122     locs(NULL),
123     decodedInstruction(NULL),
124     sizePrefixPresent(false),
125     addrSizePrefixPresent(false)
126     {
127       if(a == Arch_x86_64) setMode(true);
128       
129     }
130     INSTRUCTION_EXPORT InstructionDecoder_x86::~InstructionDecoder_x86()
131     {
132         if(decodedInstruction) decodedInstruction->~ia32_instruction();
133         free(decodedInstruction);
134         if(locs) locs->~ia32_locations();
135         free(locs);
136
137     }
138     static const unsigned char modrm_use_sib = 4;
139     
140     INSTRUCTION_EXPORT void InstructionDecoder_x86::setMode(bool is64)
141     {
142         ia32_set_mode_64(is64);
143     }
144     
145       Expression::Ptr InstructionDecoder_x86::makeSIBExpression(const InstructionDecoder::buffer& b)
146     {
147         unsigned scale;
148         Register index;
149         Register base;
150         Result_Type registerType = ia32_is_mode_64() ? u64 : u32;
151
152         decode_SIB(locs->sib_byte, scale, index, base);
153
154         Expression::Ptr scaleAST(make_shared(singleton_object_pool<Immediate>::construct(Result(u8, dword_t(scale)))));
155         Expression::Ptr indexAST(make_shared(singleton_object_pool<RegisterAST>::construct(makeRegisterID(index, registerType,
156                                     locs->rex_x))));
157         Expression::Ptr baseAST;
158         if(base == 0x05)
159         {
160             switch(locs->modrm_mod)
161             {
162                 case 0x00:
163                     baseAST = decodeImmediate(op_d, b.start + locs->sib_position + 1, true);
164                     break;
165                 case 0x01: 
166                 case 0x02: 
167                     baseAST = make_shared(singleton_object_pool<RegisterAST>::construct(makeRegisterID(base, 
168                                                                                                registerType,
169                                                                                                locs->rex_b)));
170                     break;
171                 case 0x03:
172                 default:
173                     assert(0);
174                     break;
175             };
176         }
177         else
178         {
179             baseAST = make_shared(singleton_object_pool<RegisterAST>::construct(makeRegisterID(base, 
180                                                                                                registerType,
181                                                                                                locs->rex_b)));
182         }
183
184         if(index == 0x04 && (!(ia32_is_mode_64()) || !(locs->rex_x)))
185         {
186             return baseAST;
187         }
188         return makeAddExpression(baseAST, makeMultiplyExpression(indexAST, scaleAST, registerType), registerType);
189     }
190
191       Expression::Ptr InstructionDecoder_x86::makeModRMExpression(const InstructionDecoder::buffer& b,
192                                                                   unsigned int opType)
193     {
194        unsigned int regType = op_d;
195         Result_Type aw = ia32_is_mode_64() ? u64 : u32;
196         if (opType == op_lea) {
197             // For an LEA, aw (address width) is insufficient, use makeSizeType
198             aw = makeSizeType(opType);
199         }
200         if(ia32_is_mode_64())
201         {
202             regType = op_q;
203         }
204         Expression::Ptr e =
205             makeRegisterExpression(makeRegisterID(locs->modrm_rm, regType, locs->rex_b));
206         switch(locs->modrm_mod)
207         {
208             case 0:
209                 if(locs->modrm_rm == modrm_use_sib) {
210                     e = makeSIBExpression(b);
211                 }
212                 if(locs->modrm_rm == 0x5 && !addrSizePrefixPresent)
213                 {
214                     assert(locs->opcode_position > -1);
215                     if(ia32_is_mode_64())
216                     {
217                         e = makeAddExpression(makeRegisterExpression(x86_64::rip),
218                                             getModRMDisplacement(b), aw);
219                     }
220                     else
221                     {
222                         e = getModRMDisplacement(b);
223                     }
224         
225                 }
226                 if(locs->modrm_rm == 0x6 && addrSizePrefixPresent)
227                 {
228                     e = getModRMDisplacement(b);
229                 }
230                 if(opType == op_lea)
231                 {
232                     return e;
233                 }
234                 return makeDereferenceExpression(e, makeSizeType(opType));
235                 assert(0);
236                 break;
237             case 1:
238             case 2:
239             {
240                 if(locs->modrm_rm == modrm_use_sib) {
241                     e = makeSIBExpression(b);
242                 }
243                 Expression::Ptr disp_e = makeAddExpression(e, getModRMDisplacement(b), aw);
244                 if(opType == op_lea)
245                 {
246                     return disp_e;
247                 }
248                 return makeDereferenceExpression(disp_e, makeSizeType(opType));
249             }
250             assert(0);
251             break;
252             case 3:
253                 return makeRegisterExpression(makeRegisterID(locs->modrm_rm, opType, locs->rex_b));
254             default:
255                 return Expression::Ptr();
256         
257         };
258         // can't get here, but make the compiler happy...
259         assert(0);
260         return Expression::Ptr();
261     }
262
263     Expression::Ptr InstructionDecoder_x86::decodeImmediate(unsigned int opType, const unsigned char* immStart, 
264                                                             bool isSigned)
265     {
266         // rex_w indicates we need to sign-extend also.
267         isSigned = isSigned || locs->rex_w;
268
269         switch(opType)
270         {
271             case op_b:
272                 return Immediate::makeImmediate(Result(isSigned ? s8 : u8 ,*(const byte_t*)(immStart)));
273                 break;
274             case op_d:
275                 return Immediate::makeImmediate(Result(isSigned ? s32 : u32,*(const dword_t*)(immStart)));
276             case op_w:
277                 return Immediate::makeImmediate(Result(isSigned ? s16 : u16,*(const word_t*)(immStart)));
278                 break;
279             case op_q:
280                 return Immediate::makeImmediate(Result(isSigned ? s64 : u64,*(const int64_t*)(immStart)));
281                 break;
282             case op_v:
283                 if (locs->rex_w) {
284                     return Immediate::makeImmediate(Result(isSigned ? s64 : u64,*(const int64_t*)(immStart)));
285                 }
286                 //FALLTHROUGH
287             case op_z:
288                 // 32 bit mode & no prefix, or 16 bit mode & prefix => 32 bit
289                 // 16 bit mode, no prefix or 32 bit mode, prefix => 16 bit
290                 if(!sizePrefixPresent)
291                 {
292                     return Immediate::makeImmediate(Result(isSigned ? s32 : u32,*(const dword_t*)(immStart)));
293                 }
294                 else
295                 {
296                     return Immediate::makeImmediate(Result(isSigned ? s16 : u16,*(const word_t*)(immStart)));
297                 }
298                 break;
299             case op_p:
300                 // 32 bit mode & no prefix, or 16 bit mode & prefix => 48 bit
301                 // 16 bit mode, no prefix or 32 bit mode, prefix => 32 bit
302                 if(!sizePrefixPresent)
303                 {
304                     return Immediate::makeImmediate(Result(isSigned ? s48 : u48,*(const int64_t*)(immStart)));
305                 }
306                 else
307                 {
308                     return Immediate::makeImmediate(Result(isSigned ? s32 : u32,*(const dword_t*)(immStart)));
309                 }
310
311                 break;
312             case op_a:
313             case op_dq:
314             case op_pd:
315             case op_ps:
316             case op_s:
317             case op_si:
318             case op_lea:
319             case op_allgprs:
320             case op_512:
321             case op_c:
322                 assert(!"Can't happen: opType unexpected for valid ways to decode an immediate");
323                 return Expression::Ptr();
324             default:
325                 assert(!"Can't happen: opType out of range");
326                 return Expression::Ptr();
327         }
328     }
329     
330     Expression::Ptr InstructionDecoder_x86::getModRMDisplacement(const InstructionDecoder::buffer& b)
331     {
332         int disp_pos;
333
334         if(locs->sib_position != -1)
335         {
336             disp_pos = locs->sib_position + 1;
337         }
338         else
339         {
340             disp_pos = locs->modrm_position + 1;
341         }
342         switch(locs->modrm_mod)
343         {
344             case 1:
345                 return make_shared(singleton_object_pool<Immediate>::construct(Result(s8, (*(const byte_t*)(b.start +
346                         disp_pos)))));
347                 break;
348             case 2:
349                 if(sizePrefixPresent)
350                 {
351                     return make_shared(singleton_object_pool<Immediate>::construct(Result(s16, *((const word_t*)(b.start +
352                             disp_pos)))));
353                 }
354                 else
355                 {
356                     return make_shared(singleton_object_pool<Immediate>::construct(Result(s32, *((const dword_t*)(b.start +
357                             disp_pos)))));
358                 }
359                 break;
360             case 0:
361                 // In 16-bit mode, the word displacement is modrm r/m 6
362                 if(sizePrefixPresent)
363                 {
364                     if(locs->modrm_rm == 6)
365                     {
366                         return make_shared(singleton_object_pool<Immediate>::construct(Result(s16,
367                                            *((const dword_t*)(b.start + disp_pos)))));
368                     }
369                     // TODO FIXME; this was decoding wrong, but I'm not sure
370                     // why...
371                     else if (locs->modrm_rm == 5) {
372                         assert(b.start + disp_pos + 4 <= b.end);
373                         return make_shared(singleton_object_pool<Immediate>::construct(Result(s32,
374                                            *((const dword_t*)(b.start + disp_pos)))));
375                     } else {
376                         assert(b.start + disp_pos + 1 <= b.end);
377                         return make_shared(singleton_object_pool<Immediate>::construct(Result(s8, 0)));
378                     }
379                     break;
380                 }
381                 // ...and in 32-bit mode, the dword displacement is modrm r/m 5
382                 else
383                 {
384                     if(locs->modrm_rm == 5)
385                     {
386                         if (b.start + disp_pos + 4 <= b.end) 
387                             return make_shared(singleton_object_pool<Immediate>::construct(Result(s32,
388                                                *((const dword_t*)(b.start + disp_pos)))));
389                         else
390                             return make_shared(singleton_object_pool<Immediate>::construct(Result()));
391                     }
392                     else
393                     {
394                         if (b.start + disp_pos + 1 <= b.end)
395                             return make_shared(singleton_object_pool<Immediate>::construct(Result(s8, 0)));
396                         else
397                             return make_shared(singleton_object_pool<Immediate>::construct(Result()));
398                     }
399                     break;
400                 }
401             default:
402                 assert(b.start + disp_pos + 1 <= b.end);
403                 return make_shared(singleton_object_pool<Immediate>::construct(Result(s8, 0)));
404                 break;
405         }
406     }
407
408     enum intelRegBanks
409     {
410         b_8bitNoREX = 0,
411         b_16bit,
412         b_32bit,
413         b_segment,
414         b_64bit,
415         b_xmm,
416         b_xmmhigh,
417         b_mm,
418         b_cr,
419         b_dr,
420         b_tr,
421         b_amd64ext,
422         b_8bitWithREX,
423         b_fpstack,
424         amd64_ext_8,
425         amd64_ext_16,
426         amd64_ext_32
427     };
428     static MachRegister IntelRegTable32[][8] = {
429         {
430             x86::al, x86::cl, x86::dl, x86::bl, x86::ah, x86::ch, x86::dh, x86::bh
431         },
432         {
433             x86::ax, x86::cx, x86::dx, x86::bx, x86::sp, x86::bp, x86::si, x86::di
434         },
435         {
436             x86::eax, x86::ecx, x86::edx, x86::ebx, x86::esp, x86::ebp, x86::esi, x86::edi
437         },
438         {
439            x86::es, x86::cs, x86::ss, x86::ds, x86::fs, x86::gs, InvalidReg, InvalidReg
440         },
441         {
442             x86_64::rax, x86_64::rcx, x86_64::rdx, x86_64::rbx, x86_64::rsp, x86_64::rbp, x86_64::rsi, x86_64::rdi
443         },
444         {
445             x86::xmm0, x86::xmm1, x86::xmm2, x86::xmm3, x86::xmm4, x86::xmm5, x86::xmm6, x86::xmm7
446         },
447         {
448             x86_64::xmm8, x86_64::xmm9, x86_64::xmm10, x86_64::xmm11, x86_64::xmm12, x86_64::xmm13, x86_64::xmm14, x86_64::xmm15
449         },
450         {
451             x86::mm0, x86::mm1, x86::mm2, x86::mm3, x86::mm4, x86::mm5, x86::mm6, x86::mm7
452         },
453         {
454             x86::cr0, x86::cr1, x86::cr2, x86::cr3, x86::cr4, x86::cr5, x86::cr6, x86::cr7
455         },
456         {
457             x86::dr0, x86::dr1, x86::dr2, x86::dr3, x86::dr4, x86::dr5, x86::dr6, x86::dr7
458         },
459         {
460             x86::tr0, x86::tr1, x86::tr2, x86::tr3, x86::tr4, x86::tr5, x86::tr6, x86::tr7
461         },
462         {
463             x86_64::r8, x86_64::r9, x86_64::r10, x86_64::r11, x86_64::r12, x86_64::r13, x86_64::r14, x86_64::r15
464         },
465         {
466             x86_64::al, x86_64::cl, x86_64::dl, x86_64::bl, x86_64::spl, x86_64::bpl, x86_64::sil, x86_64::dil
467         },
468         {
469             x86::st0, x86::st1, x86::st2, x86::st3, x86::st4, x86::st5, x86::st6, x86::st7
470         }
471
472     };
473     static MachRegister IntelRegTable64[][8] = {
474         {
475             x86_64::al, x86_64::cl, x86_64::dl, x86_64::bl, x86_64::ah, x86_64::ch, x86_64::dh, x86_64::bh
476         },
477         {
478             x86_64::ax, x86_64::cx, x86_64::dx, x86_64::bx, x86_64::sp, x86_64::bp, x86_64::si, x86_64::di
479         },
480         {
481             x86_64::eax, x86_64::ecx, x86_64::edx, x86_64::ebx, x86_64::esp, x86_64::ebp, x86_64::esi, x86_64::edi
482         },
483         {
484             x86_64::es, x86_64::cs, x86_64::ss, x86_64::ds, x86_64::fs, x86_64::gs, InvalidReg, InvalidReg
485         },
486         {
487             x86_64::rax, x86_64::rcx, x86_64::rdx, x86_64::rbx, x86_64::rsp, x86_64::rbp, x86_64::rsi, x86_64::rdi
488         },
489         {
490             x86_64::xmm0, x86_64::xmm1, x86_64::xmm2, x86_64::xmm3, x86_64::xmm4, x86_64::xmm5, x86_64::xmm6, x86_64::xmm7
491         },
492         {
493             x86_64::xmm8, x86_64::xmm9, x86_64::xmm10, x86_64::xmm11, x86_64::xmm12, x86_64::xmm13, x86_64::xmm14, x86_64::xmm15
494         },
495         {
496             x86_64::mm0, x86_64::mm1, x86_64::mm2, x86_64::mm3, x86_64::mm4, x86_64::mm5, x86_64::mm6, x86_64::mm7
497         },
498         {
499             x86_64::cr0, x86_64::cr1, x86_64::cr2, x86_64::cr3, x86_64::cr4, x86_64::cr5, x86_64::cr6, x86_64::cr7
500         },
501         {
502             x86_64::dr0, x86_64::dr1, x86_64::dr2, x86_64::dr3, x86_64::dr4, x86_64::dr5, x86_64::dr6, x86_64::dr7
503         },
504         {
505             x86_64::tr0, x86_64::tr1, x86_64::tr2, x86_64::tr3, x86_64::tr4, x86_64::tr5, x86_64::tr6, x86_64::tr7
506         },
507         {
508             x86_64::r8, x86_64::r9, x86_64::r10, x86_64::r11, x86_64::r12, x86_64::r13, x86_64::r14, x86_64::r15
509         },
510         {
511             x86_64::al, x86_64::cl, x86_64::dl, x86_64::bl, x86_64::spl, x86_64::bpl, x86_64::sil, x86_64::dil
512         },
513         {
514             x86_64::st0, x86_64::st1, x86_64::st2, x86_64::st3, x86_64::st4, x86_64::st5, x86_64::st6, x86_64::st7
515         },
516         {
517             x86_64::r8b, x86_64::r9b, x86_64::r10b, x86_64::r11b, x86_64::r12b, x86_64::r13b, x86_64::r14b, x86_64::r15b 
518         },
519         {
520             x86_64::r8w, x86_64::r9w, x86_64::r10w, x86_64::r11w, x86_64::r12w, x86_64::r13w, x86_64::r14w, x86_64::r15w 
521         },
522         {
523             x86_64::r8d, x86_64::r9d, x86_64::r10d, x86_64::r11d, x86_64::r12d, x86_64::r13d, x86_64::r14d, x86_64::r15d 
524         },
525   {
526     x86_64::ymm0, x86_64::ymm1, x86_64::ymm2, x86_64::ymm3, x86_64::ymm4, x86_64::ymm5, x86_64::ymm6, x86_64::ymm7
527   },
528   {
529     x86_64::ymm8, x86_64::ymm9, x86_64::ymm10, x86_64::ymm11, x86_64::ymm12, x86_64::ymm13, x86_64::ymm14, x86_64::ymm15
530   }
531
532     };
533
534   /* Uses the appropriate lookup table based on the 
535      decoder architecture */
536   class IntelRegTable_access {
537     public:
538         inline MachRegister operator()(Architecture arch,
539                                        intelRegBanks bank,
540                                        int index)
541         {
542             assert(index >= 0 && index < 8);
543     
544             if(arch == Arch_x86_64)
545                 return IntelRegTable64[bank][index];
546             else if(arch == Arch_x86) 
547             {
548               if(bank > b_fpstack) return InvalidReg;
549               return IntelRegTable32[bank][index];
550             }
551             assert(0);
552             return InvalidReg;
553         }
554
555   };
556   static IntelRegTable_access IntelRegTable;
557
558       bool InstructionDecoder_x86::isDefault64Insn()
559       {
560         switch(m_Operation->getID())
561         {
562         case e_jmp:
563         case e_pop:
564         case e_push:
565         case e_call:
566           return true;
567         default:
568           return false;
569         }
570         
571       }
572       
573
574     MachRegister InstructionDecoder_x86::makeRegisterID(unsigned int intelReg, unsigned int opType,
575                                         bool isExtendedReg)
576     {
577         MachRegister retVal;
578         
579
580         if(isExtendedReg)
581         {
582             switch(opType)
583             {
584                 case op_q:  
585                     retVal = IntelRegTable(m_Arch,b_amd64ext,intelReg);
586                     break;
587                 case op_d:
588                     retVal = IntelRegTable(m_Arch,amd64_ext_32,intelReg);
589                     break;
590                 case op_w:
591                     retVal = IntelRegTable(m_Arch,amd64_ext_16,intelReg);
592                     break;
593                 case op_b:
594                     retVal = IntelRegTable(m_Arch,amd64_ext_8,intelReg);
595                     break;
596                 case op_v:
597                     if (locs->rex_w || isDefault64Insn())
598                         retVal = IntelRegTable(m_Arch, b_amd64ext, intelReg);
599                     else if (!sizePrefixPresent)
600                         retVal = IntelRegTable(m_Arch, amd64_ext_32, intelReg);
601                     else
602                         retVal = IntelRegTable(m_Arch, amd64_ext_16, intelReg);
603                     break;      
604                 case op_p:
605                 case op_z:
606                     if (!sizePrefixPresent)
607                         retVal = IntelRegTable(m_Arch, amd64_ext_32, intelReg);
608                     else
609                         retVal = IntelRegTable(m_Arch, amd64_ext_16, intelReg);
610                     break;
611                 default:
612                     retVal = InvalidReg;
613             }
614         }
615         /* Promotion to 64-bit only applies to the operand types
616            that are varible (c,v,z). Ignoring c and z because they
617            do the right thing on 32- and 64-bit code.
618         else if(locs->rex_w)
619         {
620             // AMD64 with 64-bit operands
621             retVal = IntelRegTable[b_64bit][intelReg];
622         }
623         */
624         else
625         {
626             switch(opType)
627             {
628                 case op_v:
629                   if(locs->rex_w || isDefault64Insn())
630                         retVal = IntelRegTable(m_Arch,b_64bit,intelReg);
631                     else
632                         retVal = IntelRegTable(m_Arch,b_32bit,intelReg);
633                     break;
634                 case op_b:
635                     if (locs->rex_position == -1) {
636                         retVal = IntelRegTable(m_Arch,b_8bitNoREX,intelReg);
637                     } else {
638                         retVal = IntelRegTable(m_Arch,b_8bitWithREX,intelReg);
639                     }
640                     break;
641                 case op_q:
642                     retVal = IntelRegTable(m_Arch,b_64bit,intelReg);
643                     break;
644                 case op_w:
645                     retVal = IntelRegTable(m_Arch,b_16bit,intelReg);
646                     break;
647                 case op_f:
648                 case op_dbl:
649                     retVal = IntelRegTable(m_Arch,b_fpstack,intelReg);
650                     break;
651                 case op_d:
652                 case op_si:
653                     retVal = IntelRegTable(m_Arch,b_32bit,intelReg);
654                     break;
655                 default:
656                     retVal = IntelRegTable(m_Arch,b_32bit,intelReg);
657                     break;
658             }
659         }
660
661         if (!ia32_is_mode_64()) {
662           if ((retVal.val() & 0x00ffffff) == 0x0001000c)
663             assert(0);
664         }
665
666         return MachRegister((retVal.val() & ~retVal.getArchitecture()) | m_Arch);
667     }
668     
669     Result_Type InstructionDecoder_x86::makeSizeType(unsigned int opType)
670     {
671         switch(opType)
672         {
673             case op_b:
674             case op_c:
675                 return u8;
676             case op_d:
677             case op_ss:
678             case op_allgprs:
679             case op_si:
680                 return u32;
681             case op_w:
682             case op_a:
683                 return u16;
684             case op_q:
685             case op_sd:
686                 return u64;
687             case op_v:
688             case op_lea:
689             case op_z:
690                 if (locs->rex_w) 
691                 {
692                     return u64;
693                 }
694               if(ia32_is_mode_64() || !sizePrefixPresent)
695                 {
696                     return u32;
697                 }
698                 else
699                 {
700                     return u16;
701                 }
702                 break;
703             case op_y:
704                 if(ia32_is_mode_64())
705                         return u64;
706                 else
707                         return u32;
708                 break;
709             case op_p:
710                 // book says operand size; arch-x86 says word + word * operand size
711                 if(!ia32_is_mode_64() ^ sizePrefixPresent)
712                 {
713                     return u48;
714                 }
715                 else
716                 {
717                     return u32;
718                 }
719             case op_dq:
720             case op_qq:
721                 return u64;
722             case op_512:
723                 return m512;
724             case op_pi:
725             case op_ps:
726             case op_pd:
727                 return dbl128;
728             case op_s:
729                 return u48;
730             case op_f:
731                 return sp_float;
732             case op_dbl:
733                 return dp_float;
734             case op_14:
735                 return m14;
736             default:
737                 assert(!"Can't happen!");
738                 return u8;
739         }
740     }
741
742
743     bool InstructionDecoder_x86::decodeOneOperand(const InstructionDecoder::buffer& b,
744                                                   const ia32_operand& operand,
745                                                   int & imm_index, /* immediate operand index */
746                                                   const Instruction* insn_to_complete, 
747                                                   bool isRead, bool isWritten)
748     {
749        bool isCFT = false;
750       bool isCall = false;
751       bool isConditional = false;
752       InsnCategory cat = insn_to_complete->getCategory();
753       if(cat == c_BranchInsn || cat == c_CallInsn)
754         {
755           isCFT = true;
756           if(cat == c_CallInsn)
757             {
758               isCall = true;
759             }
760         }
761       if (cat == c_BranchInsn && insn_to_complete->getOperation().getID() != e_jmp) {
762         isConditional = true;
763       }
764
765       unsigned int optype = operand.optype;
766       int vex_vvvv = 0;
767       // int vex_l = 0;
768     if(decodedInstruction && decodedInstruction->getPrefix()->vex_prefix[0])
769     {
770       /* The vvvv bits are bits 3, 4, 5, 6 and are in 1's complement */
771       if(decodedInstruction->getPrefix()->vex_prefix[1])
772       {
773         // vex_l = decodedInstruction->getPrefix()->vex_prefix[1] & VEX3_L;
774         vex_vvvv = (unsigned char)VEXGET_VVVV(decodedInstruction->getPrefix()->vex_prefix[1]);
775       } else {
776         // vex_l = decodedInstruction->getPrefix()->vex_prefix[0] & VEX2_L;
777         vex_vvvv = (unsigned char)VEXGET_VVVV(decodedInstruction->getPrefix()->vex_prefix[0]);
778       }
779
780       vex_vvvv = (unsigned char)((~vex_vvvv) & 0x0f);
781       if(vex_vvvv >= 0x0f)
782           vex_vvvv = -1;
783     }
784       if (sizePrefixPresent && 
785           ((optype == op_v) ||
786            (optype == op_z))) {
787         optype = op_w;
788       }
789       if(optype == op_y) {
790           if(ia32_is_mode_64() && locs->rex_w)
791                   optype = op_q;
792           else
793                   optype = op_d;
794       }
795                 switch(operand.admet)
796                 {
797                     case 0:
798                     // No operand
799                     {
800 /*                        fprintf(stderr, "ERROR: Instruction with mismatched operands. Raw bytes: ");
801                         for(unsigned int i = 0; i < decodedInstruction->getSize(); i++) {
802                             fprintf(stderr, "%x ", b.start[i]);
803                         }
804                         fprintf(stderr, "\n");*/
805                         assert(!"Mismatched number of operands--check tables");
806                         return false;
807                     }
808                     case am_A:
809                     {
810                         // am_A only shows up as a far call/jump.  Position 1 should be universally safe.
811                         Expression::Ptr addr(decodeImmediate(optype, b.start + 1));
812                         insn_to_complete->addSuccessor(addr, isCall, false, false, false);
813                     }
814                     break;
815                     case am_C:
816                     {
817                         Expression::Ptr op(makeRegisterExpression(IntelRegTable(m_Arch,b_cr,locs->modrm_reg)));
818                         insn_to_complete->appendOperand(op, isRead, isWritten);
819                     }
820                     break;
821                     case am_D:
822                     {
823                         Expression::Ptr op(makeRegisterExpression(IntelRegTable(m_Arch,b_dr,locs->modrm_reg)));
824                         insn_to_complete->appendOperand(op, isRead, isWritten);
825                     }
826                     break;
827                     case am_E:
828                     // am_M is like am_E, except that mod of 0x03 should never occur (am_M specified memory,
829                     // mod of 0x03 specifies direct register access).
830                     case am_M:
831                     // am_R is the inverse of am_M; it should only have a mod of 3
832                     case am_R:
833                     // can be am_R or am_M      
834                     case am_RM: 
835                         if(isCFT)
836                         {
837                           insn_to_complete->addSuccessor(makeModRMExpression(b, optype), isCall, true, false, false);
838                         }
839                         else
840                         {
841                           insn_to_complete->appendOperand(makeModRMExpression(b, optype), isRead, isWritten);
842                         }
843                     break;
844                     case am_F:
845                     {
846                         Expression::Ptr op(makeRegisterExpression(x86::flags));
847                         insn_to_complete->appendOperand(op, isRead, isWritten);
848                     }
849                     break;
850                     case am_G:
851                     {
852                         Expression::Ptr op(makeRegisterExpression(makeRegisterID(locs->modrm_reg,
853                                 optype, locs->rex_r)));
854                         insn_to_complete->appendOperand(op, isRead, isWritten);
855                     }
856                     break;
857                     case am_H:
858                       {
859                         if(vex_vvvv < 0)
860                         {
861                           printf("BAD VVVV: 0x%x\n", vex_vvvv);
862                           assert(0);
863                           break; /* Invalid instruction */
864                         }
865                           /* Operand comes from the VEX.vvvv bits */
866                          insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,
867                               vex_vvvv <= 7 ? b_xmm : b_xmmhigh, vex_vvvv <= 7 ? vex_vvvv : vex_vvvv - 8)),
868                               isRead, isWritten);
869                       }
870                       break;
871                     case am_I:
872                         insn_to_complete->appendOperand(decodeImmediate(optype, b.start + 
873                                                                         locs->imm_position[imm_index++]), 
874                                                         isRead, isWritten);
875                         break;
876                     case am_J:
877                     {
878                         Expression::Ptr Offset(decodeImmediate(optype, 
879                                                                b.start + locs->imm_position[imm_index++], 
880                                                                true));
881                         Expression::Ptr EIP(makeRegisterExpression(MachRegister::getPC(m_Arch)));
882                         Expression::Ptr InsnSize(make_shared(singleton_object_pool<Immediate>::construct(Result(u8,
883                             decodedInstruction->getSize()))));
884                         Expression::Ptr postEIP(makeAddExpression(EIP, InsnSize, u32));
885
886                         Expression::Ptr op(makeAddExpression(Offset, postEIP, u32));
887                         insn_to_complete->addSuccessor(op, isCall, false, isConditional, false);
888                         if (isConditional) 
889                           insn_to_complete->addSuccessor(postEIP, false, false, true, true);
890                     }
891                     break;
892                     case am_O:
893                     {
894                     // Address/offset width, which is *not* what's encoded by the optype...
895                     // The deref's width is what's actually encoded here.
896                         int pseudoOpType;
897                         switch(locs->address_size)
898                         {
899                             case 1:
900                                 pseudoOpType = op_b;
901                                 break;
902                             case 2:
903                                 pseudoOpType = op_w;
904                                 break;
905                             case 4:
906                                 pseudoOpType = op_d;
907                                 break;
908                             case 0:
909                                 // closest I can get to "will be address size by default"
910                                 pseudoOpType = op_v;
911                                 break;
912                             default:
913                                 assert(!"Bad address size, should be 0, 1, 2, or 4!");
914                                 pseudoOpType = op_b;
915                                 break;
916                         }
917
918
919                         int offset_position = locs->opcode_position;
920                         if(locs->modrm_position > offset_position && locs->modrm_operand <
921                            (int)(insn_to_complete->m_Operands.size()))
922                         {
923                             offset_position = locs->modrm_position;
924                         }
925                         if(locs->sib_position > offset_position)
926                         {
927                             offset_position = locs->sib_position;
928                         }
929                         offset_position++;
930                         insn_to_complete->appendOperand(makeDereferenceExpression(
931                                 decodeImmediate(pseudoOpType, b.start + offset_position), makeSizeType(optype)), 
932                                                         isRead, isWritten);
933                     }
934                     break;
935                     case am_P:
936                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,b_mm,locs->modrm_reg)),
937                                 isRead, isWritten);
938                         break;
939                     case am_Q:
940         
941                         switch(locs->modrm_mod)
942                         {
943                             // direct dereference
944                             case 0x00:
945                             case 0x01:
946                             case 0x02:
947                               insn_to_complete->appendOperand(makeModRMExpression(b, optype), isRead, isWritten);
948                                 break;
949                             case 0x03:
950                                 // use of actual register
951                                 insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,b_mm,locs->modrm_rm)),
952                                                                isRead, isWritten);
953                                 break;
954                             default:
955                                 assert(!"2-bit value modrm_mod out of range");
956                                 break;
957                         };
958                         break;
959                     case am_S:
960                     // Segment register in modrm reg field.
961                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,b_segment,locs->modrm_reg)),
962                                 isRead, isWritten);
963                         break;
964                     case am_T:
965                         // test register in modrm reg; should only be tr6/tr7, but we'll decode any of them
966                         // NOTE: this only appears in deprecated opcodes
967                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,b_tr,locs->modrm_reg)),
968                                                        isRead, isWritten);
969                         break;
970                     case am_UM:
971                         switch(locs->modrm_mod)
972                         {
973                         // direct dereference
974                         case 0x00:
975                         case 0x01:
976                         case 0x02:
977                                 insn_to_complete->appendOperand(makeModRMExpression(b, makeSizeType(optype)),
978                                                 isRead, isWritten);
979                                 break;
980                         case 0x03:
981                                 // use of actual register
982                                 {
983                                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,
984                                                         locs->rex_b ? b_xmmhigh : b_xmm, locs->modrm_rm)),
985                                                         isRead, isWritten);
986                                         break;
987                                 }
988                         default:
989                                 assert(!"2-bit value modrm_mod out of range");
990                                 break;
991                         };
992                         break;
993                     case am_V:
994                        
995                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,
996                                 locs->rex_r ? b_xmmhigh : b_xmm,locs->modrm_reg)),
997                                     isRead, isWritten);
998                         break;
999                     case am_U:
1000                         insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,
1001                                         locs->rex_b ? b_xmmhigh : b_xmm, locs->modrm_rm)),
1002                                         isRead, isWritten);
1003                         break;
1004                     case am_W:
1005                         switch(locs->modrm_mod)
1006                         {
1007                             // direct dereference
1008                             case 0x00:
1009                             case 0x01:
1010                             case 0x02:
1011                               insn_to_complete->appendOperand(makeModRMExpression(b, makeSizeType(optype)),
1012                                                                isRead, isWritten);
1013                                 break;
1014                             case 0x03:
1015                             // use of actual register
1016                             {
1017                                 insn_to_complete->appendOperand(makeRegisterExpression(IntelRegTable(m_Arch,
1018                                         locs->rex_b ? b_xmmhigh : b_xmm, locs->modrm_rm)),
1019                                         isRead, isWritten);
1020                                 break;
1021                             }
1022                             default:
1023                                 assert(!"2-bit value modrm_mod out of range");
1024                                 break;
1025                         };
1026                         break;
1027                     case am_X:
1028                     {
1029                         MachRegister si_reg;
1030                         if(m_Arch == Arch_x86)
1031                         {
1032                                 if(addrSizePrefixPresent)
1033                                 {
1034                                         si_reg = x86::si;
1035                                 } else
1036                                 {
1037                                         si_reg = x86::esi;
1038                                 }
1039                         }
1040                         else
1041                         {
1042                                 if(addrSizePrefixPresent)
1043                                 {
1044                                         si_reg = x86_64::esi;
1045                                 } else
1046                                 {
1047                                         si_reg = x86_64::rsi;
1048                                 }
1049                         }
1050                         Expression::Ptr ds(makeRegisterExpression(m_Arch == Arch_x86 ? x86::ds : x86_64::ds));
1051                         Expression::Ptr si(makeRegisterExpression(si_reg));
1052                         Expression::Ptr segmentOffset(make_shared(singleton_object_pool<Immediate>::construct(
1053                                 Result(u32, 0x10))));
1054                         Expression::Ptr ds_segment = makeMultiplyExpression(ds, segmentOffset, u32);
1055                         Expression::Ptr ds_si = makeAddExpression(ds_segment, si, u32);
1056                         insn_to_complete->appendOperand(makeDereferenceExpression(ds_si, makeSizeType(optype)),
1057                                                        isRead, isWritten);
1058                     }
1059                     break;
1060                     case am_Y:
1061                     {
1062                         MachRegister di_reg;
1063                         if(m_Arch == Arch_x86)
1064                         {
1065                                 if(addrSizePrefixPresent)
1066                                 {
1067                                         di_reg = x86::di;
1068                                 } else
1069                                 {
1070                                         di_reg = x86::edi;
1071                                 }
1072                         }
1073                         else
1074                         {
1075                                 if(addrSizePrefixPresent)
1076                                 {
1077                                         di_reg = x86_64::edi;
1078                                 } else
1079                                 {
1080                                         di_reg = x86_64::rdi;
1081                                 }
1082                         }
1083                         Expression::Ptr es(makeRegisterExpression(m_Arch == Arch_x86 ? x86::es : x86_64::es));
1084                         Expression::Ptr di(makeRegisterExpression(di_reg));
1085                         Expression::Ptr es_segment = makeMultiplyExpression(es,
1086                             make_shared(singleton_object_pool<Immediate>::construct(Result(u32, 0x10))), u32);
1087                         Expression::Ptr es_di = makeAddExpression(es_segment, di, u32);
1088                         insn_to_complete->appendOperand(makeDereferenceExpression(es_di, makeSizeType(optype)),
1089                                                        isRead, isWritten);
1090                     }
1091                     break;
1092                     case am_tworeghack:
1093                     {
1094                         if(optype == op_edxeax)
1095                         {
1096                             Expression::Ptr edx(makeRegisterExpression(m_Arch == Arch_x86 ? x86::edx : x86_64::edx));
1097                             Expression::Ptr eax(makeRegisterExpression(m_Arch == Arch_x86 ? x86::eax : x86_64::eax));
1098                             Expression::Ptr highAddr = makeMultiplyExpression(edx,
1099                                     Immediate::makeImmediate(Result(u64, 2^32)), u64);
1100                             Expression::Ptr addr = makeAddExpression(highAddr, eax, u64);
1101                             Expression::Ptr op = makeDereferenceExpression(addr, u64);
1102                             insn_to_complete->appendOperand(op, isRead, isWritten);
1103                         }
1104                         else if (optype == op_ecxebx)
1105                         {
1106                             Expression::Ptr ecx(makeRegisterExpression(m_Arch == Arch_x86 ? x86::ecx : x86_64::ecx));
1107                             Expression::Ptr ebx(makeRegisterExpression(m_Arch == Arch_x86 ? x86::ebx : x86_64::ebx));
1108                             Expression::Ptr highAddr = makeMultiplyExpression(ecx,
1109                                     Immediate::makeImmediate(Result(u64, 2^32)), u64);
1110                             Expression::Ptr addr = makeAddExpression(highAddr, ebx, u64);
1111                             Expression::Ptr op = makeDereferenceExpression(addr, u64);
1112                             insn_to_complete->appendOperand(op, isRead, isWritten);
1113                         }
1114                     }
1115                     break;
1116                     
1117                     case am_reg:
1118                     {
1119                         MachRegister r(optype);
1120                         r = MachRegister((r.val() & ~r.getArchitecture()) | m_Arch);
1121                         entryID entryid = decodedInstruction->getEntry()->getID(locs);
1122                         if(locs->rex_b && insn_to_complete->m_Operands.empty() && 
1123                             (entryid == e_push || entryid == e_pop || entryid == e_xchg || ((*(b.start + locs->opcode_position) & 0xf0) == 0xb0) ) )
1124                         {
1125                             // FP stack registers are not affected by the rex_b bit in AM_REG.
1126                            if(r.regClass() != (unsigned) x86::MMX)
1127                             {
1128                                 r = MachRegister((r.val()) | x86_64::r8.val());
1129                             }
1130                         }
1131                         if(sizePrefixPresent)
1132                         {
1133                             r = MachRegister((r.val() & ~x86::FULL) | x86::W_REG);
1134                         }
1135                         Expression::Ptr op(makeRegisterExpression(r));
1136                         insn_to_complete->appendOperand(op, isRead, isWritten);
1137                     }
1138                     break;
1139                 case am_stackH:
1140                 case am_stackP:
1141                 // handled elsewhere
1142                     break;
1143                 case am_allgprs:
1144                 {
1145                     if(m_Arch == Arch_x86)
1146                     {
1147                         insn_to_complete->appendOperand(makeRegisterExpression(x86::eax), isRead, isWritten);
1148                         insn_to_complete->appendOperand(makeRegisterExpression(x86::ecx), isRead, isWritten);
1149                         insn_to_complete->appendOperand(makeRegisterExpression(x86::edx), isRead, isWritten);
1150                         insn_to_complete->appendOperand(makeRegisterExpression(x86::ebx), isRead, isWritten);
1151                         insn_to_complete->appendOperand(makeRegisterExpression(x86::esp), isRead, isWritten);
1152                         insn_to_complete->appendOperand(makeRegisterExpression(x86::ebp), isRead, isWritten);
1153                         insn_to_complete->appendOperand(makeRegisterExpression(x86::esi), isRead, isWritten);
1154                         insn_to_complete->appendOperand(makeRegisterExpression(x86::edi), isRead, isWritten);
1155                     }
1156                     else
1157                     {
1158                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::eax), isRead, isWritten);
1159                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::ecx), isRead, isWritten);
1160                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::edx), isRead, isWritten);
1161                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::ebx), isRead, isWritten);
1162                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::esp), isRead, isWritten);
1163                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::ebp), isRead, isWritten);
1164                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::esi), isRead, isWritten);
1165                         insn_to_complete->appendOperand(makeRegisterExpression(x86_64::edi), isRead, isWritten);
1166                     }
1167                 }
1168                     break;
1169                 case am_ImplImm: {
1170                   insn_to_complete->appendOperand(Immediate::makeImmediate(Result(makeSizeType(optype), 1)), isRead, isWritten);
1171                   break;
1172                 }
1173
1174                 default:
1175                     printf("decodeOneOperand() called with unknown addressing method %d\n", operand.admet);
1176                         break;
1177                 };
1178                 return true;
1179             }
1180
1181     extern ia32_entry invalid;
1182     
1183     void InstructionDecoder_x86::doIA32Decode(InstructionDecoder::buffer& b)
1184     {
1185         if(decodedInstruction == NULL)
1186         {
1187             decodedInstruction = reinterpret_cast<ia32_instruction*>(malloc(sizeof(ia32_instruction)));
1188             assert(decodedInstruction);
1189         }
1190         if(locs == NULL)
1191         {
1192             locs = reinterpret_cast<ia32_locations*>(malloc(sizeof(ia32_locations)));
1193             assert(locs);
1194         }
1195         locs = new(locs) ia32_locations; //reinit();
1196         assert(locs->sib_position == -1);
1197         decodedInstruction = new (decodedInstruction) ia32_instruction(NULL, NULL, locs);
1198         ia32_decode(IA32_DECODE_PREFIXES, b.start, *decodedInstruction);
1199         sizePrefixPresent = (decodedInstruction->getPrefix()->getOperSzPrefix() == 0x66);
1200         if (decodedInstruction->getPrefix()->rexW()) {
1201            // as per 2.2.1.2 - rex.w overrides 66h
1202            sizePrefixPresent = false;
1203         }
1204         addrSizePrefixPresent = (decodedInstruction->getPrefix()->getAddrSzPrefix() == 0x67);
1205         static ia32_entry invalid = { e_No_Entry, 0, 0, true, { {0,0}, {0,0}, {0,0} }, 0, 0 };
1206         if(decodedInstruction->getEntry()) {
1207             m_Operation = make_shared(singleton_object_pool<Operation>::construct(decodedInstruction->getEntry(),
1208                                     decodedInstruction->getPrefix(), locs, m_Arch));
1209             
1210         }
1211         else
1212         {
1213                 // Gap parsing can trigger this case; in particular, when it encounters prefixes in an invalid order.
1214                 // Notably, if a REX prefix (0x40-0x48) appears followed by another prefix (0x66, 0x67, etc)
1215                 // we'll reject the instruction as invalid and send it back with no entry.  Since this is a common
1216                 // byte sequence to see in, for example, ASCII strings, we want to simply accept this and move on, not
1217                 // yell at the user.
1218             m_Operation = make_shared(singleton_object_pool<Operation>::construct(&invalid,
1219                                     decodedInstruction->getPrefix(), locs, m_Arch));
1220         }
1221
1222     }
1223     
1224     void InstructionDecoder_x86::decodeOpcode(InstructionDecoder::buffer& b)
1225     {
1226         doIA32Decode(b);
1227         b.start += decodedInstruction->getSize();
1228     }
1229     
1230       bool InstructionDecoder_x86::decodeOperands(const Instruction* insn_to_complete)
1231     {
1232        int imm_index = 0; // handle multiple immediate operands
1233         if(!decodedInstruction) return false;
1234         unsigned int opsema = decodedInstruction->getEntry()->opsema & 0xFF;
1235         InstructionDecoder::buffer b(insn_to_complete->ptr(), insn_to_complete->size());
1236
1237         if (decodedInstruction->getEntry()->getID() == e_ret_near ||
1238             decodedInstruction->getEntry()->getID() == e_ret_far) {
1239            Expression::Ptr ret_addr = makeDereferenceExpression(makeRegisterExpression(ia32_is_mode_64() ? x86_64::rsp : x86::esp), 
1240                                                                 ia32_is_mode_64() ? u64 : u32);
1241            insn_to_complete->addSuccessor(ret_addr, false, true, false, false);
1242         }
1243
1244         for(int i = 0; i < 3; i++)
1245         {
1246             if(decodedInstruction->getEntry()->operands[i].admet == 0 && 
1247                decodedInstruction->getEntry()->operands[i].optype == 0)
1248                 return true;
1249             if(!decodeOneOperand(b,
1250                                  decodedInstruction->getEntry()->operands[i], 
1251                                  imm_index, 
1252                                  insn_to_complete, 
1253                                  readsOperand(opsema, i),
1254                                  writesOperand(opsema, i)))
1255             {
1256                 return false;
1257             }
1258         }
1259
1260         /* Does this instruction have a 4th operand? */
1261         if(decodedInstruction->getEntry()->opsema >= s4OP)
1262         {
1263           if(!decodeOneOperand(b,
1264             {am_I, op_b}, /* This is always an IMM8 */
1265             imm_index,
1266             insn_to_complete,
1267             readsOperand(opsema, 3),
1268             writesOperand(opsema, 3)))
1269             {
1270                 return false;
1271             }
1272         }
1273     
1274         return true;
1275     }
1276
1277     
1278       INSTRUCTION_EXPORT Instruction::Ptr InstructionDecoder_x86::decode(InstructionDecoder::buffer& b)
1279     {
1280         return InstructionDecoderImpl::decode(b);
1281     }
1282     void InstructionDecoder_x86::doDelayedDecode(const Instruction* insn_to_complete)
1283     {
1284       InstructionDecoder::buffer b(insn_to_complete->ptr(), insn_to_complete->size());
1285       //insn_to_complete->m_Operands.reserve(4);
1286       doIA32Decode(b);        
1287       decodeOperands(insn_to_complete);
1288     }
1289     
1290 };
1291 };
1292