2015-05-24 06:55:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Copyright 2008 Dolphin Emulator Project
  
						 
					
						
							
								
									
										
										
										
											2015-05-18 01:08:10 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Licensed under GPLv2+
  
						 
					
						
							
								
									
										
										
										
											2013-04-17 23:09:55 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Refer to the license.txt file included.
  
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2013-10-26 11:55:41 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  <cinttypes> 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-07 20:06:58 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "Common/CommonTypes.h" 
  
						 
					
						
							
								
									
										
										
										
											2014-02-17 05:18:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "Common/CPUDetect.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "Common/x64Emitter.h" 
  
						 
					
						
							
								
									
										
										
										
											2014-06-05 19:29:54 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "Common/Logging/Log.h" 
  
						 
					
						
							
								
									
										
										
										
											2014-02-17 05:18:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								namespace  Gen  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// TODO(ector): Add EAX special casing, for ever so slightly smaller code.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								struct  NormalOpDef  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									u8  toRm8 ,  toRm32 ,  fromRm8 ,  fromRm32 ,  imm8 ,  imm32 ,  simm8 ,  eaximm8 ,  eaximm32 ,  ext ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// 0xCC is code for invalid combination of immediates
  
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  const  NormalOpDef  normalops [ 11 ]  =  
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x00 ,  0x01 ,  0x02 ,  0x03 ,  0x80 ,  0x81 ,  0x83 ,  0x04 ,  0x05 ,  0 } ,  //ADD
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 0x10 ,  0x11 ,  0x12 ,  0x13 ,  0x80 ,  0x81 ,  0x83 ,  0x14 ,  0x15 ,  2 } ,  //ADC
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x28 ,  0x29 ,  0x2A ,  0x2B ,  0x80 ,  0x81 ,  0x83 ,  0x2C ,  0x2D ,  5 } ,  //SUB
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 0x18 ,  0x19 ,  0x1A ,  0x1B ,  0x80 ,  0x81 ,  0x83 ,  0x1C ,  0x1D ,  3 } ,  //SBB
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x20 ,  0x21 ,  0x22 ,  0x23 ,  0x80 ,  0x81 ,  0x83 ,  0x24 ,  0x25 ,  4 } ,  //AND
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 0x08 ,  0x09 ,  0x0A ,  0x0B ,  0x80 ,  0x81 ,  0x83 ,  0x0C ,  0x0D ,  1 } ,  //OR
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x30 ,  0x31 ,  0x32 ,  0x33 ,  0x80 ,  0x81 ,  0x83 ,  0x34 ,  0x35 ,  6 } ,  //XOR
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 0x88 ,  0x89 ,  0x8A ,  0x8B ,  0xC6 ,  0xC7 ,  0xCC ,  0xCC ,  0xCC ,  0 } ,  //MOV
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x84 ,  0x85 ,  0x84 ,  0x85 ,  0xF6 ,  0xF7 ,  0xCC ,  0xA8 ,  0xA9 ,  0 } ,  //TEST (to == from)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 0x38 ,  0x39 ,  0x3A ,  0x3B ,  0x80 ,  0x81 ,  0x83 ,  0x3C ,  0x3D ,  7 } ,  //CMP
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 0x86 ,  0x87 ,  0x86 ,  0x87 ,  0xCC ,  0xCC ,  0xCC ,  0xCC ,  0xCC ,  7 } ,  //XCHG
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								enum  NormalSSEOps  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-09-18 07:43:31 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseCMP          =  0xC2 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseADD          =  0x58 ,  //ADD
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseSUB          =  0x5C ,  //SUB
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseAND          =  0x54 ,  //AND
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseANDN         =  0x55 ,  //ANDN
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseOR           =  0x56 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseXOR          =  0x57 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMUL          =  0x59 ,  //MUL
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseDIV          =  0x5E ,  //DIV
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMIN          =  0x5D ,  //MIN
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMAX          =  0x5F ,  //MAX
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseCOMIS        =  0x2F ,  //COMIS
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseUCOMIS       =  0x2E ,  //UCOMIS
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseSQRT         =  0x51 ,  //SQRT
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseRSQRT        =  0x52 ,  //RSQRT (NO DOUBLE PRECISION!!!)
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVAPfromRM  =  0x28 ,  //MOVAP from RM
 
							 
						 
					
						
							
								
									
										
										
										
											2013-09-18 07:43:31 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVAPtoRM    =  0x29 ,  //MOVAP to RM
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVUPfromRM  =  0x10 ,  //MOVUP from RM
 
							 
						 
					
						
							
								
									
										
										
										
											2013-09-18 07:43:31 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVUPtoRM    =  0x11 ,  //MOVUP to RM
 
							 
						 
					
						
							
								
									
										
										
										
											2015-01-07 11:09:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVLPfromRM  =  0x12 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVLPtoRM    =  0x13 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVHPfromRM  =  0x16 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVHPtoRM    =  0x17 , 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-18 03:57:13 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVHLPS      =  0x12 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVLHPS      =  0x16 , 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-10 17:56:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVDQfromRM  =  0x6F , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVDQtoRM    =  0x7F , 
							 
						 
					
						
							
								
									
										
										
										
											2013-09-18 07:43:31 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMASKMOVDQU   =  0xF7 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseLDDQU        =  0xF0 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseSHUF         =  0xC6 , 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sseMOVNTDQ      =  0xE7 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sseMOVNTP       =  0x2B , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SetCodePtr ( u8 *  ptr )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									code  =  ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								const  u8 *  XEmitter : : GetCodePtr ( )  const  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  code ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								u8 *  XEmitter : : GetWritableCodePtr ( )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  code ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ReserveCodeSpace ( int  bytes )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  bytes ;  i + + ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										* code + +  =  0xCC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								const  u8 *  XEmitter : : AlignCode4 ( )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  c  =  int ( ( u64 ) code  &  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( c ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ReserveCodeSpace ( 4 - c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  code ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								const  u8 *  XEmitter : : AlignCode16 ( )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  c  =  int ( ( u64 ) code  &  15 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( c ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ReserveCodeSpace ( 16 - c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  code ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								const  u8 *  XEmitter : : AlignCodePage ( )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  c  =  int ( ( u64 ) code  &  4095 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( c ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ReserveCodeSpace ( 4096 - c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  code ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// This operation modifies flags; check to see the flags are locked.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// If the flags are locked, we should immediately and loudly fail before
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// causing a subtle JIT bug.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CheckFlags ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! flags_locked ,  " Attempt to modify flags while flags locked! " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 17:33:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteModRM ( int  mod ,  int  reg ,  int  rm )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-01-25 17:33:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( ( u8 ) ( ( mod  < <  6 )  |  ( ( reg  &  7 )  < <  3 )  |  ( rm  &  7 ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteSIB ( int  scale ,  int  index ,  int  base )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( ( u8 ) ( ( scale  < <  6 )  |  ( ( index  &  7 )  < <  3 )  |  ( base  &  7 ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  OpArg : : WriteREX ( XEmitter *  emit ,  int  opBits ,  int  bits ,  int  customOp )  const  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( customOp  = =  - 1 )        customOp  =  operandReg ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									u8  op  =  0x40 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-25 13:50:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// REX.W (whether operation is a 64-bit operation)
 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( opBits  = =  64 )          op  | =  8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-25 13:50:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// REX.R (whether ModR/M reg field refers to R8-R15.
 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( customOp  &  8 )          op  | =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-25 13:50:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// REX.X (whether ModR/M SIB index field refers to R8-R15)
 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( indexReg  &  8 )          op  | =  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-25 13:50:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// REX.B (whether ModR/M rm or SIB base or opcode reg field refers to R8-R15)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( offsetOrBaseReg  &  8 )   op  | =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Write REX if wr have REX bits to write, or if the operation accesses
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// SIL, DIL, BPL, or SPL.
 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( op  ! =  0x40  | | 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									    ( scale  = =  SCALE_NONE  & &  bits  = =  8  & &  ( offsetOrBaseReg  &  0x10c )  = =  4 )  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									    ( opBits  = =  8  & &  ( customOp  &  0x10c )  = =  4 ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write8 ( op ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-25 13:50:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Check the operation doesn't access AH, BH, CH, or DH.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_dbg_assert_ ( DYNA_REC ,  ( offsetOrBaseReg  &  0x100 )  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_dbg_assert_ ( DYNA_REC ,  ( customOp  &  0x100 )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:38:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  OpArg : : WriteVEX ( XEmitter *  emit ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  int  L ,  int  pp ,  int  mmmmm ,  int  W )  const  
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  R  =  ! ( regOp1  &  8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  X  =  ! ( indexReg  &  8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  B  =  ! ( offsetOrBaseReg  &  8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  vvvv  =  ( regOp2  = =  X64Reg : : INVALID_REG )  ?  0xf  :  ( regOp2  ^  0xf ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// do we need any VEX fields that only appear in the three-byte form?
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( X  = =  1  & &  B  = =  1  & &  W  = =  0  & &  mmmmm  = =  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-20 09:33:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										u8  RvvvvLpp  =  ( R  < <  7 )  |  ( vvvv  < <  3 )  |  ( L  < <  2 )  |  pp ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write8 ( 0xC5 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( RvvvvLpp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										u8  RXBmmmmm  =  ( R  < <  7 )  |  ( X  < <  6 )  |  ( B  < <  5 )  |  mmmmm ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-20 09:33:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										u8  WvvvvLpp  =  ( W  < <  7 )  |  ( vvvv  < <  3 )  |  ( L  < <  2 )  |  pp ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write8 ( 0xC4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( RXBmmmmm ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( WvvvvLpp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  OpArg : : WriteRest ( XEmitter *  emit ,  int  extraBytes ,  X64Reg  _operandReg ,  
						 
					
						
							
								
									
										
										
										
											2013-09-18 07:43:31 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  warn_64bit_offset )  const 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( _operandReg  = =  INVALID_REG ) 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_operandReg  =  ( X64Reg ) this - > operandReg ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mod  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ireg  =  indexReg ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  SIB  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  _offsetOrBaseReg  =  this - > offsetOrBaseReg ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( scale  = =  SCALE_RIP )  //Also, on 32-bit, just an immediate address
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Oh, RIP addressing.
 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_offsetOrBaseReg  =  5 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > WriteModRM ( 0 ,  _operandReg ,  _offsetOrBaseReg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//TODO : add some checks
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										u64  ripAddr  =  ( u64 ) emit - > GetCodePtr ( )  +  4  +  extraBytes ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-09-26 19:37:30 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s64  distance  =  ( s64 ) offset  -  ( s64 ) ripAddr ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-29 11:05:44 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC , 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-11 00:30:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										             ( distance  <  0x80000000LL  & & 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										              distance  > =   - 0x80000000LL )  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             ! warn_64bit_offset , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             " WriteRest: op out of range (0x% "  PRIx64  "  uses 0x% "  PRIx64  " ) " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             ripAddr ,  offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-09-26 19:37:30 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s32  offs  =  ( s32 ) distance ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write32 ( ( u32 ) offs ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( scale  = =  0 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Oh, no memory, Just a reg.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mod  =  3 ;  //11
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-17 00:49:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//Ah good, no scaling.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( scale  = =  SCALE_ATREG  & &  ! ( ( _offsetOrBaseReg  &  7 )  = =  4  | |  ( _offsetOrBaseReg  &  7 )  = =  5 ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											//Okay, we're good. No SIB necessary.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  ioff  =  ( int ) offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ioff  = =  0 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mod  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											else  if  ( ioff < - 128  | |  ioff > 127 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mod  =  2 ;  //32-bit displacement
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mod  =  1 ;  //8-bit displacement
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2011-06-29 22:40:01 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else  if  ( scale  > =  SCALE_NOBASE_2  & &  scale  < =  SCALE_NOBASE_8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											SIB  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mod  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_offsetOrBaseReg  =  5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-17 00:49:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ( _offsetOrBaseReg  &  7 )  = =  4 )  //this would occupy the SIB encoding :(
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												//So we have to fake it with SIB encoding :(
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												SIB  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( scale  > =  SCALE_1  & &  scale  <  SCALE_ATREG ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												SIB  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( scale  = =  SCALE_ATREG  & &  ( ( _offsetOrBaseReg  &  7 )  = =  4 ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												SIB  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ireg  =  _offsetOrBaseReg ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											//Okay, we're fine. Just disp encoding.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											//We need displacement. Which size?
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  ioff  =  ( int ) ( s64 ) offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ioff  <  - 128  | |  ioff  >  127 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mod  =  2 ;  //32-bit displacement
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mod  =  1 ;  //8-bit displacement
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Okay. Time to do the actual writing
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// ModRM byte:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  oreg  =  _offsetOrBaseReg ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( SIB ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										oreg  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									emit - > WriteModRM ( mod ,  _operandReg & 7 ,  oreg & 7 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( SIB ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//SIB byte
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  ss ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										switch  ( scale ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  SCALE_NONE :  _offsetOrBaseReg  =  4 ;  ss  =  0 ;  break ;  //RSP
 
							 
						 
					
						
							
								
									
										
										
										
											2011-06-29 22:40:01 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  SCALE_1 :  ss  =  0 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_2 :  ss  =  1 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_4 :  ss  =  2 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_8 :  ss  =  3 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_NOBASE_2 :  ss  =  1 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_NOBASE_4 :  ss  =  2 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  SCALE_NOBASE_8 :  ss  =  3 ;  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  SCALE_ATREG :  ss  =  0 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default :  _assert_msg_ ( DYNA_REC ,  0 ,  " Invalid scale for SIB byte " ) ;  ss  =  0 ;  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write8 ( ( u8 ) ( ( ss  < <  6 )  |  ( ( ireg & 7 ) < < 3 )  |  ( _offsetOrBaseReg & 7 ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( mod  = =  1 )  //8-bit disp
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										emit - > Write8 ( ( u8 ) ( s8 ) ( s32 ) offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2011-06-29 22:40:01 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( mod  = =  2  | |  ( scale  > =  SCALE_NOBASE_2  & &  scale  < =  SCALE_NOBASE_8 ) )  //32-bit disp
 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write32 ( ( u32 ) offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// W = operand extended width (1 if 64-bit)
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// R = register# upper bit
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// X = scale amnt upper bit
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// B = base register# upper bit
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : Rex ( int  w ,  int  r ,  int  x ,  int  b )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									w  =  w  ?  1  :  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									r  =  r  ?  1  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									x  =  x  ?  1  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									b  =  b  ?  1  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									u8  rx  =  ( u8 ) ( 0x40  |  ( w  < <  3 )  |  ( r  < <  2 )  |  ( x  < <  1 )  |  ( b ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( rx  ! =  0x40 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( rx ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : JMP ( const  u8 *  addr ,  bool  force5Bytes )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									u64  fn  =  ( u64 ) addr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! force5Bytes ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s64  distance  =  ( s64 ) ( fn  -  ( ( u64 ) code  +  2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  distance  > =  - 0x80  & &  distance  <  0x80 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											     " Jump target too far away, needs force5Bytes = true " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//8 bits will do
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xEB ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( ( u8 ) ( s8 ) distance ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s64  distance  =  ( s64 ) ( fn  -  ( ( u64 ) code  +  5 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-12-16 22:38:31 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-03-11 00:30:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             distance  > =  - 0x80000000LL  & &  distance  <  0x80000000LL , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             " Jump target too far away, needs indirect register " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xE9 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write32 ( ( u32 ) ( s32 ) distance ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : JMPptr ( const  OpArg &  arg2 )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									OpArg  arg  =  arg2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( arg . IsImm ( ) )  _assert_msg_ ( DYNA_REC ,  0 ,  " JMPptr - Imm argument " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . operandReg  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//Can be used to trap other processors, before overwriting their code
  
						 
					
						
							
								
									
										
										
										
											2015-01-11 00:17:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// not used in Dolphin
  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : JMPself ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xEB ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xFE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CALLptr ( OpArg  arg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( arg . IsImm ( ) )  _assert_msg_ ( DYNA_REC ,  0 ,  " CALLptr - Imm argument " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . operandReg  =  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CALL ( const  void *  fnptr )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									u64  distance  =  u64 ( fnptr )  -  ( u64 ( code )  +  5 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-11 00:30:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									             distance  <  0x0000000080000000ULL  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									             distance  > =   0xFFFFFFFF80000000ULL , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									             " CALL out of range (%p calls %p) " ,  code ,  fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0xE8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write32 ( u32 ( distance ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								FixupBranch  XEmitter : : J ( bool  force5bytes )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									FixupBranch  branch ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									branch . type  =  force5bytes  ?  1  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									branch . ptr  =  code  +  ( force5bytes  ?  5  :  2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! force5bytes ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//8 bits will do
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0xEB ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xE9 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write32 ( 0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  branch ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								FixupBranch  XEmitter : : J_CC ( CCFlags  conditionCode ,  bool  force5bytes )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									FixupBranch  branch ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									branch . type  =  force5bytes  ?  1  :  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-04-11 12:27:27 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									branch . ptr  =  code  +  ( force5bytes  ?  6  :  2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! force5bytes ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//8 bits will do
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x70  +  conditionCode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x80  +  conditionCode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write32 ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  branch ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-06-03 22:57:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : J_CC ( CCFlags  conditionCode ,  const  u8 *  addr )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									u64  fn  =  ( u64 ) addr ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-03 22:57:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									s64  distance  =  ( s64 ) ( fn  -  ( ( u64 ) code  +  2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( distance  <  - 0x80  | |  distance  > =  0x80 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-03 22:57:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										distance  =  ( s64 ) ( fn  -  ( ( u64 ) code  +  6 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-11 00:30:55 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										             distance  > =  - 0x80000000LL  & &  distance  <  0x80000000LL , 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-03 22:57:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										             " Jump target too far away, needs indirect register " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x80  +  conditionCode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write32 ( ( u32 ) ( s32 ) distance ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-03 22:57:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x70  +  conditionCode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) ( s8 ) distance ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SetJumpTarget ( const  FixupBranch &  branch )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( branch . type  = =  0 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-12-16 22:38:31 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s64  distance  =  ( s64 ) ( code  -  branch . ptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  distance  > =  - 0x80  & &  distance  <  0x80 ,  " Jump target too far away, needs force5Bytes = true " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-06-30 16:17:20 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										branch . ptr [ - 1 ]  =  ( u8 ) ( s8 ) distance ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( branch . type  = =  1 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-12-16 22:38:31 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s64  distance  =  ( s64 ) ( code  -  branch . ptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  distance  > =  - 0x80000000LL  & &  distance  <  0x80000000LL ,  " Jump target too far away, needs indirect register " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										( ( s32 * ) branch . ptr ) [ - 1 ]  =  ( s32 ) distance ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// INC/DEC considered harmful on newer CPUs due to partial flag set.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// Use ADD, SUB instead.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : INC ( int  bits ,  OpArg  arg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( arg . IsImm ( ) )  _assert_msg_ ( DYNA_REC ,  0 ,  " INC - Imm argument " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . operandReg  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  = =  16 )  { Write8 ( 0x66 ) ; } 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( bits  = =  8  ?  0xFE  :  0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DEC ( int  bits ,  OpArg  arg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( arg . IsImm ( ) )  _assert_msg_ ( DYNA_REC ,  0 ,  " DEC - Imm argument " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . operandReg  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  = =  16 )  { Write8 ( 0x66 ) ; } 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( bits  = =  8  ?  0xFE  :  0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								*/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								//Single byte opcodes
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//There is no PUSHAD/POPAD in 64-bit mode.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : INT3 ( )  { Write8 ( 0xCC ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RET ( )   { Write8 ( 0xC3 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RET_FAST ( )   { Write8 ( 0xF3 ) ;  Write8 ( 0xC3 ) ; }  //two-byte return (rep ret) - recommended by AMD optimization manual for the case of jumping to a ret
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-04-23 21:15:09 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// The first sign of decadence: optimized NOPs.
  
						 
					
						
							
								
									
										
										
										
											2014-04-30 10:12:15 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : NOP ( size_t  size )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-04-30 10:12:15 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_dbg_assert_ ( DYNA_REC ,  ( int ) size  >  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-04-23 21:15:09 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									while  ( true ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										switch  ( size ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  0 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  1 : 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Write8 ( 0x90 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-04-23 21:15:09 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ;  Write8 ( 0x90 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x40 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  5 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x44 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  6 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ;  Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x44 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  7 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x80 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x84 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  9 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ;  Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ;  Write8 ( 0x84 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  10 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ;  Write8 ( 0x66 ) ;  Write8 ( 0x0F ) ;  Write8 ( 0x1F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x84 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Even though x86 instructions are allowed to be up to 15 bytes long,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// AMD advises against using NOPs longer than 11 bytes because they
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// carry a performance penalty on CPUs older than AMD family 16h.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ;  Write8 ( 0x66 ) ;  Write8 ( 0x66 ) ;  Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x1F ) ;  Write8 ( 0x84 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ;  Write8 ( 0x00 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											size  - =  11 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-11-13 21:28:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PAUSE ( )  { Write8 ( 0xF3 ) ;  NOP ( ) ; }  //use in tight spinloops for energy saving on some CPU
  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CLC ( )   { CheckFlags ( ) ;  Write8 ( 0xF8 ) ; }  //clear carry
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMC ( )   { CheckFlags ( ) ;  Write8 ( 0xF5 ) ; }  //flip carry
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : STC ( )   { CheckFlags ( ) ;  Write8 ( 0xF9 ) ; }  //set carry
  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//TODO: xchg ah, al ???
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : XCHG_AHAL ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x86 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xe0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// alt. 86 c4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//These two can not be executed on early Intel 64-bit CPU:s, only on AMD!
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : LAHF ( )  { Write8 ( 0x9F ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SAHF ( )  { CheckFlags ( ) ;  Write8 ( 0x9E ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PUSHF ( )  { Write8 ( 0x9C ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : POPF ( )   { CheckFlags ( ) ;  Write8 ( 0x9D ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : LFENCE ( )  { Write8 ( 0x0F ) ;  Write8 ( 0xAE ) ;  Write8 ( 0xE8 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MFENCE ( )  { Write8 ( 0x0F ) ;  Write8 ( 0xAE ) ;  Write8 ( 0xF0 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SFENCE ( )  { Write8 ( 0x0F ) ;  Write8 ( 0xAE ) ;  Write8 ( 0xF8 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : WriteSimple1Byte ( int  bits ,  u8  byte ,  X64Reg  reg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rex ( bits  = =  64 ,  0 ,  0 ,  ( int ) reg  > >  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( byte  +  ( ( int ) reg  &  7 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : WriteSimple2Byte ( int  bits ,  u8  byte1 ,  u8  byte2 ,  X64Reg  reg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rex ( bits = = 64 ,  0 ,  0 ,  ( int ) reg  > >  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( byte1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( byte2  +  ( ( int ) reg  &  7 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CWD ( int  bits )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rex ( bits  = =  64 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x99 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CBW ( int  bits )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rex ( bits  = =  32 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x98 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//Simple opcodes
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//push/pop do not need wide to be 64-bit
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PUSH ( X64Reg  reg )  { WriteSimple1Byte ( 32 ,  0x50 ,  reg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : POP ( X64Reg  reg )   { WriteSimple1Byte ( 32 ,  0x58 ,  reg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PUSH ( int  bits ,  const  OpArg &  reg )  
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( reg . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PUSH ( reg . GetSimpleReg ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else  if  ( reg . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										switch  ( reg . GetImmBits ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x6A ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( ( u8 ) ( s8 ) reg . offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  16 : 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Write8 ( 0x68 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write16 ( ( u16 ) ( s16 ) ( s32 ) reg . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  32 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x68 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write32 ( ( u32 ) reg . offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default : 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  0 ,  " PUSH - Bad imm bits " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										reg . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										reg . WriteRest ( this ,  0 ,  ( X64Reg ) 6 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : POP ( int  /*bits*/ ,  const  OpArg &  reg )  
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( reg . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										POP ( reg . GetSimpleReg ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-26 11:28:13 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " POP - Unsupported encoding " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : BSWAP ( int  bits ,  X64Reg  reg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  > =  32 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										WriteSimple2Byte ( bits ,  0x0F ,  0xC8 ,  reg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ROL ( 16 ,  R ( reg ) ,  Imm8 ( 8 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Do nothing - can't bswap a single byte...
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " BSWAP - Wrong number of bits " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Undefined opcode - reserved
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// If we ever need a way to always cause a non-breakpoint hard exception...
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : UD2 ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x0B ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PREFETCH ( PrefetchLevel  level ,  OpArg  arg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! arg . IsImm ( ) ,  " PREFETCH - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . operandReg  =  ( u8 ) level ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x18 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SETcc ( CCFlags  flag ,  OpArg  dest )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! dest . IsImm ( ) ,  " SETcc - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . operandReg  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . WriteREX ( this ,  0 ,  8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x90  +  ( u8 ) flag ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									dest . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMOVcc ( int  bits ,  X64Reg  dest ,  OpArg  src ,  CCFlags  flag )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " CMOVcc - Imm argument " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  bits  ! =  8 ,  " CMOVcc - 8 bits unsupported " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . operandReg  =  dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x40  +  ( u8 ) flag ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									src . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : WriteMulDivType ( int  bits ,  OpArg  src ,  int  ext )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " WriteMulDivType - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . operandReg  =  ext ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  bits ,  bits ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xF6 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0xF7 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									src . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MUL ( int  bits ,  const  OpArg &  src )   { WriteMulDivType ( bits ,  src ,  4 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DIV ( int  bits ,  const  OpArg &  src )   { WriteMulDivType ( bits ,  src ,  6 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : IMUL ( int  bits ,  const  OpArg &  src )  { WriteMulDivType ( bits ,  src ,  5 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : IDIV ( int  bits ,  const  OpArg &  src )  { WriteMulDivType ( bits ,  src ,  7 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : NEG ( int  bits ,  const  OpArg &  src )   { WriteMulDivType ( bits ,  src ,  3 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : NOT ( int  bits ,  const  OpArg &  src )   { WriteMulDivType ( bits ,  src ,  2 ) ; }  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteBitSearchType ( int  bits ,  X64Reg  dest ,  OpArg  src ,  u8  byte2 ,  bool  rep )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " WriteBitSearchType - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . operandReg  =  ( u8 ) dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( rep ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0xF3 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( byte2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									src . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVNTI ( int  bits ,  const  OpArg &  dest ,  X64Reg  src )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  < =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " MOVNTI - bits<=16 " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteBitSearchType ( bits ,  src ,  dest ,  0xC3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : BSF ( int  bits ,  X64Reg  dest ,  const  OpArg &  src )  { WriteBitSearchType ( bits , dest , src , 0xBC ) ; }  // Bottom bit to top bit
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BSR ( int  bits ,  X64Reg  dest ,  const  OpArg &  src )  { WriteBitSearchType ( bits , dest , src , 0xBD ) ; }  // Top bit to bottom bit
  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : TZCNT ( int  bits ,  X64Reg  dest ,  const  OpArg &  src )  
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! cpu_info . bBMI1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use BMI1 on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteBitSearchType ( bits ,  dest ,  src ,  0xBC ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : LZCNT ( int  bits ,  X64Reg  dest ,  const  OpArg &  src )  
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-14 05:31:22 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! cpu_info . bLZCNT ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use LZCNT on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteBitSearchType ( bits ,  dest ,  src ,  0xBD ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVSX ( int  dbits ,  int  sbits ,  X64Reg  dest ,  OpArg  src )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " MOVSX - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dbits  = =  sbits ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										MOV ( dbits ,  R ( dest ) ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . operandReg  =  ( u8 ) dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dbits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  dbits ,  sbits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( sbits  = =  8 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0xBE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( sbits  = =  16 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xBF ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( sbits  = =  32  & &  dbits  = =  64 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x63 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Crash ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									src . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVZX ( int  dbits ,  int  sbits ,  X64Reg  dest ,  OpArg  src )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " MOVZX - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dbits  = =  sbits ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										MOV ( dbits ,  R ( dest ) ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									src . operandReg  =  ( u8 ) dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dbits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2011-02-19 14:20:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									//the 32bit result is automatically zero extended to 64bit
 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  dbits  = =  64  ?  32  :  dbits ,  sbits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( sbits  = =  8 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xB6 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( sbits  = =  16 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xB7 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2012-08-25 01:00:13 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else  if  ( sbits  = =  32  & &  dbits  = =  64 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x8B ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 08:55:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " MOVZX - Invalid size " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteMOVBE ( int  bits ,  u8  op ,  X64Reg  reg ,  const  OpArg &  arg )  
						 
					
						
							
								
									
										
										
										
											2014-03-16 03:43:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  cpu_info . bMOVBE ,  " Generating MOVBE on a system that does not support it. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-01-13 22:31:21 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										MOV ( 8 ,  op  &  1  ?  arg  :  R ( reg ) ,  op  &  1  ?  R ( reg )  :  arg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-16 03:43:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-01-13 22:31:21 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! arg . IsSimpleReg ( )  & &  ! arg . IsImm ( ) ,  " MOVBE: need r<-m or m<-r! " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  bits ,  bits ,  reg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-01-13 22:31:21 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x38 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( op ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ,  0 ,  reg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-03-16 03:43:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2015-01-13 22:31:21 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVBE ( int  bits ,  X64Reg  dest ,  const  OpArg &  src )  { WriteMOVBE ( bits ,  0xF0 ,  dest ,  src ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVBE ( int  bits ,  const  OpArg &  dest ,  X64Reg  src )  { WriteMOVBE ( bits ,  0xF1 ,  src ,  dest ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:50:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : LoadAndSwap ( int  size ,  X64Reg  dst ,  const  OpArg &  src )  
						 
					
						
							
								
									
										
										
										
											2015-01-14 23:31:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( cpu_info . bMOVBE ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MOVBE ( size ,  dst ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MOV ( size ,  R ( dst ) ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										BSWAP ( size ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:50:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SwapAndStore ( int  size ,  const  OpArg &  dst ,  X64Reg  src )  
						 
					
						
							
								
									
										
										
										
											2015-01-14 23:31:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( cpu_info . bMOVBE ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MOVBE ( size ,  dst ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										BSWAP ( size ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MOV ( size ,  dst ,  R ( src ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : LEA ( int  bits ,  X64Reg  dest ,  OpArg  src )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:24:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! src . IsImm ( ) ,  " LEA - Imm argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . operandReg  =  ( u8 ) dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ;  //TODO: performance warning
 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x8D ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									src . WriteRest ( this ,  0 ,  INVALID_REG ,  bits  = =  64 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//shift can be either imm8 or cl
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteShift ( int  bits ,  OpArg  dest ,  const  OpArg &  shift ,  int  ext )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  writeImm  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( dest . IsImm ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteShift - can't shift imms " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ( shift . IsSimpleReg ( )  & &  shift . GetSimpleReg ( )  ! =  ECX )  | |  ( shift . IsImm ( )  & &  shift . GetImmBits ( )  ! =  8 ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteShift - illegal argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . operandReg  =  ext ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . WriteREX ( this ,  bits ,  bits ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( shift . GetImmBits ( )  = =  8 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//ok an imm
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										u8  imm  =  ( u8 ) shift . offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( imm  = =  1 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Write8 ( bits  = =  8  ?  0xD0  :  0xD1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											writeImm  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write8 ( bits  = =  8  ?  0xC0  :  0xC1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( bits  = =  8  ?  0xD2  :  0xD3 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . WriteRest ( this ,  writeImm  ?  1  :  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( writeImm ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) shift . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-01-11 00:17:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// large rotates and shift are slower on Intel than AMD
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// Intel likes to rotate by 1, and the op is smaller too
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ROL ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  0 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ROR ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RCL ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RCR ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  3 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHL ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  4 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHR ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  5 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SAR ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  shift )  { WriteShift ( bits ,  dest ,  shift ,  7 ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// index can be either imm8 or register, don't use memory destination because it's slow
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteBitTest ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  index ,  int  ext )  
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dest . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteBitTest - can't test imms " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ( index . IsImm ( )  & &  index . GetImmBits ( )  ! =  8 ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteBitTest - illegal argument " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( index . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										dest . WriteREX ( this ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0xBA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  1 ,  ( X64Reg ) ext ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) index . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										X64Reg  operand  =  index . GetSimpleReg ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										dest . WriteREX ( this ,  bits ,  bits ,  operand ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0x83  +  8 * ext ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  1 ,  operand ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : BT ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  index )   { WriteBitTest ( bits ,  dest ,  index ,  4 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BTS ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  index )  { WriteBitTest ( bits ,  dest ,  index ,  5 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BTR ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  index )  { WriteBitTest ( bits ,  dest ,  index ,  6 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BTC ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  index )  { WriteBitTest ( bits ,  dest ,  index ,  7 ) ; }  
						 
					
						
							
								
									
										
										
										
											2012-01-05 22:36:27 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								//shift can be either imm8 or cl
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SHRD ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  src ,  const  OpArg &  shift )  
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dest . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHRD - can't use imms as destination " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! src . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHRD - must use simple register as source " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ( shift . IsSimpleReg ( )  & &  shift . GetSimpleReg ( )  ! =  ECX )  | |  ( shift . IsImm ( )  & &  shift . GetImmBits ( )  ! =  8 ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHRD - illegal shift " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									X64Reg  operand  =  src . GetSimpleReg ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . WriteREX ( this ,  bits ,  bits ,  operand ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( shift . GetImmBits ( )  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0xAC ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  1 ,  operand ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) shift . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0xAD ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  0 ,  operand ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SHLD ( int  bits ,  const  OpArg &  dest ,  const  OpArg &  src ,  const  OpArg &  shift )  
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( dest . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHLD - can't use imms as destination " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! src . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHLD - must use simple register as source " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ( shift . IsSimpleReg ( )  & &  shift . GetSimpleReg ( )  ! =  ECX )  | |  ( shift . IsImm ( )  & &  shift . GetImmBits ( )  ! =  8 ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " SHLD - illegal shift " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-06 01:23:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									X64Reg  operand  =  src . GetSimpleReg ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dest . WriteREX ( this ,  bits ,  bits ,  operand ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2012-01-09 00:10:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( shift . GetImmBits ( )  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0xA4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  1 ,  operand ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) shift . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x0F ) ;  Write8 ( 0xA5 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dest . WriteRest ( this ,  0 ,  operand ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  OpArg : : WriteSingleByteOp ( XEmitter *  emit ,  u8  op ,  X64Reg  _operandReg ,  int  bits )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									this - > operandReg  =  ( u8 ) _operandReg ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteREX ( emit ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									emit - > Write8 ( op ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteRest ( emit ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								//operand can either be immediate or register
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  OpArg : : WriteNormalOp ( XEmitter *  emit ,  bool  toRM ,  NormalOp  op ,  const  OpArg &  operand ,  int  bits )  const  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-08-27 20:36:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									X64Reg  _operandReg ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( IsImm ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - Imm argument, wrong order " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  immToWrite  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( operand . IsImm ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										WriteREX ( emit ,  bits ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! toRM ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - Writing to Imm (!toRM) " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( operand . scale  = =  SCALE_IMM8  & &  bits  = =  8 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// op al, imm8
 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ! scale  & &  offsetOrBaseReg  = =  AL  & &  normalops [ op ] . eaximm8  ! =  0xCC ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												emit - > Write8 ( normalops [ op ] . eaximm8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												emit - > Write8 ( ( u8 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// mov reg, imm8
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! scale  & &  op  = =  nrmMOV ) 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												emit - > Write8 ( 0xB0  +  ( offsetOrBaseReg  &  7 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												emit - > Write8 ( ( u8 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// op r/m8, imm8
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											emit - > Write8 ( normalops [ op ] . imm8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											immToWrite  =  8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else  if  ( ( operand . scale  = =  SCALE_IMM16  & &  bits  = =  16 )  | | 
							 
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												 ( operand . scale  = =  SCALE_IMM32  & &  bits  = =  32 )  | | 
							 
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												 ( operand . scale  = =  SCALE_IMM32  & &  bits  = =  64 ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// Try to save immediate size if we can, but first check to see
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// if the instruction supports simm8.
 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// op r/m, imm8
 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( normalops [ op ] . simm8  ! =  0xCC  & & 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											    ( ( operand . scale  = =  SCALE_IMM16  & &  ( s16 ) operand . offset  = =  ( s8 ) operand . offset )  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											     ( operand . scale  = =  SCALE_IMM32  & &  ( s32 ) operand . offset  = =  ( s8 ) operand . offset ) ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												emit - > Write8 ( normalops [ op ] . simm8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												immToWrite  =  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// mov reg, imm
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! scale  & &  op  = =  nrmMOV  & &  bits  ! =  64 ) 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													emit - > Write8 ( 0xB8  +  ( offsetOrBaseReg  &  7 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														emit - > Write16 ( ( u16 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														emit - > Write32 ( ( u32 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													return ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// op eax, imm
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! scale  & &  offsetOrBaseReg  = =  EAX  & &  normalops [ op ] . eaximm32  ! =  0xCC ) 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													emit - > Write8 ( normalops [ op ] . eaximm32 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														emit - > Write16 ( ( u16 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														emit - > Write32 ( ( u32 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													return ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// op r/m, imm
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												emit - > Write8 ( normalops [ op ] . imm32 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												immToWrite  =  bits  = =  16  ?  16  :  32 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else  if  ( ( operand . scale  = =  SCALE_IMM8  & &  bits  = =  16 )  | | 
							 
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												 ( operand . scale  = =  SCALE_IMM8  & &  bits  = =  32 )  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												 ( operand . scale  = =  SCALE_IMM8  & &  bits  = =  64 ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// op r/m, imm8
 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											emit - > Write8 ( normalops [ op ] . simm8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											immToWrite  =  8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else  if  ( operand . scale  = =  SCALE_IMM64  & &  bits  = =  64 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( scale ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - MOV with 64-bit imm requres register destination " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// mov reg64, imm64
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											else  if  ( op  = =  nrmMOV ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												emit - > Write8 ( 0xB8  +  ( offsetOrBaseReg  &  7 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												emit - > Write64 ( ( u64 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - Only MOV can take 64-bit imm " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-11-09 16:21:11 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - Unhandled case %d %d " ,  operand . scale ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_operandReg  =  ( X64Reg ) normalops [ op ] . ext ;  //pass extension in REG of ModRM
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_operandReg  =  ( X64Reg ) operand . offsetOrBaseReg ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										WriteREX ( emit ,  bits ,  bits ,  _operandReg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// op r/m, reg
 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( toRM ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											emit - > Write8 ( bits  = =  8  ?  normalops [ op ] . toRm8  :  normalops [ op ] . toRm32 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// op reg, r/m
 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 02:11:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											emit - > Write8 ( bits  = =  8  ?  normalops [ op ] . fromRm8  :  normalops [ op ] . fromRm32 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-10 23:54:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteRest ( emit ,  immToWrite  > >  3 ,  _operandReg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( immToWrite ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									case  0 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write8 ( ( u8 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									case  16 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write16 ( ( u16 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									case  32 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										emit - > Write32 ( ( u32 ) operand . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									default : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - Unhandled case " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteNormalOp ( int  bits ,  NormalOp  op ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( a1 . IsImm ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//Booh! Can't write to an imm
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " WriteNormalOp - a1 cannot be imm " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( a2 . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-20 23:07:59 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										a1 . WriteNormalOp ( this ,  true ,  op ,  a2 ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( a1 . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-20 23:07:59 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											a2 . WriteNormalOp ( this ,  false ,  op ,  a1 ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-15 07:08:08 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  a2 . IsSimpleReg ( )  | |  a2 . IsImm ( ) ,  " WriteNormalOp - a1 and a2 cannot both be memory " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-20 23:07:59 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											a1 . WriteNormalOp ( this ,  true ,  op ,  a2 ,  bits ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ADD  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmADD ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ADC  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmADC ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SUB  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmSUB ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SBB  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmSBB ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : AND  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmAND ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : OR   ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmOR  ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : XOR  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmXOR ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOV  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-02 10:16:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( a1 . IsSimpleReg ( )  & &  a2 . IsSimpleReg ( )  & &  a1 . GetSimpleReg ( )  = =  a2 . GetSimpleReg ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERROR_LOG ( DYNA_REC ,  " Redundant MOV @ %p - bug in JIT? " ,  code ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-03-20 23:07:59 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteNormalOp ( bits ,  nrmMOV ,  a1 ,  a2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : TEST ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmTEST ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMP  ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { CheckFlags ( ) ;  WriteNormalOp ( bits ,  nrmCMP ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : XCHG ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  { WriteNormalOp ( bits ,  nrmXCHG ,  a1 ,  a2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMP_or_TEST ( int  bits ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  
						 
					
						
							
								
									
										
										
										
											2015-02-21 11:12:03 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( a1 . IsSimpleReg ( )  & &  a2 . IsImm ( )  & &  a2 . offset  = =  0 )  // turn 'CMP reg, 0' into shorter 'TEST reg, reg'
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										WriteNormalOp ( bits ,  nrmTEST ,  a1 ,  a1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										WriteNormalOp ( bits ,  nrmCMP ,  a1 ,  a2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : IMUL ( int  bits ,  X64Reg  regOp ,  const  OpArg &  a1 ,  const  OpArg &  a2 )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " IMUL - illegal bit size! " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( a1 . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " IMUL - second arg cannot be imm! " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! a2 . IsImm ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " IMUL - third arg must be imm! " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									a1 . WriteREX ( this ,  bits ,  bits ,  regOp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-06 16:36:53 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( a2 . GetImmBits ( )  = =  8  | | 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									    ( a2 . GetImmBits ( )  = =  16  & &  ( s8 ) a2 . offset  = =  ( s16 ) a2 . offset )  | | 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									    ( a2 . GetImmBits ( )  = =  32  & &  ( s8 ) a2 . offset  = =  ( s32 ) a2 . offset ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x6B ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										a1 . WriteRest ( this ,  1 ,  regOp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( u8 ) a2 . offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x69 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( a2 . GetImmBits ( )  = =  16  & &  bits  = =  16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											a1 . WriteRest ( this ,  2 ,  regOp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write16 ( ( u16 ) a2 . offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										else  if  ( a2 . GetImmBits ( )  = =  32  & &  ( bits  = =  32  | |  bits  = =  64 ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											a1 . WriteRest ( this ,  4 ,  regOp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Write32 ( ( u32 ) a2 . offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_assert_msg_ ( DYNA_REC ,  0 ,  " IMUL - unhandled case! " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : IMUL ( int  bits ,  X64Reg  regOp ,  const  OpArg &  a )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-09-26 20:40:24 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  8 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " IMUL - illegal bit size! " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( a . IsImm ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										IMUL ( bits ,  regOp ,  R ( regOp ) ,  a )  ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-04-09 19:18:50 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  16 ) 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									a . WriteREX ( this ,  bits ,  bits ,  regOp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xAF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									a . WriteRest ( this ,  0 ,  regOp ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-18 06:46:32 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteSSEOp ( u8  opPrefix ,  u16  op ,  X64Reg  regOp ,  OpArg  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( opPrefix ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( opPrefix ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . operandReg  =  regOp ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( op  >  0xFF ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( ( op  > >  8 )  &  0xFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( op  &  0xFF ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteRest ( this ,  extrabytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  int  GetVEXmmmmm ( u16  op )  
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Currently, only 0x38 and 0x3A are used as secondary escape byte.
 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ( op  > >  8 )  = =  0x3A ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else  if  ( ( op  > >  8 )  = =  0x38 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  int  GetVEXpp ( u8  opPrefix )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( opPrefix  = =  0x66 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else  if  ( opPrefix  = =  0xF3 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else  if  ( opPrefix  = =  0xF2 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteVEXOp ( u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  W ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mmmmm  =  GetVEXmmmmm ( op ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pp  =  GetVEXpp ( opPrefix ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// FIXME: we currently don't support 256-bit instructions, and "size" is not the vector size here
 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:38:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteVEX ( this ,  regOp1 ,  regOp2 ,  0 ,  pp ,  mmmmm ,  W ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( op  &  0xFF ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteRest ( this ,  extrabytes ,  regOp1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteVEXOp4 ( u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  X64Reg  regOp3 ,  int  W )  
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteVEXOp ( opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  W ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( ( u8 ) regOp3  < <  4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteAVXOp ( u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  W ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bAVX ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use AVX on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteVEXOp ( opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  W ,  extrabytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteAVXOp4 ( u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  X64Reg  regOp3 ,  int  W )  
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bAVX ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use AVX on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteVEXOp4 ( opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  regOp3 ,  W ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteFMA3Op ( u8  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  W )  
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bFMA ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use FMA3 on a system that doesn't support it. Computer is v. f'n madd. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteVEXOp ( 0x66 ,  0x3800  |  op ,  regOp1 ,  regOp2 ,  arg ,  W ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 09:20:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteFMA4Op ( u8  op ,  X64Reg  dest ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  W )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bFMA4 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use FMA4 on a system that doesn't support it. Computer is v. f'n madd. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteVEXOp4 ( 0x66 ,  0x3A00  |  op ,  dest ,  regOp1 ,  arg ,  regOp2 ,  W ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteBMIOp ( int  size ,  u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CheckFlags ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( size  ! =  32  & &  size  ! =  64 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " VEX GPR instructions only support 32-bit and 64-bit modes! " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  W  =  size  = =  64 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									WriteVEXOp ( opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  W ,  extrabytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteBMI1Op ( int  size ,  u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bBMI1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use BMI1 on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteBMIOp ( size ,  opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  extrabytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteBMI2Op ( int  size ,  u8  opPrefix ,  u16  op ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bBMI2 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use BMI2 on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 07:07:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteBMIOp ( size ,  opPrefix ,  op ,  regOp1 ,  regOp2 ,  arg ,  extrabytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-24 17:39:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVD_xmm ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x6E ,  dest ,  arg ,  0 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVD_xmm ( const  OpArg &  arg ,  X64Reg  src )  { WriteSSEOp ( 0x66 ,  0x7E ,  src ,  arg ,  0 ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVQ_xmm ( X64Reg  dest ,  OpArg  arg )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Alternate encoding
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// This does not display correctly in MSVC's debugger, it thinks it's a MOVD
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										arg . operandReg  =  dest ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										arg . WriteREX ( this ,  64 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x6E ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										arg . WriteRest ( this ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVQ_xmm ( OpArg  arg ,  X64Reg  src )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-05-30 21:09:19 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( src  >  7  | |  arg . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Alternate encoding
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// This does not display correctly in MSVC's debugger, it thinks it's a MOVD
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										arg . operandReg  =  src ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										arg . WriteREX ( this ,  64 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Write8 ( 0x7E ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										arg . WriteRest ( this ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										arg . operandReg  =  src ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0x0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Write8 ( 0xD6 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										arg . WriteRest ( this ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : WriteMXCSR ( OpArg  arg ,  int  ext )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( arg . IsImm ( )  | |  arg . IsSimpleReg ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_assert_msg_ ( DYNA_REC ,  0 ,  " MXCSR - invalid operand " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . operandReg  =  ext ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 05:37:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteREX ( this ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0x0F ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xAE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arg . WriteRest ( this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : STMXCSR ( const  OpArg &  memloc )  { WriteMXCSR ( memloc ,  3 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : LDMXCSR ( const  OpArg &  memloc )  { WriteMXCSR ( memloc ,  2 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVNTDQ ( const  OpArg &  arg ,  X64Reg  regOp )  { WriteSSEOp ( 0x66 ,  sseMOVNTDQ ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVNTPS ( const  OpArg &  arg ,  X64Reg  regOp )  { WriteSSEOp ( 0x00 ,  sseMOVNTP ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVNTPD ( const  OpArg &  arg ,  X64Reg  regOp )  { WriteSSEOp ( 0x66 ,  sseMOVNTP ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ADDSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseADD ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ADDSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseADD ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SUBSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseSUB ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SUBSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseSUB ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMPSS ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  compare )  { WriteSSEOp ( 0xF3 ,  sseCMP ,  regOp ,  arg ,  1 ) ;  Write8 ( compare ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMPSD ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  compare )  { WriteSSEOp ( 0xF2 ,  sseCMP ,  regOp ,  arg ,  1 ) ;  Write8 ( compare ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MULSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseMUL ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MULSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseMUL ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DIVSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseDIV ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DIVSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseDIV ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MINSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseMIN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MINSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseMIN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MAXSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseMAX ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MAXSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseMAX ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SQRTSS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0xF3 ,  sseSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SQRTSD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0xF2 ,  sseSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RSQRTSS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  sseRSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ADDPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseADD ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ADDPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseADD ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SUBPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseSUB ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SUBPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseSUB ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMPPS ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  compare )  { WriteSSEOp ( 0x00 ,  sseCMP ,  regOp ,  arg ,  1 ) ;  Write8 ( compare ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CMPPD ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  compare )  { WriteSSEOp ( 0x66 ,  sseCMP ,  regOp ,  arg ,  1 ) ;  Write8 ( compare ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ANDPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseAND ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ANDPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseAND ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ANDNPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseANDN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ANDNPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseANDN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ORPS ( X64Reg  regOp ,  const  OpArg &  arg )     { WriteSSEOp ( 0x00 ,  sseOR ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ORPD ( X64Reg  regOp ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  sseOR ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : XORPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseXOR ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : XORPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseXOR ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MULPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseMUL ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MULPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseMUL ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DIVPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseDIV ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : DIVPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseDIV ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MINPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseMIN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MINPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseMIN ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MAXPS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x00 ,  sseMAX ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MAXPD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  sseMAX ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SQRTPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SQRTPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RSQRTPS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  sseRSQRT ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHUFPS ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  shuffle )  { WriteSSEOp ( 0x00 ,  sseSHUF ,  regOp ,  arg , 1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHUFPD ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  shuffle )  { WriteSSEOp ( 0x66 ,  sseSHUF ,  regOp ,  arg , 1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : COMISS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseCOMIS ,  regOp ,  arg ) ; }  //weird that these should be packed
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : COMISD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseCOMIS ,  regOp ,  arg ) ; }  //ordered
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : UCOMISS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  sseUCOMIS ,  regOp ,  arg ) ; }  //unordered
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : UCOMISD ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  sseUCOMIS ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVAPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseMOVAPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVAPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseMOVAPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVAPS ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x00 ,  sseMOVAPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVAPD ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x66 ,  sseMOVAPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVUPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseMOVUPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVUPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseMOVUPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVUPS ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x00 ,  sseMOVUPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVUPD ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x66 ,  sseMOVUPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVDQA ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseMOVDQfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVDQA ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x66 ,  sseMOVDQtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVDQU ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0xF3 ,  sseMOVDQfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVDQU ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0xF3 ,  sseMOVDQtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVSS ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF3 ,  sseMOVUPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVSD ( X64Reg  regOp ,  const  OpArg &  arg )    { WriteSSEOp ( 0xF2 ,  sseMOVUPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVSS ( const  OpArg &  arg ,  X64Reg  regOp )    { WriteSSEOp ( 0xF3 ,  sseMOVUPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVSD ( const  OpArg &  arg ,  X64Reg  regOp )    { WriteSSEOp ( 0xF2 ,  sseMOVUPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVLPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseMOVLPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVLPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseMOVLPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVLPS ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x00 ,  sseMOVLPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVLPD ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x66 ,  sseMOVLPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVHPS ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x00 ,  sseMOVHPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVHPD ( X64Reg  regOp ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  sseMOVHPfromRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVHPS ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x00 ,  sseMOVHPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVHPD ( const  OpArg &  arg ,  X64Reg  regOp )   { WriteSSEOp ( 0x66 ,  sseMOVHPtoRM ,  regOp ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVHLPS ( X64Reg  regOp1 ,  X64Reg  regOp2 )  { WriteSSEOp ( 0x00 ,  sseMOVHLPS ,  regOp1 ,  R ( regOp2 ) ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVLHPS ( X64Reg  regOp1 ,  X64Reg  regOp2 )  { WriteSSEOp ( 0x00 ,  sseMOVLHPS ,  regOp1 ,  R ( regOp2 ) ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CVTPS2PD ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  0x5A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTPD2PS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x5A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CVTSD2SS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF2 ,  0x5A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTSS2SD ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0x5A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTSD2SI ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF2 ,  0x2D ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTSS2SI ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0x2D ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTSI2SD ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF2 ,  0x2A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTSI2SS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0x2A ,  regOp ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CVTDQ2PD ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0xE6 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTDQ2PS ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  0x5B ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTPD2DQ ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF2 ,  0xE6 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTPS2DQ ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x5B ,  regOp ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CVTTSD2SI ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF2 ,  0x2C ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTTSS2SI ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0x2C ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTTPS2DQ ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0xF3 ,  0x5B ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : CVTTPD2DQ ( X64Reg  regOp ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0xE6 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MASKMOVDQU ( X64Reg  dest ,  X64Reg  src )   { WriteSSEOp ( 0x66 ,  sseMASKMOVDQU ,  dest ,  R ( src ) ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVMSKPS ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  0x50 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MOVMSKPD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x50 ,  dest ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : LDDQU ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0xF2 ,  sseLDDQU ,  dest ,  arg ) ; }  // For integer data only
  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// THESE TWO ARE UNTESTED.
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : UNPCKLPS ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  0x14 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : UNPCKHPS ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x00 ,  0x15 ,  dest ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : UNPCKLPD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x14 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : UNPCKHPD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x15 ,  dest ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : MOVDDUP ( X64Reg  regOp ,  const  OpArg &  arg )  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( cpu_info . bSSE3 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										WriteSSEOp ( 0xF2 ,  0x12 ,  regOp ,  arg ) ;  //SSE3 movddup
 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Simulate this instruction with SSE2 instructions
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! arg . IsSimpleReg ( regOp ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2012-06-02 10:06:47 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											MOVSD ( regOp ,  arg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										UNPCKLPD ( regOp ,  R ( regOp ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//There are a few more left
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2013-04-19 09:21:45 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Also some integer instructions are missing
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PACKSSDW ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x6B ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PACKSSWB ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x63 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PACKUSWB ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x67 ,  dest ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 21:45:39 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PUNPCKLBW ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x60 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PUNPCKLWD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x61 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PUNPCKLDQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x62 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PUNPCKLQDQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSEOp ( 0x66 ,  0x6C ,  dest ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRLW ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x71 ,  ( X64Reg ) 2 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRLD ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x72 ,  ( X64Reg ) 2 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-09-06 03:03:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRLQ ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x73 ,  ( X64Reg ) 2 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRLQ ( X64Reg  reg ,  const  OpArg &  arg )  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0xd3 ,  reg ,  arg ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-06 20:39:57 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-10-10 22:34:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRLDQ ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-10 17:21:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x73 ,  ( X64Reg ) 3 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSLLW ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x71 ,  ( X64Reg ) 6 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSLLD ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x72 ,  ( X64Reg ) 6 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-09-06 03:03:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSLLQ ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x73 ,  ( X64Reg ) 6 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2010-09-06 03:03:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-10-10 22:34:03 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSLLDQ ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2014-10-10 17:21:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( 0x66 ,  0x73 ,  ( X64Reg ) 7 ,  R ( reg ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-09-06 03:03:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// WARNING not REX compatible
  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRAW ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2010-09-06 03:03:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( reg  >  7 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " The PSRAW-emitter does not support regs above 7 " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x71 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xE0  |  reg ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// WARNING not REX compatible
  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSRAD ( X64Reg  reg ,  int  shift )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( reg  >  7 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " The PSRAD-emitter does not support regs above 7 " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x66 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x72 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0xE0  |  reg ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( shift ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteSSSE3Op ( u8  opPrefix ,  u16  op ,  X64Reg  regOp ,  const  OpArg &  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2014-07-26 18:59:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bSSSE3 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use SSSE3 on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( opPrefix ,  op ,  regOp ,  arg ,  extrabytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-03 23:56:11 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteSSE41Op ( u8  opPrefix ,  u16  op ,  X64Reg  regOp ,  const  OpArg &  arg ,  int  extrabytes )  
						 
					
						
							
								
									
										
										
										
											2014-07-26 18:59:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! cpu_info . bSSE4_1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										PanicAlert ( " Trying to use SSE4.1 on a system that doesn't support it. Bad programmer. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 10:05:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									WriteSSEOp ( opPrefix ,  op ,  regOp ,  arg ,  extrabytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-07-26 18:59:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PSHUFB ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSSE3Op ( 0x66 ,  0x3800 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PTEST ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSE41Op ( 0x66 ,  0x3817 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PACKUSDW ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x382b ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXBW ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3820 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXBD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3821 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXBQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3822 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXWD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3823 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXWQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3824 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVSXDQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3825 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXBW ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3830 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXBD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3831 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXBQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3832 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXWD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3833 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXWQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3834 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVZXDQ ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3835 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PBLENDVB ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3810 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLENDVPS ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3814 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLENDVPD ( X64Reg  dest ,  const  OpArg &  arg )  { WriteSSE41Op ( 0x66 ,  0x3815 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLENDPS ( X64Reg  dest ,  const  OpArg &  arg ,  u8  blend )  { WriteSSE41Op ( 0x66 ,  0x3A0C ,  dest ,  arg ,  1 ) ;  Write8 ( blend ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLENDPD ( X64Reg  dest ,  const  OpArg &  arg ,  u8  blend )  { WriteSSE41Op ( 0x66 ,  0x3A0D ,  dest ,  arg ,  1 ) ;  Write8 ( blend ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PAND ( X64Reg  dest ,  const  OpArg &  arg )      { WriteSSEOp ( 0x66 ,  0xDB ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PANDN ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xDF ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PXOR ( X64Reg  dest ,  const  OpArg &  arg )      { WriteSSEOp ( 0x66 ,  0xEF ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : POR ( X64Reg  dest ,  const  OpArg &  arg )       { WriteSSEOp ( 0x66 ,  0xEB ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDB ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xFC ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDW ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xFD ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDD ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xFE ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDQ ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xD4 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDSB ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xEC ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDSW ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xED ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDUSB ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0xDC ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PADDUSW ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0xDD ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBB ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xF8 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBW ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xF9 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBD ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xFA ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBQ ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xFB ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBSB ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xE8 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBSW ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xE9 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBUSB ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0xD8 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSUBUSW ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0xD9 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PAVGB ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xE0 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PAVGW ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xE3 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPEQB ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x74 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPEQW ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x75 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPEQD ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x76 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPGTB ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x64 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPGTW ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x65 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PCMPGTD ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0x66 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PEXTRW ( X64Reg  dest ,  const  OpArg &  arg ,  u8  subreg )  { WriteSSEOp ( 0x66 ,  0xC5 ,  dest ,  arg ) ;  Write8 ( subreg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PINSRW ( X64Reg  dest ,  const  OpArg &  arg ,  u8  subreg )  { WriteSSEOp ( 0x66 ,  0xC4 ,  dest ,  arg ) ;  Write8 ( subreg ) ; }  
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:58:27 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : PINSRD ( X64Reg  dest ,  const  OpArg &  arg ,  u8  subreg )  { WriteSSE41Op ( 0x66 ,  0x3A22 ,  dest ,  arg ) ;  Write8 ( subreg ) ; }  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMADDWD ( X64Reg  dest ,  const  OpArg &  arg )   { WriteSSEOp ( 0x66 ,  0xF5 ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSADBW ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xF6 ,  dest ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMAXSW ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xEE ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMAXUB ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xDE ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMINSW ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xEA ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMINUB ( X64Reg  dest ,  const  OpArg &  arg )    { WriteSSEOp ( 0x66 ,  0xDA ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PMOVMSKB ( X64Reg  dest ,  const  OpArg &  arg )     { WriteSSEOp ( 0x66 ,  0xD7 ,  dest ,  arg ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSHUFD ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  shuffle )     { WriteSSEOp ( 0x66 ,  0x70 ,  regOp ,  arg ,  1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSHUFLW ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  shuffle )    { WriteSSEOp ( 0xF2 ,  0x70 ,  regOp ,  arg ,  1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PSHUFHW ( X64Reg  regOp ,  const  OpArg &  arg ,  u8  shuffle )    { WriteSSEOp ( 0xF3 ,  0x70 ,  regOp ,  arg ,  1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// VEX
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : VADDSD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0xF2 ,  sseADD ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VSUBSD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0xF2 ,  sseSUB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VMULSD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0xF2 ,  sseMUL ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VDIVSD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0xF2 ,  sseDIV ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VADDPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseADD ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VSUBPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseSUB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VMULPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseMUL ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VDIVPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseDIV ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VSQRTSD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )   { WriteAVXOp ( 0xF2 ,  sseSQRT ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VCMPPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  u8  compare )   { WriteAVXOp ( 0x66 ,  sseCMP ,  regOp1 ,  regOp2 ,  arg ,  0 ,  1 ) ;  Write8 ( compare ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VSHUFPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  u8  shuffle )  { WriteAVXOp ( 0x66 ,  sseSHUF ,  regOp1 ,  regOp2 ,  arg ,  0 ,  1 ) ;  Write8 ( shuffle ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VUNPCKLPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ) { WriteAVXOp ( 0x66 ,  0x14 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VUNPCKHPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ) { WriteAVXOp ( 0x66 ,  0x15 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VBLENDVPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg ,  X64Reg  regOp3 )  { WriteAVXOp4 ( 0x66 ,  0x3A4B ,  regOp1 ,  regOp2 ,  arg ,  regOp3 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VANDPS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x00 ,  sseAND ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VANDPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseAND ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VANDNPS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )   { WriteAVXOp ( 0x00 ,  sseANDN ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VANDNPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )   { WriteAVXOp ( 0x66 ,  sseANDN ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VORPS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteAVXOp ( 0x00 ,  sseOR ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VORPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteAVXOp ( 0x66 ,  sseOR ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VXORPS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x00 ,  sseXOR ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VXORPD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  sseXOR ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VPAND ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteAVXOp ( 0x66 ,  0xDB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VPANDN ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteAVXOp ( 0x66 ,  0xDF ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VPOR ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )      { WriteAVXOp ( 0x66 ,  0xEB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VPXOR ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteAVXOp ( 0x66 ,  0xEF ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x98 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xA8 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xB8 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x98 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xA8 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xB8 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD132SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x99 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD213SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xA9 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD231SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xB9 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD132SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x99 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD213SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xA9 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADD231SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xB9 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x9A ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xAA ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xBA ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x9A ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xAA ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xBA ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB132SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x9B ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB213SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xAB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB231SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xBB ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB132SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0x9B ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB213SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xAB ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUB231SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )     { WriteFMA3Op ( 0xBB ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9C ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAC ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBC ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9C ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAC ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBC ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD132SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9D ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD213SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAD ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD231SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBD ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD132SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9D ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD213SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAD ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMADD231SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBD ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9E ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAE ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBE ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9E ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAE ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBE ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB132SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9F ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB213SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAF ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB231SS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBF ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB132SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0x9F ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB213SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xAF ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFNMSUB231SD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )    { WriteFMA3Op ( 0xBF ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0x96 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xA6 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xB6 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0x96 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xA6 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMADDSUB231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xB6 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD132PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0x97 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD213PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xA7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD231PS ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xB7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD132PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0x97 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD213PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xA7 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : VFMSUBADD231PD ( X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA3Op ( 0xB7 ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-17 09:20:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define FMA4(name, op) \ 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : name ( X64Reg  dest ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteFMA4Op ( op ,  dest ,  regOp1 ,  regOp2 ,  arg ,  1 ) ; }  \ 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : name ( X64Reg  dest ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 )  { WriteFMA4Op ( op ,  dest ,  regOp1 ,  regOp2 ,  arg ,  0 ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDSUBPS ,  0x5C )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDSUBPD ,  0x5D )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBADDPS ,  0x5E )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBADDPD ,  0x5F )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDPS ,  0x68 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDPD ,  0x69 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDSS ,  0x6A )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMADDSD ,  0x6B )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBPS ,  0x6C )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBPD ,  0x6D )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBSS ,  0x6E )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFMSUBSD ,  0x6F )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMADDPS ,  0x78 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMADDPD ,  0x79 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMADDSS ,  0x7A )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMADDSD ,  0x7B )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMSUBPS ,  0x7C )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMSUBPD ,  0x7D )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMSUBSS ,  0x7E )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								FMA4 ( VFNMSUBSD ,  0x7F )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# undef FMA4 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : SARX ( int  bits ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 )  { WriteBMI2Op ( bits ,  0xF3 ,  0x38F7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHLX ( int  bits ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 )  { WriteBMI2Op ( bits ,  0x66 ,  0x38F7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : SHRX ( int  bits ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 )  { WriteBMI2Op ( bits ,  0xF2 ,  0x38F7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : RORX ( int  bits ,  X64Reg  regOp ,  const  OpArg &  arg ,  u8  rotate )       { WriteBMI2Op ( bits ,  0xF2 ,  0x3AF0 ,  regOp ,  INVALID_REG ,  arg ,  1 ) ;  Write8 ( rotate ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PEXT ( int  bits ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteBMI2Op ( bits ,  0xF3 ,  0x38F5 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : PDEP ( int  bits ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteBMI2Op ( bits ,  0xF2 ,  0x38F5 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : MULX ( int  bits ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteBMI2Op ( bits ,  0xF2 ,  0x38F6 ,  regOp2 ,  regOp1 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BZHI ( int  bits ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 )  { WriteBMI2Op ( bits ,  0x00 ,  0x38F5 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLSR ( int  bits ,  X64Reg  regOp ,  const  OpArg &  arg )                  { WriteBMI1Op ( bits ,  0x00 ,  0x38F3 ,  ( X64Reg ) 0x1 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLSMSK ( int  bits ,  X64Reg  regOp ,  const  OpArg &  arg )                { WriteBMI1Op ( bits ,  0x00 ,  0x38F3 ,  ( X64Reg ) 0x2 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BLSI ( int  bits ,  X64Reg  regOp ,  const  OpArg &  arg )                  { WriteBMI1Op ( bits ,  0x00 ,  0x38F3 ,  ( X64Reg ) 0x3 ,  regOp ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : BEXTR ( int  bits ,  X64Reg  regOp1 ,  const  OpArg &  arg ,  X64Reg  regOp2 ) { WriteBMI1Op ( bits ,  0x00 ,  0x38F7 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : ANDN ( int  bits ,  X64Reg  regOp1 ,  X64Reg  regOp2 ,  const  OpArg &  arg )  { WriteBMI1Op ( bits ,  0x00 ,  0x38F2 ,  regOp1 ,  regOp2 ,  arg ) ; }  
						 
					
						
							
								
									
										
										
										
											2013-11-04 21:37:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Prefixes
  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : LOCK ( )   {  Write8 ( 0xF0 ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : REP ( )    {  Write8 ( 0xF3 ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : REPNE ( )  {  Write8 ( 0xF2 ) ;  }  
						 
					
						
							
								
									
										
										
										
											2014-09-15 23:03:07 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : FSOverride ( )  {  Write8 ( 0x64 ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : GSOverride ( )  {  Write8 ( 0x65 ) ;  }  
						 
					
						
							
								
									
										
										
										
											2010-01-16 19:01:00 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : FWAIT ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Write8 ( 0x9B ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// TODO: make this more generic
  
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : WriteFloatLoadStore ( int  bits ,  FloatOp  op ,  FloatOp  op_80b ,  const  OpArg &  arg )  
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mf  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 08:55:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_assert_msg_ ( DYNA_REC ,  ! ( bits  = =  80  & &  op_80b  = =  floatINVALID ) ,  " WriteFloatLoadStore: 80 bits not supported for this instruction " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( bits ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									case  32 :  mf  =  0 ;  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 08:55:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									case  64 :  mf  =  4 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									case  80 :  mf  =  2 ;  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									default :  _assert_msg_ ( DYNA_REC ,  0 ,  " WriteFloatLoadStore: invalid bits (should be 32/64/80) " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 08:55:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Write8 ( 0xd9  |  mf ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// x87 instructions use the reg field of the ModR/M byte as opcode:
 
							 
						 
					
						
							
								
									
										
										
										
											2014-09-02 08:55:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bits  = =  80 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										op  =  op_80b ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									arg . WriteRest ( this ,  0 ,  ( X64Reg )  op ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-28 22:15:09 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : FLD ( int  bits ,  const  OpArg &  src )    {  WriteFloatLoadStore ( bits ,  floatLD ,  floatLD80 ,  src ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : FST ( int  bits ,  const  OpArg &  dest )   {  WriteFloatLoadStore ( bits ,  floatST ,  floatINVALID ,  dest ) ;  }  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  XEmitter : : FSTP ( int  bits ,  const  OpArg &  dest )  {  WriteFloatLoadStore ( bits ,  floatSTP ,  floatSTP80 ,  dest ) ;  }  
						 
					
						
							
								
									
										
										
										
											2014-02-03 23:56:11 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : FNSTSW_AX ( )  {  Write8 ( 0xDF ) ;  Write8 ( 0xE0 ) ;  }  
						 
					
						
							
								
									
										
										
										
											2014-01-25 18:38:06 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-08-26 11:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : RDTSC ( )  {  Write8 ( 0x0F ) ;  Write8 ( 0x31 ) ;  }  
						 
					
						
							
								
									
										
										
										
											2013-10-29 01:23:17 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// helper routines for setting pointers
  
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CallCdeclFunction3 ( void *  fnptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 )  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef _MSC_VER 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,   Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDI ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RSI ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CallCdeclFunction4 ( void *  fnptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 )  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef _MSC_VER 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDI ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RSI ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CallCdeclFunction5 ( void *  fnptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 ,  u32  arg4 )  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef _MSC_VER 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,   Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,   Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x20 ) ,  Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDI ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RSI ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,   Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2008-12-19 21:24:52 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : CallCdeclFunction6 ( void *  fnptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 ,  u32  arg4 ,  u32  arg5 )  
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef _MSC_VER 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x20 ) ,  Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x28 ) ,  Imm32 ( arg5 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDI ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RSI ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg5 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALL ( fnptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// See header
  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ___CallCdeclImport3 ( void *  impptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CALLptr ( M ( impptr ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ___CallCdeclImport4 ( void *  impptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CALLptr ( M ( impptr ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ___CallCdeclImport5 ( void *  impptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 ,  u32  arg4 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x20 ) ,  Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALLptr ( M ( impptr ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-08-30 16:14:56 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  XEmitter : : ___CallCdeclImport6 ( void *  impptr ,  u32  arg0 ,  u32  arg1 ,  u32  arg2 ,  u32  arg3 ,  u32  arg4 ,  u32  arg5 )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2013-03-19 21:51:12 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RCX ) ,  Imm32 ( arg0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( RDX ) ,  Imm32 ( arg1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R8 ) ,  Imm32 ( arg2 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  R ( R9 ) ,  Imm32 ( arg3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2008-12-08 05:30:24 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x20 ) ,  Imm32 ( arg4 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									MOV ( 32 ,  MDisp ( RSP ,  0x28 ) ,  Imm32 ( arg5 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CALLptr ( M ( impptr ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}