1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef FLUTTER_FLOW_FRAME_TIMINGS_H_
6#define FLUTTER_FLOW_FRAME_TIMINGS_H_
7
8#include <mutex>
9
10#include "flutter/common/settings.h"
11#include "flutter/flow/raster_cache.h"
12#include "flutter/fml/macros.h"
13#include "flutter/fml/status.h"
14#include "flutter/fml/time/time_delta.h"
15#include "flutter/fml/time/time_point.h"
16
17#define TRACE_EVENT_WITH_FRAME_NUMBER(recorder, category_group, name, \
18 flow_id_count, flow_ids) \
19 TRACE_EVENT1_WITH_FLOW_IDS(category_group, name, flow_id_count, flow_ids, \
20 "frame_number", \
21 recorder->GetFrameNumberTraceArg())
22
23namespace flutter {
24
25/// Records timestamps for various phases of a frame rendering process.
26///
27/// Recorder is created on vsync and destroyed after the rasterization of the
28/// frame. This class is thread safe and doesn't require additional
29/// synchronization.
30class FrameTimingsRecorder {
31 public:
32 /// Various states that the recorder can be in. When created the recorder is
33 /// in an unitialized state and transtions in sequential order of the states.
34 enum class State : uint32_t {
35 kUninitialized,
36 kVsync,
37 kBuildStart,
38 kBuildEnd,
39 kRasterStart,
40 kRasterEnd,
41 };
42
43 /// Default constructor, initializes the recorder with State::kUninitialized.
44 FrameTimingsRecorder();
45
46 /// Constructor with a pre-populated frame number.
47 explicit FrameTimingsRecorder(uint64_t frame_number);
48
49 ~FrameTimingsRecorder();
50
51 /// Timestamp of the vsync signal.
52 fml::TimePoint GetVsyncStartTime() const;
53
54 /// Timestamp of when the frame was targeted to be presented.
55 ///
56 /// This is typically the next vsync signal timestamp.
57 fml::TimePoint GetVsyncTargetTime() const;
58
59 /// Timestamp of when the frame building started.
60 fml::TimePoint GetBuildStartTime() const;
61
62 /// Timestamp of when the frame was finished building.
63 fml::TimePoint GetBuildEndTime() const;
64
65 /// Timestamp of when the frame rasterization started.
66 fml::TimePoint GetRasterStartTime() const;
67
68 /// Timestamp of when the frame rasterization finished.
69 fml::TimePoint GetRasterEndTime() const;
70
71 /// Timestamp of when the frame rasterization is complete in wall-time.
72 fml::TimePoint GetRasterEndWallTime() const;
73
74 /// Duration of the frame build time.
75 fml::TimeDelta GetBuildDuration() const;
76
77 /// Count of the layer cache entries
78 size_t GetLayerCacheCount() const;
79
80 /// Total Bytes in all layer cache entries
81 size_t GetLayerCacheBytes() const;
82
83 /// Count of the picture cache entries
84 size_t GetPictureCacheCount() const;
85
86 /// Total Bytes in all picture cache entries
87 size_t GetPictureCacheBytes() const;
88
89 /// Records a vsync event.
90 void RecordVsync(fml::TimePoint vsync_start, fml::TimePoint vsync_target);
91
92 /// Records a build start event.
93 void RecordBuildStart(fml::TimePoint build_start);
94
95 /// Records a build end event.
96 void RecordBuildEnd(fml::TimePoint build_end);
97
98 /// Records a raster start event.
99 void RecordRasterStart(fml::TimePoint raster_start);
100
101 /// Clones the recorder until (and including) the specified state.
102 std::unique_ptr<FrameTimingsRecorder> CloneUntil(State state);
103
104 /// Records a raster end event, and builds a `FrameTiming` that summarizes all
105 /// the events. This summary is sent to the framework.
106 FrameTiming RecordRasterEnd(const RasterCache* cache = nullptr);
107
108 /// Returns the frame number. Frame number is unique per frame and a frame
109 /// built earlier will have a frame number less than a frame that has been
110 /// built at a later point of time.
111 uint64_t GetFrameNumber() const;
112
113 /// Returns the frame number in a fml tracing friendly format.
114 const char* GetFrameNumberTraceArg() const;
115
116 /// Returns the recorded time from when `RecordRasterEnd` is called.
117 FrameTiming GetRecordedTime() const;
118
119 private:
120 FML_FRIEND_TEST(FrameTimingsRecorderTest, ThrowWhenRecordBuildBeforeVsync);
121 FML_FRIEND_TEST(FrameTimingsRecorderTest,
122 ThrowWhenRecordRasterBeforeBuildEnd);
123
124 [[nodiscard]] fml::Status RecordVsyncImpl(fml::TimePoint vsync_start,
125 fml::TimePoint vsync_target);
126 [[nodiscard]] fml::Status RecordBuildStartImpl(fml::TimePoint build_start);
127 [[nodiscard]] fml::Status RecordBuildEndImpl(fml::TimePoint build_end);
128 [[nodiscard]] fml::Status RecordRasterStartImpl(fml::TimePoint raster_start);
129
130 static std::atomic<uint64_t> frame_number_gen_;
131
132 mutable std::mutex state_mutex_;
133 State state_ = State::kUninitialized;
134
135 const uint64_t frame_number_;
136 const std::string frame_number_trace_arg_val_;
137
138 fml::TimePoint vsync_start_;
139 fml::TimePoint vsync_target_;
140 fml::TimePoint build_start_;
141 fml::TimePoint build_end_;
142 fml::TimePoint raster_start_;
143 fml::TimePoint raster_end_;
144 fml::TimePoint raster_end_wall_time_;
145
146 size_t layer_cache_count_;
147 size_t layer_cache_bytes_;
148 size_t picture_cache_count_;
149 size_t picture_cache_bytes_;
150
151 // Set when `RecordRasterEnd` is called. Cannot be reset once set.
152 FrameTiming timing_;
153
154 FML_DISALLOW_COPY_ASSIGN_AND_MOVE(FrameTimingsRecorder);
155};
156
157} // namespace flutter
158
159#endif // FLUTTER_FLOW_FRAME_TIMINGS_H_
160

source code of flutter_engine/flutter/flow/frame_timings.h