mirror of https://github.com/PCSX2/pcsx2.git
Implemented the 16 bit forms of Group 1 instructions into the new emitter.
git-svn-id: http://pcsx2.googlecode.com/svn/trunk@922 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
parent
5f354c3cee
commit
920e99145e
|
@ -46,9 +46,16 @@ extern __threadlocal u8 *x86Ptr;
|
|||
extern __threadlocal u8 *j8Ptr[32];
|
||||
extern __threadlocal u32 *j32Ptr[32];
|
||||
|
||||
template< typename T >
|
||||
static emitterT void x86write( T val )
|
||||
{
|
||||
*(T*)x86Ptr = val;
|
||||
x86Ptr += sizeof(T);
|
||||
}
|
||||
|
||||
static emitterT void write8( u8 val )
|
||||
{
|
||||
*x86Ptr = (u8)val;
|
||||
*x86Ptr = val;
|
||||
x86Ptr++;
|
||||
}
|
||||
|
||||
|
@ -271,9 +278,9 @@ extern void ADD32MtoR( x86IntRegType to, uptr from );
|
|||
// add r16 to r16
|
||||
extern void ADD16RtoR( x86IntRegType to , x86IntRegType from );
|
||||
// add imm16 to r16
|
||||
extern void ADD16ItoR( x86IntRegType to, s16 from );
|
||||
extern void ADD16ItoR( x86IntRegType to, u16 imm );
|
||||
// add imm16 to m16
|
||||
extern void ADD16ItoM( uptr to, s16 from );
|
||||
extern void ADD16ItoM( uptr to, u16 imm );
|
||||
// add r16 to m16
|
||||
extern void ADD16RtoM( uptr to, x86IntRegType from );
|
||||
// add m16 to r16
|
||||
|
@ -313,7 +320,7 @@ extern void SUB32MtoR( x86IntRegType to, uptr from ) ;
|
|||
// sub r32 to m32
|
||||
extern void SUB32RtoM( uptr to, x86IntRegType from );
|
||||
// sub r16 to r16
|
||||
extern void SUB16RtoR( x86IntRegType to, u16 from );
|
||||
extern void SUB16RtoR( x86IntRegType to, x86IntRegType from );
|
||||
// sub imm16 to r16
|
||||
extern void SUB16ItoR( x86IntRegType to, u16 from );
|
||||
// sub imm16 to m16
|
||||
|
@ -643,12 +650,6 @@ extern void CMP32ItoM( uptr to, u32 from );
|
|||
extern void CMP32RtoR( x86IntRegType to, x86IntRegType from );
|
||||
// cmp m32 to r32
|
||||
extern void CMP32MtoR( x86IntRegType to, uptr from );
|
||||
// cmp imm32 to [r32]
|
||||
extern void CMP32I8toRm( x86IntRegType to, u8 from);
|
||||
// cmp imm32 to [r32+off]
|
||||
extern void CMP32I8toRm8( x86IntRegType to, u8 from, u8 off);
|
||||
// cmp imm8 to [r32]
|
||||
extern void CMP32I8toM( uptr to, u8 from);
|
||||
|
||||
// cmp imm16 to r16
|
||||
extern void CMP16ItoR( x86IntRegType to, u16 from );
|
||||
|
|
|
@ -46,13 +46,27 @@ enum Group1InstructionType
|
|||
};
|
||||
|
||||
|
||||
emitterT void Group1_32( Group1InstructionType inst, x86Register to, x86Register from )
|
||||
static emitterT void Group1( Group1InstructionType inst, x86Register to, x86Register from )
|
||||
{
|
||||
write8( 0x01 | (inst<<3) );
|
||||
ModRM( 3, from.Id, to.Id );
|
||||
}
|
||||
|
||||
emitterT void Group1_32( Group1InstructionType inst, x86Register to, u32 imm )
|
||||
static emitterT void Group1( Group1InstructionType inst, const ModSib& sibdest, x86Register from )
|
||||
{
|
||||
write8( 0x01 | (inst<<3) );
|
||||
EmitSibMagic( from, sibdest );
|
||||
}
|
||||
|
||||
/* add m32 to r32 */
|
||||
static emitterT void Group1( Group1InstructionType inst, x86Register to, const ModSib& sibsrc )
|
||||
{
|
||||
write8( 0x03 | (inst<<3) );
|
||||
EmitSibMagic( to, sibsrc );
|
||||
}
|
||||
|
||||
template< typename T >
|
||||
static emitterT void Group1_Imm( Group1InstructionType inst, x86Register to, T imm )
|
||||
{
|
||||
if( is_s8( imm ) )
|
||||
{
|
||||
|
@ -69,11 +83,12 @@ emitterT void Group1_32( Group1InstructionType inst, x86Register to, u32 imm )
|
|||
write8( 0x81 );
|
||||
ModRM( 3, inst, to.Id );
|
||||
}
|
||||
write32( imm );
|
||||
x86write<T>( imm );
|
||||
}
|
||||
}
|
||||
|
||||
emitterT void Group1_32( Group1InstructionType inst, const ModSib& sibdest, u32 imm )
|
||||
template< typename T >
|
||||
static emitterT void Group1_Imm( Group1InstructionType inst, const ModSib& sibdest, T imm )
|
||||
{
|
||||
write8( is_s8( imm ) ? 0x83 : 0x81 );
|
||||
|
||||
|
@ -82,23 +97,10 @@ emitterT void Group1_32( Group1InstructionType inst, const ModSib& sibdest, u32
|
|||
if( is_s8( imm ) )
|
||||
write8( (s8)imm );
|
||||
else
|
||||
write32( imm );
|
||||
x86write<T>( imm );
|
||||
}
|
||||
|
||||
emitterT void Group1_32( Group1InstructionType inst, const ModSib& sibdest, x86Register from )
|
||||
{
|
||||
write8( 0x01 | (inst<<3) );
|
||||
EmitSibMagic( from, sibdest );
|
||||
}
|
||||
|
||||
/* add m32 to r32 */
|
||||
emitterT void Group1_32( Group1InstructionType inst, x86Register to, const ModSib& sibsrc )
|
||||
{
|
||||
write8( 0x03 | (inst<<3) );
|
||||
EmitSibMagic( to, sibsrc );
|
||||
}
|
||||
|
||||
emitterT void Group1_8( Group1InstructionType inst, x86Register to, s8 imm )
|
||||
static emitterT void Group1_8( Group1InstructionType inst, x86Register to, s8 imm )
|
||||
{
|
||||
if( to == eax )
|
||||
{
|
||||
|
@ -113,28 +115,30 @@ emitterT void Group1_8( Group1InstructionType inst, x86Register to, s8 imm )
|
|||
}
|
||||
}
|
||||
|
||||
// 16 bit instruction prefix!
|
||||
static __forceinline void prefix16() { write8(0x66); }
|
||||
static __forceinline x86Register cvt2reg( x86Register16 src ) { return x86Register( src.Id ); }
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
#define DEFINE_GROUP1_OPCODE( lwr, cod ) \
|
||||
emitterT void lwr##32( x86Register to, x86Register from ) { Group1_32( G1Type_##cod, to, from ); } \
|
||||
emitterT void lwr##32( x86Register to, u32 imm ) { Group1_32( G1Type_##cod, to, imm ); } \
|
||||
emitterT void lwr##32( x86Register to, void* from ) { Group1_32( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##32( void* to, x86Register from ) { Group1_32( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##32( void* to, u32 imm ) { Group1_32( G1Type_##cod, ptr[to], imm ); } \
|
||||
emitterT void lwr##32( x86Register to, const x86ModRm& from ) { Group1_32( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##32( const x86ModRm& to, x86Register from ) { Group1_32( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##32( const x86ModRm& to, u32 imm ) { Group1_32( G1Type_##cod, ptr[to], imm ); }
|
||||
|
||||
/*
|
||||
emitterT void lwr##16( x86Register16 to, x86Register16 from ) { Group1_32( G1Type_##cod, to, from ); } \
|
||||
emitterT void lwr##16( x86Register16 to, u16 imm ) { Group1_32( G1Type_##cod, to, imm ); } \
|
||||
emitterT void lwr##16( x86Register16 to, void* from ) { Group1_32( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##16( void* to, x86Register16 from ) { Group1_32( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##16( void* to, u16 imm ) { Group1_32( G1Type_##cod, ptr[to], imm ); } \
|
||||
emitterT void lwr##16( x86Register16 to, const x86ModRm& from ){ Group1_32( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##16( const x86ModRm& to, x86Register16 from ){ Group1_32( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##16( const x86ModRm& to, u32 imm ) { Group1_32( G1Type_##cod, ptr[to], imm ); }
|
||||
*/
|
||||
emitterT void lwr##32( x86Register to, x86Register from ) { Group1( G1Type_##cod, to, from ); } \
|
||||
emitterT void lwr##32( x86Register to, void* from ) { Group1( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##32( void* to, x86Register from ) { Group1( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##32( x86Register to, const x86ModRm& from ) { Group1( G1Type_##cod, to, ptr[from] ); } \
|
||||
emitterT void lwr##32( const x86ModRm& to, x86Register from ) { Group1( G1Type_##cod, ptr[to], from ); } \
|
||||
emitterT void lwr##32( x86Register to, u32 imm ) { Group1_Imm( G1Type_##cod, to, imm ); } \
|
||||
emitterT void lwr##32( void* to, u32 imm ) { Group1_Imm( G1Type_##cod, ptr[to], imm ); } \
|
||||
emitterT void lwr##32( const x86ModRm& to, u32 imm ) { Group1_Imm( G1Type_##cod, ptr[to], imm ); } \
|
||||
\
|
||||
emitterT void lwr##16( x86Register16 to, x86Register16 from ) { prefix16(); Group1( G1Type_##cod, cvt2reg(to), cvt2reg(from) ); } \
|
||||
emitterT void lwr##16( x86Register16 to, void* from ) { prefix16(); Group1( G1Type_##cod, cvt2reg(to), ptr[from] ); } \
|
||||
emitterT void lwr##16( void* to, x86Register16 from ) { prefix16(); Group1( G1Type_##cod, ptr[to], cvt2reg(from) ); } \
|
||||
emitterT void lwr##16( x86Register16 to, const x86ModRm& from ){ prefix16(); Group1( G1Type_##cod, cvt2reg(to), ptr[from] ); } \
|
||||
emitterT void lwr##16( const x86ModRm& to, x86Register16 from ){ prefix16(); Group1( G1Type_##cod, ptr[to], cvt2reg(from) ); } \
|
||||
emitterT void lwr##16( x86Register16 to, u16 imm ) { prefix16(); Group1_Imm( G1Type_##cod, cvt2reg(to), imm ); } \
|
||||
emitterT void lwr##16( void* to, u16 imm ) { prefix16(); Group1_Imm( G1Type_##cod, ptr[to], imm ); } \
|
||||
emitterT void lwr##16( const x86ModRm& to, u16 imm ) { prefix16(); Group1_Imm( G1Type_##cod, ptr[to], imm ); }
|
||||
|
||||
DEFINE_GROUP1_OPCODE( add, ADD );
|
||||
DEFINE_GROUP1_OPCODE( cmp, CMP );
|
||||
|
@ -153,6 +157,10 @@ static __forceinline x86Emitter::x86Register _reghlp( x86IntRegType src )
|
|||
return x86Emitter::x86Register( src );
|
||||
}
|
||||
|
||||
static __forceinline x86Emitter::x86Register16 _reghlp16( x86IntRegType src )
|
||||
{
|
||||
return x86Emitter::x86Register16( src );
|
||||
}
|
||||
|
||||
static __forceinline x86Emitter::x86ModRm _mrmhlp( x86IntRegType src )
|
||||
{
|
||||
|
@ -167,9 +175,18 @@ static __forceinline x86Emitter::x86ModRm _mrmhlp( x86IntRegType src )
|
|||
emitterT void cod##32MtoR( x86IntRegType to, uptr from ) { x86Emitter::lwr##32( _reghlp(to), (void*)from ); } \
|
||||
emitterT void cod##32RtoM( uptr to, x86IntRegType from ) { x86Emitter::lwr##32( (void*)to, _reghlp(from) ); } \
|
||||
emitterT void cod##32ItoM( uptr to, u32 imm ) { x86Emitter::lwr##32( (void*)to, imm ); } \
|
||||
emitterT void cod##32ItoRm( x86IntRegType to, u32 imm, int offset ){ x86Emitter::lwr##32( _mrmhlp(to) + offset, imm ); } \
|
||||
emitterT void cod##32ItoRm( x86IntRegType to, u32 imm, int offset ) { x86Emitter::lwr##32( _mrmhlp(to) + offset, imm ); } \
|
||||
emitterT void cod##32RmtoR( x86IntRegType to, x86IntRegType from, int offset ) { x86Emitter::lwr##32( _reghlp(to), _mrmhlp(from) + offset ); } \
|
||||
emitterT void cod##32RtoRm( x86IntRegType to, x86IntRegType from, int offset ) { x86Emitter::lwr##32( _mrmhlp(to) + offset, _reghlp(from) ); }
|
||||
emitterT void cod##32RtoRm( x86IntRegType to, x86IntRegType from, int offset ) { x86Emitter::lwr##32( _mrmhlp(to) + offset, _reghlp(from) ); } \
|
||||
\
|
||||
emitterT void cod##16RtoR( x86IntRegType to, x86IntRegType from ) { x86Emitter::lwr##16( _reghlp16(to), _reghlp16(from) ); } \
|
||||
emitterT void cod##16ItoR( x86IntRegType to, u16 imm ) { x86Emitter::lwr##16( _reghlp16(to), imm ); } \
|
||||
emitterT void cod##16MtoR( x86IntRegType to, uptr from ) { x86Emitter::lwr##16( _reghlp16(to), (void*)from ); } \
|
||||
emitterT void cod##16RtoM( uptr to, x86IntRegType from ) { x86Emitter::lwr##16( (void*)to, _reghlp16(from) ); } \
|
||||
emitterT void cod##16ItoM( uptr to, u16 imm ) { x86Emitter::lwr##16( (void*)to, imm ); } \
|
||||
emitterT void cod##16ItoRm( x86IntRegType to, u16 imm, int offset ) { x86Emitter::lwr##16( _mrmhlp(to) + offset, imm ); } \
|
||||
emitterT void cod##16RmtoR( x86IntRegType to, x86IntRegType from, int offset ) { x86Emitter::lwr##16( _reghlp16(to), _mrmhlp(from) + offset ); } \
|
||||
emitterT void cod##16RtoRm( x86IntRegType to, x86IntRegType from, int offset ) { x86Emitter::lwr##16( _mrmhlp(to) + offset, _reghlp16(from) ); }
|
||||
|
||||
DEFINE_GROUP1_OPCODE_LEGACY( add, ADD );
|
||||
DEFINE_GROUP1_OPCODE_LEGACY( cmp, CMP );
|
||||
|
@ -180,6 +197,8 @@ DEFINE_GROUP1_OPCODE_LEGACY( and, AND );
|
|||
DEFINE_GROUP1_OPCODE_LEGACY( sub, SUB );
|
||||
DEFINE_GROUP1_OPCODE_LEGACY( xor, XOR );
|
||||
|
||||
// Special forms needed by the legacy emitter syntax:
|
||||
|
||||
emitterT void AND32I8toR( x86IntRegType to, s8 from )
|
||||
{
|
||||
x86Emitter::and32( _reghlp(to), from );
|
||||
|
|
|
@ -802,80 +802,6 @@ emitterT void CMOVLE32MtoR( x86IntRegType to, uptr from )
|
|||
// arithmetic instructions /
|
||||
////////////////////////////////////
|
||||
|
||||
// add r16 to r16
|
||||
emitterT void ADD16RtoR( x86IntRegType to , x86IntRegType from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexRB(0,to,from);
|
||||
write8( 0x03 );
|
||||
ModRM( 3, to, from );
|
||||
}
|
||||
|
||||
/* add imm16 to r16 */
|
||||
emitterT void ADD16ItoR( x86IntRegType to, s16 imm )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexB(0,to);
|
||||
|
||||
if (to == EAX)
|
||||
{
|
||||
write8( 0x05 );
|
||||
write16( imm );
|
||||
}
|
||||
else if(is_s8(imm))
|
||||
{
|
||||
write8( 0x83 );
|
||||
ModRM( 3, 0, to );
|
||||
write8((u8)imm );
|
||||
}
|
||||
else
|
||||
{
|
||||
write8( 0x81 );
|
||||
ModRM( 3, 0, to );
|
||||
write16( imm );
|
||||
}
|
||||
}
|
||||
|
||||
/* add imm16 to m16 */
|
||||
emitterT void ADD16ItoM( uptr to, s16 imm )
|
||||
{
|
||||
write8( 0x66 );
|
||||
if(is_s8(imm))
|
||||
{
|
||||
write8( 0x83 );
|
||||
ModRM( 0, 0, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write8((u8)imm );
|
||||
}
|
||||
else
|
||||
{
|
||||
write8( 0x81 );
|
||||
ModRM( 0, 0, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write16( imm );
|
||||
}
|
||||
}
|
||||
|
||||
/* add r16 to m16 */
|
||||
emitterT void ADD16RtoM(uptr to, x86IntRegType from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexR(0,from);
|
||||
write8( 0x01 );
|
||||
ModRM( 0, from, DISP32 );
|
||||
write32( MEMADDR(to, 4) );
|
||||
}
|
||||
|
||||
/* add m16 to r16 */
|
||||
emitterT void ADD16MtoR( x86IntRegType to, uptr from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexR(0,to);
|
||||
write8( 0x03 );
|
||||
ModRM( 0, to, DISP32 );
|
||||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
// add m8 to r8
|
||||
emitterT void ADD8MtoR( x86IntRegType to, uptr from )
|
||||
{
|
||||
|
@ -915,49 +841,6 @@ emitterT void INC16M( u32 to )
|
|||
write32( MEMADDR(to, 4) );
|
||||
}
|
||||
|
||||
|
||||
|
||||
// sub r16 to r16
|
||||
emitterT void SUB16RtoR( x86IntRegType to, u16 from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexRB(0,to,from);
|
||||
write8( 0x2b );
|
||||
ModRM( 3, to, from );
|
||||
}
|
||||
|
||||
/* sub imm16 to r16 */
|
||||
emitterT void SUB16ItoR( x86IntRegType to, u16 from ) {
|
||||
write8( 0x66 );
|
||||
RexB(0,to);
|
||||
if ( to == EAX ) {
|
||||
write8( 0x2D );
|
||||
}
|
||||
else {
|
||||
write8( 0x81 );
|
||||
ModRM( 3, 5, to );
|
||||
}
|
||||
write16( from );
|
||||
}
|
||||
|
||||
/* sub imm16 to m16 */
|
||||
emitterT void SUB16ItoM( uptr to, u16 from ) {
|
||||
write8( 0x66 );
|
||||
write8( 0x81 );
|
||||
ModRM( 0, 5, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write16( from );
|
||||
}
|
||||
|
||||
/* sub m16 to r16 */
|
||||
emitterT void SUB16MtoR( x86IntRegType to, uptr from ) {
|
||||
write8( 0x66 );
|
||||
RexR(0,to);
|
||||
write8( 0x2B );
|
||||
ModRM( 0, to, DISP32 );
|
||||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
/* dec r32 */
|
||||
emitterT void DEC32R( x86IntRegType to )
|
||||
{
|
||||
|
@ -1331,60 +1214,6 @@ emitterT void SHRD32ItoR( x86IntRegType to, x86IntRegType from, u8 shift )
|
|||
// logical instructions /
|
||||
////////////////////////////////////
|
||||
|
||||
// or r16 to r16
|
||||
emitterT void OR16RtoR( x86IntRegType to, x86IntRegType from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexRB(0,from,to);
|
||||
write8( 0x09 );
|
||||
ModRM( 3, from, to );
|
||||
}
|
||||
|
||||
// or imm16 to r16
|
||||
emitterT void OR16ItoR( x86IntRegType to, u16 from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexB(0,to);
|
||||
if ( to == EAX ) {
|
||||
write8( 0x0D );
|
||||
}
|
||||
else {
|
||||
write8( 0x81 );
|
||||
ModRM( 3, 1, to );
|
||||
}
|
||||
write16( from );
|
||||
}
|
||||
|
||||
// or imm16 to m316
|
||||
emitterT void OR16ItoM( uptr to, u16 from )
|
||||
{
|
||||
write8(0x66);
|
||||
write8( 0x81 );
|
||||
ModRM( 0, 1, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write16( from );
|
||||
}
|
||||
|
||||
/* or m16 to r16 */
|
||||
emitterT void OR16MtoR( x86IntRegType to, uptr from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexR(0,to);
|
||||
write8( 0x0B );
|
||||
ModRM( 0, to, DISP32 );
|
||||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
// or r16 to m16
|
||||
emitterT void OR16RtoM( uptr to, x86IntRegType from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexR(0,from);
|
||||
write8( 0x09 );
|
||||
ModRM( 0, from, DISP32 );
|
||||
write32( MEMADDR(to, 4) );
|
||||
}
|
||||
|
||||
// or r8 to r8
|
||||
emitterT void OR8RtoR( x86IntRegType to, x86IntRegType from )
|
||||
{
|
||||
|
@ -1420,77 +1249,6 @@ emitterT void OR8MtoR( x86IntRegType to, uptr from )
|
|||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
// and r16 to r16
|
||||
emitterT void AND16RtoR( x86IntRegType to, x86IntRegType from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexRB(0,to,from);
|
||||
write8( 0x23 );
|
||||
ModRM( 3, to, from );
|
||||
}
|
||||
|
||||
/* and imm16 to r16 */
|
||||
emitterT void AND16ItoR( x86IntRegType to, u16 from )
|
||||
{
|
||||
write8(0x66);
|
||||
RexB(0,to);
|
||||
|
||||
if ( to == EAX ) {
|
||||
write8( 0x25 );
|
||||
write16( from );
|
||||
}
|
||||
else if ( from < 0x80 ) {
|
||||
write8( 0x83 );
|
||||
ModRM( 3, 0x4, to );
|
||||
write8((u8)from );
|
||||
}
|
||||
else {
|
||||
write8( 0x81 );
|
||||
ModRM( 3, 0x4, to );
|
||||
write16( from );
|
||||
}
|
||||
}
|
||||
|
||||
/* and imm16 to m16 */
|
||||
emitterT void AND16ItoM( uptr to, u16 from )
|
||||
{
|
||||
write8(0x66);
|
||||
if ( from < 0x80 ) {
|
||||
write8( 0x83 );
|
||||
ModRM( 0, 0x4, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write8((u8)from );
|
||||
}
|
||||
else
|
||||
{
|
||||
write8( 0x81 );
|
||||
ModRM( 0, 0x4, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write16( from );
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/* and r16 to m16 */
|
||||
emitterT void AND16RtoM( uptr to, x86IntRegType from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexR(0,from);
|
||||
write8( 0x21 );
|
||||
ModRM( 0, from, DISP32 );
|
||||
write32( MEMADDR(to, 4) );
|
||||
}
|
||||
|
||||
/* and m16 to r16 */
|
||||
emitterT void AND16MtoR( x86IntRegType to, uptr from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexR(0,to);
|
||||
write8( 0x23 );
|
||||
ModRM( 0, to, DISP32 );
|
||||
write32( MEMADDR(from, 4));
|
||||
}
|
||||
|
||||
/* and imm8 to r8 */
|
||||
emitterT void AND8ItoR( x86IntRegType to, u8 from )
|
||||
{
|
||||
|
@ -1906,93 +1664,6 @@ emitterT void CALL32M( u32 to )
|
|||
// misc instructions /
|
||||
////////////////////////////////////
|
||||
|
||||
// cmp imm8 to [r32] (byte ptr)
|
||||
emitterT void CMP8I8toRm( x86IntRegType to, s8 from, s8 off=0 )
|
||||
{
|
||||
RexB(0,to);
|
||||
write8( 0x80 );
|
||||
ModRM( (off != 0), 7, to );
|
||||
if( off != 0 ) write8(off);
|
||||
write8(from);
|
||||
}
|
||||
|
||||
// cmp imm8 to [r32]
|
||||
emitterT void CMP32I8toRm( x86IntRegType to, u8 from, s8 off=0 )
|
||||
{
|
||||
RexB(0,to);
|
||||
write8( 0x83 );
|
||||
ModRM( (off!=0), 7, to );
|
||||
if( off != 0 ) write8(off);
|
||||
write8(from);
|
||||
}
|
||||
|
||||
// cmp imm32 to [r32]
|
||||
emitterT void CMP32ItoRm( x86IntRegType to, u32 from, s8 off=0 )
|
||||
{
|
||||
// fixme : This should use the imm8 form if 'from' is between 127 and -128.
|
||||
|
||||
RexB(0,to);
|
||||
write8( 0x81 );
|
||||
ModRM( (off != 0), 7, to );
|
||||
if( off != 0 ) write8(off);
|
||||
write32(from);
|
||||
}
|
||||
|
||||
// cmp imm8 to [mem] (dword ptr)
|
||||
emitterT void CMP32I8toM( uptr to, u8 from )
|
||||
{
|
||||
write8( 0x83 );
|
||||
ModRM( 0, 7, DISP32 );
|
||||
write32( MEMADDR(to, 5) );
|
||||
write8( from );
|
||||
}
|
||||
|
||||
/* cmp imm16 to r16 */
|
||||
emitterT void CMP16ItoR( x86IntRegType to, u16 from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexB(0,to);
|
||||
if ( to == EAX )
|
||||
{
|
||||
write8( 0x3D );
|
||||
}
|
||||
else
|
||||
{
|
||||
write8( 0x81 );
|
||||
ModRM( 3, 7, to );
|
||||
}
|
||||
write16( from );
|
||||
}
|
||||
|
||||
/* cmp imm16 to m16 */
|
||||
emitterT void CMP16ItoM( uptr to, u16 from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
write8( 0x81 );
|
||||
ModRM( 0, 7, DISP32 );
|
||||
write32( MEMADDR(to, 6) );
|
||||
write16( from );
|
||||
}
|
||||
|
||||
/* cmp r16 to r16 */
|
||||
emitterT void CMP16RtoR( x86IntRegType to, x86IntRegType from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexRB(0,from,to);
|
||||
write8( 0x39 );
|
||||
ModRM( 3, from, to );
|
||||
}
|
||||
|
||||
/* cmp m16 to r16 */
|
||||
emitterT void CMP16MtoR( x86IntRegType to, uptr from )
|
||||
{
|
||||
write8( 0x66 );
|
||||
RexR(0,to);
|
||||
write8( 0x3B );
|
||||
ModRM( 0, to, DISP32 );
|
||||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
// cmp imm8 to r8
|
||||
emitterT void CMP8ItoR( x86IntRegType to, u8 from )
|
||||
{
|
||||
|
@ -2018,6 +1689,16 @@ emitterT void CMP8MtoR( x86IntRegType to, uptr from )
|
|||
write32( MEMADDR(from, 4) );
|
||||
}
|
||||
|
||||
// cmp imm8 to [r32] (byte ptr)
|
||||
emitterT void CMP8I8toRm( x86IntRegType to, s8 from, s8 off=0 )
|
||||
{
|
||||
RexB(0,to);
|
||||
write8( 0x80 );
|
||||
ModRM( (off != 0), 7, to );
|
||||
if( off != 0 ) write8(off);
|
||||
write8(from);
|
||||
}
|
||||
|
||||
/* test imm32 to r32 */
|
||||
emitterT void TEST32ItoR( x86IntRegType to, u32 from )
|
||||
{
|
||||
|
|
|
@ -151,7 +151,9 @@ struct CPUINFO{
|
|||
extern CPUINFO cpuinfo;
|
||||
//------------------------------------------------------------------
|
||||
|
||||
static __forceinline bool is_s8( u32 imm ) { return (s8)imm == (s32)imm; }
|
||||
// templated version of is_s8 is required, so that u16's get correct sign extension treatment.
|
||||
template< typename T >
|
||||
static __forceinline bool is_s8( T imm ) { return (s8)imm == (s32)imm; }
|
||||
|
||||
namespace x86Emitter
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue