1 /*
2  * Copyright 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ANDROID_GUI_FRAMETIMESTAMPS_H
18 #define ANDROID_GUI_FRAMETIMESTAMPS_H
19 
20 #include <android/gui/FrameEvent.h>
21 
22 #include <gui/CompositorTiming.h>
23 #include <ui/FenceTime.h>
24 #include <utils/Flattenable.h>
25 #include <utils/StrongPointer.h>
26 #include <utils/Timers.h>
27 
28 #include <array>
29 #include <bitset>
30 #include <vector>
31 
32 namespace android {
33 
34 struct FrameEvents;
35 class FrameEventHistoryDelta;
36 
37 using gui::CompositorTiming;
38 using gui::FrameEvent;
39 
40 // A collection of timestamps corresponding to a single frame.
41 struct FrameEvents {
42     static constexpr auto EVENT_COUNT =
43             static_cast<size_t>(FrameEvent::EVENT_COUNT);
44     static_assert(EVENT_COUNT <= 32, "Event count sanity check failed.");
45     static constexpr nsecs_t TIMESTAMP_PENDING = -2;
46 
isValidTimestampFrameEvents47     static inline bool isValidTimestamp(nsecs_t time) {
48         return time != TIMESTAMP_PENDING;
49     }
50 
51     bool hasPostedInfo() const;
52     bool hasRequestedPresentInfo() const;
53     bool hasLatchInfo() const;
54     bool hasFirstRefreshStartInfo() const;
55     bool hasLastRefreshStartInfo() const;
56     bool hasAcquireInfo() const;
57     bool hasGpuCompositionDoneInfo() const;
58     bool hasDisplayPresentInfo() const;
59     bool hasReleaseInfo() const;
60     bool hasDequeueReadyInfo() const;
61 
62     void checkFencesForCompletion();
63     void dump(std::string& outString) const;
64 
65     bool valid{false};
66     int connectId{0};
67     uint64_t frameNumber{0};
68 
69     // Whether or not certain points in the frame's life cycle have been
70     // encountered help us determine if timestamps aren't available because
71     // a) we'll just never get them or b) they're not ready yet.
72     bool addPostCompositeCalled{false};
73     bool addReleaseCalled{false};
74 
75     nsecs_t postedTime{TIMESTAMP_PENDING};
76     nsecs_t requestedPresentTime{TIMESTAMP_PENDING};
77     nsecs_t latchTime{TIMESTAMP_PENDING};
78     nsecs_t firstRefreshStartTime{TIMESTAMP_PENDING};
79     nsecs_t lastRefreshStartTime{TIMESTAMP_PENDING};
80     nsecs_t dequeueReadyTime{TIMESTAMP_PENDING};
81 
82     std::shared_ptr<FenceTime> acquireFence{FenceTime::NO_FENCE};
83     std::shared_ptr<FenceTime> gpuCompositionDoneFence{FenceTime::NO_FENCE};
84     std::shared_ptr<FenceTime> displayPresentFence{FenceTime::NO_FENCE};
85     std::shared_ptr<FenceTime> releaseFence{FenceTime::NO_FENCE};
86 };
87 
88 // A short history of frames that are synchronized between the consumer and
89 // producer via deltas.
90 class FrameEventHistory {
91 public:
92     FrameEventHistory();
93     virtual ~FrameEventHistory();
94 
95     FrameEvents* getFrame(uint64_t frameNumber);
96     FrameEvents* getFrame(uint64_t frameNumber, size_t* iHint);
97     void checkFencesForCompletion();
98     void dump(std::string& outString) const;
99 
100     static const size_t INITIAL_MAX_FRAME_HISTORY;
101 
102 protected:
103     void resize(size_t newSize);
104 
105     std::vector<FrameEvents> mFrames;
106 
107     CompositorTiming mCompositorTiming;
108 };
109 
110 
111 // The producer's interface to FrameEventHistory
112 class ProducerFrameEventHistory : public FrameEventHistory {
113 public:
114     ~ProducerFrameEventHistory() override;
115 
116     // Public for testing.
117     static nsecs_t snapToNextTick(
118             nsecs_t timestamp, nsecs_t tickPhase, nsecs_t tickInterval);
getReportedCompositeDeadline()119     nsecs_t getReportedCompositeDeadline() const { return mCompositorTiming.deadline; };
120 
121     nsecs_t getNextCompositeDeadline(const nsecs_t now) const;
getCompositeInterval()122     nsecs_t getCompositeInterval() const { return mCompositorTiming.interval; }
getCompositeToPresentLatency()123     nsecs_t getCompositeToPresentLatency() const {
124         return mCompositorTiming.presentLatency;
125     }
126 
127     // virtual for testing.
128     virtual void updateAcquireFence(
129             uint64_t frameNumber, std::shared_ptr<FenceTime>&& acquire);
130     void applyDelta(const FrameEventHistoryDelta& delta);
131 
132     void updateSignalTimes();
133 
134 protected:
135     void applyFenceDelta(FenceTimeline* timeline,
136             std::shared_ptr<FenceTime>* dst,
137             const FenceTime::Snapshot& src) const;
138 
139     // virtual for testing.
140     virtual std::shared_ptr<FenceTime> createFenceTime(
141             const sp<Fence>& fence) const;
142 
143     void resize(size_t newSize);
144 
145     size_t mAcquireOffset{0};
146 
147     // The consumer updates it's timelines in Layer and SurfaceFlinger since
148     // they can coordinate shared timelines better. The producer doesn't have
149     // shared timelines though, so just let it own and update all of them.
150     FenceTimeline mAcquireTimeline;
151     FenceTimeline mGpuCompositionDoneTimeline;
152     FenceTimeline mPresentTimeline;
153     FenceTimeline mReleaseTimeline;
154 };
155 
156 
157 // Used by the consumer to create a new frame event record that is
158 // partially complete.
159 struct NewFrameEventsEntry {
160     uint64_t frameNumber{0};
161     nsecs_t postedTime{0};
162     nsecs_t requestedPresentTime{0};
163     std::shared_ptr<FenceTime> acquireFence{FenceTime::NO_FENCE};
164 };
165 
166 // Used by the consumer to keep track of which fields it already sent to
167 // the producer.
168 class FrameEventDirtyFields {
169 public:
reset()170     inline void reset() { mBitset.reset(); }
anyDirty()171     inline bool anyDirty() const { return mBitset.any(); }
172 
173     template <FrameEvent event>
setDirty()174     inline void setDirty() {
175         constexpr size_t eventIndex = static_cast<size_t>(event);
176         static_assert(eventIndex < FrameEvents::EVENT_COUNT, "Bad index.");
177         mBitset.set(eventIndex);
178     }
179 
180     template <FrameEvent event>
isDirty()181     inline bool isDirty() const {
182         constexpr size_t eventIndex = static_cast<size_t>(event);
183         static_assert(eventIndex < FrameEvents::EVENT_COUNT, "Bad index.");
184         return mBitset[eventIndex];
185     }
186 
187 private:
188     std::bitset<FrameEvents::EVENT_COUNT> mBitset;
189 };
190 
191 
192 // The consumer's interface to FrameEventHistory
193 class ConsumerFrameEventHistory : public FrameEventHistory {
194 public:
195     ConsumerFrameEventHistory();
196     ~ConsumerFrameEventHistory() override;
197 
198     void onDisconnect();
199     void setProducerWantsEvents();
200 
201     void initializeCompositorTiming(const CompositorTiming& compositorTiming);
202 
203     void addQueue(const NewFrameEventsEntry& newEntry);
204     void addLatch(uint64_t frameNumber, nsecs_t latchTime);
205     void addPreComposition(uint64_t frameNumber, nsecs_t refreshStartTime);
206     void addPostComposition(uint64_t frameNumber,
207             const std::shared_ptr<FenceTime>& gpuCompositionDone,
208             const std::shared_ptr<FenceTime>& displayPresent,
209             const CompositorTiming& compositorTiming);
210     void addRelease(uint64_t frameNumber, nsecs_t dequeueReadyTime,
211             std::shared_ptr<FenceTime>&& release);
212 
213     void getAndResetDelta(FrameEventHistoryDelta* delta);
214 
215     void resize(size_t newSize);
216 
217 private:
218     void getFrameDelta(FrameEventHistoryDelta* delta,
219                        const std::vector<FrameEvents>::iterator& frame);
220 
221     std::vector<FrameEventDirtyFields> mFramesDirty;
222 
223     size_t mQueueOffset{0};
224     size_t mCompositionOffset{0};
225     size_t mReleaseOffset{0};
226 
227     int mCurrentConnectId{0};
228     bool mProducerWantsEvents{false};
229 };
230 
231 
232 // A single frame update from the consumer to producer that can be sent
233 // through Binder.
234 // Although this may be sent multiple times for the same frame as new
235 // timestamps are set, Fences only need to be sent once.
236 class FrameEventsDelta : public Flattenable<FrameEventsDelta> {
237 friend class ProducerFrameEventHistory;
238 public:
239     FrameEventsDelta() = default;
240     FrameEventsDelta(size_t index,
241             const FrameEvents& frameTimestamps,
242             const FrameEventDirtyFields& dirtyFields);
243 
244     // Movable.
245     FrameEventsDelta(FrameEventsDelta&& src) = default;
246     FrameEventsDelta& operator=(FrameEventsDelta&& src) = default;
247     // Not copyable.
248     FrameEventsDelta(const FrameEventsDelta& src) = delete;
249     FrameEventsDelta& operator=(const FrameEventsDelta& src) = delete;
250 
251     // Flattenable implementation
252     size_t getFlattenedSize() const;
253     size_t getFdCount() const;
254     status_t flatten(void*& buffer, size_t& size, int*& fds,
255             size_t& count) const;
256     status_t unflatten(void const*& buffer, size_t& size, int const*& fds,
257             size_t& count);
258 
259     uint64_t getFrameNumber() const;
260     bool getLatchTime(nsecs_t* latchTime) const;
261     bool getDisplayPresentFence(sp<Fence>* fence) const;
262 
263 private:
264     static constexpr size_t minFlattenedSize();
265 
266     size_t mIndex{0};
267     uint64_t mFrameNumber{0};
268 
269     bool mAddPostCompositeCalled{0};
270     bool mAddReleaseCalled{0};
271 
272     nsecs_t mPostedTime{FrameEvents::TIMESTAMP_PENDING};
273     nsecs_t mRequestedPresentTime{FrameEvents::TIMESTAMP_PENDING};
274     nsecs_t mLatchTime{FrameEvents::TIMESTAMP_PENDING};
275     nsecs_t mFirstRefreshStartTime{FrameEvents::TIMESTAMP_PENDING};
276     nsecs_t mLastRefreshStartTime{FrameEvents::TIMESTAMP_PENDING};
277     nsecs_t mDequeueReadyTime{FrameEvents::TIMESTAMP_PENDING};
278 
279     FenceTime::Snapshot mGpuCompositionDoneFence;
280     FenceTime::Snapshot mDisplayPresentFence;
281     FenceTime::Snapshot mReleaseFence;
282 
283     // This is a static method with an auto return value so we can call
284     // it without needing const and non-const versions.
285     template <typename ThisT>
286     static inline auto allFences(ThisT fed) ->
287             std::array<decltype(&fed->mReleaseFence), 3> {
288         return {{
289             &fed->mGpuCompositionDoneFence, &fed->mDisplayPresentFence,
290             &fed->mReleaseFence
291         }};
292     }
293 };
294 
295 
296 // A collection of updates from consumer to producer that can be sent
297 // through Binder.
298 class FrameEventHistoryDelta
299         : public Flattenable<FrameEventHistoryDelta> {
300 
301 friend class ConsumerFrameEventHistory;
302 friend class ProducerFrameEventHistory;
303 
304 public:
305     FrameEventHistoryDelta() = default;
306 
307     // Movable.
308     FrameEventHistoryDelta(FrameEventHistoryDelta&& src) = default;
309     FrameEventHistoryDelta& operator=(FrameEventHistoryDelta&& src) noexcept;
310     // Not copyable.
311     FrameEventHistoryDelta(const FrameEventHistoryDelta& src) = delete;
312     FrameEventHistoryDelta& operator=(
313             const FrameEventHistoryDelta& src) = delete;
314 
315     // Flattenable implementation.
316     size_t getFlattenedSize() const;
317     size_t getFdCount() const;
318     status_t flatten(void*& buffer, size_t& size, int*& fds,
319             size_t& count) const;
320     status_t unflatten(void const*& buffer, size_t& size, int const*& fds,
321             size_t& count);
322 
323     std::vector<FrameEventsDelta>::const_iterator begin() const;
324     std::vector<FrameEventsDelta>::const_iterator end() const;
325 
326 private:
327     static constexpr size_t minFlattenedSize();
328 
329     std::vector<FrameEventsDelta> mDeltas;
330     CompositorTiming mCompositorTiming;
331 };
332 
333 
334 } // namespace android
335 #endif
336