FrameTracker.h revision 82dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6add
182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis/*
282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * Copyright (C) 2012 The Android Open Source Project
382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis *
482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * Licensed under the Apache License, Version 2.0 (the "License");
582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * you may not use this file except in compliance with the License.
682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * You may obtain a copy of the License at
782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis *
882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis *      http://www.apache.org/licenses/LICENSE-2.0
982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis *
1082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * Unless required by applicable law or agreed to in writing, software
1182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * distributed under the License is distributed on an "AS IS" BASIS,
1282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * See the License for the specific language governing permissions and
1482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis * limitations under the License.
1582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis */
1682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
1782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#ifndef ANDROID_FRAMETRACKER_H
1882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#define ANDROID_FRAMETRACKER_H
1982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
2082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#include <stddef.h>
2182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
2282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#include <utils/Timers.h>
2382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#include <utils/RefBase.h>
2482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
2582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennisnamespace android {
2682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
2782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennisclass String8;
2882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennisclass Fence;
2982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
3082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// FrameTracker tracks information about the most recently rendered frames. It
3182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// uses a circular buffer of frame records, and is *NOT* thread-safe -
3282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// mutexing must be done at a higher level if multi-threaded access is
3382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// possible.
3482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis//
3582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// Some of the time values tracked may be set either as a specific timestamp
3682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// or a fence.  When a non-NULL fence is set for a given time value, the
3782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis// signal time of that fence is used instead of the timestamp.
3882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennisclass FrameTracker {
3982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
4082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennispublic:
4182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // NUM_FRAME_RECORDS is the size of the circular buffer used to track the
4282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // frame time history.
4382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    enum { NUM_FRAME_RECORDS = 128 };
4482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
4582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    FrameTracker();
4682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
4782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // setDesiredPresentTime sets the time at which the current frame
4882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // should be presented to the user under ideal (i.e. zero latency)
4982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // conditions.
5082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void setDesiredPresentTime(nsecs_t desiredPresentTime);
5182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
5282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // setFrameReadyTime sets the time at which the current frame became ready
5382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // to be presented to the user.  For example, if the frame contents is
5482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // being written to memory by some asynchronous hardware, this would be
5582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // the time at which those writes completed.
5682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void setFrameReadyTime(nsecs_t readyTime);
5782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
5882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // setFrameReadyFence sets the fence that is used to get the time at which
5982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // the current frame became ready to be presented to the user.
6082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void setFrameReadyFence(const sp<Fence>& readyFence);
6182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
6282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // setActualPresentTime sets the timestamp at which the current frame became
6382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // visible to the user.
6482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void setActualPresentTime(nsecs_t displayTime);
6582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
6682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // setActualPresentFence sets the fence that is used to get the time
6782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // at which the current frame became visible to the user.
6882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void setActualPresentFence(const sp<Fence>& fence);
6982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
7082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // advanceFrame advances the frame tracker to the next frame.
7182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void advanceFrame();
7282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
7382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // clear resets all the tracked frame data to zero.
7482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void clear();
7582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
7682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // dump appends the current frame display time history to the result string.
7782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void dump(String8& result) const;
7882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
7982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennisprivate:
8082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    struct FrameRecord {
8182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        FrameRecord() :
8282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis            desiredPresentTime(0),
8382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis            frameReadyTime(0),
8482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis            actualPresentTime(0) {}
8582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        nsecs_t desiredPresentTime;
8682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        nsecs_t frameReadyTime;
8782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        nsecs_t actualPresentTime;
8882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        sp<Fence> frameReadyFence;
8982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis        sp<Fence> actualPresentFence;
9082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    };
9182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
9282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // processFences iterates over all the frame records that have a fence set
9382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // and replaces that fence with a timestamp if the fence has signaled.  If
9482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // the fence is not signaled the record's displayTime is set to INT64_MAX.
9582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    //
9682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // This method is const because although it modifies the frame records it
9782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // does so in such a way that the information represented should not
9882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // change.  This allows it to be called from the dump method.
9982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    void processFences() const;
10082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
10182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // mFrameRecords is the circular buffer storing the tracked data for each
10282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // frame.
10382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    FrameRecord mFrameRecords[NUM_FRAME_RECORDS];
10482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
10582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // mOffset is the offset into mFrameRecords of the current frame.
10682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    size_t mOffset;
10782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
10882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // mNumFences is the total number of fences set in the frame records.  It
10982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // is incremented each time a fence is added and decremented each time a
11082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // signaled fence is removed in processFences or if advanceFrame clobbers
11182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // a fence.
11282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    //
11382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // The number of fences is tracked so that the run time of processFences
11482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    // doesn't grow with NUM_FRAME_RECORDS.
11582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis    int mNumFences;
11682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis};
11782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
11882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis}
11982dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis
12082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis#endif // ANDROID_FRAMETRACKER_H
121