summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAurelien Jarno <aurelien@aurel32.net>2012-09-11 12:26:23 +0200
committerAurelien Jarno <aurelien@aurel32.net>2012-09-22 15:10:20 +0200
commitb80bb016d8c8e9d74345a90ab6dac1cb547904e0 (patch)
treece9f817c147f7329cb26efa1c5f5e34472446e78
parent48b56ce1683dec02a29448f31861fca4dd0a0b33 (diff)
downloadqemu-b80bb016d8c8e9d74345a90ab6dac1cb547904e0.zip
tcg/optimize: check types in copy propagation
The copy propagation doesn't check the types of the temps during copy propagation. However TCG is using the mov_i32 for the i64 to i32 conversion and thus the two are not equivalent. With this patch tcg_opt_gen_mov() doesn't consider two temps of different type as copies anymore. So far it seems the optimization was not aggressive enough to trigger this bug, but it will be triggered later in this series once the copy propagation is improved. Reviewed-by: Richard Henderson <rth@twiddle.net> Signed-off-by: Aurelien Jarno <aurelien@aurel32.net>
-rw-r--r--tcg/optimize.c18
1 files changed, 8 insertions, 10 deletions
diff --git a/tcg/optimize.c b/tcg/optimize.c
index 308b7f9033..da8dffe9cd 100644
--- a/tcg/optimize.c
+++ b/tcg/optimize.c
@@ -106,12 +106,13 @@ static TCGOpcode op_to_movi(TCGOpcode op)
}
}
-static void tcg_opt_gen_mov(TCGArg *gen_args, TCGArg dst, TCGArg src,
- int nb_temps, int nb_globals)
+static void tcg_opt_gen_mov(TCGContext *s, TCGArg *gen_args,
+ TCGArg dst, TCGArg src)
{
- reset_temp(dst, nb_temps, nb_globals);
+ reset_temp(dst, s->nb_temps, s->nb_globals);
assert(temps[src].state != TCG_TEMP_COPY);
- if (src >= nb_globals) {
+ /* Only consider temps with the same type (width) as copies. */
+ if (src >= s->nb_globals && s->temps[dst].type == s->temps[src].type) {
assert(temps[src].state != TCG_TEMP_CONST);
if (temps[src].state != TCG_TEMP_HAS_COPY) {
temps[src].state = TCG_TEMP_HAS_COPY;
@@ -461,8 +462,7 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
gen_opc_buf[op_index] = INDEX_op_nop;
} else {
gen_opc_buf[op_index] = op_to_mov(op);
- tcg_opt_gen_mov(gen_args, args[0], args[1],
- nb_temps, nb_globals);
+ tcg_opt_gen_mov(s, gen_args, args[0], args[1]);
gen_args += 2;
}
args += 3;
@@ -499,8 +499,7 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
gen_opc_buf[op_index] = INDEX_op_nop;
} else {
gen_opc_buf[op_index] = op_to_mov(op);
- tcg_opt_gen_mov(gen_args, args[0], args[1], nb_temps,
- nb_globals);
+ tcg_opt_gen_mov(s, gen_args, args[0], args[1]);
gen_args += 2;
}
args += 3;
@@ -524,8 +523,7 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
break;
}
if (temps[args[1]].state != TCG_TEMP_CONST) {
- tcg_opt_gen_mov(gen_args, args[0], args[1],
- nb_temps, nb_globals);
+ tcg_opt_gen_mov(s, gen_args, args[0], args[1]);
gen_args += 2;
args += 2;
break;