Isolated OnMediaSample in Chunker
Change-Id: I3af45543a1da1d1cf0b0741dd732dc71b2c30abe
This commit is contained in:
parent
21acb41e63
commit
387fe8e33b
|
@ -48,57 +48,14 @@ Status ChunkingHandler::Process(std::unique_ptr<StreamData> stream_data) {
|
|||
case StreamDataType::kSegmentInfo:
|
||||
VLOG(3) << "Droppping existing segment info.";
|
||||
return Status::OK;
|
||||
case StreamDataType::kMediaSample: {
|
||||
const size_t stream_index = stream_data->stream_index;
|
||||
DCHECK_NE(time_scales_[stream_index], 0u)
|
||||
<< "kStreamInfo should arrive before kMediaSample";
|
||||
|
||||
if (stream_index != main_stream_index_ &&
|
||||
!stream_data->media_sample->is_key_frame()) {
|
||||
return Status(error::CHUNKING_ERROR,
|
||||
"All non video samples should be key frames.");
|
||||
}
|
||||
// The streams are expected to be roughly synchronized, so we don't expect
|
||||
// to see a lot of samples from one stream but no samples from another
|
||||
// stream.
|
||||
// The value is kind of arbitrary here. For a 24fps video, it is ~40s.
|
||||
const size_t kMaxCachedSamplesPerStream = 1000u;
|
||||
if (num_cached_samples_[stream_index] >= kMaxCachedSamplesPerStream) {
|
||||
LOG(ERROR) << "Streams are not synchronized:";
|
||||
for (size_t i = 0; i < num_cached_samples_.size(); ++i)
|
||||
LOG(ERROR) << " [Stream " << i << "] " << num_cached_samples_[i];
|
||||
return Status(error::CHUNKING_ERROR, "Streams are not synchronized.");
|
||||
}
|
||||
|
||||
cached_media_sample_stream_data_.push(std::move(stream_data));
|
||||
++num_cached_samples_[stream_index];
|
||||
|
||||
// If we have cached samples from every stream, the first sample in
|
||||
// |cached_media_samples_stream_data_| is guaranteed to be the earliest
|
||||
// sample. Extract and process that sample.
|
||||
if (std::all_of(num_cached_samples_.begin(), num_cached_samples_.end(),
|
||||
[](size_t num_samples) { return num_samples > 0; })) {
|
||||
while (true) {
|
||||
const size_t top_stream_index =
|
||||
cached_media_sample_stream_data_.top()->stream_index;
|
||||
Status status = ProcessMediaSampleStreamData(
|
||||
*cached_media_sample_stream_data_.top());
|
||||
if (!status.ok())
|
||||
return status;
|
||||
cached_media_sample_stream_data_.pop();
|
||||
if (--num_cached_samples_[top_stream_index] == 0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
return Status::OK;
|
||||
}
|
||||
case StreamDataType::kMediaSample:
|
||||
return OnMediaSample(std::move(stream_data));
|
||||
default:
|
||||
VLOG(3) << "Stream data type "
|
||||
<< static_cast<int>(stream_data->stream_data_type) << " ignored.";
|
||||
break;
|
||||
}
|
||||
return Dispatch(std::move(stream_data));
|
||||
}
|
||||
}
|
||||
|
||||
Status ChunkingHandler::OnFlushRequest(size_t input_stream_index) {
|
||||
// Process all cached samples.
|
||||
|
@ -172,6 +129,53 @@ Status ChunkingHandler::OnScte35Event(
|
|||
return Status::OK;
|
||||
}
|
||||
|
||||
Status ChunkingHandler::OnMediaSample(std::unique_ptr<StreamData> stream_data) {
|
||||
DCHECK_EQ(StreamDataType::kMediaSample, stream_data->stream_data_type);
|
||||
|
||||
const size_t stream_index = stream_data->stream_index;
|
||||
DCHECK_NE(time_scales_[stream_index], 0u)
|
||||
<< "kStreamInfo should arrive before kMediaSample";
|
||||
|
||||
if (stream_index != main_stream_index_ &&
|
||||
!stream_data->media_sample->is_key_frame()) {
|
||||
return Status(error::CHUNKING_ERROR,
|
||||
"All non video samples should be key frames.");
|
||||
}
|
||||
// The streams are expected to be roughly synchronized, so we don't expect
|
||||
// to see a lot of samples from one stream but no samples from another
|
||||
// stream.
|
||||
// The value is kind of arbitrary here. For a 24fps video, it is ~40s.
|
||||
const size_t kMaxCachedSamplesPerStream = 1000u;
|
||||
if (num_cached_samples_[stream_index] >= kMaxCachedSamplesPerStream) {
|
||||
LOG(ERROR) << "Streams are not synchronized:";
|
||||
for (size_t i = 0; i < num_cached_samples_.size(); ++i)
|
||||
LOG(ERROR) << " [Stream " << i << "] " << num_cached_samples_[i];
|
||||
return Status(error::CHUNKING_ERROR, "Streams are not synchronized.");
|
||||
}
|
||||
|
||||
cached_media_sample_stream_data_.push(std::move(stream_data));
|
||||
++num_cached_samples_[stream_index];
|
||||
|
||||
// If we have cached samples from every stream, the first sample in
|
||||
// |cached_media_samples_stream_data_| is guaranteed to be the earliest
|
||||
// sample. Extract and process that sample.
|
||||
if (std::all_of(num_cached_samples_.begin(), num_cached_samples_.end(),
|
||||
[](size_t num_samples) { return num_samples > 0; })) {
|
||||
while (true) {
|
||||
const size_t top_stream_index =
|
||||
cached_media_sample_stream_data_.top()->stream_index;
|
||||
Status status =
|
||||
ProcessMediaSampleStreamData(*cached_media_sample_stream_data_.top());
|
||||
if (!status.ok())
|
||||
return status;
|
||||
cached_media_sample_stream_data_.pop();
|
||||
if (--num_cached_samples_[top_stream_index] == 0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
return Status::OK;
|
||||
}
|
||||
|
||||
Status ChunkingHandler::ProcessMainMediaSample(const MediaSample* sample) {
|
||||
const bool is_key_frame = sample->is_key_frame();
|
||||
const int64_t timestamp = sample->dts();
|
||||
|
|
|
@ -67,6 +67,8 @@ class ChunkingHandler : public MediaHandler {
|
|||
Status OnScte35Event(uint64_t stream_index,
|
||||
std::shared_ptr<const Scte35Event> event);
|
||||
|
||||
Status OnMediaSample(std::unique_ptr<StreamData> stream_data);
|
||||
|
||||
// Processes main media sample and apply chunking if needed.
|
||||
Status ProcessMainMediaSample(const MediaSample* sample);
|
||||
|
||||
|
|
Loading…
Reference in New Issue