Commit a8ede8ba8be076ae56b7c9ce9b4f2a115589543a

Authored by bellard
1 parent 826461bb

div64 fix - raise_interrupt() fix - SSE fix


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@1202 c046a42c-6fe2-441c-8c8c-71466251a162
target-i386/exec.h
@@ -176,17 +176,13 @@ void do_interrupt(int intno, int is_int, int error_code, @@ -176,17 +176,13 @@ void do_interrupt(int intno, int is_int, int error_code,
176 void do_interrupt_user(int intno, int is_int, int error_code, 176 void do_interrupt_user(int intno, int is_int, int error_code,
177 target_ulong next_eip); 177 target_ulong next_eip);
178 void raise_interrupt(int intno, int is_int, int error_code, 178 void raise_interrupt(int intno, int is_int, int error_code,
179 - unsigned int next_eip); 179 + int next_eip_addend);
180 void raise_exception_err(int exception_index, int error_code); 180 void raise_exception_err(int exception_index, int error_code);
181 void raise_exception(int exception_index); 181 void raise_exception(int exception_index);
182 void __hidden cpu_loop_exit(void); 182 void __hidden cpu_loop_exit(void);
183 183
184 void OPPROTO op_movl_eflags_T0(void); 184 void OPPROTO op_movl_eflags_T0(void);
185 void OPPROTO op_movl_T0_eflags(void); 185 void OPPROTO op_movl_T0_eflags(void);
186 -void raise_interrupt(int intno, int is_int, int error_code,  
187 - unsigned int next_eip);  
188 -void raise_exception_err(int exception_index, int error_code);  
189 -void raise_exception(int exception_index);  
190 void helper_divl_EAX_T0(void); 186 void helper_divl_EAX_T0(void);
191 void helper_idivl_EAX_T0(void); 187 void helper_idivl_EAX_T0(void);
192 void helper_mulq_EAX_T0(void); 188 void helper_mulq_EAX_T0(void);
target-i386/helper.c
@@ -1157,12 +1157,12 @@ void do_interrupt(int intno, int is_int, int error_code, @@ -1157,12 +1157,12 @@ void do_interrupt(int intno, int is_int, int error_code,
1157 * is_int is TRUE. 1157 * is_int is TRUE.
1158 */ 1158 */
1159 void raise_interrupt(int intno, int is_int, int error_code, 1159 void raise_interrupt(int intno, int is_int, int error_code,
1160 - unsigned int next_eip) 1160 + int next_eip_addend)
1161 { 1161 {
1162 env->exception_index = intno; 1162 env->exception_index = intno;
1163 env->error_code = error_code; 1163 env->error_code = error_code;
1164 env->exception_is_int = is_int; 1164 env->exception_is_int = is_int;
1165 - env->exception_next_eip = next_eip; 1165 + env->exception_next_eip = env->eip + next_eip_addend;
1166 cpu_loop_exit(); 1166 cpu_loop_exit();
1167 } 1167 }
1168 1168
@@ -2929,14 +2929,14 @@ void helper_fxsave(target_ulong ptr, int data64) @@ -2929,14 +2929,14 @@ void helper_fxsave(target_ulong ptr, int data64)
2929 } 2929 }
2930 2930
2931 if (env->cr[4] & CR4_OSFXSR_MASK) { 2931 if (env->cr[4] & CR4_OSFXSR_MASK) {
2932 - /* XXX: finish it, endianness */ 2932 + /* XXX: finish it */
2933 stl(ptr + 0x18, 0); /* mxcsr */ 2933 stl(ptr + 0x18, 0); /* mxcsr */
2934 stl(ptr + 0x1c, 0); /* mxcsr_mask */ 2934 stl(ptr + 0x1c, 0); /* mxcsr_mask */
2935 nb_xmm_regs = 8 << data64; 2935 nb_xmm_regs = 8 << data64;
2936 addr = ptr + 0xa0; 2936 addr = ptr + 0xa0;
2937 for(i = 0; i < nb_xmm_regs; i++) { 2937 for(i = 0; i < nb_xmm_regs; i++) {
2938 - stq(addr, env->xmm_regs[i].u.q[0]);  
2939 - stq(addr, env->xmm_regs[i].u.q[1]); 2938 + stq(addr, env->xmm_regs[i].XMM_Q(0));
  2939 + stq(addr + 8, env->xmm_regs[i].XMM_Q(1));
2940 addr += 16; 2940 addr += 16;
2941 } 2941 }
2942 } 2942 }
@@ -2972,8 +2972,8 @@ void helper_fxrstor(target_ulong ptr, int data64) @@ -2972,8 +2972,8 @@ void helper_fxrstor(target_ulong ptr, int data64)
2972 nb_xmm_regs = 8 << data64; 2972 nb_xmm_regs = 8 << data64;
2973 addr = ptr + 0xa0; 2973 addr = ptr + 0xa0;
2974 for(i = 0; i < nb_xmm_regs; i++) { 2974 for(i = 0; i < nb_xmm_regs; i++) {
2975 - env->xmm_regs[i].u.q[0] = ldq(addr);  
2976 - env->xmm_regs[i].u.q[1] = ldq(addr); 2975 + env->xmm_regs[i].XMM_Q(0) = ldq(addr);
  2976 + env->xmm_regs[i].XMM_Q(1) = ldq(addr + 8);
2977 addr += 16; 2977 addr += 16;
2978 } 2978 }
2979 } 2979 }
@@ -3099,6 +3099,7 @@ static void imul64(uint64_t *plow, uint64_t *phigh, int64_t a, int64_t b) @@ -3099,6 +3099,7 @@ static void imul64(uint64_t *plow, uint64_t *phigh, int64_t a, int64_t b)
3099 } 3099 }
3100 } 3100 }
3101 3101
  3102 +/* XXX: overflow support */
3102 static void div64(uint64_t *plow, uint64_t *phigh, uint64_t b) 3103 static void div64(uint64_t *plow, uint64_t *phigh, uint64_t b)
3103 { 3104 {
3104 uint64_t q, r, a1, a0; 3105 uint64_t q, r, a1, a0;
@@ -3114,16 +3115,16 @@ static void div64(uint64_t *plow, uint64_t *phigh, uint64_t b) @@ -3114,16 +3115,16 @@ static void div64(uint64_t *plow, uint64_t *phigh, uint64_t b)
3114 } else { 3115 } else {
3115 /* XXX: use a better algorithm */ 3116 /* XXX: use a better algorithm */
3116 for(i = 0; i < 64; i++) { 3117 for(i = 0; i < 64; i++) {
  3118 + a1 = (a1 << 1) | (a0 >> 63);
3117 if (a1 >= b) { 3119 if (a1 >= b) {
3118 a1 -= b; 3120 a1 -= b;
3119 qb = 1; 3121 qb = 1;
3120 } else { 3122 } else {
3121 qb = 0; 3123 qb = 0;
3122 } 3124 }
3123 - a1 = (a1 << 1) | (a0 >> 63);  
3124 a0 = (a0 << 1) | qb; 3125 a0 = (a0 << 1) | qb;
3125 } 3126 }
3126 -#if defined(DEBUG_MULDIV) || 1 3127 +#if defined(DEBUG_MULDIV)
3127 printf("div: 0x%016llx%016llx / 0x%016llx: q=0x%016llx r=0x%016llx\n", 3128 printf("div: 0x%016llx%016llx / 0x%016llx: q=0x%016llx r=0x%016llx\n",
3128 *phigh, *plow, b, a0, a1); 3129 *phigh, *plow, b, a0, a1);
3129 #endif 3130 #endif
@@ -3167,7 +3168,7 @@ void helper_imulq_EAX_T0(void) @@ -3167,7 +3168,7 @@ void helper_imulq_EAX_T0(void)
3167 EAX = r0; 3168 EAX = r0;
3168 EDX = r1; 3169 EDX = r1;
3169 CC_DST = r0; 3170 CC_DST = r0;
3170 - CC_SRC = (r1 != (r0 >> 63)); 3171 + CC_SRC = ((int64_t)r1 != ((int64_t)r0 >> 63));
3171 } 3172 }
3172 3173
3173 void helper_imulq_T0_T1(void) 3174 void helper_imulq_T0_T1(void)
target-i386/op.c
@@ -611,11 +611,10 @@ void OPPROTO op_debug(void) @@ -611,11 +611,10 @@ void OPPROTO op_debug(void)
611 611
612 void OPPROTO op_raise_interrupt(void) 612 void OPPROTO op_raise_interrupt(void)
613 { 613 {
614 - int intno;  
615 - unsigned int next_eip; 614 + int intno, next_eip_addend;
616 intno = PARAM1; 615 intno = PARAM1;
617 - next_eip = PARAM2;  
618 - raise_interrupt(intno, 1, 0, next_eip); 616 + next_eip_addend = PARAM2;
  617 + raise_interrupt(intno, 1, 0, next_eip_addend);
619 } 618 }
620 619
621 void OPPROTO op_raise_exception(void) 620 void OPPROTO op_raise_exception(void)
target-i386/ops_mem.h
@@ -85,18 +85,16 @@ void OPPROTO glue(glue(op_ldo, MEMSUFFIX), _env_A0)(void) @@ -85,18 +85,16 @@ void OPPROTO glue(glue(op_ldo, MEMSUFFIX), _env_A0)(void)
85 { 85 {
86 XMMReg *p; 86 XMMReg *p;
87 p = (XMMReg *)((char *)env + PARAM1); 87 p = (XMMReg *)((char *)env + PARAM1);
88 - /* XXX: host endianness ? */  
89 - p->u.q[0] = glue(ldq, MEMSUFFIX)(A0);  
90 - p->u.q[1] = glue(ldq, MEMSUFFIX)(A0 + 8); 88 + p->XMM_Q(0) = glue(ldq, MEMSUFFIX)(A0);
  89 + p->XMM_Q(1) = glue(ldq, MEMSUFFIX)(A0 + 8);
91 } 90 }
92 91
93 void OPPROTO glue(glue(op_sto, MEMSUFFIX), _env_A0)(void) 92 void OPPROTO glue(glue(op_sto, MEMSUFFIX), _env_A0)(void)
94 { 93 {
95 XMMReg *p; 94 XMMReg *p;
96 p = (XMMReg *)((char *)env + PARAM1); 95 p = (XMMReg *)((char *)env + PARAM1);
97 - /* XXX: host endianness ? */  
98 - glue(stq, MEMSUFFIX)(A0, p->u.q[0]);  
99 - glue(stq, MEMSUFFIX)(A0 + 8, p->u.q[1]); 96 + glue(stq, MEMSUFFIX)(A0, p->XMM_Q(0));
  97 + glue(stq, MEMSUFFIX)(A0 + 8, p->XMM_Q(1));
100 } 98 }
101 99
102 #ifdef TARGET_X86_64 100 #ifdef TARGET_X86_64
target-i386/translate.c
@@ -2119,7 +2119,7 @@ static void gen_interrupt(DisasContext *s, int intno, @@ -2119,7 +2119,7 @@ static void gen_interrupt(DisasContext *s, int intno,
2119 if (s->cc_op != CC_OP_DYNAMIC) 2119 if (s->cc_op != CC_OP_DYNAMIC)
2120 gen_op_set_cc_op(s->cc_op); 2120 gen_op_set_cc_op(s->cc_op);
2121 gen_jmp_im(cur_eip); 2121 gen_jmp_im(cur_eip);
2122 - gen_op_raise_interrupt(intno, next_eip); 2122 + gen_op_raise_interrupt(intno, (int)(next_eip - cur_eip));
2123 s->is_jmp = 3; 2123 s->is_jmp = 3;
2124 } 2124 }
2125 2125
@@ -4452,7 +4452,8 @@ static target_ulong disas_insn(DisasContext *s, target_ulong pc_start) @@ -4452,7 +4452,8 @@ static target_ulong disas_insn(DisasContext *s, target_ulong pc_start)
4452 goto illegal_op; 4452 goto illegal_op;
4453 if (s->cc_op != CC_OP_DYNAMIC) 4453 if (s->cc_op != CC_OP_DYNAMIC)
4454 gen_op_set_cc_op(s->cc_op); 4454 gen_op_set_cc_op(s->cc_op);
4455 - gen_op_into(s->pc - s->cs_base); 4455 + gen_jmp_im(pc_start - s->cs_base);
  4456 + gen_op_into(s->pc - pc_start);
4456 break; 4457 break;
4457 case 0xf1: /* icebp (undocumented, exits to external debugger) */ 4458 case 0xf1: /* icebp (undocumented, exits to external debugger) */
4458 #if 0 4459 #if 0
@@ -4826,7 +4827,7 @@ static target_ulong disas_insn(DisasContext *s, target_ulong pc_start) @@ -4826,7 +4827,7 @@ static target_ulong disas_insn(DisasContext *s, target_ulong pc_start)
4826 /* nothing to do */ 4827 /* nothing to do */
4827 } 4828 }
4828 break; 4829 break;
4829 - case 0x1ae: /* sfence */ 4830 + case 0x1ae:
4830 modrm = ldub_code(s->pc++); 4831 modrm = ldub_code(s->pc++);
4831 mod = (modrm >> 6) & 3; 4832 mod = (modrm >> 6) & 3;
4832 op = (modrm >> 3) & 7; 4833 op = (modrm >> 3) & 7;