cpu-exec: Make debug_excp_handler a QOM CPU method
Make the debug_excp_handler target specific hook into a QOM CPU method. Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
		
							parent
							
								
									08225676b2
								
							
						
					
					
						commit
						86025ee443
					
				
							
								
								
									
										13
									
								
								cpu-exec.c
									
									
									
									
									
								
							
							
						
						
									
										13
									
								
								cpu-exec.c
									
									
									
									
									
								
							| @ -295,16 +295,10 @@ static inline TranslationBlock *tb_find_fast(CPUArchState *env) | |||||||
|     return tb; |     return tb; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| static CPUDebugExcpHandler *debug_excp_handler; |  | ||||||
| 
 |  | ||||||
| void cpu_set_debug_excp_handler(CPUDebugExcpHandler *handler) |  | ||||||
| { |  | ||||||
|     debug_excp_handler = handler; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| static void cpu_handle_debug_exception(CPUArchState *env) | static void cpu_handle_debug_exception(CPUArchState *env) | ||||||
| { | { | ||||||
|     CPUState *cpu = ENV_GET_CPU(env); |     CPUState *cpu = ENV_GET_CPU(env); | ||||||
|  |     CPUClass *cc = CPU_GET_CLASS(cpu); | ||||||
|     CPUWatchpoint *wp; |     CPUWatchpoint *wp; | ||||||
| 
 | 
 | ||||||
|     if (!cpu->watchpoint_hit) { |     if (!cpu->watchpoint_hit) { | ||||||
| @ -312,9 +306,8 @@ static void cpu_handle_debug_exception(CPUArchState *env) | |||||||
|             wp->flags &= ~BP_WATCHPOINT_HIT; |             wp->flags &= ~BP_WATCHPOINT_HIT; | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
|     if (debug_excp_handler) { | 
 | ||||||
|         debug_excp_handler(env); |     cc->debug_excp_handler(cpu); | ||||||
|     } |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| /* main execution loop */ | /* main execution loop */ | ||||||
|  | |||||||
| @ -356,10 +356,6 @@ static inline tb_page_addr_t get_page_addr_code(CPUArchState *env1, target_ulong | |||||||
| tb_page_addr_t get_page_addr_code(CPUArchState *env1, target_ulong addr); | tb_page_addr_t get_page_addr_code(CPUArchState *env1, target_ulong addr); | ||||||
| #endif | #endif | ||||||
| 
 | 
 | ||||||
| typedef void (CPUDebugExcpHandler)(CPUArchState *env); |  | ||||||
| 
 |  | ||||||
| void cpu_set_debug_excp_handler(CPUDebugExcpHandler *handler); |  | ||||||
| 
 |  | ||||||
| /* vl.c */ | /* vl.c */ | ||||||
| extern int singlestep; | extern int singlestep; | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -95,6 +95,7 @@ struct TranslationBlock; | |||||||
|  * @get_phys_page_debug: Callback for obtaining a physical address. |  * @get_phys_page_debug: Callback for obtaining a physical address. | ||||||
|  * @gdb_read_register: Callback for letting GDB read a register. |  * @gdb_read_register: Callback for letting GDB read a register. | ||||||
|  * @gdb_write_register: Callback for letting GDB write a register. |  * @gdb_write_register: Callback for letting GDB write a register. | ||||||
|  |  * @debug_excp_handler: Callback for handling debug exceptions. | ||||||
|  * @vmsd: State description for migration. |  * @vmsd: State description for migration. | ||||||
|  * @gdb_num_core_regs: Number of core registers accessible to GDB. |  * @gdb_num_core_regs: Number of core registers accessible to GDB. | ||||||
|  * @gdb_core_xml_file: File name for core registers GDB XML description. |  * @gdb_core_xml_file: File name for core registers GDB XML description. | ||||||
| @ -134,6 +135,7 @@ typedef struct CPUClass { | |||||||
|     hwaddr (*get_phys_page_debug)(CPUState *cpu, vaddr addr); |     hwaddr (*get_phys_page_debug)(CPUState *cpu, vaddr addr); | ||||||
|     int (*gdb_read_register)(CPUState *cpu, uint8_t *buf, int reg); |     int (*gdb_read_register)(CPUState *cpu, uint8_t *buf, int reg); | ||||||
|     int (*gdb_write_register)(CPUState *cpu, uint8_t *buf, int reg); |     int (*gdb_write_register)(CPUState *cpu, uint8_t *buf, int reg); | ||||||
|  |     void (*debug_excp_handler)(CPUState *cpu); | ||||||
| 
 | 
 | ||||||
|     int (*write_elf64_note)(WriteCoreDumpFunction f, CPUState *cpu, |     int (*write_elf64_note)(WriteCoreDumpFunction f, CPUState *cpu, | ||||||
|                             int cpuid, void *opaque); |                             int cpuid, void *opaque); | ||||||
|  | |||||||
| @ -202,6 +202,10 @@ static bool cpu_common_virtio_is_big_endian(CPUState *cpu) | |||||||
|     return target_words_bigendian(); |     return target_words_bigendian(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | static void cpu_common_debug_excp_handler(CPUState *cpu) | ||||||
|  | { | ||||||
|  | } | ||||||
|  | 
 | ||||||
| void cpu_dump_state(CPUState *cpu, FILE *f, fprintf_function cpu_fprintf, | void cpu_dump_state(CPUState *cpu, FILE *f, fprintf_function cpu_fprintf, | ||||||
|                     int flags) |                     int flags) | ||||||
| { | { | ||||||
| @ -340,6 +344,7 @@ static void cpu_class_init(ObjectClass *klass, void *data) | |||||||
|     k->gdb_read_register = cpu_common_gdb_read_register; |     k->gdb_read_register = cpu_common_gdb_read_register; | ||||||
|     k->gdb_write_register = cpu_common_gdb_write_register; |     k->gdb_write_register = cpu_common_gdb_write_register; | ||||||
|     k->virtio_is_big_endian = cpu_common_virtio_is_big_endian; |     k->virtio_is_big_endian = cpu_common_virtio_is_big_endian; | ||||||
|  |     k->debug_excp_handler = cpu_common_debug_excp_handler; | ||||||
|     dc->realize = cpu_common_realizefn; |     dc->realize = cpu_common_realizefn; | ||||||
|     /*
 |     /*
 | ||||||
|      * Reason: CPUs still need special care by board code: wiring up |      * Reason: CPUs still need special care by board code: wiring up | ||||||
|  | |||||||
| @ -2843,9 +2843,6 @@ static void x86_cpu_initfn(Object *obj) | |||||||
|     if (tcg_enabled() && !inited) { |     if (tcg_enabled() && !inited) { | ||||||
|         inited = 1; |         inited = 1; | ||||||
|         optimize_flags_init(); |         optimize_flags_init(); | ||||||
| #ifndef CONFIG_USER_ONLY |  | ||||||
|         cpu_set_debug_excp_handler(breakpoint_handler); |  | ||||||
| #endif |  | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -2942,6 +2939,9 @@ static void x86_cpu_common_class_init(ObjectClass *oc, void *data) | |||||||
|     cc->vmsd = &vmstate_x86_cpu; |     cc->vmsd = &vmstate_x86_cpu; | ||||||
| #endif | #endif | ||||||
|     cc->gdb_num_core_regs = CPU_NB_REGS * 2 + 25; |     cc->gdb_num_core_regs = CPU_NB_REGS * 2 + 25; | ||||||
|  | #ifndef CONFIG_USER_ONLY | ||||||
|  |     cc->debug_excp_handler = breakpoint_handler; | ||||||
|  | #endif | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| static const TypeInfo x86_cpu_type_info = { | static const TypeInfo x86_cpu_type_info = { | ||||||
|  | |||||||
| @ -1121,7 +1121,7 @@ static inline int hw_breakpoint_len(unsigned long dr7, int index) | |||||||
| void hw_breakpoint_insert(CPUX86State *env, int index); | void hw_breakpoint_insert(CPUX86State *env, int index); | ||||||
| void hw_breakpoint_remove(CPUX86State *env, int index); | void hw_breakpoint_remove(CPUX86State *env, int index); | ||||||
| bool check_hw_breakpoints(CPUX86State *env, bool force_dr6_update); | bool check_hw_breakpoints(CPUX86State *env, bool force_dr6_update); | ||||||
| void breakpoint_handler(CPUX86State *env); | void breakpoint_handler(CPUState *cs); | ||||||
| 
 | 
 | ||||||
| /* will be suppressed */ | /* will be suppressed */ | ||||||
| void cpu_x86_update_cr0(CPUX86State *env, uint32_t new_cr0); | void cpu_x86_update_cr0(CPUX86State *env, uint32_t new_cr0); | ||||||
|  | |||||||
| @ -1011,9 +1011,10 @@ bool check_hw_breakpoints(CPUX86State *env, bool force_dr6_update) | |||||||
|     return hit_enabled; |     return hit_enabled; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void breakpoint_handler(CPUX86State *env) | void breakpoint_handler(CPUState *cs) | ||||||
| { | { | ||||||
|     CPUState *cs = CPU(x86_env_get_cpu(env)); |     X86CPU *cpu = X86_CPU(cs); | ||||||
|  |     CPUX86State *env = &cpu->env; | ||||||
|     CPUBreakpoint *bp; |     CPUBreakpoint *bp; | ||||||
| 
 | 
 | ||||||
|     if (cs->watchpoint_hit) { |     if (cs->watchpoint_hit) { | ||||||
|  | |||||||
| @ -158,7 +158,6 @@ static void lm32_cpu_initfn(Object *obj) | |||||||
|     if (tcg_enabled() && !tcg_initialized) { |     if (tcg_enabled() && !tcg_initialized) { | ||||||
|         tcg_initialized = true; |         tcg_initialized = true; | ||||||
|         lm32_translate_init(); |         lm32_translate_init(); | ||||||
|         cpu_set_debug_excp_handler(lm32_debug_excp_handler); |  | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -273,6 +272,7 @@ static void lm32_cpu_class_init(ObjectClass *oc, void *data) | |||||||
|     cc->vmsd = &vmstate_lm32_cpu; |     cc->vmsd = &vmstate_lm32_cpu; | ||||||
| #endif | #endif | ||||||
|     cc->gdb_num_core_regs = 32 + 7; |     cc->gdb_num_core_regs = 32 + 7; | ||||||
|  |     cc->debug_excp_handler = lm32_debug_excp_handler; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| static void lm32_register_cpu_type(const LM32CPUInfo *info) | static void lm32_register_cpu_type(const LM32CPUInfo *info) | ||||||
|  | |||||||
| @ -211,7 +211,7 @@ void lm32_cpu_list(FILE *f, fprintf_function cpu_fprintf); | |||||||
| void lm32_translate_init(void); | void lm32_translate_init(void); | ||||||
| void cpu_lm32_set_phys_msb_ignore(CPULM32State *env, int value); | void cpu_lm32_set_phys_msb_ignore(CPULM32State *env, int value); | ||||||
| void QEMU_NORETURN raise_exception(CPULM32State *env, int index); | void QEMU_NORETURN raise_exception(CPULM32State *env, int index); | ||||||
| void lm32_debug_excp_handler(CPULM32State *env); | void lm32_debug_excp_handler(CPUState *cs); | ||||||
| void lm32_breakpoint_insert(CPULM32State *env, int index, target_ulong address); | void lm32_breakpoint_insert(CPULM32State *env, int index, target_ulong address); | ||||||
| void lm32_breakpoint_remove(CPULM32State *env, int index); | void lm32_breakpoint_remove(CPULM32State *env, int index); | ||||||
| void lm32_watchpoint_insert(CPULM32State *env, int index, target_ulong address, | void lm32_watchpoint_insert(CPULM32State *env, int index, target_ulong address, | ||||||
|  | |||||||
| @ -125,9 +125,10 @@ static bool check_watchpoints(CPULM32State *env) | |||||||
|     return false; |     return false; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void lm32_debug_excp_handler(CPULM32State *env) | void lm32_debug_excp_handler(CPUState *cs) | ||||||
| { | { | ||||||
|     CPUState *cs = CPU(lm32_env_get_cpu(env)); |     LM32CPU *cpu = LM32_CPU(cs); | ||||||
|  |     CPULM32State *env = &cpu->env; | ||||||
|     CPUBreakpoint *bp; |     CPUBreakpoint *bp; | ||||||
| 
 | 
 | ||||||
|     if (cs->watchpoint_hit) { |     if (cs->watchpoint_hit) { | ||||||
|  | |||||||
| @ -119,7 +119,6 @@ static void xtensa_cpu_initfn(Object *obj) | |||||||
|     if (tcg_enabled() && !tcg_inited) { |     if (tcg_enabled() && !tcg_inited) { | ||||||
|         tcg_inited = true; |         tcg_inited = true; | ||||||
|         xtensa_translate_init(); |         xtensa_translate_init(); | ||||||
|         cpu_set_debug_excp_handler(xtensa_breakpoint_handler); |  | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -151,6 +150,7 @@ static void xtensa_cpu_class_init(ObjectClass *oc, void *data) | |||||||
|     cc->do_unaligned_access = xtensa_cpu_do_unaligned_access; |     cc->do_unaligned_access = xtensa_cpu_do_unaligned_access; | ||||||
|     cc->get_phys_page_debug = xtensa_cpu_get_phys_page_debug; |     cc->get_phys_page_debug = xtensa_cpu_get_phys_page_debug; | ||||||
| #endif | #endif | ||||||
|  |     cc->debug_excp_handler = xtensa_breakpoint_handler; | ||||||
|     dc->vmsd = &vmstate_xtensa_cpu; |     dc->vmsd = &vmstate_xtensa_cpu; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -390,7 +390,7 @@ static inline CPUXtensaState *cpu_init(const char *cpu_model) | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void xtensa_translate_init(void); | void xtensa_translate_init(void); | ||||||
| void xtensa_breakpoint_handler(CPUXtensaState *env); | void xtensa_breakpoint_handler(CPUState *cs); | ||||||
| int cpu_xtensa_exec(CPUXtensaState *s); | int cpu_xtensa_exec(CPUXtensaState *s); | ||||||
| void xtensa_register_core(XtensaConfigList *node); | void xtensa_register_core(XtensaConfigList *node); | ||||||
| void check_interrupts(CPUXtensaState *s); | void check_interrupts(CPUXtensaState *s); | ||||||
|  | |||||||
| @ -79,9 +79,10 @@ static uint32_t check_hw_breakpoints(CPUXtensaState *env) | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void xtensa_breakpoint_handler(CPUXtensaState *env) | void xtensa_breakpoint_handler(CPUState *cs) | ||||||
| { | { | ||||||
|     CPUState *cs = CPU(xtensa_env_get_cpu(env)); |     XtensaCPU *cpu = XTENSA_CPU(cs); | ||||||
|  |     CPUXtensaState *env = &cpu->env; | ||||||
| 
 | 
 | ||||||
|     if (cs->watchpoint_hit) { |     if (cs->watchpoint_hit) { | ||||||
|         if (cs->watchpoint_hit->flags & BP_CPU) { |         if (cs->watchpoint_hit->flags & BP_CPU) { | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 Peter Maydell
						Peter Maydell