diff options
Diffstat (limited to 'gdb/gdbserver')
-rw-r--r-- | gdb/gdbserver/ChangeLog | 10 | ||||
-rw-r--r-- | gdb/gdbserver/linux-low.c | 85 | ||||
-rw-r--r-- | gdb/gdbserver/server.c | 51 |
3 files changed, 137 insertions, 9 deletions
diff --git a/gdb/gdbserver/ChangeLog b/gdb/gdbserver/ChangeLog index eea8be5..081d305 100644 --- a/gdb/gdbserver/ChangeLog +++ b/gdb/gdbserver/ChangeLog @@ -1,3 +1,13 @@ +2015-07-02 Markus Metzger <markus.t.metzger@intel.com> + + * linux-low.c: Include "rsp-low.h" + (linux_low_encode_pt_config, linux_low_encode_raw): New. + (linux_low_read_btrace): Support BTRACE_FORMAT_PT. + (linux_low_btrace_conf): Support BTRACE_FORMAT_PT. + (handle_btrace_enable_pt): New. + (handle_btrace_general_set): Support "pt". + (handle_btrace_conf_general_set): Support "pt:size". + 2015-06-29 Pierre Langlois <pierre.langlois@arm.com> * linux-aarch64-low.c (aarch64_supports_z_point_type): Enable for diff --git a/gdb/gdbserver/linux-low.c b/gdb/gdbserver/linux-low.c index 3774d170..7bb9f7f 100644 --- a/gdb/gdbserver/linux-low.c +++ b/gdb/gdbserver/linux-low.c @@ -21,6 +21,7 @@ #include "nat/linux-osdata.h" #include "agent.h" #include "tdesc.h" +#include "rsp-low.h" #include "nat/linux-nat.h" #include "nat/linux-waitpid.h" @@ -6461,6 +6462,55 @@ linux_low_disable_btrace (struct btrace_target_info *tinfo) return (err == BTRACE_ERR_NONE ? 0 : -1); } +/* Encode an Intel(R) Processor Trace configuration. */ + +static void +linux_low_encode_pt_config (struct buffer *buffer, + const struct btrace_data_pt_config *config) +{ + buffer_grow_str (buffer, "<pt-config>\n"); + + switch (config->cpu.vendor) + { + case CV_INTEL: + buffer_xml_printf (buffer, "<cpu vendor=\"GenuineIntel\" family=\"%u\" " + "model=\"%u\" stepping=\"%u\"/>\n", + config->cpu.family, config->cpu.model, + config->cpu.stepping); + break; + + default: + break; + } + + buffer_grow_str (buffer, "</pt-config>\n"); +} + +/* Encode a raw buffer. */ + +static void +linux_low_encode_raw (struct buffer *buffer, const gdb_byte *data, + unsigned int size) +{ + if (size == 0) + return; + + /* We use hex encoding - see common/rsp-low.h. */ + buffer_grow_str (buffer, "<raw>\n"); + + while (size-- > 0) + { + char elem[2]; + + elem[0] = tohex ((*data >> 4) & 0xf); + elem[1] = tohex (*data++ & 0xf); + + buffer_grow (buffer, elem, 2); + } + + buffer_grow_str (buffer, "</raw>\n"); +} + /* See to_read_btrace target method. */ static int @@ -6482,15 +6532,14 @@ linux_low_read_btrace (struct btrace_target_info *tinfo, struct buffer *buffer, else buffer_grow_str0 (buffer, "E.Generic Error."); - btrace_data_fini (&btrace); - return -1; + goto err; } switch (btrace.format) { case BTRACE_FORMAT_NONE: buffer_grow_str0 (buffer, "E.No Trace."); - break; + goto err; case BTRACE_FORMAT_BTS: buffer_grow_str (buffer, "<!DOCTYPE btrace SYSTEM \"btrace.dtd\">\n"); @@ -6505,15 +6554,31 @@ linux_low_read_btrace (struct btrace_target_info *tinfo, struct buffer *buffer, buffer_grow_str0 (buffer, "</btrace>\n"); break; - default: - buffer_grow_str0 (buffer, "E.Unknown Trace Format."); + case BTRACE_FORMAT_PT: + buffer_grow_str (buffer, "<!DOCTYPE btrace SYSTEM \"btrace.dtd\">\n"); + buffer_grow_str (buffer, "<btrace version=\"1.0\">\n"); + buffer_grow_str (buffer, "<pt>\n"); + + linux_low_encode_pt_config (buffer, &btrace.variant.pt.config); - btrace_data_fini (&btrace); - return -1; + linux_low_encode_raw (buffer, btrace.variant.pt.data, + btrace.variant.pt.size); + + buffer_grow_str (buffer, "</pt>\n"); + buffer_grow_str0 (buffer, "</btrace>\n"); + break; + + default: + buffer_grow_str0 (buffer, "E.Unsupported Trace Format."); + goto err; } btrace_data_fini (&btrace); return 0; + +err: + btrace_data_fini (&btrace); + return -1; } /* See to_btrace_conf target method. */ @@ -6540,6 +6605,12 @@ linux_low_btrace_conf (const struct btrace_target_info *tinfo, buffer_xml_printf (buffer, " size=\"0x%x\"", conf->bts.size); buffer_xml_printf (buffer, " />\n"); break; + + case BTRACE_FORMAT_PT: + buffer_xml_printf (buffer, "<pt"); + buffer_xml_printf (buffer, " size=\"0x%x\"", conf->pt.size); + buffer_xml_printf (buffer, "/>\n"); + break; } } diff --git a/gdb/gdbserver/server.c b/gdb/gdbserver/server.c index c9effc2..7e388dd 100644 --- a/gdb/gdbserver/server.c +++ b/gdb/gdbserver/server.c @@ -408,6 +408,23 @@ handle_btrace_enable_bts (struct thread_info *thread) return NULL; } +/* Handle btrace enabling in Intel(R) Processor Trace format. */ + +static const char * +handle_btrace_enable_pt (struct thread_info *thread) +{ + if (thread->btrace != NULL) + return "E.Btrace already enabled."; + + current_btrace_conf.format = BTRACE_FORMAT_PT; + thread->btrace = target_enable_btrace (thread->entry.id, + ¤t_btrace_conf); + if (thread->btrace == NULL) + return "E.Could not enable btrace."; + + return NULL; +} + /* Handle btrace disabling. */ static const char * @@ -456,10 +473,12 @@ handle_btrace_general_set (char *own_buf) if (strcmp (op, "bts") == 0) err = handle_btrace_enable_bts (thread); + else if (strcmp (op, "pt") == 0) + err = handle_btrace_enable_pt (thread); else if (strcmp (op, "off") == 0) err = handle_btrace_disable (thread); else - err = "E.Bad Qbtrace operation. Use bts or off."; + err = "E.Bad Qbtrace operation. Use bts, pt, or off."; if (err != 0) strcpy (own_buf, err); @@ -511,6 +530,21 @@ handle_btrace_conf_general_set (char *own_buf) current_btrace_conf.bts.size = (unsigned int) size; } + else if (strncmp (op, "pt:size=", strlen ("pt:size=")) == 0) + { + unsigned long size; + char *endp = NULL; + + errno = 0; + size = strtoul (op + strlen ("pt:size="), &endp, 16); + if (endp == NULL || *endp != 0 || errno != 0 || size > UINT_MAX) + { + strcpy (own_buf, "E.Bad size value."); + return -1; + } + + current_btrace_conf.pt.size = (unsigned int) size; + } else { strcpy (own_buf, "E.Bad Qbtrace configuration option."); @@ -1871,12 +1905,25 @@ crc32 (CORE_ADDR base, int len, unsigned int crc) static void supported_btrace_packets (char *buf) { + int btrace_supported = 0; + if (target_supports_btrace (BTRACE_FORMAT_BTS)) { strcat (buf, ";Qbtrace:bts+"); strcat (buf, ";Qbtrace-conf:bts:size+"); + + btrace_supported = 1; } - else + + if (target_supports_btrace (BTRACE_FORMAT_PT)) + { + strcat (buf, ";Qbtrace:pt+"); + strcat (buf, ";Qbtrace-conf:pt:size+"); + + btrace_supported = 1; + } + + if (!btrace_supported) return; strcat (buf, ";Qbtrace:off+"); |