diff options
-rw-r--r-- | gdb/gdbserver/ChangeLog | 91 | ||||
-rw-r--r-- | gdb/gdbserver/linux-aarch64-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-arm-low.c | 30 | ||||
-rw-r--r-- | gdb/gdbserver/linux-bfin-low.c | 15 | ||||
-rw-r--r-- | gdb/gdbserver/linux-cris-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-crisv32-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-low.c | 45 | ||||
-rw-r--r-- | gdb/gdbserver/linux-low.h | 9 | ||||
-rw-r--r-- | gdb/gdbserver/linux-m32r-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-m68k-low.c | 15 | ||||
-rw-r--r-- | gdb/gdbserver/linux-mips-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-nios2-low.c | 24 | ||||
-rw-r--r-- | gdb/gdbserver/linux-ppc-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-s390-low.c | 15 | ||||
-rw-r--r-- | gdb/gdbserver/linux-sh-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-sparc-low.c | 14 | ||||
-rw-r--r-- | gdb/gdbserver/linux-tic6x-low.c | 16 | ||||
-rw-r--r-- | gdb/gdbserver/linux-tile-low.c | 13 | ||||
-rw-r--r-- | gdb/gdbserver/linux-x86-low.c | 15 | ||||
-rw-r--r-- | gdb/gdbserver/linux-xtensa-low.c | 15 | ||||
-rw-r--r-- | gdb/gdbserver/target.h | 10 |
21 files changed, 356 insertions, 62 deletions
diff --git a/gdb/gdbserver/ChangeLog b/gdb/gdbserver/ChangeLog index 8e73d9f..10ae158 100644 --- a/gdb/gdbserver/ChangeLog +++ b/gdb/gdbserver/ChangeLog @@ -1,5 +1,96 @@ 2015-10-21 Antoine Tremblay <antoine.tremblay@ericsson.com> + * linux-aarch64-low.c (aarch64_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-arm-low.c (arm_breakpoint_kind_from_pc): New function. + (arm_sw_breakpoint_from_kind): New function. + * linux-bfin-low.c (bfin_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-cris-low.c (cris_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-crisv32-low.c (cris_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-low.c (linux_wait_1): Call breakpoint_kind_from_pc + and sw_breakpoint_from_kind to increment the pc. + (linux_breakpoint_kind_from_pc): New function. + (linux_sw_breakpoint_from_kind): New function. + (struct target_ops) <sw_breakpoint_from_kind>: Initialize field. + (initialize_low): Call breakpoint_kind_from_pc and + sw_breakpoint_from_kind to replace breakpoint_data/len. + * linux-low.h (struct linux_target_ops) <breakpoint_kind_from_pc>: + New field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Likewise. + * linux-m32r-low.c (m32r_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-m68k-low.c (m68k_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-mips-low.c (mips_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-nios2-low.c (nios2_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-ppc-low.c (ppc_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-s390-low.c (s390_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-sh-low.c (sh_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-sparc-low.c (sparc_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-tic6x-low.c (tic6x_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-tile-low.c (tile_sw_breakpoint_from_kind): New function. + * linux-x86-low.c (x86_sw_breakpoint_from_kind): New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + * linux-xtensa-low.c (xtensa_sw_breakpoint_from_kind) New function. + (struct linux_target_ops) <breakpoint>: Remove. + (struct linux_target_ops) <breakpoint_len>: Remove. + (struct linux_target_ops) <breakpoint_kind_from_pc>: Initialize field. + (struct linux_target_ops) <sw_breakpoint_from_kind>: Initialize field. + +2015-10-21 Antoine Tremblay <antoine.tremblay@ericsson.com> + * linux-cris-low.c (cris_get_pc): Remove void arg. 2015-10-16 Aleksandar Ristovski <aristovski@qnx.com> diff --git a/gdb/gdbserver/linux-aarch64-low.c b/gdb/gdbserver/linux-aarch64-low.c index 780c5e3..cb49a04 100644 --- a/gdb/gdbserver/linux-aarch64-low.c +++ b/gdb/gdbserver/linux-aarch64-low.c @@ -2931,6 +2931,15 @@ aarch64_supports_range_stepping (void) return 1; } +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +aarch64_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = aarch64_breakpoint_len; + return aarch64_breakpoint; +} + struct linux_target_ops the_low_target = { aarch64_arch_setup, @@ -2940,8 +2949,8 @@ struct linux_target_ops the_low_target = NULL, /* fetch_register */ aarch64_get_pc, aarch64_set_pc, - (const unsigned char *) &aarch64_breakpoint, - aarch64_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + aarch64_sw_breakpoint_from_kind, NULL, /* breakpoint_reinsert_addr */ 0, /* decr_pc_after_break */ aarch64_breakpoint_at, diff --git a/gdb/gdbserver/linux-arm-low.c b/gdb/gdbserver/linux-arm-low.c index a277bb6..3a56620 100644 --- a/gdb/gdbserver/linux-arm-low.c +++ b/gdb/gdbserver/linux-arm-low.c @@ -913,26 +913,34 @@ arm_regs_info (void) return ®s_info_arm; } -struct linux_target_ops the_low_target = { - arm_arch_setup, - arm_regs_info, - arm_cannot_fetch_register, - arm_cannot_store_register, - NULL, /* fetch_register */ - arm_get_pc, - arm_set_pc, +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ +static const gdb_byte * +arm_sw_breakpoint_from_kind (int kind , int *size) +{ + *size = arm_breakpoint_len; /* Define an ARM-mode breakpoint; we only set breakpoints in the C library, which is most likely to be ARM. If the kernel supports clone events, we will never insert a breakpoint, so even a Thumb C library will work; so will mixing EABI/non-EABI gdbserver and application. */ #ifndef __ARM_EABI__ - (const unsigned char *) &arm_breakpoint, + return (const gdb_byte *) &arm_breakpoint; #else - (const unsigned char *) &arm_eabi_breakpoint, + return (const gdb_byte *) &arm_eabi_breakpoint; #endif - arm_breakpoint_len, +} + +struct linux_target_ops the_low_target = { + arm_arch_setup, + arm_regs_info, + arm_cannot_fetch_register, + arm_cannot_store_register, + NULL, /* fetch_register */ + arm_get_pc, + arm_set_pc, + NULL, /* breakpoint_kind_from_pc */ + arm_sw_breakpoint_from_kind, arm_reinsert_addr, 0, arm_breakpoint_at, diff --git a/gdb/gdbserver/linux-bfin-low.c b/gdb/gdbserver/linux-bfin-low.c index 4002f22..d3b83fc 100644 --- a/gdb/gdbserver/linux-bfin-low.c +++ b/gdb/gdbserver/linux-bfin-low.c @@ -73,7 +73,16 @@ bfin_set_pc (struct regcache *regcache, CORE_ADDR pc) } #define bfin_breakpoint_len 2 -static const unsigned char bfin_breakpoint[bfin_breakpoint_len] = {0xa1, 0x00}; +static const gdb_byte bfin_breakpoint[bfin_breakpoint_len] = {0xa1, 0x00}; + +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +bfin_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = bfin_breakpoint_len; + return bfin_breakpoint; +} static int bfin_breakpoint_at (CORE_ADDR where) @@ -122,8 +131,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ bfin_get_pc, bfin_set_pc, - bfin_breakpoint, - bfin_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + bfin_sw_breakpoint_from_kind, NULL, /* breakpoint_reinsert_addr */ 2, bfin_breakpoint_at, diff --git a/gdb/gdbserver/linux-cris-low.c b/gdb/gdbserver/linux-cris-low.c index 135e37a..d7b70e3 100644 --- a/gdb/gdbserver/linux-cris-low.c +++ b/gdb/gdbserver/linux-cris-low.c @@ -81,6 +81,15 @@ cris_set_pc (struct regcache *regcache, CORE_ADDR pc) static const unsigned short cris_breakpoint = 0xe938; #define cris_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +cris_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = cris_breakpoint_len; + return (const gdb_byte *) &cris_breakpoint; +} + static int cris_breakpoint_at (CORE_ADDR where) { @@ -140,8 +149,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ cris_get_pc, cris_set_pc, - (const unsigned char *) &cris_breakpoint, - cris_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + cris_sw_breakpoint_from_kind, cris_reinsert_addr, 0, cris_breakpoint_at, diff --git a/gdb/gdbserver/linux-crisv32-low.c b/gdb/gdbserver/linux-crisv32-low.c index 5120863..f97122e 100644 --- a/gdb/gdbserver/linux-crisv32-low.c +++ b/gdb/gdbserver/linux-crisv32-low.c @@ -77,6 +77,15 @@ cris_set_pc (struct regcache *regcache, CORE_ADDR pc) static const unsigned short cris_breakpoint = 0xe938; #define cris_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +cris_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = cris_breakpoint_len; + return (const gdb_byte *) &cris_breakpoint; +} + static int cris_breakpoint_at (CORE_ADDR where) { @@ -420,8 +429,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ cris_get_pc, cris_set_pc, - (const unsigned char *) &cris_breakpoint, - cris_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + cris_sw_breakpoint_from_kind, cris_reinsert_addr, 0, cris_breakpoint_at, diff --git a/gdb/gdbserver/linux-low.c b/gdb/gdbserver/linux-low.c index 3a1a6ae..398c0aa 100644 --- a/gdb/gdbserver/linux-low.c +++ b/gdb/gdbserver/linux-low.c @@ -3012,7 +3012,12 @@ linux_wait_1 (ptid_t ptid, if (!ptid_equal (step_over_bkpt, null_ptid) && event_child->stop_reason == TARGET_STOPPED_BY_SW_BREAKPOINT) { - unsigned int increment_pc = the_low_target.breakpoint_len; + int increment_pc = 0; + int breakpoint_kind = 0; + CORE_ADDR stop_pc = event_child->stop_pc; + + breakpoint_kind = the_target->breakpoint_kind_from_pc (&stop_pc); + the_target->sw_breakpoint_from_kind (breakpoint_kind, &increment_pc); if (debug_threads) { @@ -6932,6 +6937,28 @@ current_lwp_ptid (void) return ptid_of (current_thread); } +/* Implementation of the target_ops method "breakpoint_kind_from_pc". */ + +static int +linux_breakpoint_kind_from_pc (CORE_ADDR *pcptr) +{ + if (the_low_target.breakpoint_kind_from_pc != NULL) + return (*the_low_target.breakpoint_kind_from_pc) (pcptr); + else + /* Default breakpoint kind value. */ + return 0; +} + +/* Implementation of the target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +linux_sw_breakpoint_from_kind (int kind, int *size) +{ + gdb_assert (the_low_target.sw_breakpoint_from_kind != NULL); + + return (*the_low_target.sw_breakpoint_from_kind) (kind, size); +} + static struct target_ops linux_target_ops = { linux_create_inferior, linux_arch_setup, @@ -7026,6 +7053,8 @@ static struct target_ops linux_target_ops = { linux_mntns_open_cloexec, linux_mntns_unlink, linux_mntns_readlink, + linux_breakpoint_kind_from_pc, + linux_sw_breakpoint_from_kind }; static void @@ -7053,10 +7082,20 @@ void initialize_low (void) { struct sigaction sigchld_action; + int breakpoint_kind = 0; + int breakpoint_size = 0; + const gdb_byte *breakpoint = NULL; + memset (&sigchld_action, 0, sizeof (sigchld_action)); set_target_ops (&linux_target_ops); - set_breakpoint_data (the_low_target.breakpoint, - the_low_target.breakpoint_len); + + breakpoint_kind = the_target->breakpoint_kind_from_pc (NULL); + breakpoint = the_target->sw_breakpoint_from_kind (breakpoint_kind, + &breakpoint_size); + + set_breakpoint_data (breakpoint, + breakpoint_size); + linux_init_signals (); linux_ptrace_init_warnings (); diff --git a/gdb/gdbserver/linux-low.h b/gdb/gdbserver/linux-low.h index f8f6e78..28dd4db 100644 --- a/gdb/gdbserver/linux-low.h +++ b/gdb/gdbserver/linux-low.h @@ -141,8 +141,13 @@ struct linux_target_ops CORE_ADDR (*get_pc) (struct regcache *regcache); void (*set_pc) (struct regcache *regcache, CORE_ADDR newpc); - const unsigned char *breakpoint; - int breakpoint_len; + + /* See target.h for details. */ + int (*breakpoint_kind_from_pc) (CORE_ADDR *pcptr); + + /* See target.h for details. */ + const gdb_byte *(*sw_breakpoint_from_kind) (int kind, int *size); + CORE_ADDR (*breakpoint_reinsert_addr) (void); int decr_pc_after_break; diff --git a/gdb/gdbserver/linux-m32r-low.c b/gdb/gdbserver/linux-m32r-low.c index 8ffeda2..bb1002f 100644 --- a/gdb/gdbserver/linux-m32r-low.c +++ b/gdb/gdbserver/linux-m32r-low.c @@ -73,6 +73,15 @@ m32r_set_pc (struct regcache *regcache, CORE_ADDR pc) static const unsigned short m32r_breakpoint = 0x10f1; #define m32r_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +m32r_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = m32r_breakpoint_len; + return (const gdb_byte *) &m32r_breakpoint; +} + static int m32r_breakpoint_at (CORE_ADDR where) { @@ -120,8 +129,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ m32r_get_pc, m32r_set_pc, - (const unsigned char *) &m32r_breakpoint, - m32r_breakpoint_len, + NULL, /* breakpoint_from_pc */ + m32r_sw_breakpoint_from_kind, NULL, 0, m32r_breakpoint_at, diff --git a/gdb/gdbserver/linux-m68k-low.c b/gdb/gdbserver/linux-m68k-low.c index 39c9cc5..ba8e5e9 100644 --- a/gdb/gdbserver/linux-m68k-low.c +++ b/gdb/gdbserver/linux-m68k-low.c @@ -122,9 +122,18 @@ static struct regset_info m68k_regsets[] = { { 0, 0, 0, -1, -1, NULL, NULL } }; -static const unsigned char m68k_breakpoint[] = { 0x4E, 0x4F }; +static const gdb_byte m68k_breakpoint[] = { 0x4E, 0x4F }; #define m68k_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +m68k_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = m68k_breakpoint_len; + return m68k_breakpoint; +} + static CORE_ADDR m68k_get_pc (struct regcache *regcache) { @@ -215,8 +224,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ m68k_get_pc, m68k_set_pc, - m68k_breakpoint, - m68k_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + m68k_sw_breakpoint_from_kind, NULL, 2, m68k_breakpoint_at, diff --git a/gdb/gdbserver/linux-mips-low.c b/gdb/gdbserver/linux-mips-low.c index d1181b6..344d7a5 100644 --- a/gdb/gdbserver/linux-mips-low.c +++ b/gdb/gdbserver/linux-mips-low.c @@ -266,6 +266,15 @@ mips_set_pc (struct regcache *regcache, CORE_ADDR pc) static const unsigned int mips_breakpoint = 0x0005000d; #define mips_breakpoint_len 4 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +mips_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = mips_breakpoint_len; + return (const gdb_byte *) &mips_breakpoint; +} + /* We only place breakpoints in empty marker functions, and thread locking is outside of the function. So rather than importing software single-step, we can just run until exit. */ @@ -881,8 +890,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ mips_get_pc, mips_set_pc, - (const unsigned char *) &mips_breakpoint, - mips_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + mips_sw_breakpoint_from_kind, mips_reinsert_addr, 0, mips_breakpoint_at, diff --git a/gdb/gdbserver/linux-nios2-low.c b/gdb/gdbserver/linux-nios2-low.c index 71542b4..95a2d9e 100644 --- a/gdb/gdbserver/linux-nios2-low.c +++ b/gdb/gdbserver/linux-nios2-low.c @@ -127,9 +127,23 @@ nios2_set_pc (struct regcache *regcache, CORE_ADDR pc) #define NIOS2_BREAKPOINT 0x003b6ffa #endif +/* We only register the 4-byte breakpoint, even on R2 targets which also + support 2-byte breakpoints. Since there is no supports_z_point_type + function provided, gdbserver never inserts software breakpoints itself + and instead relies on GDB to insert the breakpoint of the correct length + via a memory write. */ static const unsigned int nios2_breakpoint = NIOS2_BREAKPOINT; #define nios2_breakpoint_len 4 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +nios2_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = nios2_breakpoint_len; + return (const gdb_byte *) &nios2_breakpoint; +} + /* Implement the breakpoint_reinsert_addr linux_target_ops method. */ static CORE_ADDR @@ -263,14 +277,8 @@ struct linux_target_ops the_low_target = NULL, nios2_get_pc, nios2_set_pc, - - /* We only register the 4-byte breakpoint, even on R2 targets which also - support 2-byte breakpoints. Since there is no supports_z_point_type - function provided, gdbserver never inserts software breakpoints itself - and instead relies on GDB to insert the breakpoint of the correct length - via a memory write. */ - (const unsigned char *) &nios2_breakpoint, - nios2_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + nios2_sw_breakpoint_from_kind, nios2_reinsert_addr, 0, nios2_breakpoint_at, diff --git a/gdb/gdbserver/linux-ppc-low.c b/gdb/gdbserver/linux-ppc-low.c index 188fac0..6e6a936 100644 --- a/gdb/gdbserver/linux-ppc-low.c +++ b/gdb/gdbserver/linux-ppc-low.c @@ -486,6 +486,15 @@ ppc_arch_setup (void) static const unsigned int ppc_breakpoint = 0x7d821008; #define ppc_breakpoint_len 4 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +ppc_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = ppc_breakpoint_len; + return (const gdb_byte *) &ppc_breakpoint; +} + static int ppc_breakpoint_at (CORE_ADDR where) { @@ -685,8 +694,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ ppc_get_pc, ppc_set_pc, - (const unsigned char *) &ppc_breakpoint, - ppc_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + ppc_sw_breakpoint_from_kind, NULL, 0, ppc_breakpoint_at, diff --git a/gdb/gdbserver/linux-s390-low.c b/gdb/gdbserver/linux-s390-low.c index 8a0a689..2ba1221 100644 --- a/gdb/gdbserver/linux-s390-low.c +++ b/gdb/gdbserver/linux-s390-low.c @@ -394,9 +394,18 @@ static struct regset_info s390_regsets[] = { }; -static const unsigned char s390_breakpoint[] = { 0, 1 }; +static const gdb_byte s390_breakpoint[] = { 0, 1 }; #define s390_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +s390_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = s390_breakpoint_len; + return s390_breakpoint; +} + static CORE_ADDR s390_get_pc (struct regcache *regcache) { @@ -665,8 +674,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ s390_get_pc, s390_set_pc, - s390_breakpoint, - s390_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + s390_sw_breakpoint_from_kind, NULL, s390_breakpoint_len, s390_breakpoint_at, diff --git a/gdb/gdbserver/linux-sh-low.c b/gdb/gdbserver/linux-sh-low.c index 218d4d3..f7f3239 100644 --- a/gdb/gdbserver/linux-sh-low.c +++ b/gdb/gdbserver/linux-sh-low.c @@ -77,6 +77,15 @@ sh_set_pc (struct regcache *regcache, CORE_ADDR pc) static const unsigned short sh_breakpoint = 0xc3c3; #define sh_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +sh_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = sh_breakpoint_len; + return (const gdb_byte *) &sh_breakpoint; +} + static int sh_breakpoint_at (CORE_ADDR where) { @@ -148,8 +157,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ sh_get_pc, sh_set_pc, - (const unsigned char *) &sh_breakpoint, - sh_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + sh_sw_breakpoint_from_kind, NULL, 0, sh_breakpoint_at, diff --git a/gdb/gdbserver/linux-sparc-low.c b/gdb/gdbserver/linux-sparc-low.c index 796af8a..0691867 100644 --- a/gdb/gdbserver/linux-sparc-low.c +++ b/gdb/gdbserver/linux-sparc-low.c @@ -235,11 +235,19 @@ sparc_get_pc (struct regcache *regcache) return pc; } -static const unsigned char sparc_breakpoint[INSN_SIZE] = { +static const gdb_byte sparc_breakpoint[INSN_SIZE] = { 0x91, 0xd0, 0x20, 0x01 }; #define sparc_breakpoint_len INSN_SIZE +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const unsigned char * +sparc_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = sparc_breakpoint_len; + return sparc_breakpoint; +} static int sparc_breakpoint_at (CORE_ADDR where) @@ -323,8 +331,8 @@ struct linux_target_ops the_low_target = { sparc_get_pc, /* No sparc_set_pc is needed. */ NULL, - (const unsigned char *) sparc_breakpoint, - sparc_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + sparc_sw_breakpoint_from_kind, sparc_reinsert_addr, 0, sparc_breakpoint_at, diff --git a/gdb/gdbserver/linux-tic6x-low.c b/gdb/gdbserver/linux-tic6x-low.c index a2ac3ee..d9476fd 100644 --- a/gdb/gdbserver/linux-tic6x-low.c +++ b/gdb/gdbserver/linux-tic6x-low.c @@ -171,6 +171,16 @@ extern struct linux_target_ops the_low_target; static int *tic6x_regmap; static unsigned int tic6x_breakpoint; +#define tic6x_breakpoint_len 4 + +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +tic6x_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = tic6x_breakpoint_len; + return (const gdb_byte *) &tic6x_breakpoint; +} /* Forward definition. */ static struct usrregs_info tic6x_usrregs_info; @@ -247,8 +257,6 @@ tic6x_set_pc (struct regcache *regcache, CORE_ADDR pc) supply_register_by_name (regcache, "PC", newpc.buf); } -#define tic6x_breakpoint_len 4 - static int tic6x_breakpoint_at (CORE_ADDR where) { @@ -367,8 +375,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ tic6x_get_pc, tic6x_set_pc, - (const unsigned char *) &tic6x_breakpoint, - tic6x_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + tic6x_sw_breakpoint_from_kind, NULL, 0, tic6x_breakpoint_at, diff --git a/gdb/gdbserver/linux-tile-low.c b/gdb/gdbserver/linux-tile-low.c index 6aaea6a..e31a620 100644 --- a/gdb/gdbserver/linux-tile-low.c +++ b/gdb/gdbserver/linux-tile-low.c @@ -88,6 +88,15 @@ tile_set_pc (struct regcache *regcache, CORE_ADDR pc) static uint64_t tile_breakpoint = 0x400b3cae70166000ULL; #define tile_breakpoint_len 8 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +tile_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = tile_breakpoint_len; + return (const gdb_byte *) &tile_breakpoint; +} + static int tile_breakpoint_at (CORE_ADDR where) { @@ -182,8 +191,8 @@ struct linux_target_ops the_low_target = NULL, tile_get_pc, tile_set_pc, - (const unsigned char *) &tile_breakpoint, - tile_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + tile_sw_breakpoint_from_kind, NULL, 0, tile_breakpoint_at, diff --git a/gdb/gdbserver/linux-x86-low.c b/gdb/gdbserver/linux-x86-low.c index 20d4257..406d552 100644 --- a/gdb/gdbserver/linux-x86-low.c +++ b/gdb/gdbserver/linux-x86-low.c @@ -502,7 +502,7 @@ x86_set_pc (struct regcache *regcache, CORE_ADDR pc) } } -static const unsigned char x86_breakpoint[] = { 0xCC }; +static const gdb_byte x86_breakpoint[] = { 0xCC }; #define x86_breakpoint_len 1 static int @@ -3243,6 +3243,15 @@ x86_emit_ops (void) return &i386_emit_ops; } +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +x86_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = x86_breakpoint_len; + return x86_breakpoint; +} + static int x86_supports_range_stepping (void) { @@ -3261,8 +3270,8 @@ struct linux_target_ops the_low_target = NULL, /* fetch_register */ x86_get_pc, x86_set_pc, - x86_breakpoint, - x86_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + x86_sw_breakpoint_from_kind, NULL, 1, x86_breakpoint_at, diff --git a/gdb/gdbserver/linux-xtensa-low.c b/gdb/gdbserver/linux-xtensa-low.c index debe467..fa6f418 100644 --- a/gdb/gdbserver/linux-xtensa-low.c +++ b/gdb/gdbserver/linux-xtensa-low.c @@ -151,9 +151,18 @@ static struct regset_info xtensa_regsets[] = { #define XTENSA_BREAKPOINT {0x2d,0xf0} #endif -static const unsigned char xtensa_breakpoint[] = XTENSA_BREAKPOINT; +static const gdb_byte xtensa_breakpoint[] = XTENSA_BREAKPOINT; #define xtensa_breakpoint_len 2 +/* Implementation of linux_target_ops method "sw_breakpoint_from_kind". */ + +static const gdb_byte * +xtensa_sw_breakpoint_from_kind (int kind, int *size) +{ + *size = xtensa_breakpoint_len; + return xtensa_breakpoint; +} + static CORE_ADDR xtensa_get_pc (struct regcache *regcache) { @@ -234,8 +243,8 @@ struct linux_target_ops the_low_target = { NULL, /* fetch_register */ xtensa_get_pc, xtensa_set_pc, - xtensa_breakpoint, - xtensa_breakpoint_len, + NULL, /* breakpoint_kind_from_pc */ + xtensa_sw_breakpoint_from_kind, NULL, 0, xtensa_breakpoint_at, diff --git a/gdb/gdbserver/target.h b/gdb/gdbserver/target.h index a2842b4..e4c0639 100644 --- a/gdb/gdbserver/target.h +++ b/gdb/gdbserver/target.h @@ -441,6 +441,16 @@ struct target_ops readlink(2). */ ssize_t (*multifs_readlink) (int pid, const char *filename, char *buf, size_t bufsiz); + + /* Return the breakpoint kind for this target based on PC. The PCPTR is + adjusted to the real memory location in case a flag (e.g., the Thumb bit on + ARM) was present in the PC. */ + int (*breakpoint_kind_from_pc) (CORE_ADDR *pcptr); + + /* Return the software breakpoint from KIND. KIND can have target + specific meaning like the Z0 kind parameter. + SIZE is set to the software breakpoint's length in memory. */ + const gdb_byte *(*sw_breakpoint_from_kind) (int kind, int *size); }; extern struct target_ops *the_target; |