+2016-02-25 Marcin Kościelnicki <koriakin@0x04.net>
+
+ PR gdb/13808
+ * Makefile.in: Add i386-*-linux-ipa.o and amd64-*-linux-ipa.o.
+ * configure.srv: Ditto.
+ * linux-aarch64-ipa.c (get_ipa_tdesc): New function.
+ (initialize_low_tracepoint): Remove ipa_tdesc assignment.
+ * linux-amd64-ipa.c: Add "linux-x86-tdesc.h" include.
+ (init_registers_amd64_linux): Remove prototype.
+ (tdesc_amd64_linux): Remove declaration.
+ (get_ipa_tdesc): New function.
+ (initialize_low_tracepoint): Remove ipa_tdesc assignment,
+ initialize remaining tdescs.
+ * linux-i386-ipa.c: Add "linux-x86-tdesc.h" include.
+ (init_registers_i386_linux): Remove prototype.
+ (tdesc_i386_linux): Remove declaration.
+ (get_ipa_tdesc): New function.
+ (initialize_low_tracepoint): Remove ipa_tdesc assignment,
+ initialize remaining tdescs.
+ * linux-low.c (linux_get_ipa_tdesc_idx): New function.
+ (linux_target_ops): wire in linux_get_ipa_tdesc_idx.
+ * linux-low.h (struct linux_target_ops): Add get_ipa_tdesc_idx.
+ * linux-x86-low.c: Move tdesc declarations to linux-x86-tdesc.h.
+ (x86_get_ipa_tdesc_idx): New function.
+ (the_low_target): Wire in x86_get_ipa_tdesc_idx.
+ * linux-x86-tdesc.h: New file.
+ * target.h (struct target_ops): Add get_ipa_tdesc_idx.
+ (target_get_ipa_tdesc_idx): New macro.
+ * tracepoint.c (ipa_tdesc_idx): New macro.
+ (struct ipa_sym_addresses): Add addr_ipa_tdesc_idx.
+ (symbol_list): Add ipa_tdesc_idx.
+ (cmd_qtstart): Write ipa_tdesc_idx in the target.
+ (ipa_tdesc): Remove.
+ (ipa_tdesc_idx): New variable.
+ (get_context_regcache): Use get_ipa_tdesc.
+ (gdb_collect): Ditto.
+ (gdb_probe): Ditto.
+ * tracepoint.h (get_ipa_tdesc): New prototype.
+ (ipa_tdesc): Remove.
+
2016-02-24 Pedro Alves <palves@redhat.com>
* linux-low.c (check_stopped_by_breakpoint): Rename to ...
i386-linux-ipa.o: i386-linux.c
$(IPAGENT_COMPILE) $<
$(POSTCOMPILE)
+i386-mmx-linux-ipa.o: i386-mmx-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
+i386-avx-linux-ipa.o: i386-avx-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
+i386-mpx-linux-ipa.o: i386-mpx-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
+i386-avx512-linux-ipa.o: i386-avx512-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
linux-i386-ipa.o: linux-i386-ipa.c
$(IPAGENT_COMPILE) $<
$(POSTCOMPILE)
amd64-linux-ipa.o: amd64-linux.c
$(IPAGENT_COMPILE) $<
$(POSTCOMPILE)
+amd64-avx-linux-ipa.o: amd64-avx-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
+amd64-mpx-linux-ipa.o: amd64-mpx-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
+amd64-avx512-linux-ipa.o: amd64-avx512-linux.c
+ $(IPAGENT_COMPILE) $<
+ $(POSTCOMPILE)
linux-aarch64-ipa.o: linux-aarch64-ipa.c
$(IPAGENT_COMPILE) $<
$(POSTCOMPILE)
srv_amd64_regobj="amd64.o amd64-avx.o amd64-avx512.o amd64-mpx.o x32.o x32-avx.o x32-avx512.o"
srv_amd64_linux_regobj="amd64-linux.o amd64-avx-linux.o amd64-avx512-linux.o amd64-mpx-linux.o x32-linux.o x32-avx-linux.o x32-avx512-linux.o"
-ipa_i386_linux_regobj=i386-linux-ipa.o
-ipa_amd64_linux_regobj=amd64-linux-ipa.o
+ipa_i386_linux_regobj="i386-linux-ipa.o i386-avx-linux-ipa.o i386-avx512-linux-ipa.o i386-mpx-linux-ipa.o i386-mmx-linux-ipa.o"
+ipa_amd64_linux_regobj="amd64-linux-ipa.o amd64-avx-linux-ipa.o amd64-avx512-linux-ipa.o amd64-mpx-linux-ipa.o"
srv_i386_32bit_xmlfiles="i386/32bit-core.xml i386/32bit-sse.xml i386/32bit-avx.xml i386/32bit-avx512.xml i386/32bit-mpx.xml"
srv_i386_64bit_xmlfiles="i386/64bit-core.xml i386/64bit-sse.xml i386/64bit-avx.xml i386/64bit-avx512.xml i386/x32-core.xml i386/64bit-mpx.xml"
+ aarch64_ft_collect_regmap[regnum] * FT_CR_SIZE);
}
+/* Return target_desc to use for IPA, given the tdesc index passed by
+ gdbserver. Index is ignored, since we have only one tdesc
+ at the moment. */
+
+const struct target_desc *
+get_ipa_tdesc (int idx)
+{
+ return tdesc_aarch64;
+}
+
void
initialize_low_tracepoint (void)
{
init_registers_aarch64 ();
- ipa_tdesc = tdesc_aarch64;
}
#include "server.h"
#include "tracepoint.h"
+#include "linux-x86-tdesc.h"
/* Defined in auto-generated file amd64-linux.c. */
void init_registers_amd64_linux (void);
#endif /* HAVE_UST */
+/* Return target_desc to use for IPA, given the tdesc index passed by
+ gdbserver. */
+
+const struct target_desc *
+get_ipa_tdesc (int idx)
+{
+ switch (idx)
+ {
+ case X86_TDESC_SSE:
+ return tdesc_amd64_linux;
+ case X86_TDESC_AVX:
+ return tdesc_amd64_avx_linux;
+ case X86_TDESC_MPX:
+ return tdesc_amd64_mpx_linux;
+ case X86_TDESC_AVX512:
+ return tdesc_amd64_avx512_linux;
+ default:
+ internal_error (__FILE__, __LINE__,
+ "unknown ipa tdesc index: %d", idx);
+ return tdesc_amd64_linux;
+ }
+}
+
void
initialize_low_tracepoint (void)
{
init_registers_amd64_linux ();
- ipa_tdesc = tdesc_amd64_linux;
+ init_registers_amd64_avx_linux ();
+ init_registers_amd64_mpx_linux ();
+ init_registers_amd64_avx512_linux ();
}
#include "server.h"
#include <sys/mman.h>
#include "tracepoint.h"
+#include "linux-x86-tdesc.h"
/* GDB register numbers. */
#define i386_num_regs 16
-/* Defined in auto-generated file i386-linux.c. */
-void init_registers_i386_linux (void);
-extern const struct target_desc *tdesc_i386_linux;
-
#define FT_CR_EAX 15
#define FT_CR_ECX 14
#define FT_CR_EDX 13
}
}
+/* Return target_desc to use for IPA, given the tdesc index passed by
+ gdbserver. */
+
+const struct target_desc *
+get_ipa_tdesc (int idx)
+{
+ switch (idx)
+ {
+ case X86_TDESC_MMX:
+ return tdesc_i386_mmx_linux;
+ case X86_TDESC_SSE:
+ return tdesc_i386_linux;
+ case X86_TDESC_AVX:
+ return tdesc_i386_avx_linux;
+ case X86_TDESC_MPX:
+ return tdesc_i386_mpx_linux;
+ case X86_TDESC_AVX512:
+ return tdesc_i386_avx512_linux;
+ default:
+ internal_error (__FILE__, __LINE__,
+ "unknown ipa tdesc index: %d", idx);
+ return tdesc_i386_linux;
+ }
+}
+
void
initialize_low_tracepoint (void)
{
+ init_registers_i386_mmx_linux ();
init_registers_i386_linux ();
- ipa_tdesc = tdesc_i386_linux;
+ init_registers_i386_avx_linux ();
+ init_registers_i386_mpx_linux ();
+ init_registers_i386_avx512_linux ();
initialize_fast_tracepoint_trampoline_buffer ();
}
&& linux_supports_tracesysgood ());
}
+static int
+linux_get_ipa_tdesc_idx (void)
+{
+ if (the_low_target.get_ipa_tdesc_idx == NULL)
+ return 0;
+
+ return (*the_low_target.get_ipa_tdesc_idx) ();
+}
+
static int
linux_supports_tracepoints (void)
{
linux_breakpoint_kind_from_current_state,
linux_supports_software_single_step,
linux_supports_catch_syscall,
+ linux_get_ipa_tdesc_idx,
};
#ifdef HAVE_LINUX_REGSETS
due to SYSCALL_SIGTRAP. */
void (*get_syscall_trapinfo) (struct regcache *regcache,
int *sysno, int *sysret);
+
+ /* See target.h. */
+ int (*get_ipa_tdesc_idx) (void);
};
extern struct linux_target_ops the_low_target;
#include "nat/linux-nat.h"
#include "nat/x86-linux.h"
#include "nat/x86-linux-dregs.h"
-
-#ifdef __x86_64__
-/* Defined in auto-generated file amd64-linux.c. */
-void init_registers_amd64_linux (void);
-extern const struct target_desc *tdesc_amd64_linux;
-
-/* Defined in auto-generated file amd64-avx-linux.c. */
-void init_registers_amd64_avx_linux (void);
-extern const struct target_desc *tdesc_amd64_avx_linux;
-
-/* Defined in auto-generated file amd64-avx512-linux.c. */
-void init_registers_amd64_avx512_linux (void);
-extern const struct target_desc *tdesc_amd64_avx512_linux;
-
-/* Defined in auto-generated file amd64-mpx-linux.c. */
-void init_registers_amd64_mpx_linux (void);
-extern const struct target_desc *tdesc_amd64_mpx_linux;
-
-/* Defined in auto-generated file x32-linux.c. */
-void init_registers_x32_linux (void);
-extern const struct target_desc *tdesc_x32_linux;
-
-/* Defined in auto-generated file x32-avx-linux.c. */
-void init_registers_x32_avx_linux (void);
-extern const struct target_desc *tdesc_x32_avx_linux;
-
-/* Defined in auto-generated file x32-avx512-linux.c. */
-void init_registers_x32_avx512_linux (void);
-extern const struct target_desc *tdesc_x32_avx512_linux;
-
-#endif
-
-/* Defined in auto-generated file i386-linux.c. */
-void init_registers_i386_linux (void);
-extern const struct target_desc *tdesc_i386_linux;
-
-/* Defined in auto-generated file i386-mmx-linux.c. */
-void init_registers_i386_mmx_linux (void);
-extern const struct target_desc *tdesc_i386_mmx_linux;
-
-/* Defined in auto-generated file i386-avx-linux.c. */
-void init_registers_i386_avx_linux (void);
-extern const struct target_desc *tdesc_i386_avx_linux;
-
-/* Defined in auto-generated file i386-avx512-linux.c. */
-void init_registers_i386_avx512_linux (void);
-extern const struct target_desc *tdesc_i386_avx512_linux;
-
-/* Defined in auto-generated file i386-mpx-linux.c. */
-void init_registers_i386_mpx_linux (void);
-extern const struct target_desc *tdesc_i386_mpx_linux;
+#include "linux-x86-tdesc.h"
#ifdef __x86_64__
static struct target_desc *tdesc_amd64_linux_no_xml;
return 1;
}
+static int
+x86_get_ipa_tdesc_idx (void)
+{
+ struct regcache *regcache = get_thread_regcache (current_thread, 0);
+ const struct target_desc *tdesc = regcache->tdesc;
+
+#ifdef __x86_64__
+ if (tdesc == tdesc_amd64_linux || tdesc == tdesc_amd64_linux_no_xml
+ || tdesc == tdesc_x32_linux)
+ return X86_TDESC_SSE;
+ if (tdesc == tdesc_amd64_avx_linux || tdesc == tdesc_x32_avx_linux)
+ return X86_TDESC_AVX;
+ if (tdesc == tdesc_amd64_mpx_linux)
+ return X86_TDESC_MPX;
+ if (tdesc == tdesc_amd64_avx512_linux || tdesc == tdesc_x32_avx512_linux)
+ return X86_TDESC_AVX512;
+#endif
+
+ if (tdesc == tdesc_i386_mmx_linux)
+ return X86_TDESC_MMX;
+ if (tdesc == tdesc_i386_linux || tdesc == tdesc_i386_linux_no_xml)
+ return X86_TDESC_SSE;
+ if (tdesc == tdesc_i386_avx_linux)
+ return X86_TDESC_AVX;
+ if (tdesc == tdesc_i386_mpx_linux)
+ return X86_TDESC_MPX;
+ if (tdesc == tdesc_i386_avx512_linux)
+ return X86_TDESC_AVX512;
+
+ return 0;
+}
+
/* This is initialized assuming an amd64 target.
x86_arch_setup will correct it for i386 or amd64 targets. */
NULL, /* breakpoint_kind_from_current_state */
x86_supports_hardware_single_step,
x86_get_syscall_trapinfo,
+ x86_get_ipa_tdesc_idx,
};
void
--- /dev/null
+/* Low level support for x86 (i386 and x86-64), shared between gdbserver
+ and IPA.
+
+ Copyright (C) 2016 Free Software Foundation, Inc.
+
+ This file is part of GDB.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <http://www.gnu.org/licenses/>. */
+
+/* Note: since IPA obviously knows what ABI it's running on (i386 vs x86_64
+ vs x32), it's sufficient to pass only the register set here. This,
+ together with the ABI known at IPA compile time, maps to a tdesc. */
+
+enum x86_linux_tdesc {
+ X86_TDESC_MMX = 0,
+ X86_TDESC_SSE = 1,
+ X86_TDESC_AVX = 2,
+ X86_TDESC_MPX = 3,
+ X86_TDESC_AVX512 = 4,
+};
+
+#ifdef __x86_64__
+
+#if defined __LP64__ || !defined IN_PROCESS_AGENT
+/* Defined in auto-generated file amd64-linux.c. */
+void init_registers_amd64_linux (void);
+extern const struct target_desc *tdesc_amd64_linux;
+
+/* Defined in auto-generated file amd64-avx-linux.c. */
+void init_registers_amd64_avx_linux (void);
+extern const struct target_desc *tdesc_amd64_avx_linux;
+
+/* Defined in auto-generated file amd64-avx512-linux.c. */
+void init_registers_amd64_avx512_linux (void);
+extern const struct target_desc *tdesc_amd64_avx512_linux;
+
+/* Defined in auto-generated file amd64-mpx-linux.c. */
+void init_registers_amd64_mpx_linux (void);
+extern const struct target_desc *tdesc_amd64_mpx_linux;
+#endif
+
+#if defined __ILP32__ || !defined IN_PROCESS_AGENT
+/* Defined in auto-generated file x32-linux.c. */
+void init_registers_x32_linux (void);
+extern const struct target_desc *tdesc_x32_linux;
+
+/* Defined in auto-generated file x32-avx-linux.c. */
+void init_registers_x32_avx_linux (void);
+extern const struct target_desc *tdesc_x32_avx_linux;
+
+/* Defined in auto-generated file x32-avx512-linux.c. */
+void init_registers_x32_avx512_linux (void);
+extern const struct target_desc *tdesc_x32_avx512_linux;
+#endif
+
+#endif
+
+#if defined __i386__ || !defined IN_PROCESS_AGENT
+/* Defined in auto-generated file i386-linux.c. */
+void init_registers_i386_linux (void);
+extern const struct target_desc *tdesc_i386_linux;
+
+/* Defined in auto-generated file i386-mmx-linux.c. */
+void init_registers_i386_mmx_linux (void);
+extern const struct target_desc *tdesc_i386_mmx_linux;
+
+/* Defined in auto-generated file i386-avx-linux.c. */
+void init_registers_i386_avx_linux (void);
+extern const struct target_desc *tdesc_i386_avx_linux;
+
+/* Defined in auto-generated file i386-avx512-linux.c. */
+void init_registers_i386_avx512_linux (void);
+extern const struct target_desc *tdesc_i386_avx512_linux;
+
+/* Defined in auto-generated file i386-mpx-linux.c. */
+void init_registers_i386_mpx_linux (void);
+extern const struct target_desc *tdesc_i386_mpx_linux;
+#endif
/* Return 1 if the target supports catch syscall, 0 (or leave the
callback NULL) otherwise. */
int (*supports_catch_syscall) (void);
+
+ /* Return tdesc index for IPA. */
+ int (*get_ipa_tdesc_idx) (void);
};
extern struct target_ops *the_target;
(the_target->supports_catch_syscall ? \
(*the_target->supports_catch_syscall) () : 0)
+#define target_get_ipa_tdesc_idx() \
+ (the_target->get_ipa_tdesc_idx \
+ ? (*the_target->get_ipa_tdesc_idx) () : 0)
+
#define target_supports_tracepoints() \
(the_target->supports_tracepoints \
? (*the_target->supports_tracepoints) () : 0)
# define ust_loaded IPA_SYM_EXPORTED_NAME (ust_loaded)
# define helper_thread_id IPA_SYM_EXPORTED_NAME (helper_thread_id)
# define cmd_buf IPA_SYM_EXPORTED_NAME (cmd_buf)
+# define ipa_tdesc_idx IPA_SYM_EXPORTED_NAME (ipa_tdesc_idx)
#endif
#ifndef IN_PROCESS_AGENT
CORE_ADDR addr_get_trace_state_variable_value;
CORE_ADDR addr_set_trace_state_variable_value;
CORE_ADDR addr_ust_loaded;
+ CORE_ADDR addr_ipa_tdesc_idx;
};
static struct
IPA_SYM(get_trace_state_variable_value),
IPA_SYM(set_trace_state_variable_value),
IPA_SYM(ust_loaded),
+ IPA_SYM(ipa_tdesc_idx),
};
static struct ipa_sym_addresses ipa_sym_addrs;
*packet = '\0';
+ /* Tell IPA about the correct tdesc. */
+ if (write_inferior_integer (ipa_sym_addrs.addr_ipa_tdesc_idx,
+ target_get_ipa_tdesc_idx ()))
+ error ("Error setting ipa_tdesc_idx variable in lib");
+
/* Start out empty. */
if (agent_loaded_p ())
write_inferior_data_pointer (ipa_sym_addrs.addr_tracepoints, 0);
#endif
#ifdef IN_PROCESS_AGENT
-/* The target description used by the IPA. Given that the IPA library
- is built for a specific architecture that is loaded into the
- inferior, there only needs to be one such description per
- build. */
-const struct target_desc *ipa_tdesc;
+/* The target description index for IPA. Passed from gdbserver, used
+ to select ipa_tdesc. */
+EXTERN_C_PUSH
+IP_AGENT_EXPORT_VAR int ipa_tdesc_idx;
+EXTERN_C_POP
#endif
static struct regcache *
get_context_regcache (struct tracepoint_hit_ctx *ctx)
{
struct regcache *regcache = NULL;
-
#ifdef IN_PROCESS_AGENT
+ const struct target_desc *ipa_tdesc = get_ipa_tdesc (ipa_tdesc_idx);
+
if (ctx->type == fast_tracepoint)
{
struct fast_tracepoint_ctx *fctx = (struct fast_tracepoint_ctx *) ctx;
gdb_collect (struct tracepoint *tpoint, unsigned char *regs)
{
struct fast_tracepoint_ctx ctx;
+ const struct target_desc *ipa_tdesc;
/* Don't do anything until the trace run is completely set up. */
if (!tracing)
return;
+ ipa_tdesc = get_ipa_tdesc (ipa_tdesc_idx);
ctx.base.type = fast_tracepoint;
ctx.regs = regs;
ctx.regcache_initted = 0;
{
struct tracepoint *tpoint;
struct static_tracepoint_ctx ctx;
+ const struct target_desc *ipa_tdesc;
/* Don't do anything until the trace run is completely set up. */
if (!tracing)
return;
}
+ ipa_tdesc = get_ipa_tdesc (ipa_tdesc_idx);
ctx.base.type = static_tracepoint;
ctx.regcache_initted = 0;
ctx.regs = regs;
#ifdef IN_PROCESS_AGENT
void initialize_low_tracepoint (void);
+const struct target_desc *get_ipa_tdesc (int idx);
void supply_fast_tracepoint_registers (struct regcache *regcache,
const unsigned char *regs);
void supply_static_tracepoint_registers (struct regcache *regcache,
CORE_ADDR pc);
void set_trampoline_buffer_space (CORE_ADDR begin, CORE_ADDR end,
char *errmsg);
-
-extern const struct target_desc *ipa_tdesc;
-
#else
void stop_tracing (void);
+2016-02-25 Marcin Kościelnicki <koriakin@0x04.net>
+
+ PR gdb/13808
+ * gdb.trace/ftrace.exp (test_fast_tracepoints): Remove kfail.
+
2016-02-25 Marcin Kościelnicki <koriakin@0x04.net>
* gdb.trace/ftrace.exp: Remove unnecessary target check.
gdb_test "tfind pc *set_point" "Found trace frame .*" \
"tfind set_point frame, first time"
- setup_kfail "gdb/13808" "x86_64-*-linux*"
gdb_test "print globvar" " = 1"
gdb_test "tfind pc *set_point" "Found trace frame .*" \