Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 3e5af2d2 authored by Brian C. Anderson's avatar Brian C. Anderson Committed by Android (Google) Code Review
Browse files

Merge "Track frame events incrementally and per layer."

parents b9c2c16c d6927fb1
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -66,8 +66,9 @@ public:
        virtual void onFrameReplaced(const BufferItem& item) override;
        virtual void onBuffersReleased() override;
        virtual void onSidebandStreamChanged() override;
        virtual bool getFrameTimestamps(uint64_t frameNumber,
                FrameTimestamps* outTimestamps) const override;
        virtual bool addAndGetFrameTimestamps(
                const NewFrameEventsEntry* newTimestamps,
                uint64_t frameNumber, FrameTimestamps* outTimestamps) override;
    private:
        // mConsumerListener is a weak reference to the IConsumerListener.  This is
        // the raison d'etre of ProxyConsumerListener.
+5 −1
Original line number Diff line number Diff line
@@ -178,7 +178,7 @@ public:

    // See IGraphicBufferProducer::getFrameTimestamps
    virtual bool getFrameTimestamps(uint64_t frameNumber,
            FrameTimestamps* outTimestamps) const override;
            FrameTimestamps* outTimestamps) override;

    // See IGraphicBufferProducer::getUniqueId
    virtual status_t getUniqueId(uint64_t* outId) const override;
@@ -195,6 +195,10 @@ private:
    // BufferQueueCore::INVALID_BUFFER_SLOT otherwise
    int getFreeSlotLocked() const;

    bool addAndGetFrameTimestamps(
            const NewFrameEventsEntry* newTimestamps,
            uint64_t frameNumber, FrameTimestamps* outTimestamps);

    // waitForFreeSlotThenRelock finds the oldest slot in the FREE state. It may
    // block if there are no available slots and we are not in non-blocking
    // mode (producer and consumer controlled by the application). If it blocks,
+83 −1
Original line number Diff line number Diff line
@@ -17,11 +17,20 @@
#ifndef ANDROID_GUI_FRAMETIMESTAMPS_H
#define ANDROID_GUI_FRAMETIMESTAMPS_H

#include <utils/Timers.h>
#include <ui/Fence.h>
#include <utils/Flattenable.h>
#include <utils/StrongPointer.h>
#include <utils/Timers.h>

#include <array>

namespace android {


struct FrameEvents;
class String8;


enum class SupportableFrameTimestamps {
    REQUESTED_PRESENT,
    ACQUIRE,
@@ -32,8 +41,14 @@ enum class SupportableFrameTimestamps {
    RELEASE_TIME,
};


// The timestamps the consumer sends to the producer over binder.
struct FrameTimestamps : public LightFlattenablePod<FrameTimestamps> {
    FrameTimestamps() = default;
    explicit FrameTimestamps(const FrameEvents& fences);

    uint64_t frameNumber{0};
    nsecs_t postedTime{0};
    nsecs_t requestedPresentTime{0};
    nsecs_t acquireTime{0};
    nsecs_t refreshStartTime{0};
@@ -43,5 +58,72 @@ struct FrameTimestamps : public LightFlattenablePod<FrameTimestamps> {
    nsecs_t releaseTime{0};
};


// A collection of timestamps corresponding to a single frame.
struct FrameEvents {
    void checkFencesForCompletion();
    void dump(String8& outString) const;

    bool valid{false};
    uint64_t frameNumber{0};

    // Whether or not certain points in the frame's life cycle have been
    // encountered help us determine if timestamps aren't available because
    // a) we'll just never get them or b) they're not ready yet.
    bool addPostCompositeCalled{false};
    bool addRetireCalled{false};

    nsecs_t postedTime{0};
    nsecs_t requestedPresentTime{0};
    nsecs_t latchTime{0};
    nsecs_t firstRefreshStartTime{0};
    nsecs_t lastRefreshStartTime{0};

    nsecs_t acquireTime{0};
    nsecs_t gpuCompositionDoneTime{0};
    nsecs_t displayPresentTime{0};
    nsecs_t displayRetireTime{0};
    nsecs_t releaseTime{0};

    sp<Fence> acquireFence{Fence::NO_FENCE};
    sp<Fence> gpuCompositionDoneFence{Fence::NO_FENCE};
    sp<Fence> displayPresentFence{Fence::NO_FENCE};
    sp<Fence> displayRetireFence{Fence::NO_FENCE};
    sp<Fence> releaseFence{Fence::NO_FENCE};
};


struct NewFrameEventsEntry {
    uint64_t frameNumber{0};
    nsecs_t postedTime{0};
    nsecs_t requestedPresentTime{0};
    sp<Fence> acquireFence{Fence::NO_FENCE};
};


class FrameEventHistory {
public:
    FrameEvents* getFrame(uint64_t frameNumber);
    FrameEvents* getFrame(uint64_t frameNumber, size_t* iHint);
    void checkFencesForCompletion();
    void dump(String8& outString) const;

    void addQueue(const NewFrameEventsEntry& newFrameEntry);
    void addLatch(uint64_t frameNumber, nsecs_t latchTime);
    void addPreComposition(uint64_t frameNumber, nsecs_t refreshStartTime);
    void addPostComposition(uint64_t frameNumber,
            sp<Fence> gpuCompositionDone, sp<Fence> displayPresent);
    void addRetire(uint64_t frameNumber, sp<Fence> displayRetire);
    void addRelease(uint64_t frameNumber, sp<Fence> release);

private:
    static constexpr size_t MAX_FRAME_HISTORY = 8;
    std::array<FrameEvents, MAX_FRAME_HISTORY> mFrames;
    size_t mQueueOffset{0};
    size_t mCompositionOffset{0};
    size_t mRetireOffset{0};
    size_t mReleaseOffset{0};
};

} // namespace android
#endif
+7 −4
Original line number Diff line number Diff line
@@ -82,10 +82,13 @@ public:
    // different stream.
    virtual void onSidebandStreamChanged() = 0; /* Asynchronous */

    // See IGraphicBufferProducer::getFrameTimestamps
    // This queries the consumer for the timestamps
    virtual bool getFrameTimestamps(uint64_t /*frameNumber*/,
            FrameTimestamps* /*outTimestamps*/) const { return false; }
    // Notifies the consumer of any new producer-side events and then queries
    // the consumer timestamps
    virtual bool addAndGetFrameTimestamps(
            const NewFrameEventsEntry* /*newTimestamps*/,
            uint64_t /*frameNumber*/, FrameTimestamps* /*outTimestamps*/) {
        return false;
    }
};


+1 −1
Original line number Diff line number Diff line
@@ -594,7 +594,7 @@ public:
    //
    // If a fence has not yet signaled the timestamp returned will be 0;
    virtual bool getFrameTimestamps(uint64_t /*frameNumber*/,
            FrameTimestamps* /*outTimestamps*/) const { return false; }
            FrameTimestamps* /*outTimestamps*/) { return false; }

    // Returns a unique id for this BufferQueue
    virtual status_t getUniqueId(uint64_t* outId) const = 0;
Loading