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