Commit 9c29504eb71238241f29667bd96fb83c97668e1a
1 parent
a986fcc4
alpha: convert cmov and bcond to TCG
Patch mostly by Tristan Gingold git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5245 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
3 changed files
with
69 additions
and
115 deletions
target-alpha/op.c
| ... | ... | @@ -434,72 +434,6 @@ void OPPROTO op_cmpbge (void) |
| 434 | 434 | RETURN(); |
| 435 | 435 | } |
| 436 | 436 | |
| 437 | -void OPPROTO op_cmpeqz (void) | |
| 438 | -{ | |
| 439 | - if (T0 == 0) | |
| 440 | - T0 = 1; | |
| 441 | - else | |
| 442 | - T0 = 0; | |
| 443 | - RETURN(); | |
| 444 | -} | |
| 445 | - | |
| 446 | -void OPPROTO op_cmpnez (void) | |
| 447 | -{ | |
| 448 | - if (T0 != 0) | |
| 449 | - T0 = 1; | |
| 450 | - else | |
| 451 | - T0 = 0; | |
| 452 | - RETURN(); | |
| 453 | -} | |
| 454 | - | |
| 455 | -void OPPROTO op_cmpltz (void) | |
| 456 | -{ | |
| 457 | - if ((int64_t)T0 < 0) | |
| 458 | - T0 = 1; | |
| 459 | - else | |
| 460 | - T0 = 0; | |
| 461 | - RETURN(); | |
| 462 | -} | |
| 463 | - | |
| 464 | -void OPPROTO op_cmplez (void) | |
| 465 | -{ | |
| 466 | - if ((int64_t)T0 <= 0) | |
| 467 | - T0 = 1; | |
| 468 | - else | |
| 469 | - T0 = 0; | |
| 470 | - RETURN(); | |
| 471 | -} | |
| 472 | - | |
| 473 | -void OPPROTO op_cmpgtz (void) | |
| 474 | -{ | |
| 475 | - if ((int64_t)T0 > 0) | |
| 476 | - T0 = 1; | |
| 477 | - else | |
| 478 | - T0 = 0; | |
| 479 | - RETURN(); | |
| 480 | -} | |
| 481 | - | |
| 482 | -void OPPROTO op_cmpgez (void) | |
| 483 | -{ | |
| 484 | - if ((int64_t)T0 >= 0) | |
| 485 | - T0 = 1; | |
| 486 | - else | |
| 487 | - T0 = 0; | |
| 488 | - RETURN(); | |
| 489 | -} | |
| 490 | - | |
| 491 | -void OPPROTO op_cmplbs (void) | |
| 492 | -{ | |
| 493 | - T0 &= 1; | |
| 494 | - RETURN(); | |
| 495 | -} | |
| 496 | - | |
| 497 | -void OPPROTO op_cmplbc (void) | |
| 498 | -{ | |
| 499 | - T0 = (~T0) & 1; | |
| 500 | - RETURN(); | |
| 501 | -} | |
| 502 | - | |
| 503 | 437 | #if 0 // Qemu does not know how to do this... |
| 504 | 438 | void OPPROTO op_bcond (void) |
| 505 | 439 | { | ... | ... |
target-alpha/op_template.h
| ... | ... | @@ -37,15 +37,7 @@ void OPPROTO glue(op_reset_FT, REG) (void) |
| 37 | 37 | |
| 38 | 38 | #endif /* REG < 3 */ |
| 39 | 39 | |
| 40 | -/* Fixed-point register moves */ | |
| 41 | 40 | #if REG < 31 |
| 42 | -void OPPROTO glue(op_cmov_ir, REG) (void) | |
| 43 | -{ | |
| 44 | - if (T0) | |
| 45 | - env->ir[REG] = T1; | |
| 46 | - RETURN(); | |
| 47 | -} | |
| 48 | - | |
| 49 | 41 | /* floating point registers moves */ |
| 50 | 42 | void OPPROTO glue(op_load_FT0_fir, REG) (void) |
| 51 | 43 | { | ... | ... |
target-alpha/translate.c
| ... | ... | @@ -124,11 +124,6 @@ static always_inline void func (int n) \ |
| 124 | 124 | NAME ## _table[n](); \ |
| 125 | 125 | } |
| 126 | 126 | |
| 127 | -/* IR moves */ | |
| 128 | -/* Special hacks for ir31 */ | |
| 129 | -#define gen_op_cmov_ir31 gen_op_nop | |
| 130 | -GEN32(gen_op_cmov_ir, gen_op_cmov_ir); | |
| 131 | - | |
| 132 | 127 | /* FIR moves */ |
| 133 | 128 | /* Special hacks for fir31 */ |
| 134 | 129 | #define gen_op_load_FT0_fir31 gen_op_reset_FT0 |
| ... | ... | @@ -328,16 +323,32 @@ static always_inline void gen_store_fmem (DisasContext *ctx, |
| 328 | 323 | } |
| 329 | 324 | |
| 330 | 325 | static always_inline void gen_bcond (DisasContext *ctx, |
| 331 | - void (*gen_test_op)(void), | |
| 332 | - int ra, int32_t disp16) | |
| 326 | + TCGCond cond, | |
| 327 | + int ra, int32_t disp16, int mask) | |
| 333 | 328 | { |
| 334 | - tcg_gen_movi_i64(cpu_T[1], ctx->pc + (int64_t)(disp16 << 2)); | |
| 335 | - if (ra != 31) | |
| 336 | - tcg_gen_mov_i64(cpu_T[0], cpu_ir[ra]); | |
| 337 | - else | |
| 338 | - tcg_gen_movi_i64(cpu_T[0], 0); | |
| 339 | - (*gen_test_op)(); | |
| 340 | - _gen_op_bcond(ctx); | |
| 329 | + int l1, l2; | |
| 330 | + | |
| 331 | + l1 = gen_new_label(); | |
| 332 | + l2 = gen_new_label(); | |
| 333 | + if (likely(ra != 31)) { | |
| 334 | + if (mask) { | |
| 335 | + TCGv tmp = tcg_temp_new(TCG_TYPE_I64); | |
| 336 | + tcg_gen_andi_i64(tmp, cpu_ir[ra], 1); | |
| 337 | + tcg_gen_brcondi_i64(cond, tmp, 0, l1); | |
| 338 | + tcg_temp_free(tmp); | |
| 339 | + } else | |
| 340 | + tcg_gen_brcondi_i64(cond, cpu_ir[ra], 0, l1); | |
| 341 | + } else { | |
| 342 | + /* Very uncommon case - Do not bother to optimize. */ | |
| 343 | + TCGv tmp = tcg_const_i64(0); | |
| 344 | + tcg_gen_brcondi_i64(cond, tmp, 0, l1); | |
| 345 | + tcg_temp_free(tmp); | |
| 346 | + } | |
| 347 | + tcg_gen_movi_i64(cpu_pc, ctx->pc); | |
| 348 | + tcg_gen_br(l2); | |
| 349 | + gen_set_label(l1); | |
| 350 | + tcg_gen_movi_i64(cpu_pc, ctx->pc + (int64_t)(disp16 << 2)); | |
| 351 | + gen_set_label(l2); | |
| 341 | 352 | } |
| 342 | 353 | |
| 343 | 354 | static always_inline void gen_fbcond (DisasContext *ctx, |
| ... | ... | @@ -371,22 +382,39 @@ static always_inline void gen_arith3 (DisasContext *ctx, |
| 371 | 382 | } |
| 372 | 383 | |
| 373 | 384 | static always_inline void gen_cmov (DisasContext *ctx, |
| 374 | - void (*gen_test_op)(void), | |
| 385 | + TCGCond inv_cond, | |
| 375 | 386 | int ra, int rb, int rc, |
| 376 | - int islit, uint8_t lit) | |
| 387 | + int islit, int8_t lit, int mask) | |
| 377 | 388 | { |
| 378 | - if (ra != 31) | |
| 379 | - tcg_gen_mov_i64(cpu_T[0], cpu_ir[ra]); | |
| 380 | - else | |
| 381 | - tcg_gen_movi_i64(cpu_T[0], 0); | |
| 389 | + int l1; | |
| 390 | + | |
| 391 | + if (unlikely(rc == 31)) | |
| 392 | + return; | |
| 393 | + | |
| 394 | + l1 = gen_new_label(); | |
| 395 | + | |
| 396 | + if (ra != 31) { | |
| 397 | + if (mask) { | |
| 398 | + TCGv tmp = tcg_temp_new(TCG_TYPE_I64); | |
| 399 | + tcg_gen_andi_i64(tmp, cpu_ir[ra], 1); | |
| 400 | + tcg_gen_brcondi_i64(inv_cond, tmp, 0, l1); | |
| 401 | + tcg_temp_free(tmp); | |
| 402 | + } else | |
| 403 | + tcg_gen_brcondi_i64(inv_cond, cpu_ir[ra], 0, l1); | |
| 404 | + } else { | |
| 405 | + /* Very uncommon case - Do not bother to optimize. */ | |
| 406 | + TCGv tmp = tcg_const_i64(0); | |
| 407 | + tcg_gen_brcondi_i64(inv_cond, tmp, 0, l1); | |
| 408 | + tcg_temp_free(tmp); | |
| 409 | + } | |
| 410 | + | |
| 382 | 411 | if (islit) |
| 383 | - tcg_gen_movi_i64(cpu_T[1], lit); | |
| 412 | + tcg_gen_movi_i64(cpu_ir[rc], lit); | |
| 384 | 413 | else if (rb != 31) |
| 385 | - tcg_gen_mov_i64(cpu_T[1], cpu_ir[rb]); | |
| 414 | + tcg_gen_mov_i64(cpu_ir[rc], cpu_ir[rb]); | |
| 386 | 415 | else |
| 387 | - tcg_gen_movi_i64(cpu_T[1], 0); | |
| 388 | - (*gen_test_op)(); | |
| 389 | - gen_op_cmov_ir(rc); | |
| 416 | + tcg_gen_movi_i64(cpu_ir[rc], 0); | |
| 417 | + gen_set_label(l1); | |
| 390 | 418 | } |
| 391 | 419 | |
| 392 | 420 | static always_inline void gen_farith2 (DisasContext *ctx, |
| ... | ... | @@ -933,11 +961,11 @@ static always_inline int translate_one (DisasContext *ctx, uint32_t insn) |
| 933 | 961 | break; |
| 934 | 962 | case 0x14: |
| 935 | 963 | /* CMOVLBS */ |
| 936 | - gen_cmov(ctx, &gen_op_cmplbs, ra, rb, rc, islit, lit); | |
| 964 | + gen_cmov(ctx, TCG_COND_EQ, ra, rb, rc, islit, lit, 1); | |
| 937 | 965 | break; |
| 938 | 966 | case 0x16: |
| 939 | 967 | /* CMOVLBC */ |
| 940 | - gen_cmov(ctx, &gen_op_cmplbc, ra, rb, rc, islit, lit); | |
| 968 | + gen_cmov(ctx, TCG_COND_NE, ra, rb, rc, islit, lit, 1); | |
| 941 | 969 | break; |
| 942 | 970 | case 0x20: |
| 943 | 971 | /* BIS */ |
| ... | ... | @@ -961,11 +989,11 @@ static always_inline int translate_one (DisasContext *ctx, uint32_t insn) |
| 961 | 989 | break; |
| 962 | 990 | case 0x24: |
| 963 | 991 | /* CMOVEQ */ |
| 964 | - gen_cmov(ctx, &gen_op_cmpeqz, ra, rb, rc, islit, lit); | |
| 992 | + gen_cmov(ctx, TCG_COND_NE, ra, rb, rc, islit, lit, 0); | |
| 965 | 993 | break; |
| 966 | 994 | case 0x26: |
| 967 | 995 | /* CMOVNE */ |
| 968 | - gen_cmov(ctx, &gen_op_cmpnez, ra, rb, rc, islit, lit); | |
| 996 | + gen_cmov(ctx, TCG_COND_EQ, ra, rb, rc, islit, lit, 0); | |
| 969 | 997 | break; |
| 970 | 998 | case 0x28: |
| 971 | 999 | /* ORNOT */ |
| ... | ... | @@ -1011,11 +1039,11 @@ static always_inline int translate_one (DisasContext *ctx, uint32_t insn) |
| 1011 | 1039 | break; |
| 1012 | 1040 | case 0x44: |
| 1013 | 1041 | /* CMOVLT */ |
| 1014 | - gen_cmov(ctx, &gen_op_cmpltz, ra, rb, rc, islit, lit); | |
| 1042 | + gen_cmov(ctx, TCG_COND_GE, ra, rb, rc, islit, lit, 0); | |
| 1015 | 1043 | break; |
| 1016 | 1044 | case 0x46: |
| 1017 | 1045 | /* CMOVGE */ |
| 1018 | - gen_cmov(ctx, &gen_op_cmpgez, ra, rb, rc, islit, lit); | |
| 1046 | + gen_cmov(ctx, TCG_COND_LT, ra, rb, rc, islit, lit, 0); | |
| 1019 | 1047 | break; |
| 1020 | 1048 | case 0x48: |
| 1021 | 1049 | /* EQV */ |
| ... | ... | @@ -1053,11 +1081,11 @@ static always_inline int translate_one (DisasContext *ctx, uint32_t insn) |
| 1053 | 1081 | break; |
| 1054 | 1082 | case 0x64: |
| 1055 | 1083 | /* CMOVLE */ |
| 1056 | - gen_cmov(ctx, &gen_op_cmplez, ra, rb, rc, islit, lit); | |
| 1084 | + gen_cmov(ctx, TCG_COND_GT, ra, rb, rc, islit, lit, 0); | |
| 1057 | 1085 | break; |
| 1058 | 1086 | case 0x66: |
| 1059 | 1087 | /* CMOVGT */ |
| 1060 | - gen_cmov(ctx, &gen_op_cmpgtz, ra, rb, rc, islit, lit); | |
| 1088 | + gen_cmov(ctx, TCG_COND_LE, ra, rb, rc, islit, lit, 0); | |
| 1061 | 1089 | break; |
| 1062 | 1090 | case 0x6C: |
| 1063 | 1091 | /* IMPLVER */ |
| ... | ... | @@ -2173,42 +2201,42 @@ static always_inline int translate_one (DisasContext *ctx, uint32_t insn) |
| 2173 | 2201 | break; |
| 2174 | 2202 | case 0x38: |
| 2175 | 2203 | /* BLBC */ |
| 2176 | - gen_bcond(ctx, &gen_op_cmplbc, ra, disp16); | |
| 2204 | + gen_bcond(ctx, TCG_COND_EQ, ra, disp16, 1); | |
| 2177 | 2205 | ret = 1; |
| 2178 | 2206 | break; |
| 2179 | 2207 | case 0x39: |
| 2180 | 2208 | /* BEQ */ |
| 2181 | - gen_bcond(ctx, &gen_op_cmpeqz, ra, disp16); | |
| 2209 | + gen_bcond(ctx, TCG_COND_EQ, ra, disp16, 0); | |
| 2182 | 2210 | ret = 1; |
| 2183 | 2211 | break; |
| 2184 | 2212 | case 0x3A: |
| 2185 | 2213 | /* BLT */ |
| 2186 | - gen_bcond(ctx, &gen_op_cmpltz, ra, disp16); | |
| 2214 | + gen_bcond(ctx, TCG_COND_LT, ra, disp16, 0); | |
| 2187 | 2215 | ret = 1; |
| 2188 | 2216 | break; |
| 2189 | 2217 | case 0x3B: |
| 2190 | 2218 | /* BLE */ |
| 2191 | - gen_bcond(ctx, &gen_op_cmplez, ra, disp16); | |
| 2219 | + gen_bcond(ctx, TCG_COND_LE, ra, disp16, 0); | |
| 2192 | 2220 | ret = 1; |
| 2193 | 2221 | break; |
| 2194 | 2222 | case 0x3C: |
| 2195 | 2223 | /* BLBS */ |
| 2196 | - gen_bcond(ctx, &gen_op_cmplbs, ra, disp16); | |
| 2224 | + gen_bcond(ctx, TCG_COND_NE, ra, disp16, 1); | |
| 2197 | 2225 | ret = 1; |
| 2198 | 2226 | break; |
| 2199 | 2227 | case 0x3D: |
| 2200 | 2228 | /* BNE */ |
| 2201 | - gen_bcond(ctx, &gen_op_cmpnez, ra, disp16); | |
| 2229 | + gen_bcond(ctx, TCG_COND_NE, ra, disp16, 0); | |
| 2202 | 2230 | ret = 1; |
| 2203 | 2231 | break; |
| 2204 | 2232 | case 0x3E: |
| 2205 | 2233 | /* BGE */ |
| 2206 | - gen_bcond(ctx, &gen_op_cmpgez, ra, disp16); | |
| 2234 | + gen_bcond(ctx, TCG_COND_GE, ra, disp16, 0); | |
| 2207 | 2235 | ret = 1; |
| 2208 | 2236 | break; |
| 2209 | 2237 | case 0x3F: |
| 2210 | 2238 | /* BGT */ |
| 2211 | - gen_bcond(ctx, &gen_op_cmpgtz, ra, disp16); | |
| 2239 | + gen_bcond(ctx, TCG_COND_GT, ra, disp16, 0); | |
| 2212 | 2240 | ret = 1; |
| 2213 | 2241 | break; |
| 2214 | 2242 | invalid_opc: | ... | ... |