From 66ca84b58114ad73b5843f62f9f5fbead1126fca Mon Sep 17 00:00:00 2001 From: David Brownell Date: Tue, 1 Dec 2009 21:47:45 -0800 Subject: ARM: core DPM support for watchpoints This is a NOP unless the underlying core exposes two new methods, and neither of the two cores using this (ARM11xx, Cortex-A8) do so yet. This patch only updates those cores so they pass a flag saying whether or not to update breakpoint and watchpoint status before resuming; and removing some now-needless anti-segfault code from ARM11. Cortex-A8 didn't have that code ... yes, it segfaulted when setting watchpoints. NOTE: this uses a slightly different strategy for setting/clearing breakpoints than the ARM7/ARM9/etc code uses. It leaves them alone unless it's *got* to change something, to speed halt/resume cycles (including single stepping). ALSO NOTE: this under-delivers for Cortex-A8, where regions with size up to 2 GBytes can be watched ... it handles watchpoints which ARM11 can also handle (size 1/2/4 bytes). Should get fixed later. Signed-off-by: David Brownell --- src/target/arm_dpm.h | 52 ++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 48 insertions(+), 4 deletions(-) (limited to 'src/target/arm_dpm.h') diff --git a/src/target/arm_dpm.h b/src/target/arm_dpm.h index 67ce2180..5d665a86 100644 --- a/src/target/arm_dpm.h +++ b/src/target/arm_dpm.h @@ -31,6 +31,26 @@ * registers are compatible. */ +struct dpm_bp { + struct breakpoint *bp; + /* bp->address == breakpoint value register + * control == breakpoint control register + */ + uint32_t control; + /* true if hardware state needs flushing */ + bool dirty; +}; + +struct dpm_wp { + struct watchpoint *wp; + /* wp->address == watchpoint value register + * control == watchpoint control register + */ + uint32_t control; + /* true if hardware state needs flushing */ + bool dirty; +}; + /** * This wraps an implementation of DPM primitives. Each interface * provider supplies a structure like this, which is the glue between @@ -74,9 +94,33 @@ struct arm_dpm { int (*instr_read_data_r0)(struct arm_dpm *, uint32_t opcode, uint32_t *data); - // FIXME -- add breakpoint support - - // FIXME -- add watchpoint support (including context-sensitive ones) + /* BREAKPOINT/WATCHPOINT SUPPORT */ + + /** + * Enables one breakpoint or watchpoint by writing to the + * hardware registers. The specified breakpoint/watchpoint + * must currently be disabled. Indices 0..15 are used for + * breakpoints; indices 16..31 are for watchpoints. + */ + int (*bpwp_enable)(struct arm_dpm *, unsigned index, + uint32_t addr, uint32_t control); + + /** + * Disables one breakpoint or watchpoint by clearing its + * hardware control registers. Indices are the same ones + * accepted by bpwp_enable(). + */ + int (*bpwp_disable)(struct arm_dpm *, unsigned index); + + /* The breakpoint and watchpoint arrays are private to the + * DPM infrastructure. There are nbp indices in the dbp + * array. There are nwp indices in the dwp array. + */ + + unsigned nbp; + unsigned nwp; + struct dpm_bp *dbp; + struct dpm_wp *dwp; // FIXME -- read/write DCSR methods and symbols }; @@ -85,6 +129,6 @@ int arm_dpm_setup(struct arm_dpm *dpm); int arm_dpm_reinitialize(struct arm_dpm *dpm); int arm_dpm_read_current_registers(struct arm_dpm *); -int arm_dpm_write_dirty_registers(struct arm_dpm *); +int arm_dpm_write_dirty_registers(struct arm_dpm *, bool bpwp); #endif /* __ARM_DPM_H */ -- cgit v1.2.3