Fix for 4198445 HC - Support for Widevine Live Streaming (adaptive)
Change-Id: Id3a8a997fb1186c6af6e94f2fc2d4788238a0452
This commit is contained in:
Binary file not shown.
@@ -54,6 +54,7 @@ public class ConfigXMLParser {
|
|||||||
public void end() {
|
public void end() {
|
||||||
if (currentAssetDescriptor.getUri().indexOf(".wvm") != -1
|
if (currentAssetDescriptor.getUri().indexOf(".wvm") != -1
|
||||||
|| currentAssetDescriptor.getUri().indexOf(".ts") != -1
|
|| currentAssetDescriptor.getUri().indexOf(".ts") != -1
|
||||||
|
|| currentAssetDescriptor.getUri().indexOf(".m3u8") != -1
|
||||||
|| !currentAssetDescriptor.getUri().substring(currentAssetDescriptor
|
|| !currentAssetDescriptor.getUri().substring(currentAssetDescriptor
|
||||||
.getUri().lastIndexOf("/")).contains(".")) {
|
.getUri().lastIndexOf("/")).contains(".")) {
|
||||||
assetDescriptors.add(currentAssetDescriptor.copy());
|
assetDescriptors.add(currentAssetDescriptor.copy());
|
||||||
|
|||||||
@@ -38,7 +38,8 @@ public class DownloadActivity extends AssetActivity {
|
|||||||
File file = new File(dir.getAbsolutePath() + File.separator + name);
|
File file = new File(dir.getAbsolutePath() + File.separator + name);
|
||||||
if (!file.isDirectory()
|
if (!file.isDirectory()
|
||||||
&& !name.equals("curl")
|
&& !name.equals("curl")
|
||||||
&& (name.contains(".wvm") || name.contains(".ts") || name.contains(".mp4") || !name.contains(".")))
|
&& (name.contains(".wvm") || name.contains(".ts") || name.contains(".mp4") ||
|
||||||
|
name.contains(".m3u8") | !name.contains(".")))
|
||||||
return true;
|
return true;
|
||||||
else
|
else
|
||||||
return false;
|
return false;
|
||||||
|
|||||||
Binary file not shown.
@@ -241,6 +241,15 @@ status_t WVMExtractorImpl::readMetaData()
|
|||||||
videoMetaData->setInt32(kKeyWidth, width);
|
videoMetaData->setInt32(kKeyWidth, width);
|
||||||
videoMetaData->setInt32(kKeyHeight, height);
|
videoMetaData->setInt32(kKeyHeight, height);
|
||||||
|
|
||||||
|
if (mIsLiveStream) {
|
||||||
|
float scaleUsed;
|
||||||
|
result = WV_Play(mSession, 1.0, &scaleUsed, "npt=now-");
|
||||||
|
if (result != WV_Status_OK) {
|
||||||
|
LOGE("WV_Play for live stream setup failed: %d", result);
|
||||||
|
return ERROR_IO;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
status_t status;
|
status_t status;
|
||||||
|
|
||||||
status = readAVCCMetaData(videoMetaData);
|
status = readAVCCMetaData(videoMetaData);
|
||||||
@@ -251,8 +260,15 @@ status_t WVMExtractorImpl::readMetaData()
|
|||||||
if (status != OK)
|
if (status != OK)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
mAudioSource = new WVMMediaSource(mSession, WV_EsSelector_Audio, audioMetaData);
|
if (mIsLiveStream) {
|
||||||
mVideoSource = new WVMMediaSource(mSession, WV_EsSelector_Video, videoMetaData);
|
result = WV_Pause(mSession, "");
|
||||||
|
if (result != WV_Status_OK) {
|
||||||
|
LOGE("WV_Pause for live stream setup failed: %d", result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
mAudioSource = new WVMMediaSource(mSession, WV_EsSelector_Audio, audioMetaData, mIsLiveStream);
|
||||||
|
mVideoSource = new WVMMediaSource(mSession, WV_EsSelector_Video, videoMetaData, mIsLiveStream);
|
||||||
|
|
||||||
// Since the WVExtractor goes away soon after this, we delegate ownership of some resources
|
// Since the WVExtractor goes away soon after this, we delegate ownership of some resources
|
||||||
// to the constructed media source
|
// to the constructed media source
|
||||||
@@ -276,7 +292,7 @@ status_t WVMExtractorImpl::readAVCCMetaData(sp<MetaData> videoMetaData)
|
|||||||
|
|
||||||
const unsigned char *config;
|
const unsigned char *config;
|
||||||
unsigned long size;
|
unsigned long size;
|
||||||
int limit = 50;
|
int limit = 500;
|
||||||
do {
|
do {
|
||||||
size_t bytesRead;
|
size_t bytesRead;
|
||||||
bool auStart, sync;
|
bool auStart, sync;
|
||||||
@@ -293,7 +309,7 @@ status_t WVMExtractorImpl::readAVCCMetaData(sp<MetaData> videoMetaData)
|
|||||||
|
|
||||||
result = WV_Info_GetCodecConfig(mSession, WV_CodecConfigType_AVCC, config, size);
|
result = WV_Info_GetCodecConfig(mSession, WV_CodecConfigType_AVCC, config, size);
|
||||||
if (result != WV_Status_OK)
|
if (result != WV_Status_OK)
|
||||||
usleep(100);
|
usleep(10000);
|
||||||
} while (result == WV_Status_Warning_Not_Available && limit-- > 0);
|
} while (result == WV_Status_Warning_Not_Available && limit-- > 0);
|
||||||
|
|
||||||
if (result != WV_Status_OK) {
|
if (result != WV_Status_OK) {
|
||||||
@@ -322,7 +338,7 @@ status_t WVMExtractorImpl::readESDSMetaData(sp<MetaData> audioMetaData)
|
|||||||
|
|
||||||
const unsigned char *config;
|
const unsigned char *config;
|
||||||
unsigned long size;
|
unsigned long size;
|
||||||
int limit = 50;
|
int limit = 500;
|
||||||
do {
|
do {
|
||||||
size_t bytesRead;
|
size_t bytesRead;
|
||||||
bool auStart, sync;
|
bool auStart, sync;
|
||||||
@@ -339,7 +355,7 @@ status_t WVMExtractorImpl::readESDSMetaData(sp<MetaData> audioMetaData)
|
|||||||
|
|
||||||
result = WV_Info_GetCodecConfig(mSession, WV_CodecConfigType_ESDS, config, size);
|
result = WV_Info_GetCodecConfig(mSession, WV_CodecConfigType_ESDS, config, size);
|
||||||
if (result != WV_Status_OK)
|
if (result != WV_Status_OK)
|
||||||
usleep(100);
|
usleep(10000);
|
||||||
} while (result == WV_Status_Warning_Not_Available && limit-- > 0);
|
} while (result == WV_Status_Warning_Not_Available && limit-- > 0);
|
||||||
|
|
||||||
if (result != WV_Status_OK) {
|
if (result != WV_Status_OK) {
|
||||||
|
|||||||
@@ -36,11 +36,13 @@ static void _cb(int code)
|
|||||||
status_t WVMMediaSource::sLastError = NO_ERROR;
|
status_t WVMMediaSource::sLastError = NO_ERROR;
|
||||||
|
|
||||||
WVMMediaSource::WVMMediaSource(WVSession *session, WVEsSelector esSelector,
|
WVMMediaSource::WVMMediaSource(WVSession *session, WVEsSelector esSelector,
|
||||||
const sp<MetaData> &metaData)
|
const sp<MetaData> &metaData, bool isLive)
|
||||||
: mSession(session),
|
: mSession(session),
|
||||||
mESSelector(esSelector),
|
mESSelector(esSelector),
|
||||||
mTrackMetaData(metaData),
|
mTrackMetaData(metaData),
|
||||||
mStarted(false),
|
mStarted(false),
|
||||||
|
mIsLiveStream(isLive),
|
||||||
|
mNewSegment(false),
|
||||||
mGroup(NULL),
|
mGroup(NULL),
|
||||||
mDts(0),
|
mDts(0),
|
||||||
mPts(0)
|
mPts(0)
|
||||||
@@ -88,6 +90,7 @@ status_t WVMMediaSource::start(MetaData *)
|
|||||||
|
|
||||||
allocBufferGroup();
|
allocBufferGroup();
|
||||||
|
|
||||||
|
mNewSegment = true;
|
||||||
mStarted = true;
|
mStarted = true;
|
||||||
mLogOnce = true;
|
mLogOnce = true;
|
||||||
|
|
||||||
@@ -157,6 +160,15 @@ status_t WVMMediaSource::read(MediaBuffer **buffer, const ReadOptions *options)
|
|||||||
*buffer = NULL;
|
*buffer = NULL;
|
||||||
bool seekNextSync = false;
|
bool seekNextSync = false;
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
// The sync bits aren't working right yet on live streams, so need to disable this
|
||||||
|
// for now.
|
||||||
|
if (mIsLiveStream && mNewSegment && (mESSelector == WV_EsSelector_Video)) {
|
||||||
|
seekNextSync = true;
|
||||||
|
mNewSegment = false;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
int64_t seekTimeUs;
|
int64_t seekTimeUs;
|
||||||
|
|
||||||
int retryLimit = 500; // Limit on number of retries before timeout, 10ms per retry
|
int retryLimit = 500; // Limit on number of retries before timeout, 10ms per retry
|
||||||
@@ -332,9 +344,9 @@ status_t WVMMediaSource::read(MediaBuffer **buffer, const ReadOptions *options)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
LOGD("[%p] %s set range_length=%d, get range_length=%d kKeyTime=%lld sync=%d\n", mediaBuf,
|
LOGD("[%p] %s packet length=%d kKeyTime=%lld %s\n", mediaBuf,
|
||||||
(mESSelector == WV_EsSelector_Video ? "video" : "audio"),
|
(mESSelector == WV_EsSelector_Video ? "video" : "audio"),
|
||||||
bytesRead + offset, mediaBuf->range_length(), keyTime, syncFrame);
|
bytesRead + offset, keyTime, syncFrame ? "sync" : "");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
*buffer = mediaBuf;
|
*buffer = mediaBuf;
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ class WVMFileSource;
|
|||||||
class WVMMediaSource : public MediaSource {
|
class WVMMediaSource : public MediaSource {
|
||||||
public:
|
public:
|
||||||
WVMMediaSource(WVSession *session, WVEsSelector esSelector,
|
WVMMediaSource(WVSession *session, WVEsSelector esSelector,
|
||||||
const sp<MetaData> &metaData);
|
const sp<MetaData> &metaData, bool isLive);
|
||||||
|
|
||||||
void delegateFileSource(sp<WVMFileSource> fileSource);
|
void delegateFileSource(sp<WVMFileSource> fileSource);
|
||||||
void delegateDataSource(sp<DataSource> dataSource);
|
void delegateDataSource(sp<DataSource> dataSource);
|
||||||
@@ -60,6 +60,8 @@ private:
|
|||||||
|
|
||||||
bool mStarted;
|
bool mStarted;
|
||||||
bool mLogOnce;
|
bool mLogOnce;
|
||||||
|
bool mIsLiveStream;
|
||||||
|
bool mNewSegment;
|
||||||
|
|
||||||
MediaBufferGroup *mGroup;
|
MediaBufferGroup *mGroup;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user