diff options
-rw-r--r-- | tools/perf/util/tsc.c | 12 | ||||
-rw-r--r-- | tools/perf/util/tsc.h | 5 |
2 files changed, 14 insertions, 3 deletions
diff --git a/tools/perf/util/tsc.c b/tools/perf/util/tsc.c index 9e3f04ddddf8..c0ca40204649 100644 --- a/tools/perf/util/tsc.c +++ b/tools/perf/util/tsc.c @@ -28,6 +28,10 @@ u64 tsc_to_perf_time(u64 cyc, struct perf_tsc_conversion *tc) { u64 quot, rem; + if (tc->cap_user_time_short) + cyc = tc->time_cycles + + ((cyc - tc->time_cycles) & tc->time_mask); + quot = cyc >> tc->time_shift; rem = cyc & (((u64)1 << tc->time_shift) - 1); return tc->time_zero + quot * tc->time_mult + @@ -37,7 +41,6 @@ u64 tsc_to_perf_time(u64 cyc, struct perf_tsc_conversion *tc) int perf_read_tsc_conversion(const struct perf_event_mmap_page *pc, struct perf_tsc_conversion *tc) { - bool cap_user_time_zero; u32 seq; int i = 0; @@ -47,7 +50,10 @@ int perf_read_tsc_conversion(const struct perf_event_mmap_page *pc, tc->time_mult = pc->time_mult; tc->time_shift = pc->time_shift; tc->time_zero = pc->time_zero; - cap_user_time_zero = pc->cap_user_time_zero; + tc->time_cycles = pc->time_cycles; + tc->time_mask = pc->time_mask; + tc->cap_user_time_zero = pc->cap_user_time_zero; + tc->cap_user_time_short = pc->cap_user_time_short; rmb(); if (pc->lock == seq && !(seq & 1)) break; @@ -57,7 +63,7 @@ int perf_read_tsc_conversion(const struct perf_event_mmap_page *pc, } } - if (!cap_user_time_zero) + if (!tc->cap_user_time_zero) return -EOPNOTSUPP; return 0; diff --git a/tools/perf/util/tsc.h b/tools/perf/util/tsc.h index 3c5a632ee57c..72a15419f3b3 100644 --- a/tools/perf/util/tsc.h +++ b/tools/perf/util/tsc.h @@ -8,6 +8,11 @@ struct perf_tsc_conversion { u16 time_shift; u32 time_mult; u64 time_zero; + u64 time_cycles; + u64 time_mask; + + bool cap_user_time_zero; + bool cap_user_time_short; }; struct perf_event_mmap_page; |