1 //===-- TaskTimer.h ---------------------------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef LLDB_SOURCE_PLUGINS_TRACE_INTEL_PT_TASKTIMER_H
10 #define LLDB_SOURCE_PLUGINS_TRACE_INTEL_PT_TASKTIMER_H
11 
12 #include "lldb/lldb-types.h"
13 
14 #include "llvm/ADT/DenseMap.h"
15 #include "llvm/ADT/StringRef.h"
16 
17 #include <chrono>
18 #include <functional>
19 #include <unordered_map>
20 
21 namespace lldb_private {
22 namespace trace_intel_pt {
23 
24 /// Class used to track the duration of long running tasks related to a single
25 /// scope for reporting.
26 class ScopedTaskTimer {
27 public:
28   /// Execute the given \p task and record its duration.
29   ///
30   /// \param[in] name
31   ///     The name used to identify this task for reporting.
32   ///
33   /// \param[in] task
34   ///     The task function.
35   ///
36   /// \return
37   ///     The return value of the task.
38   template <typename C> auto TimeTask(llvm::StringRef name, C task) {
39     auto start = std::chrono::steady_clock::now();
40     auto result = task();
41     auto end = std::chrono::steady_clock::now();
42     std::chrono::milliseconds duration =
43         std::chrono::duration_cast<std::chrono::milliseconds>(end - start);
44     m_timed_tasks.insert({name.str(), duration});
45     return result;
46   }
47 
48   /// Executive the given \p callback on each recorded task.
49   ///
50   /// \param[in] callback
51   ///     The first parameter of the callback is the name of the recorded task,
52   ///     and the second parameter is the duration of that task.
53   void ForEachTimedTask(std::function<void(const std::string &name,
54                                            std::chrono::milliseconds duration)>
55                             callback);
56 
57 private:
58   std::unordered_map<std::string, std::chrono::milliseconds> m_timed_tasks;
59 };
60 
61 /// Class used to track the duration of long running tasks for reporting.
62 class TaskTimer {
63 public:
64   /// \return
65   ///     The timer object for the given thread.
66   ScopedTaskTimer &ForThread(lldb::tid_t tid);
67 
68   /// \return
69   ///     The timer object for global tasks.
70   ScopedTaskTimer &ForGlobal();
71 
72 private:
73   llvm::DenseMap<lldb::tid_t, ScopedTaskTimer> m_thread_timers;
74   ScopedTaskTimer m_global_timer;
75 };
76 
77 } // namespace trace_intel_pt
78 } // namespace lldb_private
79 
80 #endif // LLDB_SOURCE_PLUGINS_TRACE_INTEL_PT_TASKTIMER_H
81