perf/core improvements and fixes:

User visible:
 
 . Allow configuring the default 'perf report -s' sort order in ~/.perfconfig,
   for instance, "sym,dso" may be more fitting for kernel developers. (Arnaldo Carvalho de Melo)
 
 - Support x8/x16/x32/x64 hexadecimal "types" in ftrace and 'perf probe' (Masami Hiramatsu)
 
 Infrastructure:
 
 - Skip running the feature tests for 'make install-doc' (Rui Teng)
 
 - Introduce tools/include/linux/time64.h with *SEC_PER_*SEC macros
   to use in all of tools/ (Arnaldo Carvalho de Melo)
 
 - Break down symbol__disassemble() into multiple functions, to ease
   future work on better reporting the errors that may take place in
   the various steps it performs (possibly decompressing kernel module
   files, getting build-id keyed files, calling objdump, parsing its
   output, etc) (Arnaldo Carvalho de Melo)
 
 - Typo fixes in various places (Colin Ian King)
 
 - Remove superfluous NULL check in the TUI code (Colin Ian King)
 
 - Allow displaying multiple header lines in the TUI browser, prep
   work for the 'perf c2c' browser (Jiri Olsa)
 
 - Copy coresight-pmu.h header file needed by perf tools (Mathieu Poirier)
 
 - Use __weak definition from linux/compiler.h (Rui Teng)
 
 Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v2
 
 iQIcBAABCAAGBQJXvK7zAAoJENZQFvNTUqpALZgP/jfaHzj3x3/ieFgi2vLz6mru
 6JIkCYb7FMKZjYqbw0LW/Pz8/xC6g8isIQRtHCOlqPl7XyByfxyZJ447cLR397/y
 nkk+KCg9jGgZF/6fWqy2GjndErgc8OMW2O2EaQLiFwpaQRSnizIltlakTVA9uqv3
 PDy7/gc+Kv7ZXC+/SsCgXagQVqGKmIkTVHxKKwrORcXQKGGhRJ2cl+dIJGPt3ZIX
 eeIM774nIGnGp9jDw4U6DNBBpSHY2gxXAqDFDIoy1/g5wQmAWiTaR6lnSecRmhoq
 t7l0BrqU6h+d2EFXzEW0nX08SX1D3pF46d3Yy/IWloX66Jvx8mBDX9lei+W4bxza
 RoervodTX0457vlslHnVdWJhxbeXuMgASYSKMVDpsHxan66+HpQso6IULVRqVWvI
 86Yjs2YxhBLqpTfK3Vqyq0flHOPRig07I292arZ4wx32M3j3diUBPfFr3v6PjRBS
 K9CyKAw5gN0hbVK/4JVRNbyOsyWM2SnoxGw42KQodrCERTycZwgJbJOydiW/AxUO
 fgaZQvlmA8/zg5b9+YGDditmRnQYkFAt1Kqxsw4LPzgWDl2jK26wA8WVH3yZsAf3
 GI2I5T/xMuqrsixKU6EOzZKbvC65Cbb32EvTCUdAUH3TqGnAUgpTXVcTtUft5+Pi
 4/54tBq2f48SQoNWXQKa
 =ZWN5
 -----END PGP SIGNATURE-----

Merge tag 'perf-core-for-mingo-20160823' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux into perf/core

Pull perf/core improvements and fixes from Arnaldo Carvalho de Melo:

User visible changes:

. Allow configuring the default 'perf report -s' sort order in ~/.perfconfig,
  for instance, "sym,dso" may be more fitting for kernel developers. (Arnaldo Carvalho de Melo)

- Support x8/x16/x32/x64 hexadecimal "types" in ftrace and 'perf probe' (Masami Hiramatsu)

Infrastructure changes:

- Skip running the feature tests for 'make install-doc' (Rui Teng)

- Introduce tools/include/linux/time64.h with *SEC_PER_*SEC macros
  to use in all of tools/ (Arnaldo Carvalho de Melo)

- Break down symbol__disassemble() into multiple functions, to ease
  future work on better reporting the errors that may take place in
  the various steps it performs (possibly decompressing kernel module
  files, getting build-id keyed files, calling objdump, parsing its
  output, etc) (Arnaldo Carvalho de Melo)

- Typo fixes in various places (Colin Ian King)

- Remove superfluous NULL check in the TUI code (Colin Ian King)

- Allow displaying multiple header lines in the TUI browser, prep
  work for the 'perf c2c' browser (Jiri Olsa)

- Copy coresight-pmu.h header file needed by perf tools (Mathieu Poirier)

- Use __weak definition from linux/compiler.h (Rui Teng)

Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Signed-off-by: Ingo Molnar <mingo@kernel.org>
This commit is contained in:
Ingo Molnar 2016-08-24 11:08:10 +02:00
commit 36e674a051
56 changed files with 475 additions and 233 deletions

View File

@ -44,8 +44,8 @@ Synopsis of kprobe_events
+|-offs(FETCHARG) : Fetch memory at FETCHARG +|- offs address.(**)
NAME=FETCHARG : Set NAME as the argument name of FETCHARG.
FETCHARG:TYPE : Set TYPE as the type of FETCHARG. Currently, basic types
(u8/u16/u32/u64/s8/s16/s32/s64), "string" and bitfield
are supported.
(u8/u16/u32/u64/s8/s16/s32/s64), hexadecimal types
(x8/x16/x32/x64), "string" and bitfield are supported.
(*) only for return probe.
(**) this is useful for fetching a field of data structures.
@ -54,7 +54,10 @@ Types
-----
Several types are supported for fetch-args. Kprobe tracer will access memory
by given type. Prefix 's' and 'u' means those types are signed and unsigned
respectively. Traced arguments are shown in decimal (signed) or hex (unsigned).
respectively. 'x' prefix implies it is unsigned. Traced arguments are shown
in decimal ('s' and 'u') or hexadecimal ('x'). Without type casting, 'x32'
or 'x64' is used depends on the architecture (e.g. x86-32 uses x32, and
x86-64 uses x64).
String type is a special type, which fetches a "null-terminated" string from
kernel space. This means it will fail and store NULL if the string container
has been paged out.

View File

@ -40,8 +40,8 @@ Synopsis of uprobe_tracer
+|-offs(FETCHARG) : Fetch memory at FETCHARG +|- offs address.(**)
NAME=FETCHARG : Set NAME as the argument name of FETCHARG.
FETCHARG:TYPE : Set TYPE as the type of FETCHARG. Currently, basic types
(u8/u16/u32/u64/s8/s16/s32/s64), "string" and bitfield
are supported.
(u8/u16/u32/u64/s8/s16/s32/s64), hexadecimal types
(x8/x16/x32/x64), "string" and bitfield are supported.
(*) only for return probe.
(**) this is useful for fetching a field of data structures.
@ -50,7 +50,10 @@ Types
-----
Several types are supported for fetch-args. Uprobe tracer will access memory
by given type. Prefix 's' and 'u' means those types are signed and unsigned
respectively. Traced arguments are shown in decimal (signed) or hex (unsigned).
respectively. 'x' prefix implies it is unsigned. Traced arguments are shown
in decimal ('s' and 'u') or hexadecimal ('x'). Without type casting, 'x32'
or 'x64' is used depends on the architecture (e.g. x86-32 uses x32, and
x86-64 uses x64).
String type is a special type, which fetches a "null-terminated" string from
user space.
Bitfield is another special type, which takes 3 parameters, bit-width, bit-

View File

@ -4123,6 +4123,30 @@ static const char readme_msg[] =
"\t\t\t traces\n"
#endif
#endif /* CONFIG_STACK_TRACER */
#ifdef CONFIG_KPROBE_EVENT
" kprobe_events\t\t- Add/remove/show the kernel dynamic events\n"
"\t\t\t Write into this file to define/undefine new trace events.\n"
#endif
#ifdef CONFIG_UPROBE_EVENT
" uprobe_events\t\t- Add/remove/show the userspace dynamic events\n"
"\t\t\t Write into this file to define/undefine new trace events.\n"
#endif
#if defined(CONFIG_KPROBE_EVENT) || defined(CONFIG_UPROBE_EVENT)
"\t accepts: event-definitions (one definition per line)\n"
"\t Format: p|r[:[<group>/]<event>] <place> [<args>]\n"
"\t -:[<group>/]<event>\n"
#ifdef CONFIG_KPROBE_EVENT
"\t place: [<module>:]<symbol>[+<offset>]|<memaddr>\n"
#endif
#ifdef CONFIG_UPROBE_EVENT
"\t place: <path>:<offset>\n"
#endif
"\t args: <name>=fetcharg[:type]\n"
"\t fetcharg: %<register>, @<address>, @<symbol>[+|-<offset>],\n"
"\t $stack<index>, $stack, $retval, $comm\n"
"\t type: s8/16/32/64, u8/16/32/64, x8/16/32/64, string,\n"
"\t b<bit-width>@<bit-offset>/<container-size>\n"
#endif
" events/\t\t- Directory containing all trace event subsystems:\n"
" enable\t\t- Write 0/1 to enable/disable tracing of all events\n"
" events/<system>/\t- Directory containing all trace events for <system>:\n"

View File

@ -253,6 +253,10 @@ static const struct fetch_type kprobes_fetch_type_table[] = {
ASSIGN_FETCH_TYPE(s16, u16, 1),
ASSIGN_FETCH_TYPE(s32, u32, 1),
ASSIGN_FETCH_TYPE(s64, u64, 1),
ASSIGN_FETCH_TYPE_ALIAS(x8, u8, u8, 0),
ASSIGN_FETCH_TYPE_ALIAS(x16, u16, u16, 0),
ASSIGN_FETCH_TYPE_ALIAS(x32, u32, u32, 0),
ASSIGN_FETCH_TYPE_ALIAS(x64, u64, u64, 0),
ASSIGN_FETCH_TYPE_END
};

View File

@ -36,24 +36,28 @@ const char *reserved_field_names[] = {
};
/* Printing in basic type function template */
#define DEFINE_BASIC_PRINT_TYPE_FUNC(type, fmt) \
int PRINT_TYPE_FUNC_NAME(type)(struct trace_seq *s, const char *name, \
#define DEFINE_BASIC_PRINT_TYPE_FUNC(tname, type, fmt) \
int PRINT_TYPE_FUNC_NAME(tname)(struct trace_seq *s, const char *name, \
void *data, void *ent) \
{ \
trace_seq_printf(s, " %s=" fmt, name, *(type *)data); \
return !trace_seq_has_overflowed(s); \
} \
const char PRINT_TYPE_FMT_NAME(type)[] = fmt; \
NOKPROBE_SYMBOL(PRINT_TYPE_FUNC_NAME(type));
const char PRINT_TYPE_FMT_NAME(tname)[] = fmt; \
NOKPROBE_SYMBOL(PRINT_TYPE_FUNC_NAME(tname));
DEFINE_BASIC_PRINT_TYPE_FUNC(u8 , "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(u16, "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(u32, "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(u64, "0x%Lx")
DEFINE_BASIC_PRINT_TYPE_FUNC(s8, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s16, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s32, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s64, "%Ld")
DEFINE_BASIC_PRINT_TYPE_FUNC(u8, u8, "%u")
DEFINE_BASIC_PRINT_TYPE_FUNC(u16, u16, "%u")
DEFINE_BASIC_PRINT_TYPE_FUNC(u32, u32, "%u")
DEFINE_BASIC_PRINT_TYPE_FUNC(u64, u64, "%Lu")
DEFINE_BASIC_PRINT_TYPE_FUNC(s8, s8, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s16, s16, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s32, s32, "%d")
DEFINE_BASIC_PRINT_TYPE_FUNC(s64, s64, "%Ld")
DEFINE_BASIC_PRINT_TYPE_FUNC(x8, u8, "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(x16, u16, "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(x32, u32, "0x%x")
DEFINE_BASIC_PRINT_TYPE_FUNC(x64, u64, "0x%Lx")
/* Print type function for string type */
int PRINT_TYPE_FUNC_NAME(string)(struct trace_seq *s, const char *name,

View File

@ -149,6 +149,11 @@ DECLARE_BASIC_PRINT_TYPE_FUNC(s8);
DECLARE_BASIC_PRINT_TYPE_FUNC(s16);
DECLARE_BASIC_PRINT_TYPE_FUNC(s32);
DECLARE_BASIC_PRINT_TYPE_FUNC(s64);
DECLARE_BASIC_PRINT_TYPE_FUNC(x8);
DECLARE_BASIC_PRINT_TYPE_FUNC(x16);
DECLARE_BASIC_PRINT_TYPE_FUNC(x32);
DECLARE_BASIC_PRINT_TYPE_FUNC(x64);
DECLARE_BASIC_PRINT_TYPE_FUNC(string);
#define FETCH_FUNC_NAME(method, type) fetch_##method##_##type
@ -203,7 +208,7 @@ DEFINE_FETCH_##method(u32) \
DEFINE_FETCH_##method(u64)
/* Default (unsigned long) fetch type */
#define __DEFAULT_FETCH_TYPE(t) u##t
#define __DEFAULT_FETCH_TYPE(t) x##t
#define _DEFAULT_FETCH_TYPE(t) __DEFAULT_FETCH_TYPE(t)
#define DEFAULT_FETCH_TYPE _DEFAULT_FETCH_TYPE(BITS_PER_LONG)
#define DEFAULT_FETCH_TYPE_STR __stringify(DEFAULT_FETCH_TYPE)
@ -234,6 +239,10 @@ ASSIGN_FETCH_FUNC(file_offset, ftype), \
#define ASSIGN_FETCH_TYPE(ptype, ftype, sign) \
__ASSIGN_FETCH_TYPE(#ptype, ptype, ftype, sizeof(ftype), sign, #ptype)
/* If ptype is an alias of atype, use this macro (show atype in format) */
#define ASSIGN_FETCH_TYPE_ALIAS(ptype, atype, ftype, sign) \
__ASSIGN_FETCH_TYPE(#ptype, ptype, ftype, sizeof(ftype), sign, #atype)
#define ASSIGN_FETCH_TYPE_END {}
#define FETCH_TYPE_STRING 0

View File

@ -211,6 +211,10 @@ static const struct fetch_type uprobes_fetch_type_table[] = {
ASSIGN_FETCH_TYPE(s16, u16, 1),
ASSIGN_FETCH_TYPE(s32, u32, 1),
ASSIGN_FETCH_TYPE(s64, u64, 1),
ASSIGN_FETCH_TYPE_ALIAS(x8, u8, u8, 0),
ASSIGN_FETCH_TYPE_ALIAS(x16, u16, u16, 0),
ASSIGN_FETCH_TYPE_ALIAS(x32, u32, u32, 0),
ASSIGN_FETCH_TYPE_ALIAS(x64, u64, u64, 0),
ASSIGN_FETCH_TYPE_END
};

View File

@ -0,0 +1,39 @@
/*
* Copyright(C) 2015 Linaro Limited. All rights reserved.
* Author: Mathieu Poirier <mathieu.poirier@linaro.org>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 as published by
* the Free Software Foundation.
*
* 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/>.
*/
#ifndef _LINUX_CORESIGHT_PMU_H
#define _LINUX_CORESIGHT_PMU_H
#define CORESIGHT_ETM_PMU_NAME "cs_etm"
#define CORESIGHT_ETM_PMU_SEED 0x10
/* ETMv3.5/PTM's ETMCR config bit */
#define ETM_OPT_CYCACC 12
#define ETM_OPT_TS 28
static inline int coresight_get_trace_id(int cpu)
{
/*
* A trace ID of value 0 is invalid, so let's start at some
* random value that fits in 7 bits and go from there. Since
* the common convention is to have data trace IDs be I(N) + 1,
* set instruction trace IDs as a function of the CPU number.
*/
return (CORESIGHT_ETM_PMU_SEED + (cpu * 2));
}
#endif

View File

@ -8,7 +8,11 @@ void *memdup(const void *src, size_t len);
int strtobool(const char *s, bool *res);
#ifdef __GLIBC__
/*
* glibc based builds needs the extern while uClibc doesn't.
* However uClibc headers also define __GLIBC__ hence the hack below
*/
#if defined(__GLIBC__) && !defined(__UCLIBC__)
extern size_t strlcpy(char *dest, const char *src, size_t size);
#endif

View File

@ -0,0 +1,12 @@
#ifndef _TOOLS_LINUX_TIME64_H
#define _TOOLS_LINUX_TIME64_H
#define MSEC_PER_SEC 1000L
#define USEC_PER_MSEC 1000L
#define NSEC_PER_USEC 1000L
#define NSEC_PER_MSEC 1000000L
#define USEC_PER_SEC 1000000L
#define NSEC_PER_SEC 1000000000L
#define FSEC_PER_SEC 1000000000000000LL
#endif /* _LINUX_TIME64_H */

View File

@ -382,6 +382,10 @@ call-graph.*::
histogram entry. Default is 0 which means no limitation.
report.*::
report.sort_order::
Allows changing the default sort order from "comm,dso,symbol" to
some other default, for instance "sym,dso" may be more fitting for
kernel developers.
report.percent-limit::
This one is mostly the same as call-graph.threshold but works for
histogram entries. Entries having an overhead lower than this

View File

@ -176,13 +176,12 @@ Each probe argument follows below syntax.
'NAME' specifies the name of this argument (optional). You can use the name of local variable, local data structure member (e.g. var->field, var.field2), local array with fixed index (e.g. array[1], var->array[0], var->pointer[2]), or kprobe-tracer argument format (e.g. $retval, %ax, etc). Note that the name of this argument will be set as the last member name if you specify a local data structure member (e.g. field2 for 'var->field1.field2'.)
'$vars' and '$params' special arguments are also available for NAME, '$vars' is expanded to the local variables (including function parameters) which can access at given probe point. '$params' is expanded to only the function parameters.
'TYPE' casts the type of this argument (optional). If omitted, perf probe automatically set the type based on debuginfo. Currently, basic types (u8/u16/u32/u64/s8/s16/s32/s64), signedness casting (u/s), "string" and bitfield are supported. (see TYPES for detail)
'TYPE' casts the type of this argument (optional). If omitted, perf probe automatically set the type based on debuginfo (*). Currently, basic types (u8/u16/u32/u64/s8/s16/s32/s64), hexadecimal integers (x/x8/x16/x32/x64), signedness casting (u/s), "string" and bitfield are supported. (see TYPES for detail)
On x86 systems %REG is always the short form of the register: for example %AX. %RAX or %EAX is not valid.
TYPES
-----
Basic types (u8/u16/u32/u64/s8/s16/s32/s64) are integer types. Prefix 's' and 'u' means those types are signed and unsigned respectively. Traced arguments are shown in decimal (signed) or hex (unsigned). You can also use 's' or 'u' to specify only signedness and leave its size auto-detected by perf probe.
Basic types (u8/u16/u32/u64/s8/s16/s32/s64) and hexadecimal integers (x8/x16/x32/x64) are integer types. Prefix 's' and 'u' means those types are signed and unsigned respectively, and 'x' means that is shown in hexadecimal format. Traced arguments are shown in decimal (sNN/uNN) or hex (xNN). You can also use 's' or 'u' to specify only signedness and leave its size auto-detected by perf probe. Moreover, you can use 'x' to explicitly specify to be shown in hexadecimal (the size is also auto-detected).
String type is a special type, which fetches a "null-terminated" string from kernel space. This means it will fail and store NULL if the string container has been paged out. You can specify 'string' type only for the local variable or structure member which is an array of or a pointer to 'char' or 'unsigned char' type.
Bitfield is another special type, which takes 3 parameters, bit-width, bit-offset, and container-size (usually 32). The syntax is;

View File

@ -60,6 +60,7 @@ tools/include/asm-generic/bitops.h
tools/include/linux/atomic.h
tools/include/linux/bitops.h
tools/include/linux/compiler.h
tools/include/linux/coresight-pmu.h
tools/include/linux/filter.h
tools/include/linux/hash.h
tools/include/linux/kernel.h
@ -77,4 +78,5 @@ tools/include/linux/stringify.h
tools/include/linux/types.h
tools/include/linux/err.h
tools/include/linux/bitmap.h
tools/include/linux/time64.h
tools/arch/*/include/uapi/asm/perf_regs.h

View File

@ -165,7 +165,7 @@ SUBCMD_DIR = $(srctree)/tools/lib/subcmd/
# non-config cases
config := 1
NON_CONFIG_TARGETS := clean TAGS tags cscope help
NON_CONFIG_TARGETS := clean TAGS tags cscope help install-doc
ifdef MAKECMDGOALS
ifeq ($(filter-out $(NON_CONFIG_TARGETS),$(MAKECMDGOALS)),)
@ -429,6 +429,9 @@ $(PERF_IN): prepare FORCE
@(test -f ../../include/asm-generic/bitops/fls64.h && ( \
(diff -B ../include/asm-generic/bitops/fls64.h ../../include/asm-generic/bitops/fls64.h >/dev/null) \
|| echo "Warning: tools/include/asm-generic/bitops/fls64.h differs from kernel" >&2 )) || true
@(test -f ../../include/linux/coresight-pmu.h && ( \
(diff -B ../include/linux/coresight-pmu.h ../../include/linux/coresight-pmu.h >/dev/null) \
|| echo "Warning: tools/include/linux/coresight-pmu.h differs from kernel" >&2 )) || true
$(Q)$(MAKE) $(build)=perf
$(OUTPUT)perf: $(PERFLIBS) $(PERF_IN) $(LIBTRACEEVENT_DYNAMIC_LIST)

View File

@ -16,6 +16,7 @@
#include <subcmd/parse-options.h>
#include <linux/compiler.h>
#include <linux/kernel.h>
#include <linux/time64.h>
#include <errno.h>
#include "bench.h"
#include "futex.h"
@ -62,7 +63,7 @@ static void print_summary(void)
printf("Requeued %d of %d threads in %.4f ms (+-%.2f%%)\n",
requeued_avg,
nthreads,
requeuetime_avg/1e3,
requeuetime_avg / USEC_PER_MSEC,
rel_stddev_stats(requeuetime_stddev, requeuetime_avg));
}
@ -184,7 +185,7 @@ int bench_futex_requeue(int argc, const char **argv,
if (!silent) {
printf("[Run %d]: Requeued %d of %d threads in %.4f ms\n",
j + 1, nrequeued, nthreads, runtime.tv_usec/1e3);
j + 1, nrequeued, nthreads, runtime.tv_usec / (double)USEC_PER_MSEC);
}
/* everybody should be blocked on futex2, wake'em up */

View File

@ -15,6 +15,7 @@
#include <subcmd/parse-options.h>
#include <linux/compiler.h>
#include <linux/kernel.h>
#include <linux/time64.h>
#include <errno.h>
#include "bench.h"
#include "futex.h"
@ -156,7 +157,7 @@ static void print_run(struct thread_data *waking_worker, unsigned int run_num)
printf("[Run %d]: Avg per-thread latency (waking %d/%d threads) "
"in %.4f ms (+-%.2f%%)\n", run_num + 1, wakeup_avg,
nblocked_threads, waketime_avg/1e3,
nblocked_threads, waketime_avg / USEC_PER_MSEC,
rel_stddev_stats(waketime_stddev, waketime_avg));
}
@ -172,7 +173,7 @@ static void print_summary(void)
printf("Avg per-thread latency (waking %d/%d threads) in %.4f ms (+-%.2f%%)\n",
wakeup_avg,
nblocked_threads,
waketime_avg/1e3,
waketime_avg / USEC_PER_MSEC,
rel_stddev_stats(waketime_stddev, waketime_avg));
}

View File

@ -16,6 +16,7 @@
#include <subcmd/parse-options.h>
#include <linux/compiler.h>
#include <linux/kernel.h>
#include <linux/time64.h>
#include <errno.h>
#include "bench.h"
#include "futex.h"
@ -81,7 +82,7 @@ static void print_summary(void)
printf("Wokeup %d of %d threads in %.4f ms (+-%.2f%%)\n",
wakeup_avg,
nthreads,
waketime_avg/1e3,
waketime_avg / USEC_PER_MSEC,
rel_stddev_stats(waketime_stddev, waketime_avg));
}
@ -182,7 +183,7 @@ int bench_futex_wake(int argc, const char **argv,
if (!silent) {
printf("[Run %d]: Wokeup %d of %d threads in %.4f ms\n",
j + 1, nwoken, nthreads, runtime.tv_usec/1e3);
j + 1, nwoken, nthreads, runtime.tv_usec / (double)USEC_PER_MSEC);
}
for (i = 0; i < nthreads; i++) {

View File

@ -21,6 +21,7 @@
#include <string.h>
#include <sys/time.h>
#include <errno.h>
#include <linux/time64.h>
#define K 1024
@ -89,7 +90,7 @@ static u64 get_cycles(void)
static double timeval2double(struct timeval *ts)
{
return (double)ts->tv_sec + (double)ts->tv_usec / (double)1000000;
return (double)ts->tv_sec + (double)ts->tv_usec / (double)USEC_PER_SEC;
}
#define print_bps(x) do { \

View File

@ -30,6 +30,7 @@
#include <sys/wait.h>
#include <sys/prctl.h>
#include <sys/types.h>
#include <linux/time64.h>
#include <numa.h>
#include <numaif.h>
@ -1004,7 +1005,7 @@ static void calc_convergence(double runtime_ns_max, double *convergence)
if (strong && process_groups == g->p.nr_proc) {
if (!*convergence) {
*convergence = runtime_ns_max;
tprintf(" (%6.1fs converged)\n", *convergence/1e9);
tprintf(" (%6.1fs converged)\n", *convergence / NSEC_PER_SEC);
if (g->p.measure_convergence) {
g->all_converged = true;
g->stop_work = true;
@ -1012,7 +1013,7 @@ static void calc_convergence(double runtime_ns_max, double *convergence)
}
} else {
if (*convergence) {
tprintf(" (%6.1fs de-converged)", runtime_ns_max/1e9);
tprintf(" (%6.1fs de-converged)", runtime_ns_max / NSEC_PER_SEC);
*convergence = 0;
}
tprintf("\n");
@ -1022,7 +1023,7 @@ static void calc_convergence(double runtime_ns_max, double *convergence)
static void show_summary(double runtime_ns_max, int l, double *convergence)
{
tprintf("\r # %5.1f%% [%.1f mins]",
(double)(l+1)/g->p.nr_loops*100.0, runtime_ns_max/1e9 / 60.0);
(double)(l+1)/g->p.nr_loops*100.0, runtime_ns_max / NSEC_PER_SEC / 60.0);
calc_convergence(runtime_ns_max, convergence);
@ -1179,8 +1180,8 @@ static void *worker_thread(void *__tdata)
if (details >= 3) {
timersub(&stop, &start, &diff);
runtime_ns_max = diff.tv_sec * 1000000000;
runtime_ns_max += diff.tv_usec * 1000;
runtime_ns_max = diff.tv_sec * NSEC_PER_SEC;
runtime_ns_max += diff.tv_usec * NSEC_PER_USEC;
if (details >= 0) {
printf(" #%2d / %2d: %14.2lf nsecs/op [val: %016"PRIx64"]\n",
@ -1192,23 +1193,23 @@ static void *worker_thread(void *__tdata)
continue;
timersub(&stop, &start0, &diff);
runtime_ns_max = diff.tv_sec * 1000000000ULL;
runtime_ns_max += diff.tv_usec * 1000ULL;
runtime_ns_max = diff.tv_sec * NSEC_PER_SEC;
runtime_ns_max += diff.tv_usec * NSEC_PER_USEC;
show_summary(runtime_ns_max, l, &convergence);
}
gettimeofday(&stop, NULL);
timersub(&stop, &start0, &diff);
td->runtime_ns = diff.tv_sec * 1000000000ULL;
td->runtime_ns += diff.tv_usec * 1000ULL;
td->speed_gbs = bytes_done / (td->runtime_ns / 1e9) / 1e9;
td->runtime_ns = diff.tv_sec * NSEC_PER_SEC;
td->runtime_ns += diff.tv_usec * NSEC_PER_USEC;
td->speed_gbs = bytes_done / (td->runtime_ns / NSEC_PER_SEC) / 1e9;
getrusage(RUSAGE_THREAD, &rusage);
td->system_time_ns = rusage.ru_stime.tv_sec * 1000000000ULL;
td->system_time_ns += rusage.ru_stime.tv_usec * 1000ULL;
td->user_time_ns = rusage.ru_utime.tv_sec * 1000000000ULL;
td->user_time_ns += rusage.ru_utime.tv_usec * 1000ULL;
td->system_time_ns = rusage.ru_stime.tv_sec * NSEC_PER_SEC;
td->system_time_ns += rusage.ru_stime.tv_usec * NSEC_PER_USEC;
td->user_time_ns = rusage.ru_utime.tv_sec * NSEC_PER_SEC;
td->user_time_ns += rusage.ru_utime.tv_usec * NSEC_PER_USEC;
free_data(thread_data, g->p.bytes_thread);
@ -1469,7 +1470,7 @@ static int __bench_numa(const char *name)
}
/* Wait for all the threads to start up: */
while (g->nr_tasks_started != g->p.nr_tasks)
usleep(1000);
usleep(USEC_PER_MSEC);
BUG_ON(g->nr_tasks_started != g->p.nr_tasks);
@ -1488,9 +1489,9 @@ static int __bench_numa(const char *name)
timersub(&stop, &start, &diff);
startup_sec = diff.tv_sec * 1000000000.0;
startup_sec += diff.tv_usec * 1000.0;
startup_sec /= 1e9;
startup_sec = diff.tv_sec * NSEC_PER_SEC;
startup_sec += diff.tv_usec * NSEC_PER_USEC;
startup_sec /= NSEC_PER_SEC;
tprintf(" threads initialized in %.6f seconds.\n", startup_sec);
tprintf(" #\n");
@ -1529,14 +1530,14 @@ static int __bench_numa(const char *name)
tprintf("\n ###\n");
tprintf("\n");
runtime_sec_max = diff.tv_sec * 1000000000.0;
runtime_sec_max += diff.tv_usec * 1000.0;
runtime_sec_max /= 1e9;
runtime_sec_max = diff.tv_sec * NSEC_PER_SEC;
runtime_sec_max += diff.tv_usec * NSEC_PER_USEC;
runtime_sec_max /= NSEC_PER_SEC;
runtime_sec_min = runtime_ns_min/1e9;
runtime_sec_min = runtime_ns_min / NSEC_PER_SEC;
bytes = g->bytes_done;
runtime_avg = (double)runtime_ns_sum / g->p.nr_tasks / 1e9;
runtime_avg = (double)runtime_ns_sum / g->p.nr_tasks / NSEC_PER_SEC;
if (g->p.measure_convergence) {
print_res(name, runtime_sec_max,
@ -1562,7 +1563,7 @@ static int __bench_numa(const char *name)
print_res(name, bytes / 1e9,
"GB,", "data-total", "GB data processed, total");
print_res(name, runtime_sec_max * 1e9 / (bytes / g->p.nr_tasks),
print_res(name, runtime_sec_max * NSEC_PER_SEC / (bytes / g->p.nr_tasks),
"nsecs,", "runtime/byte/thread","nsecs/byte/thread runtime");
print_res(name, bytes / g->p.nr_tasks / 1e9 / runtime_sec_max,
@ -1581,9 +1582,9 @@ static int __bench_numa(const char *name)
snprintf(tname, 32, "process%d:thread%d", p, t);
print_res(tname, td->speed_gbs,
"GB/sec", "thread-speed", "GB/sec/thread speed");
print_res(tname, td->system_time_ns / 1e9,
print_res(tname, td->system_time_ns / NSEC_PER_SEC,
"secs", "thread-system-time", "system CPU time/thread");
print_res(tname, td->user_time_ns / 1e9,
print_res(tname, td->user_time_ns / NSEC_PER_SEC,
"secs", "thread-user-time", "user CPU time/thread");
}
}

View File

@ -29,6 +29,7 @@
#include <poll.h>
#include <limits.h>
#include <err.h>
#include <linux/time64.h>
#define DATASIZE 100
@ -312,11 +313,11 @@ int bench_sched_messaging(int argc, const char **argv,
thread_mode ? "threads" : "processes");
printf(" %14s: %lu.%03lu [sec]\n", "Total time",
diff.tv_sec,
(unsigned long) (diff.tv_usec/1000));
(unsigned long) (diff.tv_usec / USEC_PER_MSEC));
break;
case BENCH_FORMAT_SIMPLE:
printf("%lu.%03lu\n", diff.tv_sec,
(unsigned long) (diff.tv_usec/1000));
(unsigned long) (diff.tv_usec / USEC_PER_MSEC));
break;
default:
/* reaching here is something disaster */

View File

@ -25,6 +25,7 @@
#include <sys/time.h>
#include <sys/types.h>
#include <sys/syscall.h>
#include <linux/time64.h>
#include <pthread.h>
@ -153,24 +154,24 @@ int bench_sched_pipe(int argc, const char **argv, const char *prefix __maybe_unu
printf("# Executed %d pipe operations between two %s\n\n",
loops, threaded ? "threads" : "processes");
result_usec = diff.tv_sec * 1000000;
result_usec = diff.tv_sec * USEC_PER_SEC;
result_usec += diff.tv_usec;
printf(" %14s: %lu.%03lu [sec]\n\n", "Total time",
diff.tv_sec,
(unsigned long) (diff.tv_usec/1000));
(unsigned long) (diff.tv_usec / USEC_PER_MSEC));
printf(" %14lf usecs/op\n",
(double)result_usec / (double)loops);
printf(" %14d ops/sec\n",
(int)((double)loops /
((double)result_usec / (double)1000000)));
((double)result_usec / (double)USEC_PER_SEC)));
break;
case BENCH_FORMAT_SIMPLE:
printf("%lu.%03lu\n",
diff.tv_sec,
(unsigned long) (diff.tv_usec / 1000));
(unsigned long) (diff.tv_usec / USEC_PER_MSEC));
break;
default:

View File

@ -1033,7 +1033,9 @@ static int hpp__entry_global(struct perf_hpp_fmt *_fmt, struct perf_hpp *hpp,
}
static int hpp__header(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists __maybe_unused)
struct hists *hists __maybe_unused,
int line __maybe_unused,
int *span __maybe_unused)
{
struct diff_hpp_fmt *dfmt =
container_of(fmt, struct diff_hpp_fmt, fmt);

View File

@ -24,6 +24,7 @@
#include <sys/timerfd.h>
#endif
#include <linux/time64.h>
#include <termios.h>
#include <semaphore.h>
#include <pthread.h>
@ -362,7 +363,7 @@ static bool handle_end_event(struct perf_kvm_stat *kvm,
if (!skip_event(decode)) {
pr_info("%" PRIu64 " VM %d, vcpu %d: %s event took %" PRIu64 "usec\n",
sample->time, sample->pid, vcpu_record->vcpu_id,
decode, time_diff/1000);
decode, time_diff / NSEC_PER_USEC);
}
}
@ -608,15 +609,15 @@ static void print_result(struct perf_kvm_stat *kvm)
pr_info("%10llu ", (unsigned long long)ecount);
pr_info("%8.2f%% ", (double)ecount / kvm->total_count * 100);
pr_info("%8.2f%% ", (double)etime / kvm->total_time * 100);
pr_info("%9.2fus ", (double)min / 1e3);
pr_info("%9.2fus ", (double)max / 1e3);
pr_info("%9.2fus ( +-%7.2f%% )", (double)etime / ecount/1e3,
pr_info("%9.2fus ", (double)min / NSEC_PER_USEC);
pr_info("%9.2fus ", (double)max / NSEC_PER_USEC);
pr_info("%9.2fus ( +-%7.2f%% )", (double)etime / ecount / NSEC_PER_USEC,
kvm_event_rel_stddev(vcpu, event));
pr_info("\n");
}
pr_info("\nTotal Samples:%" PRIu64 ", Total events handled time:%.2fus.\n\n",
kvm->total_count, kvm->total_time / 1e3);
kvm->total_count, kvm->total_time / (double)NSEC_PER_USEC);
if (kvm->lost_events)
pr_info("\nLost events: %" PRIu64 "\n\n", kvm->lost_events);

View File

@ -42,7 +42,7 @@
#include <sched.h>
#include <sys/mman.h>
#include <asm/bug.h>
#include <linux/time64.h>
struct record {
struct perf_tool tool;
@ -96,7 +96,7 @@ backward_rb_find_range(void *buf, int mask, u64 head, u64 *start, u64 *end)
*start = head;
while (true) {
if (evt_head - head >= (unsigned int)size) {
pr_debug("Finshed reading backward ring buffer: rewind\n");
pr_debug("Finished reading backward ring buffer: rewind\n");
if (evt_head - head > (unsigned int)size)
evt_head -= pheader->size;
*end = evt_head;
@ -106,7 +106,7 @@ backward_rb_find_range(void *buf, int mask, u64 head, u64 *start, u64 *end)
pheader = (struct perf_event_header *)(buf + (evt_head & mask));
if (pheader->size == 0) {
pr_debug("Finshed reading backward ring buffer: get start\n");
pr_debug("Finished reading backward ring buffer: get start\n");
*end = evt_head;
return 0;
}
@ -954,7 +954,7 @@ static int __cmd_record(struct record *rec, int argc, const char **argv)
}
if (opts->initial_delay) {
usleep(opts->initial_delay * 1000);
usleep(opts->initial_delay * USEC_PER_MSEC);
perf_evlist__enable(rec->evlist);
}

View File

@ -89,6 +89,10 @@ static int report__config(const char *var, const char *value, void *cb)
rep->queue_size = perf_config_u64(var, value);
return 0;
}
if (!strcmp(var, "report.sort_order")) {
default_sort_order = strdup(value);
return 0;
}
return 0;
}

View File

@ -26,6 +26,7 @@
#include <pthread.h>
#include <math.h>
#include <api/fs/fs.h>
#include <linux/time64.h>
#define PR_SET_NAME 15 /* Set process name */
#define MAX_CPUS 4096
@ -199,7 +200,7 @@ static u64 get_nsecs(void)
clock_gettime(CLOCK_MONOTONIC, &ts);
return ts.tv_sec * 1000000000ULL + ts.tv_nsec;
return ts.tv_sec * NSEC_PER_SEC + ts.tv_nsec;
}
static void burn_nsecs(struct perf_sched *sched, u64 nsecs)
@ -223,7 +224,7 @@ static void sleep_nsecs(u64 nsecs)
static void calibrate_run_measurement_overhead(struct perf_sched *sched)
{
u64 T0, T1, delta, min_delta = 1000000000ULL;
u64 T0, T1, delta, min_delta = NSEC_PER_SEC;
int i;
for (i = 0; i < 10; i++) {
@ -240,7 +241,7 @@ static void calibrate_run_measurement_overhead(struct perf_sched *sched)
static void calibrate_sleep_measurement_overhead(struct perf_sched *sched)
{
u64 T0, T1, delta, min_delta = 1000000000ULL;
u64 T0, T1, delta, min_delta = NSEC_PER_SEC;
int i;
for (i = 0; i < 10; i++) {
@ -452,8 +453,8 @@ static u64 get_cpu_usage_nsec_parent(void)
err = getrusage(RUSAGE_SELF, &ru);
BUG_ON(err);
sum = ru.ru_utime.tv_sec*1e9 + ru.ru_utime.tv_usec*1e3;
sum += ru.ru_stime.tv_sec*1e9 + ru.ru_stime.tv_usec*1e3;
sum = ru.ru_utime.tv_sec * NSEC_PER_SEC + ru.ru_utime.tv_usec * NSEC_PER_USEC;
sum += ru.ru_stime.tv_sec * NSEC_PER_SEC + ru.ru_stime.tv_usec * NSEC_PER_USEC;
return sum;
}
@ -667,12 +668,12 @@ static void run_one_test(struct perf_sched *sched)
sched->run_avg = delta;
sched->run_avg = (sched->run_avg * (sched->replay_repeat - 1) + delta) / sched->replay_repeat;
printf("#%-3ld: %0.3f, ", sched->nr_runs, (double)delta / 1000000.0);
printf("#%-3ld: %0.3f, ", sched->nr_runs, (double)delta / NSEC_PER_MSEC);
printf("ravg: %0.2f, ", (double)sched->run_avg / 1e6);
printf("ravg: %0.2f, ", (double)sched->run_avg / NSEC_PER_MSEC);
printf("cpu: %0.2f / %0.2f",
(double)sched->cpu_usage / 1e6, (double)sched->runavg_cpu_usage / 1e6);
(double)sched->cpu_usage / NSEC_PER_MSEC, (double)sched->runavg_cpu_usage / NSEC_PER_MSEC);
#if 0
/*
@ -680,8 +681,8 @@ static void run_one_test(struct perf_sched *sched)
* accurate than the sched->sum_exec_runtime based statistics:
*/
printf(" [%0.2f / %0.2f]",
(double)sched->parent_cpu_usage/1e6,
(double)sched->runavg_parent_cpu_usage/1e6);
(double)sched->parent_cpu_usage / NSEC_PER_MSEC,
(double)sched->runavg_parent_cpu_usage / NSEC_PER_MSEC);
#endif
printf("\n");
@ -696,13 +697,13 @@ static void test_calibrations(struct perf_sched *sched)
u64 T0, T1;
T0 = get_nsecs();
burn_nsecs(sched, 1e6);
burn_nsecs(sched, NSEC_PER_MSEC);
T1 = get_nsecs();
printf("the run test took %" PRIu64 " nsecs\n", T1 - T0);
T0 = get_nsecs();
sleep_nsecs(1e6);
sleep_nsecs(NSEC_PER_MSEC);
T1 = get_nsecs();
printf("the sleep test took %" PRIu64 " nsecs\n", T1 - T0);
@ -1213,10 +1214,10 @@ static void output_lat_thread(struct perf_sched *sched, struct work_atoms *work_
avg = work_list->total_lat / work_list->nb_atoms;
printf("|%11.3f ms |%9" PRIu64 " | avg:%9.3f ms | max:%9.3f ms | max at: %13.6f s\n",
(double)work_list->total_runtime / 1e6,
work_list->nb_atoms, (double)avg / 1e6,
(double)work_list->max_lat / 1e6,
(double)work_list->max_lat_at / 1e9);
(double)work_list->total_runtime / NSEC_PER_MSEC,
work_list->nb_atoms, (double)avg / NSEC_PER_MSEC,
(double)work_list->max_lat / NSEC_PER_MSEC,
(double)work_list->max_lat_at / NSEC_PER_SEC);
}
static int pid_cmp(struct work_atoms *l, struct work_atoms *r)
@ -1491,7 +1492,7 @@ static int map_switch_event(struct perf_sched *sched, struct perf_evsel *evsel,
if (sched->map.cpus && !cpu_map__has(sched->map.cpus, this_cpu))
goto out;
color_fprintf(stdout, color, " %12.6f secs ", (double)timestamp/1e9);
color_fprintf(stdout, color, " %12.6f secs ", (double)timestamp / NSEC_PER_SEC);
if (new_shortname) {
const char *pid_color = color;
@ -1753,7 +1754,7 @@ static int perf_sched__lat(struct perf_sched *sched)
printf(" -----------------------------------------------------------------------------------------------------------------\n");
printf(" TOTAL: |%11.3f ms |%9" PRIu64 " |\n",
(double)sched->all_runtime / 1e6, sched->all_count);
(double)sched->all_runtime / NSEC_PER_MSEC, sched->all_count);
printf(" ---------------------------------------------------\n");

View File

@ -24,6 +24,7 @@
#include "util/thread-stack.h"
#include <linux/bitmap.h>
#include <linux/stringify.h>
#include <linux/time64.h>
#include "asm/bug.h"
#include "util/mem-events.h"
@ -464,9 +465,9 @@ static void print_sample_start(struct perf_sample *sample,
if (PRINT_FIELD(TIME)) {
nsecs = sample->time;
secs = nsecs / NSECS_PER_SEC;
nsecs -= secs * NSECS_PER_SEC;
usecs = nsecs / NSECS_PER_USEC;
secs = nsecs / NSEC_PER_SEC;
nsecs -= secs * NSEC_PER_SEC;
usecs = nsecs / NSEC_PER_USEC;
if (nanosecs)
printf("%5lu.%09llu: ", secs, nsecs);
else

View File

@ -65,6 +65,7 @@
#include "util/group.h"
#include "asm/bug.h"
#include <linux/time64.h>
#include <api/fs/fs.h>
#include <stdlib.h>
#include <sys/prctl.h>
@ -172,7 +173,7 @@ static inline void diff_timespec(struct timespec *r, struct timespec *a,
{
r->tv_sec = a->tv_sec - b->tv_sec;
if (a->tv_nsec < b->tv_nsec) {
r->tv_nsec = a->tv_nsec + 1000000000L - b->tv_nsec;
r->tv_nsec = a->tv_nsec + NSEC_PER_SEC - b->tv_nsec;
r->tv_sec--;
} else {
r->tv_nsec = a->tv_nsec - b->tv_nsec ;
@ -354,7 +355,7 @@ static void process_interval(void)
diff_timespec(&rs, &ts, &ref_time);
if (STAT_RECORD) {
if (WRITE_STAT_ROUND_EVENT(rs.tv_sec * NSECS_PER_SEC + rs.tv_nsec, INTERVAL))
if (WRITE_STAT_ROUND_EVENT(rs.tv_sec * NSEC_PER_SEC + rs.tv_nsec, INTERVAL))
pr_err("failed to write stat round event\n");
}
@ -364,7 +365,7 @@ static void process_interval(void)
static void enable_counters(void)
{
if (initial_delay)
usleep(initial_delay * 1000);
usleep(initial_delay * USEC_PER_MSEC);
/*
* We need to enable counters only if:
@ -541,8 +542,8 @@ static int __run_perf_stat(int argc, const char **argv)
bool is_pipe = STAT_RECORD ? perf_stat.file.is_pipe : false;
if (interval) {
ts.tv_sec = interval / 1000;
ts.tv_nsec = (interval % 1000) * 1000000;
ts.tv_sec = interval / USEC_PER_MSEC;
ts.tv_nsec = (interval % USEC_PER_MSEC) * NSEC_PER_MSEC;
} else {
ts.tv_sec = 1;
ts.tv_nsec = 0;
@ -971,7 +972,7 @@ static void print_metric_header(void *ctx, const char *color __maybe_unused,
static void nsec_printout(int id, int nr, struct perf_evsel *evsel, double avg)
{
FILE *output = stat_config.output;
double msecs = avg / 1e6;
double msecs = avg / NSEC_PER_MSEC;
const char *fmt_v, *fmt_n;
char name[25];
@ -1460,7 +1461,7 @@ static void print_footer(void)
if (!null_run)
fprintf(output, "\n");
fprintf(output, " %17.9f seconds time elapsed",
avg_stats(&walltime_nsecs_stats)/1e9);
avg_stats(&walltime_nsecs_stats) / NSEC_PER_SEC);
if (run_count > 1) {
fprintf(output, " ");
print_noise_pct(stddev_stats(&walltime_nsecs_stats),
@ -2175,8 +2176,8 @@ static int process_stat_round_event(struct perf_tool *tool __maybe_unused,
update_stats(&walltime_nsecs_stats, stat_round->time);
if (stat_config.interval && stat_round->time) {
tsh.tv_sec = stat_round->time / NSECS_PER_SEC;
tsh.tv_nsec = stat_round->time % NSECS_PER_SEC;
tsh.tv_sec = stat_round->time / NSEC_PER_SEC;
tsh.tv_nsec = stat_round->time % NSEC_PER_SEC;
ts = &tsh;
}

View File

@ -24,6 +24,7 @@
#include "util/evlist.h"
#include "util/evsel.h"
#include <linux/rbtree.h>
#include <linux/time64.h>
#include "util/symbol.h"
#include "util/callchain.h"
#include "util/strlist.h"
@ -1288,9 +1289,9 @@ static void draw_process_bars(struct timechart *tchart)
if (c->comm) {
char comm[256];
if (c->total_time > 5000000000) /* 5 seconds */
sprintf(comm, "%s:%i (%2.2fs)", c->comm, p->pid, c->total_time / 1000000000.0);
sprintf(comm, "%s:%i (%2.2fs)", c->comm, p->pid, c->total_time / (double)NSEC_PER_SEC);
else
sprintf(comm, "%s:%i (%3.1fms)", c->comm, p->pid, c->total_time / 1000000.0);
sprintf(comm, "%s:%i (%3.1fms)", c->comm, p->pid, c->total_time / (double)NSEC_PER_MSEC);
svg_text(Y, c->start_time, comm);
}
@ -1637,7 +1638,7 @@ static int __cmd_timechart(struct timechart *tchart, const char *output_name)
write_svg_file(tchart, output_name);
pr_info("Written %2.1f seconds of trace to %s.\n",
(tchart->last_time - tchart->first_time) / 1000000000.0, output_name);
(tchart->last_time - tchart->first_time) / (double)NSEC_PER_SEC, output_name);
out_delete:
perf_session__delete(session);
return ret;
@ -1901,10 +1902,10 @@ parse_time(const struct option *opt, const char *arg, int __maybe_unused unset)
if (sscanf(arg, "%" PRIu64 "%cs", value, &unit) > 0) {
switch (unit) {
case 'm':
*value *= 1000000;
*value *= NSEC_PER_MSEC;
break;
case 'u':
*value *= 1000;
*value *= NSEC_PER_USEC;
break;
case 'n':
break;
@ -1928,7 +1929,7 @@ int cmd_timechart(int argc, const char **argv,
.ordered_events = true,
},
.proc_num = 15,
.min_time = 1000000,
.min_time = NSEC_PER_MSEC,
.merge_dist = 1000,
};
const char *output_name = "output.svg";

View File

@ -68,6 +68,7 @@
#include <sys/mman.h>
#include <linux/stringify.h>
#include <linux/time64.h>
#include <linux/types.h>
static volatile int done;
@ -624,7 +625,7 @@ static void *display_thread(void *arg)
display_setup_sig();
pthread__unblock_sigwinch();
repeat:
delay_msecs = top->delay_secs * 1000;
delay_msecs = top->delay_secs * MSEC_PER_SEC;
set_term_quiet_input(&save);
/* trash return*/
getc(stdin);

View File

@ -45,6 +45,7 @@
#include <linux/audit.h>
#include <linux/random.h>
#include <linux/stringify.h>
#include <linux/time64.h>
#ifndef O_CLOEXEC
# define O_CLOEXEC 02000000

View File

@ -14,13 +14,6 @@ void test_attr__open(struct perf_event_attr *attr, pid_t pid, int cpu,
#define HAVE_ATTR_TEST
#include "perf-sys.h"
#ifndef NSEC_PER_SEC
# define NSEC_PER_SEC 1000000000ULL
#endif
#ifndef NSEC_PER_USEC
# define NSEC_PER_USEC 1000ULL
#endif
static inline unsigned long long rdclock(void)
{
struct timespec ts;

View File

@ -97,7 +97,7 @@ int test__backward_ring_buffer(int subtest __maybe_unused)
evlist = perf_evlist__new();
if (!evlist) {
pr_debug("No ehough memory to create evlist\n");
pr_debug("No enough memory to create evlist\n");
return TEST_FAIL;
}

View File

@ -125,7 +125,7 @@ static int do_test(struct bpf_object *obj, int (*func)(void),
/* Instead of perf_evlist__new_default, don't add default events */
evlist = perf_evlist__new();
if (!evlist) {
pr_debug("No ehough memory to create evlist\n");
pr_debug("No enough memory to create evlist\n");
return TEST_FAIL;
}

View File

@ -69,8 +69,11 @@ static u32 hist_browser__nr_entries(struct hist_browser *hb)
static void hist_browser__update_rows(struct hist_browser *hb)
{
struct ui_browser *browser = &hb->b;
u16 header_offset = hb->show_headers ? 1 : 0, index_row;
struct hists *hists = hb->hists;
struct perf_hpp_list *hpp_list = hists->hpp_list;
u16 header_offset, index_row;
header_offset = hb->show_headers ? hpp_list->nr_header_lines : 0;
browser->rows = browser->height - header_offset;
/*
* Verify if we were at the last line and that line isn't
@ -99,8 +102,11 @@ static void hist_browser__refresh_dimensions(struct ui_browser *browser)
static void hist_browser__gotorc(struct hist_browser *browser, int row, int column)
{
u16 header_offset = browser->show_headers ? 1 : 0;
struct hists *hists = browser->hists;
struct perf_hpp_list *hpp_list = hists->hpp_list;
u16 header_offset;
header_offset = browser->show_headers ? hpp_list->nr_header_lines : 0;
ui_browser__gotorc(&browser->b, row + header_offset, column);
}
@ -1496,7 +1502,9 @@ static int advance_hpp_check(struct perf_hpp *hpp, int inc)
return hpp->size <= 0;
}
static int hists_browser__scnprintf_headers(struct hist_browser *browser, char *buf, size_t size)
static int
hists_browser__scnprintf_headers(struct hist_browser *browser, char *buf,
size_t size, int line)
{
struct hists *hists = browser->hists;
struct perf_hpp dummy_hpp = {
@ -1506,6 +1514,7 @@ static int hists_browser__scnprintf_headers(struct hist_browser *browser, char *
struct perf_hpp_fmt *fmt;
size_t ret = 0;
int column = 0;
int span = 0;
if (symbol_conf.use_callchain) {
ret = scnprintf(buf, size, " ");
@ -1517,10 +1526,13 @@ static int hists_browser__scnprintf_headers(struct hist_browser *browser, char *
if (perf_hpp__should_skip(fmt, hists) || column++ < browser->b.horiz_scroll)
continue;
ret = fmt->header(fmt, &dummy_hpp, hists);
ret = fmt->header(fmt, &dummy_hpp, hists, line, &span);
if (advance_hpp_check(&dummy_hpp, ret))
break;
if (span)
continue;
ret = scnprintf(dummy_hpp.buf, dummy_hpp.size, " ");
if (advance_hpp_check(&dummy_hpp, ret))
break;
@ -1554,7 +1566,7 @@ static int hists_browser__scnprintf_hierarchy_headers(struct hist_browser *brows
if (column++ < browser->b.horiz_scroll)
continue;
ret = fmt->header(fmt, &dummy_hpp, hists);
ret = fmt->header(fmt, &dummy_hpp, hists, 0, NULL);
if (advance_hpp_check(&dummy_hpp, ret))
break;
@ -1591,7 +1603,7 @@ static int hists_browser__scnprintf_hierarchy_headers(struct hist_browser *brows
}
first_col = false;
ret = fmt->header(fmt, &dummy_hpp, hists);
ret = fmt->header(fmt, &dummy_hpp, hists, 0, NULL);
dummy_hpp.buf[ret] = '\0';
start = trim(dummy_hpp.buf);
@ -1622,14 +1634,21 @@ static void hists_browser__hierarchy_headers(struct hist_browser *browser)
static void hists_browser__headers(struct hist_browser *browser)
{
char headers[1024];
struct hists *hists = browser->hists;
struct perf_hpp_list *hpp_list = hists->hpp_list;
hists_browser__scnprintf_headers(browser, headers,
sizeof(headers));
int line;
ui_browser__gotorc(&browser->b, 0, 0);
ui_browser__set_color(&browser->b, HE_COLORSET_ROOT);
ui_browser__write_nstring(&browser->b, headers, browser->b.width + 1);
for (line = 0; line < hpp_list->nr_header_lines; line++) {
char headers[1024];
hists_browser__scnprintf_headers(browser, headers,
sizeof(headers), line);
ui_browser__gotorc(&browser->b, line, 0);
ui_browser__set_color(&browser->b, HE_COLORSET_ROOT);
ui_browser__write_nstring(&browser->b, headers, browser->b.width + 1);
}
}
static void hist_browser__show_headers(struct hist_browser *browser)
@ -1656,10 +1675,13 @@ static unsigned int hist_browser__refresh(struct ui_browser *browser)
u16 header_offset = 0;
struct rb_node *nd;
struct hist_browser *hb = container_of(browser, struct hist_browser, b);
struct hists *hists = hb->hists;
if (hb->show_headers) {
struct perf_hpp_list *hpp_list = hists->hpp_list;
hist_browser__show_headers(hb);
header_offset = 1;
header_offset = hpp_list->nr_header_lines;
}
ui_browser__hists_init_top(browser);
@ -2418,8 +2440,6 @@ do_zoom_dso(struct hist_browser *browser, struct popup_action *act)
browser->hists->dso_filter = NULL;
ui_helpline__pop();
} else {
if (map == NULL)
return 0;
ui_helpline__fpush("To zoom out press ESC or ENTER + \"Zoom out of %s DSO\"",
__map__is_kernel(map) ? "the Kernel" : map->dso->short_name);
browser->hists->dso_filter = map->dso;

View File

@ -549,7 +549,7 @@ static void perf_gtk__show_hierarchy(GtkWidget *window, struct hists *hists,
strcat(buf, "+");
first_col = false;
fmt->header(fmt, &hpp, hists);
fmt->header(fmt, &hpp, hists, 0, NULL);
strcat(buf, ltrim(rtrim(hpp.buf)));
}
}

View File

@ -230,7 +230,8 @@ static int hpp__width_fn(struct perf_hpp_fmt *fmt,
}
static int hpp__header_fn(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists)
struct hists *hists, int line __maybe_unused,
int *span __maybe_unused)
{
int len = hpp__width_fn(fmt, hpp, hists);
return scnprintf(hpp->buf, hpp->size, "%*s", len, fmt->name);
@ -441,6 +442,7 @@ struct perf_hpp_fmt perf_hpp__format[] = {
struct perf_hpp_list perf_hpp_list = {
.fields = LIST_HEAD_INIT(perf_hpp_list.fields),
.sorts = LIST_HEAD_INIT(perf_hpp_list.sorts),
.nr_header_lines = 1,
};
#undef HPP__COLOR_PRINT_FNS

View File

@ -549,7 +549,7 @@ static int print_hierarchy_header(struct hists *hists, struct perf_hpp *hpp,
struct perf_hpp_list_node, list);
perf_hpp_list__for_each_format(&fmt_node->hpp, fmt) {
fmt->header(fmt, hpp, hists);
fmt->header(fmt, hpp, hists, 0, NULL);
fprintf(fp, "%s%s", hpp->buf, sep ?: " ");
}
@ -569,7 +569,7 @@ static int print_hierarchy_header(struct hists *hists, struct perf_hpp *hpp,
header_width += fprintf(fp, "+");
first_col = false;
fmt->header(fmt, hpp, hists);
fmt->header(fmt, hpp, hists, 0, NULL);
header_width += fprintf(fp, "%s", trim(hpp->buf));
}
@ -639,33 +639,52 @@ hists__fprintf_hierarchy_headers(struct hists *hists,
return print_hierarchy_header(hists, hpp, symbol_conf.field_sep, fp);
}
static int
hists__fprintf_standard_headers(struct hists *hists,
struct perf_hpp *hpp,
FILE *fp)
static void fprintf_line(struct hists *hists, struct perf_hpp *hpp,
int line, FILE *fp)
{
struct perf_hpp_fmt *fmt;
unsigned int width;
const char *sep = symbol_conf.field_sep;
bool first = true;
int span = 0;
hists__for_each_format(hists, fmt) {
if (perf_hpp__should_skip(fmt, hists))
continue;
if (!first)
if (!first && !span)
fprintf(fp, "%s", sep ?: " ");
else
first = false;
fmt->header(fmt, hpp, hists);
fprintf(fp, "%s", hpp->buf);
fmt->header(fmt, hpp, hists, line, &span);
if (!span)
fprintf(fp, "%s", hpp->buf);
}
}
static int
hists__fprintf_standard_headers(struct hists *hists,
struct perf_hpp *hpp,
FILE *fp)
{
struct perf_hpp_list *hpp_list = hists->hpp_list;
struct perf_hpp_fmt *fmt;
unsigned int width;
const char *sep = symbol_conf.field_sep;
bool first = true;
int line;
for (line = 0; line < hpp_list->nr_header_lines; line++) {
/* first # is displayed one level up */
if (line)
fprintf(fp, "# ");
fprintf_line(hists, hpp, line, fp);
fprintf(fp, "\n");
}
fprintf(fp, "\n");
if (sep)
return 1;
return hpp_list->nr_header_lines;
first = true;
@ -689,7 +708,7 @@ hists__fprintf_standard_headers(struct hists *hists,
fprintf(fp, "\n");
fprintf(fp, "#\n");
return 3;
return hpp_list->nr_header_lines + 2;
}
static int hists__fprintf_headers(struct hists *hists, FILE *fp)

View File

@ -1162,14 +1162,46 @@ int symbol__strerror_disassemble(struct symbol *sym __maybe_unused, struct map *
return 0;
}
static int dso__disassemble_filename(struct dso *dso, char *filename, size_t filename_size)
{
char linkname[PATH_MAX];
char *build_id_filename;
if (dso->symtab_type == DSO_BINARY_TYPE__KALLSYMS &&
!dso__is_kcore(dso))
return SYMBOL_ANNOTATE_ERRNO__NO_VMLINUX;
build_id_filename = dso__build_id_filename(dso, NULL, 0);
if (build_id_filename) {
__symbol__join_symfs(filename, filename_size, build_id_filename);
free(build_id_filename);
} else {
if (dso->has_build_id)
return ENOMEM;
goto fallback;
}
if (dso__is_kcore(dso) ||
readlink(filename, linkname, sizeof(linkname)) < 0 ||
strstr(linkname, DSO__NAME_KALLSYMS) ||
access(filename, R_OK)) {
fallback:
/*
* If we don't have build-ids or the build-id file isn't in the
* cache, or is just a kallsyms file, well, lets hope that this
* DSO is the same as when 'perf record' ran.
*/
__symbol__join_symfs(filename, filename_size, dso->long_name);
}
return 0;
}
int symbol__disassemble(struct symbol *sym, struct map *map, size_t privsize)
{
struct dso *dso = map->dso;
char *filename = dso__build_id_filename(dso, NULL, 0);
bool free_filename = true;
char command[PATH_MAX * 2];
FILE *file;
int err = 0;
char symfs_filename[PATH_MAX];
struct kcore_extract kce;
bool delete_extract = false;
@ -1177,38 +1209,13 @@ int symbol__disassemble(struct symbol *sym, struct map *map, size_t privsize)
int lineno = 0;
int nline;
pid_t pid;
int err = dso__disassemble_filename(dso, symfs_filename, sizeof(symfs_filename));
if (filename)
symbol__join_symfs(symfs_filename, filename);
if (filename == NULL) {
if (dso->has_build_id)
return ENOMEM;
goto fallback;
} else if (dso__is_kcore(dso) ||
readlink(symfs_filename, command, sizeof(command)) < 0 ||
strstr(command, DSO__NAME_KALLSYMS) ||
access(symfs_filename, R_OK)) {
free(filename);
fallback:
/*
* If we don't have build-ids or the build-id file isn't in the
* cache, or is just a kallsyms file, well, lets hope that this
* DSO is the same as when 'perf record' ran.
*/
filename = (char *)dso->long_name;
symbol__join_symfs(symfs_filename, filename);
free_filename = false;
}
if (dso->symtab_type == DSO_BINARY_TYPE__KALLSYMS &&
!dso__is_kcore(dso)) {
err = SYMBOL_ANNOTATE_ERRNO__NO_VMLINUX;
goto out_free_filename;
}
if (err)
return err;
pr_debug("%s: filename=%s, sym=%s, start=%#" PRIx64 ", end=%#" PRIx64 "\n", __func__,
filename, sym->name, map->unmap_ip(map, sym->start),
symfs_filename, sym->name, map->unmap_ip(map, sym->start),
map->unmap_ip(map, sym->end));
pr_debug("annotating [%p] %30s : [%p] %30s\n",
@ -1223,11 +1230,6 @@ fallback:
delete_extract = true;
strlcpy(symfs_filename, kce.extract_filename,
sizeof(symfs_filename));
if (free_filename) {
free(filename);
free_filename = false;
}
filename = symfs_filename;
}
} else if (dso__needs_decompress(dso)) {
char tmp[PATH_MAX];
@ -1236,14 +1238,14 @@ fallback:
bool ret;
if (kmod_path__parse_ext(&m, symfs_filename))
goto out_free_filename;
goto out;
snprintf(tmp, PATH_MAX, "/tmp/perf-kmod-XXXXXX");
fd = mkstemp(tmp);
if (fd < 0) {
free(m.ext);
goto out_free_filename;
goto out;
}
ret = decompress_to_file(m.ext, symfs_filename, fd);
@ -1255,7 +1257,7 @@ fallback:
close(fd);
if (!ret)
goto out_free_filename;
goto out;
strcpy(symfs_filename, tmp);
}
@ -1271,7 +1273,7 @@ fallback:
map__rip_2objdump(map, sym->end),
symbol_conf.annotate_asm_raw ? "" : "--no-show-raw",
symbol_conf.annotate_src ? "-S" : "",
symfs_filename, filename);
symfs_filename, symfs_filename);
pr_debug("Executing: %s\n", command);
@ -1333,11 +1335,10 @@ out_remove_tmp:
if (dso__needs_decompress(dso))
unlink(symfs_filename);
out_free_filename:
if (delete_extract)
kcore_extract__delete(&kce);
if (free_filename)
free(filename);
out:
return err;
out_close_stdout:

View File

@ -531,7 +531,7 @@ static int map_prologue(struct perf_probe_event *pev, int *mapping,
ptevs = malloc(array_sz);
if (!ptevs) {
pr_debug("No ehough memory: alloc ptevs failed\n");
pr_debug("No enough memory: alloc ptevs failed\n");
return -ENOMEM;
}

View File

@ -6,6 +6,7 @@
#include <stdarg.h>
#include <stdio.h>
#include <api/debug.h>
#include <linux/time64.h>
#include "cache.h"
#include "color.h"
@ -14,9 +15,6 @@
#include "util.h"
#include "target.h"
#define NSECS_PER_SEC 1000000000ULL
#define NSECS_PER_USEC 1000ULL
int verbose;
bool dump_trace = false, quiet = false;
int debug_ordered_events;
@ -54,9 +52,9 @@ static int veprintf_time(u64 t, const char *fmt, va_list args)
int ret = 0;
u64 secs, usecs, nsecs = t;
secs = nsecs / NSECS_PER_SEC;
nsecs -= secs * NSECS_PER_SEC;
usecs = nsecs / NSECS_PER_USEC;
secs = nsecs / NSEC_PER_SEC;
nsecs -= secs * NSEC_PER_SEC;
usecs = nsecs / NSEC_PER_USEC;
ret = fprintf(stderr, "[%13" PRIu64 ".%06" PRIu64 "] ",
secs, usecs);

View File

@ -507,17 +507,17 @@ static int __perf_evsel__hw_cache_name(u64 config, char *bf, size_t size)
u8 op, result, type = (config >> 0) & 0xff;
const char *err = "unknown-ext-hardware-cache-type";
if (type > PERF_COUNT_HW_CACHE_MAX)
if (type >= PERF_COUNT_HW_CACHE_MAX)
goto out_err;
op = (config >> 8) & 0xff;
err = "unknown-ext-hardware-cache-op";
if (op > PERF_COUNT_HW_CACHE_OP_MAX)
if (op >= PERF_COUNT_HW_CACHE_OP_MAX)
goto out_err;
result = (config >> 16) & 0xff;
err = "unknown-ext-hardware-cache-result";
if (result > PERF_COUNT_HW_CACHE_RESULT_MAX)
if (result >= PERF_COUNT_HW_CACHE_RESULT_MAX)
goto out_err;
err = "invalid-cache";

View File

@ -828,8 +828,7 @@ static int write_group_desc(int fd, struct perf_header *h __maybe_unused,
* default get_cpuid(): nothing gets recorded
* actual implementation must be in arch/$(ARCH)/util/header.c
*/
int __attribute__ ((weak)) get_cpuid(char *buffer __maybe_unused,
size_t sz __maybe_unused)
int __weak get_cpuid(char *buffer __maybe_unused, size_t sz __maybe_unused)
{
return -1;
}

View File

@ -230,7 +230,7 @@ struct perf_hpp {
struct perf_hpp_fmt {
const char *name;
int (*header)(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists);
struct hists *hists, int line, int *span);
int (*width)(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists);
int (*color)(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
@ -259,6 +259,7 @@ struct perf_hpp_list {
struct list_head fields;
struct list_head sorts;
int nr_header_lines;
int need_collapse;
int parent;
int sym;

View File

@ -877,3 +877,60 @@ int probe_cache__show_all_caches(struct strfilter *filter)
return 0;
}
static struct {
const char *pattern;
bool avail;
bool checked;
} probe_type_table[] = {
#define DEFINE_TYPE(idx, pat, def_avail) \
[idx] = {.pattern = pat, .avail = (def_avail)}
DEFINE_TYPE(PROBE_TYPE_U, "* u8/16/32/64,*", true),
DEFINE_TYPE(PROBE_TYPE_S, "* s8/16/32/64,*", true),
DEFINE_TYPE(PROBE_TYPE_X, "* x8/16/32/64,*", false),
DEFINE_TYPE(PROBE_TYPE_STRING, "* string,*", true),
DEFINE_TYPE(PROBE_TYPE_BITFIELD,
"* b<bit-width>@<bit-offset>/<container-size>", true),
};
bool probe_type_is_available(enum probe_type type)
{
FILE *fp;
char *buf = NULL;
size_t len = 0;
bool target_line = false;
bool ret = probe_type_table[type].avail;
if (type >= PROBE_TYPE_END)
return false;
/* We don't have to check the type which supported by default */
if (ret || probe_type_table[type].checked)
return ret;
if (asprintf(&buf, "%s/README", tracing_path) < 0)
return ret;
fp = fopen(buf, "r");
if (!fp)
goto end;
zfree(&buf);
while (getline(&buf, &len, fp) > 0 && !ret) {
if (!target_line) {
target_line = !!strstr(buf, " type: ");
if (!target_line)
continue;
} else if (strstr(buf, "\t ") != buf)
break;
ret = strglobmatch(buf, probe_type_table[type].pattern);
}
/* Cache the result */
probe_type_table[type].checked = true;
probe_type_table[type].avail = ret;
fclose(fp);
end:
free(buf);
return ret;
}

View File

@ -19,6 +19,15 @@ struct probe_cache {
struct list_head entries;
};
enum probe_type {
PROBE_TYPE_U = 0,
PROBE_TYPE_S,
PROBE_TYPE_X,
PROBE_TYPE_STRING,
PROBE_TYPE_BITFIELD,
PROBE_TYPE_END,
};
#define PF_FL_UPROBE 1
#define PF_FL_RW 2
#define for_each_probe_cache_entry(entry, pcache) \
@ -54,6 +63,7 @@ struct probe_cache_entry *probe_cache__find(struct probe_cache *pcache,
struct probe_cache_entry *probe_cache__find_by_name(struct probe_cache *pcache,
const char *group, const char *event);
int probe_cache__show_all_caches(struct strfilter *filter);
bool probe_type_is_available(enum probe_type type);
#else /* ! HAVE_LIBELF_SUPPORT */
static inline struct probe_cache *probe_cache__new(const char *tgt __maybe_unused)
{

View File

@ -39,6 +39,7 @@
#include "util.h"
#include "symbol.h"
#include "probe-finder.h"
#include "probe-file.h"
/* Kprobe tracer basic type is up to u64 */
#define MAX_BASIC_TYPE_BITS 64
@ -297,13 +298,13 @@ static int convert_variable_type(Dwarf_Die *vr_die,
char sbuf[STRERR_BUFSIZE];
int bsize, boffs, total;
int ret;
char sign;
char prefix;
/* TODO: check all types */
if (cast && strcmp(cast, "string") != 0 &&
if (cast && strcmp(cast, "string") != 0 && strcmp(cast, "x") != 0 &&
strcmp(cast, "s") != 0 && strcmp(cast, "u") != 0) {
/* Non string type is OK */
/* and respect signedness cast */
/* and respect signedness/hexadecimal cast */
tvar->type = strdup(cast);
return (tvar->type == NULL) ? -ENOMEM : 0;
}
@ -365,11 +366,15 @@ static int convert_variable_type(Dwarf_Die *vr_die,
}
if (cast && (strcmp(cast, "u") == 0))
sign = 'u';
prefix = 'u';
else if (cast && (strcmp(cast, "s") == 0))
sign = 's';
prefix = 's';
else if (cast && (strcmp(cast, "x") == 0) &&
probe_type_is_available(PROBE_TYPE_X))
prefix = 'x';
else
sign = die_is_signed_type(&type) ? 's' : 'u';
prefix = die_is_signed_type(&type) ? 's' :
probe_type_is_available(PROBE_TYPE_X) ? 'x' : 'u';
ret = dwarf_bytesize(&type);
if (ret <= 0)
@ -383,7 +388,7 @@ static int convert_variable_type(Dwarf_Die *vr_die,
dwarf_diename(&type), MAX_BASIC_TYPE_BITS);
ret = MAX_BASIC_TYPE_BITS;
}
ret = snprintf(buf, 16, "%c%d", sign, ret);
ret = snprintf(buf, 16, "%c%d", prefix, ret);
formatted:
if (ret < 0 || ret >= 16) {

View File

@ -25,6 +25,7 @@
#include <ctype.h>
#include <errno.h>
#include <linux/bitmap.h>
#include <linux/time64.h>
#include "../util.h"
#include <EXTERN.h>
@ -359,8 +360,8 @@ static void perl_process_tracepoint(struct perf_sample *sample,
if (!test_and_set_bit(event->id, events_defined))
define_event_symbols(event, handler, event->print_fmt.args);
s = nsecs / NSECS_PER_SEC;
ns = nsecs - s * NSECS_PER_SEC;
s = nsecs / NSEC_PER_SEC;
ns = nsecs - s * NSEC_PER_SEC;
scripting_context->event_data = data;
scripting_context->pevent = evsel->tp_format->pevent;

View File

@ -27,6 +27,7 @@
#include <stdbool.h>
#include <errno.h>
#include <linux/bitmap.h>
#include <linux/time64.h>
#include "../../perf.h"
#include "../debug.h"
@ -426,8 +427,8 @@ static void python_process_tracepoint(struct perf_sample *sample,
if (!dict)
Py_FatalError("couldn't create Python dict");
}
s = nsecs / NSECS_PER_SEC;
ns = nsecs - s * NSECS_PER_SEC;
s = nsecs / NSEC_PER_SEC;
ns = nsecs - s * NSEC_PER_SEC;
scripting_context->event_data = data;
scripting_context->pevent = evsel->tp_format->pevent;

View File

@ -11,7 +11,7 @@
regex_t parent_regex;
const char default_parent_pattern[] = "^sys_|^do_page_fault";
const char *parent_pattern = default_parent_pattern;
const char default_sort_order[] = "comm,dso,symbol";
const char *default_sort_order = "comm,dso,symbol";
const char default_branch_sort_order[] = "comm,dso_from,symbol_from,symbol_to,cycles";
const char default_mem_sort_order[] = "local_weight,mem,sym,dso,symbol_daddr,dso_daddr,snoop,tlb,locked";
const char default_top_sort_order[] = "dso,symbol";
@ -1492,7 +1492,8 @@ void perf_hpp__reset_sort_width(struct perf_hpp_fmt *fmt, struct hists *hists)
}
static int __sort__hpp_header(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists)
struct hists *hists, int line __maybe_unused,
int *span __maybe_unused)
{
struct hpp_sort_entry *hse;
size_t len = fmt->user_len;
@ -1797,7 +1798,9 @@ static void update_dynamic_len(struct hpp_dynamic_entry *hde,
}
static int __sort__hde_header(struct perf_hpp_fmt *fmt, struct perf_hpp *hpp,
struct hists *hists __maybe_unused)
struct hists *hists __maybe_unused,
int line __maybe_unused,
int *span __maybe_unused)
{
struct hpp_dynamic_entry *hde;
size_t len = fmt->user_len;

View File

@ -28,7 +28,7 @@ extern const char *sort_order;
extern const char *field_order;
extern const char default_parent_pattern[];
extern const char *parent_pattern;
extern const char default_sort_order[];
extern const char *default_sort_order;
extern regex_t ignore_callees_regex;
extern int have_ignore_callees;
extern enum sort_mode sort__mode;

View File

@ -18,6 +18,7 @@
#include <unistd.h>
#include <string.h>
#include <linux/bitmap.h>
#include <linux/time64.h>
#include "perf.h"
#include "svghelper.h"
@ -274,14 +275,14 @@ static char *time_to_string(u64 duration)
text[0] = 0;
if (duration < 1000) /* less than 1 usec */
if (duration < NSEC_PER_USEC) /* less than 1 usec */
return text;
if (duration < 1000 * 1000) { /* less than 1 msec */
sprintf(text, "%.1f us", duration / 1000.0);
if (duration < NSEC_PER_MSEC) { /* less than 1 msec */
sprintf(text, "%.1f us", duration / (double)NSEC_PER_USEC);
return text;
}
sprintf(text, "%.1f ms", duration / 1000.0 / 1000);
sprintf(text, "%.1f ms", duration / (double)NSEC_PER_MSEC);
return text;
}
@ -297,7 +298,7 @@ void svg_waiting(int Yslot, int cpu, u64 start, u64 end, const char *backtrace)
style = "waiting";
if (end-start > 10 * 1000000) /* 10 msec */
if (end-start > 10 * NSEC_PER_MSEC) /* 10 msec */
style = "WAITING";
text = time_to_string(end-start);

View File

@ -66,7 +66,7 @@ static int entry(u64 ip, struct unwind_info *ui)
if (__report_module(&al, ip, ui))
return -1;
e->ip = ip;
e->ip = al.addr;
e->map = al.map;
e->sym = al.sym;

View File

@ -542,7 +542,7 @@ static int entry(u64 ip, struct thread *thread,
thread__find_addr_location(thread, PERF_RECORD_MISC_USER,
MAP__FUNCTION, ip, &al);
e.ip = ip;
e.ip = al.addr;
e.map = al.map;
e.sym = al.sym;

View File

@ -15,6 +15,7 @@
#include <byteswap.h>
#include <linux/kernel.h>
#include <linux/log2.h>
#include <linux/time64.h>
#include <unistd.h>
#include "callchain.h"
#include "strlist.h"

View File

@ -179,10 +179,6 @@ static inline void *zalloc(size_t size)
#undef tolower
#undef toupper
#ifndef NSEC_PER_MSEC
#define NSEC_PER_MSEC 1000000L
#endif
int parse_nsec_time(const char *str, u64 *ptime);
extern unsigned char sane_ctype[256];