diff --git a/qemu/exec.c b/qemu/exec.c index 98706ecd..6bd65155 100644 --- a/qemu/exec.c +++ b/qemu/exec.c @@ -572,6 +572,7 @@ AddressSpace *cpu_get_address_space(CPUState *cpu, int asidx) void cpu_exec_init(CPUState *cpu, void *opaque) { struct uc_struct *uc = opaque; + CPUClass *cc = CPU_GET_CLASS(uc, cpu); CPUArchState *env = cpu->env_ptr; cpu->as = NULL; @@ -586,6 +587,11 @@ void cpu_exec_init(CPUState *cpu, void *opaque) // Unicorn: Required to clean-slate TLB state tlb_flush(cpu); + if (tcg_enabled(uc) && !cc->tcg_initialized) { + cc->tcg_initialized = true; + cc->tcg_initialize(uc); + } + #ifndef CONFIG_USER_ONLY // Unicorn: commented out diff --git a/qemu/header_gen.py b/qemu/header_gen.py index 9e710db7..94eadf74 100644 --- a/qemu/header_gen.py +++ b/qemu/header_gen.py @@ -4473,7 +4473,6 @@ sparc_symbols = ( 'cpu_sparc_init', 'cpu_sparc_set_id', 'dump_mmu', - 'gen_intermediate_code_init', 'helper_check_align', 'helper_check_ieee_exceptions', 'helper_compute_C_icc', @@ -4535,6 +4534,7 @@ sparc_symbols = ( 'sparc_reg_read', 'sparc_reg_reset', 'sparc_reg_write', + 'sparc_tcg_init', ) diff --git a/qemu/include/qom/cpu.h b/qemu/include/qom/cpu.h index 75980396..23f77101 100644 --- a/qemu/include/qom/cpu.h +++ b/qemu/include/qom/cpu.h @@ -169,6 +169,10 @@ typedef struct CPUClass { void (*cpu_exec_exit)(CPUState *cpu); bool (*cpu_exec_interrupt)(CPUState *cpu, int interrupt_request); vaddr (*adjust_watchpoint_address)(CPUState *cpu, vaddr addr, int len); + void (*tcg_initialize)(struct uc_struct *uc); + + /* Keep non-pointer data at the end to minimize holes. */ + bool tcg_initialized; } CPUClass; #ifdef HOST_WORDS_BIGENDIAN diff --git a/qemu/sparc.h b/qemu/sparc.h index 1b396dee..8fdfbe96 100644 --- a/qemu/sparc.h +++ b/qemu/sparc.h @@ -3449,7 +3449,6 @@ #define cpu_sparc_init cpu_sparc_init_sparc #define cpu_sparc_set_id cpu_sparc_set_id_sparc #define dump_mmu dump_mmu_sparc -#define gen_intermediate_code_init gen_intermediate_code_init_sparc #define helper_check_align helper_check_align_sparc #define helper_check_ieee_exceptions helper_check_ieee_exceptions_sparc #define helper_compute_C_icc helper_compute_C_icc_sparc @@ -3511,4 +3510,5 @@ #define sparc_reg_read sparc_reg_read_sparc #define sparc_reg_reset sparc_reg_reset_sparc #define sparc_reg_write sparc_reg_write_sparc +#define sparc_tcg_init sparc_tcg_init_sparc #endif diff --git a/qemu/sparc64.h b/qemu/sparc64.h index b95fd1f3..6687da6c 100644 --- a/qemu/sparc64.h +++ b/qemu/sparc64.h @@ -3449,7 +3449,6 @@ #define cpu_sparc_init cpu_sparc_init_sparc64 #define cpu_sparc_set_id cpu_sparc_set_id_sparc64 #define dump_mmu dump_mmu_sparc64 -#define gen_intermediate_code_init gen_intermediate_code_init_sparc64 #define helper_check_align helper_check_align_sparc64 #define helper_check_ieee_exceptions helper_check_ieee_exceptions_sparc64 #define helper_compute_C_icc helper_compute_C_icc_sparc64 @@ -3511,4 +3510,5 @@ #define sparc_reg_read sparc_reg_read_sparc64 #define sparc_reg_reset sparc_reg_reset_sparc64 #define sparc_reg_write sparc_reg_write_sparc64 +#define sparc_tcg_init sparc_tcg_init_sparc64 #endif diff --git a/qemu/target/arm/cpu.c b/qemu/target/arm/cpu.c index 2dd4489c..f6da4d60 100644 --- a/qemu/target/arm/cpu.c +++ b/qemu/target/arm/cpu.c @@ -461,7 +461,6 @@ static void arm_cpu_initfn(struct uc_struct *uc, Object *obj, void *opaque) if (tcg_enabled(uc)) { cpu->psci_version = 2; /* TCG implements PSCI 0.2 */ - arm_translate_init(uc); } } @@ -1516,6 +1515,7 @@ static void arm_cpu_class_init(struct uc_struct *uc, ObjectClass *oc, void *data #if !defined(CONFIG_USER_ONLY) cc->adjust_watchpoint_address = arm_adjust_watchpoint_address; #endif + cc->tcg_initialize = arm_translate_init; } static void cpu_register(struct uc_struct *uc, const ARMCPUInfo *info) diff --git a/qemu/target/i386/cpu.c b/qemu/target/i386/cpu.c index 9dcb7584..e3dc5b88 100644 --- a/qemu/target/i386/cpu.c +++ b/qemu/target/i386/cpu.c @@ -3444,10 +3444,6 @@ static int x86_cpu_realizefn(struct uc_struct *uc, DeviceState *dev, Error **err goto out; } - if (tcg_enabled(env->uc)) { - tcg_x86_init(env->uc); - } - #ifndef CONFIG_USER_ONLY //qemu_register_reset(x86_cpu_machine_reset_cb, cpu); @@ -3660,6 +3656,7 @@ static void x86_cpu_common_class_init(struct uc_struct *uc, ObjectClass *oc, voi #endif cc->cpu_exec_enter = x86_cpu_exec_enter; cc->cpu_exec_exit = x86_cpu_exec_exit; + cc->tcg_initialize = tcg_x86_init; } void x86_cpu_register_types(void *opaque) diff --git a/qemu/target/i386/translate.c b/qemu/target/i386/translate.c index a143b46b..9c30a637 100644 --- a/qemu/target/i386/translate.c +++ b/qemu/target/i386/translate.c @@ -5071,7 +5071,7 @@ static target_ulong disas_insn(DisasContext *s, CPUState *cpu) TCGv *cpu_regs = tcg_ctx->cpu_regs; TCGv *cpu_seg_base = tcg_ctx->cpu_seg_base; //TCGArg* save_opparam_ptr = tcg_ctx->gen_opparam_buf + tcg_ctx->gen_op_buf[tcg_ctx->gen_op_buf[0].prev].args; - bool cc_op_dirty = s->cc_op_dirty; + //bool cc_op_dirty = s->cc_op_dirty; bool changed_cc_op = false; s->pc_start = s->pc = pc_start; diff --git a/qemu/target/m68k/cpu.c b/qemu/target/m68k/cpu.c index 4039aae6..6e0943f1 100644 --- a/qemu/target/m68k/cpu.c +++ b/qemu/target/m68k/cpu.c @@ -234,10 +234,6 @@ static void m68k_cpu_initfn(struct uc_struct *uc, Object *obj, void *opaque) cs->env_ptr = env; cpu_exec_init(cs, opaque); - - if (tcg_enabled(uc)) { - m68k_tcg_init(uc); - } } static void m68k_cpu_class_init(struct uc_struct *uc, ObjectClass *c, void *data) @@ -262,6 +258,7 @@ static void m68k_cpu_class_init(struct uc_struct *uc, ObjectClass *c, void *data #else cc->get_phys_page_debug = m68k_cpu_get_phys_page_debug; #endif + cc->tcg_initialize = m68k_tcg_init; } static void register_cpu_type(void *opaque, const M68kCPUInfo *info) diff --git a/qemu/target/m68k/translate.c b/qemu/target/m68k/translate.c index 889288db..b2232d68 100644 --- a/qemu/target/m68k/translate.c +++ b/qemu/target/m68k/translate.c @@ -5779,14 +5779,17 @@ void gen_intermediate_code(CPUState *cs, TranslationBlock *tb) goto done_generating; } + // Unicorn: FIXME: Update to work with new TCG API // Unicorn: trace this block on request // Only hook this block if it is not broken from previous translation due to // full translation cache if (!env->uc->block_full && HOOK_EXISTS_BOUNDED(env->uc, UC_HOOK_BLOCK, pc_start)) { +#if 0 // save block address to see if we need to patch block size later env->uc->block_addr = pc_start; env->uc->size_arg = tcg_ctx->gen_op_buf[tcg_ctx->gen_op_buf[0].prev].args; gen_uc_tracecode(tcg_ctx, 0xf8f8f8f8, UC_HOOK_BLOCK_IDX, env->uc, pc_start); +#endif } else { env->uc->size_arg = -1; } diff --git a/qemu/target/mips/cpu.c b/qemu/target/mips/cpu.c index 2dfdd4c4..b45f7dfa 100644 --- a/qemu/target/mips/cpu.c +++ b/qemu/target/mips/cpu.c @@ -131,10 +131,6 @@ static void mips_cpu_initfn(struct uc_struct *uc, Object *obj, void *opaque) cs->env_ptr = env; env->cpu_model = mcc->cpu_def; cpu_exec_init(cs, opaque); - - if (tcg_enabled(uc)) { - mips_tcg_init(uc); - } } static char *mips_cpu_type_name(const char *cpu_model) @@ -182,6 +178,7 @@ static void mips_cpu_class_init(struct uc_struct *uc, ObjectClass *c, void *data cc->do_unaligned_access = mips_cpu_do_unaligned_access; cc->get_phys_page_debug = mips_cpu_get_phys_page_debug; #endif + cc->tcg_initialize = mips_tcg_init; } static void mips_cpu_cpudef_class_init(struct uc_struct *uc, ObjectClass *oc, void *data) diff --git a/qemu/target/sparc/cpu-qom.h b/qemu/target/sparc/cpu-qom.h index 8dcddc0a..ef188df9 100644 --- a/qemu/target/sparc/cpu-qom.h +++ b/qemu/target/sparc/cpu-qom.h @@ -35,6 +35,7 @@ #define SPARC_CPU_GET_CLASS(uc, obj) \ OBJECT_GET_CLASS(uc, SPARCCPUClass, (obj), TYPE_SPARC_CPU) +typedef struct sparc_def_t sparc_def_t; /** * SPARCCPUClass: * @parent_realize: The parent class' realize handler. diff --git a/qemu/target/sparc/cpu.c b/qemu/target/sparc/cpu.c index b1f5edc7..db61cc57 100644 --- a/qemu/target/sparc/cpu.c +++ b/qemu/target/sparc/cpu.c @@ -860,10 +860,6 @@ static void sparc_cpu_initfn(struct uc_struct *uc, Object *obj, void *opaque) cs->env_ptr = env; cpu_exec_init(cs, opaque); - - if (tcg_enabled(uc)) { - gen_intermediate_code_init(env); - } } static void sparc_cpu_uninitfn(struct uc_struct *uc, Object *obj, void *opaque) @@ -904,6 +900,7 @@ static void sparc_cpu_class_init(struct uc_struct *uc, ObjectClass *oc, void *da // Unicorn: commented out //cc->vmsd = &vmstate_sparc_cpu; #endif + cc->tcg_initialize = sparc_tcg_init; } void sparc_cpu_register_types(void *opaque) diff --git a/qemu/target/sparc/cpu.h b/qemu/target/sparc/cpu.h index 9494c993..1012007d 100644 --- a/qemu/target/sparc/cpu.h +++ b/qemu/target/sparc/cpu.h @@ -586,7 +586,7 @@ int sparc_cpu_memory_rw_debug(CPUState *cpu, vaddr addr, /* translate.c */ -void gen_intermediate_code_init(CPUSPARCState *env); +void sparc_tcg_init(struct uc_struct *uc); /* cpu-exec.c */ int cpu_sparc_exec(struct uc_struct *uc, CPUState *cpu); diff --git a/qemu/target/sparc/translate.c b/qemu/target/sparc/translate.c index 7ab0eaa7..e6e3a44f 100644 --- a/qemu/target/sparc/translate.c +++ b/qemu/target/sparc/translate.c @@ -141,9 +141,9 @@ static TCGv_i32 gen_load_fpr_F(DisasContext *dc, unsigned int src) TCGContext *tcg_ctx = dc->uc->tcg_ctx; #if TCG_TARGET_REG_BITS == 32 if (src & 1) { - return TCGV_LOW(tcg_ctx->cpu_fpr[src / 2]); + return TCGV_LOW(tcg_ctx, tcg_ctx->cpu_fpr[src / 2]); } else { - return TCGV_HIGH(tcg_ctx->cpu_fpr[src / 2]); + return TCGV_HIGH(tcg_ctx, tcg_ctx->cpu_fpr[src / 2]); } #else TCGv_i32 ret = get_temp_i32(dc); @@ -161,9 +161,9 @@ static void gen_store_fpr_F(DisasContext *dc, unsigned int dst, TCGv_i32 v) TCGContext *tcg_ctx = dc->uc->tcg_ctx; #if TCG_TARGET_REG_BITS == 32 if (dst & 1) { - tcg_gen_mov_i32(tcg_ctx, TCGV_LOW(tcg_ctx->cpu_fpr[dst / 2]), v); + tcg_gen_mov_i32(tcg_ctx, TCGV_LOW(tcg_ctx, tcg_ctx->cpu_fpr[dst / 2]), v); } else { - tcg_gen_mov_i32(tcg_ctx, TCGV_HIGH(tcg_ctx->cpu_fpr[dst / 2]), v); + tcg_gen_mov_i32(tcg_ctx, TCGV_HIGH(tcg_ctx, tcg_ctx->cpu_fpr[dst / 2]), v); } #else TCGv_i64 t = (TCGv_i64)v; @@ -5974,15 +5974,18 @@ void gen_intermediate_code(CPUState *cs, TranslationBlock * tb) goto done_generating; } + // Unicorn: FIXME: Amend to work with new TCG API // Unicorn: trace this block on request // Only hook this block if it is not broken from previous translation due to // full translation cache +#if 0 if (!env->uc->block_full && HOOK_EXISTS_BOUNDED(env->uc, UC_HOOK_BLOCK, pc_start)) { // save block address to see if we need to patch block size later env->uc->block_addr = pc_start; env->uc->size_arg = tcg_ctx->gen_op_buf[tcg_ctx->gen_op_buf[0].prev].args; gen_uc_tracecode(tcg_ctx, 0xf8f8f8f8, UC_HOOK_BLOCK_IDX, env->uc, pc_start); } +#endif gen_tb_start(tcg_ctx, tb); do { @@ -6070,11 +6073,13 @@ done_generating: env->uc->block_full = block_full; } -void gen_intermediate_code_init(CPUSPARCState *env) +void sparc_tcg_init(struct uc_struct *uc) { + SPARCCPU *cpu = SPARC_CPU(s->uc, uc->cpu); + CPUSPARCState *env = &cpu->env; TCGContext *tcg_ctx = env->uc->tcg_ctx; - struct uc_struct *uc = env->uc; unsigned int i; + static const char gregnames[32][4] = { "g0", "g1", "g2", "g3", "g4", "g5", "g6", "g7", "o0", "o1", "o2", "o3", "o4", "o5", "o6", "o7",