fixed 16 bit segment optimisations
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@922 c046a42c-6fe2-441c-8c8c-71466251a162
This commit is contained in:
parent
2a2820560d
commit
dc196a57e3
@ -116,7 +116,7 @@
|
||||
/* 16 or 32 segments */
|
||||
#define HF_CS32_SHIFT 4
|
||||
#define HF_SS32_SHIFT 5
|
||||
/* zero base for DS, ES and SS */
|
||||
/* zero base for DS, ES and SS : can be '0' only in 32 bit CS segment */
|
||||
#define HF_ADDSEG_SHIFT 6
|
||||
/* copy of CR0.PE (protected mode) */
|
||||
#define HF_PE_SHIFT 7
|
||||
@ -398,7 +398,9 @@ static inline void cpu_x86_load_seg_cache(CPUX86State *env,
|
||||
>> (DESC_B_SHIFT - HF_CS32_SHIFT);
|
||||
new_hflags |= (env->segs[R_SS].flags & DESC_B_MASK)
|
||||
>> (DESC_B_SHIFT - HF_SS32_SHIFT);
|
||||
if (!(env->cr[0] & CR0_PE_MASK) || (env->eflags & VM_MASK)) {
|
||||
if (!(env->cr[0] & CR0_PE_MASK) ||
|
||||
(env->eflags & VM_MASK) ||
|
||||
!(new_hflags & HF_CS32_MASK)) {
|
||||
/* XXX: try to avoid this test. The problem comes from the
|
||||
fact that is real mode or vm86 mode we only modify the
|
||||
'base' and 'selector' fields of the segment cache to go
|
||||
|
@ -1538,15 +1538,17 @@ static void gen_movl_seg_T0(DisasContext *s, int seg_reg, unsigned int cur_eip)
|
||||
gen_op_set_cc_op(s->cc_op);
|
||||
gen_op_jmp_im(cur_eip);
|
||||
gen_op_movl_seg_T0(seg_reg);
|
||||
/* abort translation because the addseg value may change or
|
||||
because ss32 may change. For R_SS, translation must always
|
||||
stop as a special handling must be done to disable hardware
|
||||
interrupts for the next instruction */
|
||||
if (seg_reg == R_SS || (s->code32 && seg_reg < R_FS))
|
||||
s->is_jmp = 3;
|
||||
} else {
|
||||
gen_op_movl_seg_T0_vm(offsetof(CPUX86State,segs[seg_reg]));
|
||||
if (seg_reg == R_SS)
|
||||
s->is_jmp = 3;
|
||||
}
|
||||
/* abort translation because the register may have a non zero base
|
||||
or because ss32 may change. For R_SS, translation must always
|
||||
stop as a special handling must be done to disable hardware
|
||||
interrupts for the next instruction */
|
||||
if (seg_reg == R_SS || (!s->addseg && seg_reg < R_FS))
|
||||
s->is_jmp = 3;
|
||||
}
|
||||
|
||||
static inline void gen_stack_update(DisasContext *s, int addend)
|
||||
@ -4572,7 +4574,7 @@ static inline int gen_intermediate_code_internal(CPUState *env,
|
||||
);
|
||||
#if 0
|
||||
/* check addseg logic */
|
||||
if (!dc->addseg && (dc->vm86 || !dc->pe))
|
||||
if (!dc->addseg && (dc->vm86 || !dc->pe || !dc->code32))
|
||||
printf("ERROR addseg\n");
|
||||
#endif
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user