MediaPlayer: overhaul buffering monitor scheme.
GenericSource: buffering monitor runs on a separate looper since readBuffer()
call can be blocked for long time.
When paused, dequeueAccess() returns -EWOULDBLOCK.
For audio offload, take into account cached data in downstream components.
NuPlayerDecoderPassThrough: flush out aggregate buffer when source doesn't have
data available.
Bug: 24295007
Change-Id: I535a438d96ee902c9b4baa7c84ed7e5063a23964
(cherry picked from commit 32ce83cf93e4eb14c9937e4b850e044f9f7fdf2c)
diff --git a/media/libmediaplayerservice/nuplayer/GenericSource.h b/media/libmediaplayerservice/nuplayer/GenericSource.h
index 2db5557..2fd703e 100644
--- a/media/libmediaplayerservice/nuplayer/GenericSource.h
+++ b/media/libmediaplayerservice/nuplayer/GenericSource.h
@@ -77,6 +77,8 @@
virtual bool isStreaming() const;
+ virtual void setOffloadAudio(bool offload);
+
protected:
virtual ~GenericSource();
@@ -111,6 +113,83 @@
sp<AnotherPacketSource> mPackets;
};
+ // Helper to monitor buffering status. The polling happens every second.
+ // When necessary, it will send out buffering events to the player.
+ struct BufferingMonitor : public AHandler {
+ public:
+ BufferingMonitor(const sp<AMessage> ¬ify);
+
+ // Set up state.
+ void prepare(const sp<NuCachedSource2> &cachedSource,
+ const sp<WVMExtractor> &wvmExtractor,
+ int64_t durationUs,
+ int64_t bitrate,
+ bool isStreaming);
+ // Stop and reset buffering monitor.
+ void stop();
+ // Cancel the current monitor task.
+ void cancelPollBuffering();
+ // Restart the monitor task.
+ void restartPollBuffering();
+ // Stop buffering task and send out corresponding events.
+ void stopBufferingIfNecessary();
+ // Make sure data source is getting data.
+ void ensureCacheIsFetching();
+ // Update media time of just extracted buffer from data source.
+ void updateQueuedTime(bool isAudio, int64_t timeUs);
+
+ // Set the offload mode.
+ void setOffloadAudio(bool offload);
+ // Update media time of last dequeued buffer which is sent to the decoder.
+ void updateDequeuedBufferTime(int64_t mediaUs);
+
+ protected:
+ virtual ~BufferingMonitor();
+ virtual void onMessageReceived(const sp<AMessage> &msg);
+
+ private:
+ enum {
+ kWhatPollBuffering,
+ };
+
+ sp<AMessage> mNotify;
+
+ sp<NuCachedSource2> mCachedSource;
+ sp<WVMExtractor> mWVMExtractor;
+ int64_t mDurationUs;
+ int64_t mBitrate;
+ bool mIsStreaming;
+
+ int64_t mAudioTimeUs;
+ int64_t mVideoTimeUs;
+ int32_t mPollBufferingGeneration;
+ bool mPrepareBuffering;
+ bool mBuffering;
+ int32_t mPrevBufferPercentage;
+
+ mutable Mutex mLock;
+
+ bool mOffloadAudio;
+ int64_t mFirstDequeuedBufferRealUs;
+ int64_t mFirstDequeuedBufferMediaUs;
+ int64_t mlastDequeuedBufferMediaUs;
+
+ void prepare_l(const sp<NuCachedSource2> &cachedSource,
+ const sp<WVMExtractor> &wvmExtractor,
+ int64_t durationUs,
+ int64_t bitrate,
+ bool isStreaming);
+ void cancelPollBuffering_l();
+ void notifyBufferingUpdate_l(int32_t percentage);
+ void startBufferingIfNecessary_l();
+ void stopBufferingIfNecessary_l();
+ void sendCacheStats_l();
+ void ensureCacheIsFetching_l();
+ int64_t getLastReadPosition_l();
+ void onPollBuffering_l();
+ void schedulePollBuffering_l();
+ };
+
Vector<sp<IMediaSource> > mSources;
Track mAudioTrack;
int64_t mAudioTimeUs;
@@ -147,17 +226,15 @@
bool mStarted;
bool mStopRead;
int64_t mBitrate;
- int32_t mPollBufferingGeneration;
+ sp<BufferingMonitor> mBufferingMonitor;
uint32_t mPendingReadBufferTypes;
- bool mBuffering;
- bool mPrepareBuffering;
- int32_t mPrevBufferPercentage;
sp<ABuffer> mGlobalTimedText;
mutable Mutex mReadBufferLock;
mutable Mutex mDisconnectLock;
sp<ALooper> mLooper;
+ sp<ALooper> mBufferingMonitorLooper;
void resetDataSource();
@@ -212,16 +289,6 @@
void queueDiscontinuityIfNeeded(
bool seeking, bool formatChange, media_track_type trackType, Track *track);
- void schedulePollBuffering();
- void cancelPollBuffering();
- void restartPollBuffering();
- void onPollBuffering();
- void notifyBufferingUpdate(int32_t percentage);
- void startBufferingIfNecessary();
- void stopBufferingIfNecessary();
- void sendCacheStats();
- void ensureCacheIsFetching();
-
DISALLOW_EVIL_CONSTRUCTORS(GenericSource);
};