Merge BSF simulation on P4 from Amithlon. Use 33-bit memory addressing model.

This commit is contained in:
gbeauche 2004-11-08 21:10:46 +00:00
parent e3c5f1769d
commit 0c255e1fbd
4 changed files with 102 additions and 47 deletions

View File

@ -200,6 +200,16 @@ LOWFUNC(NONE,READ,1,raw_pop_l_r,(R4 r))
}
LENDFUNC(NONE,READ,1,raw_pop_l_r,(R4 r))
LOWFUNC(NONE,READ,1,raw_pop_l_m,(MEMW d))
{
#if defined(__x86_64__)
POPQm(d, X86_NOREG, X86_NOREG, 1);
#else
POPLm(d, X86_NOREG, X86_NOREG, 1);
#endif
}
LENDFUNC(NONE,READ,1,raw_pop_l_m,(MEMW d))
LOWFUNC(WRITE,NONE,2,raw_bt_l_ri,(R4 r, IMM i))
{
BTLir(i, r);
@ -925,6 +935,12 @@ LOWFUNC(WRITE,NONE,2,raw_test_b_rr,(R1 d, R1 s))
}
LENDFUNC(WRITE,NONE,2,raw_test_b_rr,(R1 d, R1 s))
LOWFUNC(WRITE,NONE,2,raw_xor_l_ri,(RW4 d, IMM i))
{
XORLir(i, d);
}
LENDFUNC(WRITE,NONE,2,raw_xor_l_ri,(RW4 d, IMM i))
LOWFUNC(WRITE,NONE,2,raw_and_l_ri,(RW4 d, IMM i))
{
ANDLir(i, d);
@ -1208,6 +1224,14 @@ LOWFUNC(NONE,READ,1,raw_pop_l_r,(R4 r))
}
LENDFUNC(NONE,READ,1,raw_pop_l_r,(R4 r))
LOWFUNC(NONE,READ,1,raw_pop_l_m,(MEMW d))
{
emit_byte(0x8f);
emit_byte(0x05);
emit_long(d);
}
LENDFUNC(NONE,READ,1,raw_pop_l_m,(MEMW d))
LOWFUNC(WRITE,NONE,2,raw_bt_l_ri,(R4 r, IMM i))
{
emit_byte(0x0f);
@ -2500,6 +2524,14 @@ LOWFUNC(WRITE,NONE,2,raw_test_b_rr,(R1 d, R1 s))
}
LENDFUNC(WRITE,NONE,2,raw_test_b_rr,(R1 d, R1 s))
LOWFUNC(WRITE,NONE,2,raw_xor_l_ri,(RW4 d, IMM i))
{
emit_byte(0x81);
emit_byte(0xf0+d);
emit_long(i);
}
LENDFUNC(WRITE,NONE,2,raw_xor_l_ri,(RW4 d, IMM i))
LOWFUNC(WRITE,NONE,2,raw_and_l_ri,(RW4 d, IMM i))
{
if (optimize_imm8 && isbyte(i)) {
@ -3214,6 +3246,18 @@ static __inline__ void raw_reg_to_flags(int r)
raw_sahf(0);
}
#define FLAG_NREG3 0 /* Set to -1 if any register will do */
static __inline__ void raw_flags_set_zero(int s, int tmp)
{
raw_mov_l_rr(tmp,s);
raw_lahf(s); /* flags into ah */
raw_and_l_ri(s,0xffffbfff);
raw_and_l_ri(tmp,0x00004000);
raw_xor_l_ri(tmp,0x00004000);
raw_or_l(s,tmp);
raw_sahf(s);
}
#else
#define FLAG_NREG1 -1 /* Set to -1 if any register will do */
@ -3240,6 +3284,19 @@ static __inline__ void raw_reg_to_flags(int r)
raw_popfl();
}
#define FLAG_NREG3 -1 /* Set to -1 if any register will do */
static __inline__ void raw_flags_set_zero(int s, int tmp)
{
raw_mov_l_rr(tmp,s);
raw_pushfl();
raw_pop_l_r(s);
raw_and_l_ri(s,0xffffffbf);
raw_and_l_ri(tmp,0x00000040);
raw_xor_l_ri(tmp,0x00000040);
raw_or_l(s,tmp);
raw_push_l_r(s);
raw_popfl();
}
#endif
/* Apparently, there are enough instructions between flag store and
@ -3265,22 +3322,6 @@ static __inline__ void raw_load_flagx(uae_u32 target, uae_u32 r)
raw_mov_l_rm(target,(uintptr)live.state[r].mem);
}
#define NATIVE_FLAG_Z 0x40
static __inline__ void raw_flags_set_zero(int f, int r, int t)
{
// FIXME: this is really suboptimal
raw_pushfl();
raw_pop_l_r(f);
raw_and_l_ri(f,~NATIVE_FLAG_Z);
raw_test_l_rr(r,r);
raw_mov_l_ri(r,0);
raw_mov_l_ri(t,NATIVE_FLAG_Z);
raw_cmov_l_rr(r,t,NATIVE_CC_EQ);
raw_or_l(f,r);
raw_push_l_r(f);
raw_popfl();
}
static __inline__ void raw_inc_sp(int off)
{
raw_add_l_ri(ESP_INDEX,off);

View File

@ -348,8 +348,7 @@ DECLARE_MIDFUNC(setcc(W1 d, IMM cc));
DECLARE_MIDFUNC(setcc_m(IMM d, IMM cc));
DECLARE_MIDFUNC(cmov_l_rr(RW4 d, R4 s, IMM cc));
DECLARE_MIDFUNC(cmov_l_rm(RW4 d, IMM s, IMM cc));
/* Set native Z flag only if register is zero */
DECLARE_MIDFUNC(setzflg_l(RW4 r));
DECLARE_MIDFUNC(bsf_l_rr(W4 d, R4 s));
DECLARE_MIDFUNC(pop_m(IMM d));
DECLARE_MIDFUNC(push_m(IMM d));
DECLARE_MIDFUNC(pop_l(W4 d));
@ -516,6 +515,8 @@ extern void writelong_clobber(int address, int source, int tmp);
extern void get_n_addr(int address, int dest, int tmp);
extern void get_n_addr_jmp(int address, int dest, int tmp);
extern void calc_disp_ea_020(int base, uae_u32 dp, int target, int tmp);
/* Set native Z flag only if register is zero */
extern void set_zero(int r, int tmp);
extern int kill_rodent(int r);
extern void sync_m68k_pc(void);
extern uae_u32 get_const(int r);

View File

@ -121,6 +121,9 @@ static compop_func *nfcompfunctbl[65536];
static cpuop_func *nfcpufunctbl[65536];
uae_u8* comp_pc_p;
// From main_unix.cpp
extern bool ThirtyThreeBitAddressing;
// From newcpu.cpp
extern bool quit_program;
@ -2934,30 +2937,30 @@ MIDFUNC(3,cmov_l_rm,(RW4 d, IMM s, IMM cc))
}
MENDFUNC(3,cmov_l_rm,(RW4 d, IMM s, IMM cc))
MIDFUNC(1,setzflg_l,(RW4 r))
MIDFUNC(2,bsf_l_rr,(W4 d, W4 s))
{
if (setzflg_uses_bsf) {
CLOBBER_BSF;
r=rmw(r,4,4);
raw_bsf_l_rr(r,r);
unlock2(r);
}
else {
Dif (live.flags_in_flags!=VALID) {
write_log("setzflg() wanted flags in native flags, they are %d\n",
live.flags_in_flags);
abort();
}
r=readreg(r,4);
int f=writereg(S11,4);
int t=writereg(S12,4);
raw_flags_set_zero(f,r,t);
unlock2(f);
unlock2(r);
unlock2(t);
}
CLOBBER_BSF;
s = readreg(s, 4);
d = writereg(d, 4);
raw_bsf_l_rr(d, s);
unlock2(s);
unlock2(d);
}
MENDFUNC(1,setzflg_l,(RW4 r))
MENDFUNC(2,bsf_l_rr,(W4 d, W4 s))
/* Set the Z flag depending on the value in s. Note that the
value has to be 0 or -1 (or, more precisely, for non-zero
values, bit 14 must be set)! */
MIDFUNC(2,simulate_bsf,(W4 tmp, RW4 s))
{
CLOBBER_BSF;
s=rmw_specific(s,4,4,FLAG_NREG3);
tmp=writereg(tmp,4);
raw_flags_set_zero(s, tmp);
unlock2(tmp);
unlock2(s);
}
MENDFUNC(2,simulate_bsf,(W4 tmp, RW4 s))
MIDFUNC(2,imul_32_32,(RW4 d, R4 s))
{
@ -4879,6 +4882,14 @@ MENDFUNC(2,fmul_rr,(FRW d, FR s))
* Support functions exposed to gencomp. CREATE time *
********************************************************************/
void set_zero(int r, int tmp)
{
if (setzflg_uses_bsf)
bsf_l_rr(r,r);
else
simulate_bsf(tmp,r);
}
int kill_rodent(int r)
{
return KILLTHERAT &&
@ -5366,8 +5377,8 @@ static void writemem_real(int address, int source, int size, int tmp, int clobbe
f=source;
#if SIZEOF_VOID_P == 8
/* HACK: address calculation is suboptimal and possibly broken */
sign_extend_32_rr(address, address);
if (!ThirtyThreeBitAddressing)
sign_extend_32_rr(address, address);
#endif
switch(size) {
@ -5430,8 +5441,8 @@ static void readmem_real(int address, int dest, int size, int tmp)
f=dest;
#if SIZEOF_VOID_P == 8
/* HACK: address calculation is suboptimal and possibly broken */
sign_extend_32_rr(address, address);
if (!ThirtyThreeBitAddressing)
sign_extend_32_rr(address, address);
#endif
switch(size) {

View File

@ -1100,7 +1100,7 @@ genflags (flagtypes type, wordsizes size, char *value, char *src, char *dst)
"\tint one=scratchie++;\n"
"\tif (needed_flags&FLAG_Z) {\n"
"\tmov_l_ri(zero,0);\n"
"\tmov_l_ri(one,1);\n"
"\tmov_l_ri(one,-1);\n"
"\tmake_flags_live();\n"
"\tcmov_l_rr(zero,one,5);\n"
"\t}\n");
@ -1123,7 +1123,7 @@ genflags (flagtypes type, wordsizes size, char *value, char *src, char *dst)
comprintf("\tlive_flags();\n");
comprintf("\tif (needed_flags&FLAG_Z) {\n"
"\tcmov_l_rr(zero,one,5);\n"
"\tsetzflg_l(zero);\n"
"\tset_zero(zero, one);\n" /* No longer need one */
"\tlive_flags();\n"
"\t}\n");
comprintf("\tend_needflags();\n");
@ -1365,6 +1365,7 @@ gen_opcode (unsigned long int opcode)
genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
start_brace();
comprintf("\tint s=scratchie++;\n"
"\tint tmp=scratchie++;\n"
"\tmov_l_rr(s,src);\n");
if (curi->size == sz_byte)
comprintf("\tand_l_ri(s,7);\n");
@ -1380,6 +1381,7 @@ gen_opcode (unsigned long int opcode)
case i_BCLR: op="btr"; break;
case i_BSET: op="bts"; break;
case i_BTST: op="bt"; need_write=0; break;
default: abort();
}
comprintf("\t%s_l_rr(dst,s);\n" /* Answer now in C */
"\tsbb_l(s,s);\n" /* s is 0 if bit was 0, -1 otherwise */
@ -1387,7 +1389,7 @@ gen_opcode (unsigned long int opcode)
"\tdont_care_flags();\n",op);
if (!noflags) {
comprintf("\tstart_needflags();\n"
"\tsetzflg_l(s);\n"
"\tset_zero(s,tmp);\n"
"\tlive_flags();\n"
"\tend_needflags();\n");
}