Re: [PATCH v4 2/6] perf tools: Promote proper messages for cross-platform unwind
From: Arnaldo Carvalho de Melo
Date: Thu May 19 2016 - 10:50:23 EST
Em Thu, May 19, 2016 at 11:47:38AM +0000, He Kuang escreveu:
> Currently, perf script uses host unwind methods to parse perf.data
> callchain info regardless of the target architecture. So we get wrong
> result and no promotion when unwinding callchains of x86(32-bit) on
What you mean by "promotion" here? Can you use some other synonym so
that I can make sense of this description?
> x86(64-bit) machine.
>
> This patch shows proper error messages when we do remote unwind
> x86(32-bit) on other machines. Same thing for other platforms will be
> added in next patches.
>
> Common functions which will be used by both local unwind and remote
> unwind are separated into new file 'unwind-libunwind_common.c'.
>
> Signed-off-by: He Kuang <hekuang@xxxxxxxxxx>
> ---
> tools/perf/arch/common.c | 2 +-
> tools/perf/arch/common.h | 1 +
> tools/perf/config/Makefile | 6 ++++++
> tools/perf/util/Build | 1 +
> tools/perf/util/thread.c | 2 ++
> tools/perf/util/unwind-libunwind_common.c | 34 +++++++++++++++++++++++++++++++
> tools/perf/util/unwind.h | 5 +++++
> 7 files changed, 50 insertions(+), 1 deletion(-)
> create mode 100644 tools/perf/util/unwind-libunwind_common.c
>
> diff --git a/tools/perf/arch/common.c b/tools/perf/arch/common.c
> index e83c8ce..fa090a9 100644
> --- a/tools/perf/arch/common.c
> +++ b/tools/perf/arch/common.c
> @@ -102,7 +102,7 @@ static int lookup_triplets(const char *const *triplets, const char *name)
> * Return architecture name in a normalized form.
> * The conversion logic comes from the Makefile.
> */
> -static const char *normalize_arch(char *arch)
> +const char *normalize_arch(char *arch)
> {
> if (!strcmp(arch, "x86_64"))
> return "x86";
> diff --git a/tools/perf/arch/common.h b/tools/perf/arch/common.h
> index 7529cfb..6b01c73 100644
> --- a/tools/perf/arch/common.h
> +++ b/tools/perf/arch/common.h
> @@ -6,5 +6,6 @@
> extern const char *objdump_path;
>
> int perf_env__lookup_objdump(struct perf_env *env);
> +const char *normalize_arch(char *arch);
>
> #endif /* ARCH_PERF_COMMON_H */
> diff --git a/tools/perf/config/Makefile b/tools/perf/config/Makefile
> index 1e46277..a86b864 100644
> --- a/tools/perf/config/Makefile
> +++ b/tools/perf/config/Makefile
> @@ -345,6 +345,12 @@ ifeq ($(ARCH),powerpc)
> endif
>
> ifndef NO_LIBUNWIND
> + ifeq ($(feature-libunwind-x86), 1)
> + LIBUNWIND_LIBS += -lunwind-x86
> + $(call detected,CONFIG_LIBUNWIND_X86)
> + CFLAGS += -DHAVE_LIBUNWIND_X86_SUPPORT
> + endif
> +
> ifneq ($(feature-libunwind), 1)
> msg := $(warning No libunwind found. Please install libunwind-dev[el] >= 1.1 and/or set LIBUNWIND_DIR);
> NO_LIBUNWIND := 1
> diff --git a/tools/perf/util/Build b/tools/perf/util/Build
> index 8c6c8a0..25c31fb 100644
> --- a/tools/perf/util/Build
> +++ b/tools/perf/util/Build
> @@ -100,6 +100,7 @@ libperf-$(CONFIG_DWARF) += dwarf-aux.o
>
> libperf-$(CONFIG_LIBDW_DWARF_UNWIND) += unwind-libdw.o
> libperf-$(CONFIG_LIBUNWIND) += unwind-libunwind.o
> +libperf-$(CONFIG_LIBUNWIND) += unwind-libunwind_common.o
>
> libperf-$(CONFIG_LIBBABELTRACE) += data-convert-bt.o
>
> diff --git a/tools/perf/util/thread.c b/tools/perf/util/thread.c
> index 45fcb71..3043113 100644
> --- a/tools/perf/util/thread.c
> +++ b/tools/perf/util/thread.c
> @@ -205,6 +205,8 @@ void thread__insert_map(struct thread *thread, struct map *map)
> {
> map_groups__fixup_overlappings(thread->mg, map, stderr);
> map_groups__insert(thread->mg, map);
> +
> + unwind__get_arch(thread, map);
> }
>
> static int thread__clone_map_groups(struct thread *thread,
> diff --git a/tools/perf/util/unwind-libunwind_common.c b/tools/perf/util/unwind-libunwind_common.c
> new file mode 100644
> index 0000000..3946c99
> --- /dev/null
> +++ b/tools/perf/util/unwind-libunwind_common.c
> @@ -0,0 +1,34 @@
> +#include "thread.h"
> +#include "session.h"
> +#include "unwind.h"
> +#include "symbol.h"
> +#include "debug.h"
> +#include "arch/common.h"
> +
> +void unwind__get_arch(struct thread *thread, struct map *map)
> +{
> + const char *arch;
> + enum dso_type dso_type;
> +
> + if (!thread->mg->machine->env)
> + return;
> +
> + dso_type = dso__type(map->dso, thread->mg->machine);
> + if (dso_type == DSO__TYPE_UNKNOWN)
> + return;
> +
> + if (thread->addr_space)
> + pr_debug("unwind: thread map already set, 64bit is %d, dso=%s\n",
> + dso_type == DSO__TYPE_64BIT, map->dso->name);
> +
> + arch = normalize_arch(thread->mg->machine->env->arch);
> +
> + if (!strcmp(arch, "x86")) {
> + if (dso_type != DSO__TYPE_64BIT)
> +#ifdef HAVE_LIBUNWIND_X86_SUPPORT
> + pr_err("unwind: target platform=%s is not implemented\n", arch);
> +#else
> + pr_err("unwind: target platform=%s is not supported\n", arch);
> +#endif
> + }
> +}
> diff --git a/tools/perf/util/unwind.h b/tools/perf/util/unwind.h
> index 12790cf..889d630 100644
> --- a/tools/perf/util/unwind.h
> +++ b/tools/perf/util/unwind.h
> @@ -24,6 +24,7 @@ int libunwind__arch_reg_id(int regnum);
> int unwind__prepare_access(struct thread *thread);
> void unwind__flush_access(struct thread *thread);
> void unwind__finish_access(struct thread *thread);
> +void unwind__get_arch(struct thread *thread, struct map *map);
> #else
> static inline int unwind__prepare_access(struct thread *thread __maybe_unused)
> {
> @@ -32,6 +33,8 @@ static inline int unwind__prepare_access(struct thread *thread __maybe_unused)
>
> static inline void unwind__flush_access(struct thread *thread __maybe_unused) {}
> static inline void unwind__finish_access(struct thread *thread __maybe_unused) {}
> +static inline void unwind__get_arch(struct thread *thread __maybe_unused,
> + struct map *map __maybe_unused) {}
> #endif
> #else
> static inline int
> @@ -51,5 +54,7 @@ static inline int unwind__prepare_access(struct thread *thread __maybe_unused)
>
> static inline void unwind__flush_access(struct thread *thread __maybe_unused) {}
> static inline void unwind__finish_access(struct thread *thread __maybe_unused) {}
> +static inline void unwind__get_arch(struct thread *thread __maybe_unused,
> + struct map *map __maybe_unused) {}
> #endif /* HAVE_DWARF_UNWIND_SUPPORT */
> #endif /* __UNWIND_H */
> --
> 1.8.5.2