Changeset 37675 in vbox for trunk/src/recompiler/tcg/i386
- Timestamp:
- Jun 29, 2011 7:07:14 AM (14 years ago)
- Location:
- trunk/src/recompiler/tcg/i386
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/recompiler/tcg/i386/tcg-target.c
r36175 r37675 293 293 } 294 294 295 static inline void tgen_arithi(TCGContext *s, int c, int r0, int32_t val) 296 { 297 if (val == (int8_t)val) { 295 static inline void tgen_arithi(TCGContext *s, int c, int r0, int32_t val, int cf) 296 { 297 if (!cf && ((c == ARITH_ADD && val == 1) || (c == ARITH_SUB && val == -1))) { 298 /* inc */ 299 tcg_out_opc(s, 0x40 + r0); 300 } else if (!cf && ((c == ARITH_ADD && val == -1) || (c == ARITH_SUB && val == 1))) { 301 /* dec */ 302 tcg_out_opc(s, 0x48 + r0); 303 } else if (val == (int8_t)val) { 298 304 tcg_out_modrm(s, 0x83, c, r0); 299 305 tcg_out8(s, val); 306 } else if (c == ARITH_AND && val == 0xffu && r0 < 4) { 307 /* movzbl */ 308 tcg_out_modrm(s, 0xb6 | P_EXT, r0, r0); 309 } else if (c == ARITH_AND && val == 0xffffu) { 310 /* movzwl */ 311 tcg_out_modrm(s, 0xb7 | P_EXT, r0, r0); 300 312 } else { 301 313 tcg_out_modrm(s, 0x81, c, r0); … … 307 319 { 308 320 if (val != 0) 309 tgen_arithi(s, ARITH_ADD, reg, val );321 tgen_arithi(s, ARITH_ADD, reg, val, 0); 310 322 } 311 323 … … 314 326 { 315 327 if (val != 0) 316 tgen_arithi(s, ARITH_SUB, reg, val );328 tgen_arithi(s, ARITH_SUB, reg, val, 0); 317 329 } 318 330 #endif … … 363 375 tcg_out_modrm(s, 0x85, arg1, arg1); 364 376 } else { 365 tgen_arithi(s, ARITH_CMP, arg1, arg2 );377 tgen_arithi(s, ARITH_CMP, arg1, arg2, 0); 366 378 } 367 379 } else { … … 370 382 tcg_out_jxx(s, tcg_cond_to_jcc[cond], label_index); 371 383 } 372 373 #ifdef VBOX374 375 DECLINLINE(void) tcg_out_long_call(TCGContext *s, void* dst)376 {377 intptr_t disp;378 # ifdef VBOX379 tcg_gen_stack_alignment_check(s);380 # endif381 disp = (uintptr_t)dst - (uintptr_t)s->code_ptr - 5;382 tcg_out8(s, 0xe8); /* call disp32 */383 tcg_out32(s, disp); /* disp32 */384 }385 386 DECLINLINE(void) tcg_out_long_jmp(TCGContext *s, void* dst)387 {388 intptr_t disp = (uintptr_t)dst - (uintptr_t)s->code_ptr - 5;389 tcg_out8(s, 0xe9); /* jmp disp32 */390 tcg_out32(s, disp); /* disp32 */391 }392 393 #endif /* VBOX */394 384 395 385 /* XXX: we implement it at the target level to avoid having to … … 474 464 #endif 475 465 466 #ifndef CONFIG_USER_ONLY 467 #define GUEST_BASE 0 468 #endif 469 476 470 #if defined(VBOX) && defined(REM_PHYS_ADDR_IN_TLB) 477 static void *vbox_ld_helpers[] = { 471 472 static void * const vbox_ld_helpers[] = { 478 473 __ldub_vbox_phys, 479 474 __lduw_vbox_phys, … … 486 481 }; 487 482 488 static void * vbox_st_helpers[] = {483 static void * const vbox_st_helpers[] = { 489 484 __stb_vbox_phys, 490 485 __stw_vbox_phys, … … 493 488 }; 494 489 490 DECLINLINE(void) tcg_out_long_call(TCGContext *s, void* dst) 491 { 492 intptr_t disp; 493 # ifdef VBOX 494 tcg_gen_stack_alignment_check(s); 495 # endif 496 disp = (uintptr_t)dst - (uintptr_t)s->code_ptr - 5; 497 tcg_out8(s, 0xe8); /* call disp32 */ 498 tcg_out32(s, disp); /* disp32 */ 499 } 500 495 501 static void tcg_out_vbox_phys_read(TCGContext *s, int index, 496 502 int addr_reg, … … 503 509 AssertMsg(sizeof(RTGCPHYS) == 8, ("Physical address must be 64-bits, update caller\n")); 504 510 505 # if 0511 # if 0 506 512 tcg_out8(s, 0x6a); tcg_out8(s, 0x00); /* push $0 */ 507 513 tcg_out_push(s, addr_reg); 508 # else514 # else 509 515 /* mov addr_reg, %eax */ 510 516 tcg_out_mov(s, TCG_REG_EAX, addr_reg); 511 # endif517 # endif 512 518 513 519 tcg_out_long_call(s, vbox_ld_helpers[index]); … … 526 532 int useReg2 = ((index & 3) == 3); 527 533 528 # if 0534 # if 0 529 535 /* out parameter (value2) */ 530 536 if (useReg2) … … 536 542 tcg_out8(s, 0x6a); tcg_out8(s, 0x00); /* push $0 */ 537 543 tcg_out_push(s, addr_reg); 538 # else544 # else 539 545 Assert(val_reg != TCG_REG_EAX && (!useReg2 || (val_reg2 != TCG_REG_EAX))); 540 546 /* mov addr_reg, %eax */ … … 546 552 tcg_out_mov(s, TCG_REG_ECX, val_reg2); 547 553 548 # endif554 # endif 549 555 /* call it */ 550 556 tcg_out_long_call(s, vbox_st_helpers[index]); 551 557 552 558 /* clean stack after us */ 553 # if 0559 # if 0 554 560 tcg_out_addi(s, TCG_REG_ESP, 8 + (useReg2 ? 8 : 4)); 555 561 # endif … … 604 610 tcg_out32(s, (CPU_TLB_SIZE - 1) << CPU_TLB_ENTRY_BITS); 605 611 606 #ifndef VBOX607 612 tcg_out_opc(s, 0x8d); /* lea offset(r1, %ebp), r1 */ 608 613 tcg_out8(s, 0x80 | (r1 << 3) | 0x04); 614 #ifndef VBOX 609 615 tcg_out8(s, (5 << 3) | r1); 616 #else 617 tcg_out8(s, (TCG_AREG0 << 3) | r1); /* env, not %ebp */ 618 Assert(mem_index >= 0 && mem_index < NB_MMU_MODES); 619 #endif 610 620 tcg_out32(s, offsetof(CPUState, tlb_table[mem_index][0].addr_read)); 611 #else612 tcg_out_opc(s, 0x8d); /* lea offset(r1, env), r1 */613 tcg_out8(s, 0x80 | (r1 << 3) | 0x04);614 tcg_out8(s, (TCG_AREG0 << 3) | r1);615 tcg_out32(s, offsetof(CPUState, tlb_table[mem_index][0].addr_read));616 #endif617 621 618 622 /* cmp 0(r1), r0 */ … … 714 718 case 0: 715 719 /* movzbl */ 716 tcg_out_modrm_offset(s, 0xb6 | P_EXT, data_reg, r0, 0);720 tcg_out_modrm_offset(s, 0xb6 | P_EXT, data_reg, r0, GUEST_BASE); 717 721 break; 718 722 case 0 | 4: 719 723 /* movsbl */ 720 tcg_out_modrm_offset(s, 0xbe | P_EXT, data_reg, r0, 0);724 tcg_out_modrm_offset(s, 0xbe | P_EXT, data_reg, r0, GUEST_BASE); 721 725 break; 722 726 case 1: 723 727 /* movzwl */ 724 tcg_out_modrm_offset(s, 0xb7 | P_EXT, data_reg, r0, 0);728 tcg_out_modrm_offset(s, 0xb7 | P_EXT, data_reg, r0, GUEST_BASE); 725 729 if (bswap) { 726 730 /* rolw $8, data_reg */ … … 732 736 case 1 | 4: 733 737 /* movswl */ 734 tcg_out_modrm_offset(s, 0xbf | P_EXT, data_reg, r0, 0);738 tcg_out_modrm_offset(s, 0xbf | P_EXT, data_reg, r0, GUEST_BASE); 735 739 if (bswap) { 736 740 /* rolw $8, data_reg */ … … 745 749 case 2: 746 750 /* movl (r0), data_reg */ 747 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, 0);751 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, GUEST_BASE); 748 752 if (bswap) { 749 753 /* bswap */ … … 761 765 } 762 766 if (!bswap) { 763 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, 0);764 tcg_out_modrm_offset(s, 0x8b, data_reg2, r0, 4);767 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, GUEST_BASE); 768 tcg_out_modrm_offset(s, 0x8b, data_reg2, r0, GUEST_BASE + 4); 765 769 } else { 766 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, 4);770 tcg_out_modrm_offset(s, 0x8b, data_reg, r0, GUEST_BASE + 4); 767 771 tcg_out_opc(s, (0xc8 + data_reg) | P_EXT); 768 772 769 tcg_out_modrm_offset(s, 0x8b, data_reg2, r0, 0);773 tcg_out_modrm_offset(s, 0x8b, data_reg2, r0, GUEST_BASE); 770 774 /* bswap */ 771 775 tcg_out_opc(s, (0xc8 + data_reg2) | P_EXT); … … 842 846 tcg_out32(s, (CPU_TLB_SIZE - 1) << CPU_TLB_ENTRY_BITS); 843 847 844 #ifndef VBOX845 848 tcg_out_opc(s, 0x8d); /* lea offset(r1, %ebp), r1 */ 846 849 tcg_out8(s, 0x80 | (r1 << 3) | 0x04); 850 #ifndef VBOX 847 851 tcg_out8(s, (5 << 3) | r1); 852 #else 853 tcg_out8(s, (TCG_AREG0 << 3) | r1); /* env is not %ebp */ 854 Assert(mem_index >= 0 && mem_index < NB_MMU_MODES); 855 #endif 848 856 tcg_out32(s, offsetof(CPUState, tlb_table[mem_index][0].addr_write)); 849 #else850 tcg_out_opc(s, 0x8d); /* lea offset(r1, env), r1 */851 tcg_out8(s, 0x80 | (r1 << 3) | 0x04);852 tcg_out8(s, (TCG_AREG0 << 3) | r1);853 tcg_out32(s, offsetof(CPUState, tlb_table[mem_index][0].addr_write));854 #endif855 857 856 858 /* cmp 0(r1), r0 */ … … 1004 1006 case 0: 1005 1007 /* movb */ 1006 tcg_out_modrm_offset(s, 0x88, data_reg, r0, 0);1008 tcg_out_modrm_offset(s, 0x88, data_reg, r0, GUEST_BASE); 1007 1009 break; 1008 1010 case 1: … … 1016 1018 /* movw */ 1017 1019 tcg_out8(s, 0x66); 1018 tcg_out_modrm_offset(s, 0x89, data_reg, r0, 0);1020 tcg_out_modrm_offset(s, 0x89, data_reg, r0, GUEST_BASE); 1019 1021 break; 1020 1022 case 2: … … 1026 1028 } 1027 1029 /* movl */ 1028 tcg_out_modrm_offset(s, 0x89, data_reg, r0, 0);1030 tcg_out_modrm_offset(s, 0x89, data_reg, r0, GUEST_BASE); 1029 1031 break; 1030 1032 case 3: … … 1033 1035 /* bswap data_reg */ 1034 1036 tcg_out_opc(s, (0xc8 + r1) | P_EXT); 1035 tcg_out_modrm_offset(s, 0x89, r1, r0, 0);1037 tcg_out_modrm_offset(s, 0x89, r1, r0, GUEST_BASE); 1036 1038 tcg_out_mov(s, r1, data_reg); 1037 1039 /* bswap data_reg */ 1038 1040 tcg_out_opc(s, (0xc8 + r1) | P_EXT); 1039 tcg_out_modrm_offset(s, 0x89, r1, r0, 4);1041 tcg_out_modrm_offset(s, 0x89, r1, r0, GUEST_BASE + 4); 1040 1042 } else { 1041 tcg_out_modrm_offset(s, 0x89, data_reg, r0, 0);1042 tcg_out_modrm_offset(s, 0x89, data_reg2, r0, 4);1043 tcg_out_modrm_offset(s, 0x89, data_reg, r0, GUEST_BASE); 1044 tcg_out_modrm_offset(s, 0x89, data_reg2, r0, GUEST_BASE + 4); 1043 1045 } 1044 1046 break; … … 1158 1160 gen_arith: 1159 1161 if (const_args[2]) { 1160 tgen_arithi(s, c, args[0], args[2] );1162 tgen_arithi(s, c, args[0], args[2], 0); 1161 1163 } else { 1162 1164 tcg_out_modrm(s, 0x01 | (c << 3), args[2], args[0]); … … 1216 1218 case INDEX_op_add2_i32: 1217 1219 if (const_args[4]) 1218 tgen_arithi(s, ARITH_ADD, args[0], args[4] );1220 tgen_arithi(s, ARITH_ADD, args[0], args[4], 1); 1219 1221 else 1220 1222 tcg_out_modrm(s, 0x01 | (ARITH_ADD << 3), args[4], args[0]); 1221 1223 if (const_args[5]) 1222 tgen_arithi(s, ARITH_ADC, args[1], args[5] );1224 tgen_arithi(s, ARITH_ADC, args[1], args[5], 1); 1223 1225 else 1224 1226 tcg_out_modrm(s, 0x01 | (ARITH_ADC << 3), args[5], args[1]); … … 1226 1228 case INDEX_op_sub2_i32: 1227 1229 if (const_args[4]) 1228 tgen_arithi(s, ARITH_SUB, args[0], args[4] );1230 tgen_arithi(s, ARITH_SUB, args[0], args[4], 1); 1229 1231 else 1230 1232 tcg_out_modrm(s, 0x01 | (ARITH_SUB << 3), args[4], args[0]); 1231 1233 if (const_args[5]) 1232 tgen_arithi(s, ARITH_SBB, args[1], args[5] );1234 tgen_arithi(s, ARITH_SBB, args[1], args[5], 1); 1233 1235 else 1234 1236 tcg_out_modrm(s, 0x01 | (ARITH_SBB << 3), args[5], args[1]); … … 1263 1265 case INDEX_op_ext16s_i32: 1264 1266 tcg_out_modrm(s, 0xbf | P_EXT, args[0], args[1]); 1267 break; 1268 case INDEX_op_ext8u_i32: 1269 tcg_out_modrm(s, 0xb6 | P_EXT, args[0], args[1]); 1270 break; 1271 case INDEX_op_ext16u_i32: 1272 tcg_out_modrm(s, 0xb7 | P_EXT, args[0], args[1]); 1265 1273 break; 1266 1274 … … 1332 1340 { INDEX_op_shr_i32, { "r", "0", "ci" } }, 1333 1341 { INDEX_op_sar_i32, { "r", "0", "ci" } }, 1334 { INDEX_op_sar_i32, { "r", "0", "ci" } },1335 1342 { INDEX_op_rotl_i32, { "r", "0", "ci" } }, 1336 1343 { INDEX_op_rotr_i32, { "r", "0", "ci" } }, … … 1351 1358 { INDEX_op_ext8s_i32, { "r", "q" } }, 1352 1359 { INDEX_op_ext16s_i32, { "r", "r" } }, 1360 { INDEX_op_ext8u_i32, { "r", "q"} }, 1361 { INDEX_op_ext16u_i32, { "r", "r"} }, 1353 1362 1354 1363 #if TARGET_LONG_BITS == 32 -
trunk/src/recompiler/tcg/i386/tcg-target.h
r36175 r37675 53 53 #define TCG_TARGET_HAS_ext16s_i32 54 54 #define TCG_TARGET_HAS_rot_i32 55 #define TCG_TARGET_HAS_ext8u_i32 56 #define TCG_TARGET_HAS_ext16u_i32 57 58 #define TCG_TARGET_HAS_GUEST_BASE 55 59 56 60 /* Note: must be synced with dyngen-exec.h */
Note:
See TracChangeset
for help on using the changeset viewer.