| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "media/filters/source_buffer_stream.h" | 5 #include "media/filters/source_buffer_stream.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <map> | 8 #include <map> |
| 9 | 9 |
| 10 #include "base/bind.h" | 10 #include "base/bind.h" |
| (...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 279 return base::TimeDelta::FromMilliseconds(1000); | 279 return base::TimeDelta::FromMilliseconds(1000); |
| 280 } | 280 } |
| 281 // The maximum amount of data in bytes the stream will keep in memory. | 281 // The maximum amount of data in bytes the stream will keep in memory. |
| 282 // 12MB: approximately 5 minutes of 320Kbps content. | 282 // 12MB: approximately 5 minutes of 320Kbps content. |
| 283 // 150MB: approximately 5 minutes of 4Mbps content. | 283 // 150MB: approximately 5 minutes of 4Mbps content. |
| 284 static int kDefaultAudioMemoryLimit = 12 * 1024 * 1024; | 284 static int kDefaultAudioMemoryLimit = 12 * 1024 * 1024; |
| 285 static int kDefaultVideoMemoryLimit = 150 * 1024 * 1024; | 285 static int kDefaultVideoMemoryLimit = 150 * 1024 * 1024; |
| 286 | 286 |
| 287 namespace media { | 287 namespace media { |
| 288 | 288 |
| 289 SourceBufferStream::SourceBufferStream(const AudioDecoderConfig& audio_config) | 289 SourceBufferStream::SourceBufferStream(const AudioDecoderConfig& audio_config, |
| 290 : current_config_index_(0), | 290 const LogCB& log_cb) |
| 291 : log_cb_(log_cb), |
| 292 current_config_index_(0), |
| 291 append_config_index_(0), | 293 append_config_index_(0), |
| 292 seek_pending_(false), | 294 seek_pending_(false), |
| 293 seek_buffer_timestamp_(kNoTimestamp()), | 295 seek_buffer_timestamp_(kNoTimestamp()), |
| 294 selected_range_(NULL), | 296 selected_range_(NULL), |
| 295 media_segment_start_time_(kNoTimestamp()), | 297 media_segment_start_time_(kNoTimestamp()), |
| 296 range_for_next_append_(ranges_.end()), | 298 range_for_next_append_(ranges_.end()), |
| 297 new_media_segment_(false), | 299 new_media_segment_(false), |
| 298 last_buffer_timestamp_(kNoTimestamp()), | 300 last_buffer_timestamp_(kNoTimestamp()), |
| 299 max_interbuffer_distance_(kNoTimestamp()), | 301 max_interbuffer_distance_(kNoTimestamp()), |
| 300 memory_limit_(kDefaultAudioMemoryLimit), | 302 memory_limit_(kDefaultAudioMemoryLimit), |
| 301 config_change_pending_(false) { | 303 config_change_pending_(false) { |
| 302 DCHECK(audio_config.IsValidConfig()); | 304 DCHECK(audio_config.IsValidConfig()); |
| 303 audio_configs_.push_back(new AudioDecoderConfig()); | 305 audio_configs_.push_back(new AudioDecoderConfig()); |
| 304 audio_configs_.back()->CopyFrom(audio_config); | 306 audio_configs_.back()->CopyFrom(audio_config); |
| 305 } | 307 } |
| 306 | 308 |
| 307 SourceBufferStream::SourceBufferStream(const VideoDecoderConfig& video_config) | 309 SourceBufferStream::SourceBufferStream(const VideoDecoderConfig& video_config, |
| 308 : current_config_index_(0), | 310 const LogCB& log_cb) |
| 311 : log_cb_(log_cb), |
| 312 current_config_index_(0), |
| 309 append_config_index_(0), | 313 append_config_index_(0), |
| 310 seek_pending_(false), | 314 seek_pending_(false), |
| 311 seek_buffer_timestamp_(kNoTimestamp()), | 315 seek_buffer_timestamp_(kNoTimestamp()), |
| 312 selected_range_(NULL), | 316 selected_range_(NULL), |
| 313 media_segment_start_time_(kNoTimestamp()), | 317 media_segment_start_time_(kNoTimestamp()), |
| 314 range_for_next_append_(ranges_.end()), | 318 range_for_next_append_(ranges_.end()), |
| 315 new_media_segment_(false), | 319 new_media_segment_(false), |
| 316 last_buffer_timestamp_(kNoTimestamp()), | 320 last_buffer_timestamp_(kNoTimestamp()), |
| 317 max_interbuffer_distance_(kNoTimestamp()), | 321 max_interbuffer_distance_(kNoTimestamp()), |
| 318 memory_limit_(kDefaultVideoMemoryLimit), | 322 memory_limit_(kDefaultVideoMemoryLimit), |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 351 } | 355 } |
| 352 } | 356 } |
| 353 | 357 |
| 354 bool SourceBufferStream::Append( | 358 bool SourceBufferStream::Append( |
| 355 const SourceBufferStream::BufferQueue& buffers) { | 359 const SourceBufferStream::BufferQueue& buffers) { |
| 356 DCHECK(!buffers.empty()); | 360 DCHECK(!buffers.empty()); |
| 357 DCHECK(media_segment_start_time_ != kNoTimestamp()); | 361 DCHECK(media_segment_start_time_ != kNoTimestamp()); |
| 358 | 362 |
| 359 // New media segments must begin with a keyframe. | 363 // New media segments must begin with a keyframe. |
| 360 if (new_media_segment_ && !buffers.front()->IsKeyframe()) { | 364 if (new_media_segment_ && !buffers.front()->IsKeyframe()) { |
| 361 DVLOG(1) << "Media segment did not begin with keyframe."; | 365 MEDIA_LOG(log_cb_) <<"Media segment did not begin with keyframe."; |
| 362 return false; | 366 return false; |
| 363 } | 367 } |
| 364 | 368 |
| 365 // Buffers within a media segment should be monotonically increasing. | 369 // Buffers within a media segment should be monotonically increasing. |
| 366 if (!IsMonotonicallyIncreasing(buffers)) { | 370 if (!IsMonotonicallyIncreasing(buffers)) { |
| 367 DVLOG(1) << "Buffers were not monotonically increasing."; | 371 MEDIA_LOG(log_cb_) <<"Buffers were not monotonically increasing."; |
| 368 return false; | 372 return false; |
| 369 } | 373 } |
| 370 | 374 |
| 371 if (media_segment_start_time_ < base::TimeDelta() || | 375 if (media_segment_start_time_ < base::TimeDelta() || |
| 372 buffers.front()->GetDecodeTimestamp() < base::TimeDelta()) { | 376 buffers.front()->GetDecodeTimestamp() < base::TimeDelta()) { |
| 373 DVLOG(1) << "Cannot append a media segment with negative timestamps."; | 377 MEDIA_LOG(log_cb_) |
| 378 << "Cannot append a media segment with negative timestamps."; |
| 374 return false; | 379 return false; |
| 375 } | 380 } |
| 376 | 381 |
| 377 UpdateMaxInterbufferDistance(buffers); | 382 UpdateMaxInterbufferDistance(buffers); |
| 378 SetConfigIds(buffers); | 383 SetConfigIds(buffers); |
| 379 | 384 |
| 380 // Save a snapshot of stream state before range modifications are made. | 385 // Save a snapshot of stream state before range modifications are made. |
| 381 base::TimeDelta next_buffer_timestamp = GetNextBufferTimestamp(); | 386 base::TimeDelta next_buffer_timestamp = GetNextBufferTimestamp(); |
| 382 base::TimeDelta end_buffer_timestamp = GetEndBufferTimestamp(); | 387 base::TimeDelta end_buffer_timestamp = GetEndBufferTimestamp(); |
| 383 | 388 |
| (...skipping 646 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1030 if (max_interbuffer_distance_ == kNoTimestamp()) | 1035 if (max_interbuffer_distance_ == kNoTimestamp()) |
| 1031 return base::TimeDelta::FromMilliseconds(kDefaultBufferDurationInMs); | 1036 return base::TimeDelta::FromMilliseconds(kDefaultBufferDurationInMs); |
| 1032 return max_interbuffer_distance_; | 1037 return max_interbuffer_distance_; |
| 1033 } | 1038 } |
| 1034 | 1039 |
| 1035 bool SourceBufferStream::UpdateAudioConfig(const AudioDecoderConfig& config) { | 1040 bool SourceBufferStream::UpdateAudioConfig(const AudioDecoderConfig& config) { |
| 1036 DCHECK(!audio_configs_.empty()); | 1041 DCHECK(!audio_configs_.empty()); |
| 1037 DCHECK(video_configs_.empty()); | 1042 DCHECK(video_configs_.empty()); |
| 1038 | 1043 |
| 1039 if (audio_configs_[0]->codec() != config.codec()) { | 1044 if (audio_configs_[0]->codec() != config.codec()) { |
| 1040 DVLOG(1) << "UpdateAudioConfig() : Codec changes not allowed."; | 1045 MEDIA_LOG(log_cb_) << "Audio codec changes not allowed."; |
| 1041 return false; | 1046 return false; |
| 1042 } | 1047 } |
| 1043 | 1048 |
| 1044 if (audio_configs_[0]->samples_per_second() != config.samples_per_second()) { | 1049 if (audio_configs_[0]->samples_per_second() != config.samples_per_second()) { |
| 1045 DVLOG(1) << "UpdateAudioConfig() : Sample rate changes not allowed."; | 1050 MEDIA_LOG(log_cb_) << "Audio sample rate changes not allowed."; |
| 1046 return false; | 1051 return false; |
| 1047 } | 1052 } |
| 1048 | 1053 |
| 1049 if (audio_configs_[0]->channel_layout() != config.channel_layout()) { | 1054 if (audio_configs_[0]->channel_layout() != config.channel_layout()) { |
| 1050 DVLOG(1) << "UpdateAudioConfig() : Channel layout changes not allowed."; | 1055 MEDIA_LOG(log_cb_) << "Audio channel layout changes not allowed."; |
| 1051 return false; | 1056 return false; |
| 1052 } | 1057 } |
| 1053 | 1058 |
| 1054 if (audio_configs_[0]->bits_per_channel() != config.bits_per_channel()) { | 1059 if (audio_configs_[0]->bits_per_channel() != config.bits_per_channel()) { |
| 1055 DVLOG(1) << "UpdateAudioConfig() : Bits per channel changes not allowed."; | 1060 MEDIA_LOG(log_cb_) << "Audio bits per channel changes not allowed."; |
| 1056 return false; | 1061 return false; |
| 1057 } | 1062 } |
| 1058 | 1063 |
| 1059 // Check to see if the new config matches an existing one. | 1064 // Check to see if the new config matches an existing one. |
| 1060 for (size_t i = 0; i < audio_configs_.size(); ++i) { | 1065 for (size_t i = 0; i < audio_configs_.size(); ++i) { |
| 1061 if (config.Matches(*audio_configs_[i])) { | 1066 if (config.Matches(*audio_configs_[i])) { |
| 1062 append_config_index_ = i; | 1067 append_config_index_ = i; |
| 1063 return true; | 1068 return true; |
| 1064 } | 1069 } |
| 1065 } | 1070 } |
| 1066 | 1071 |
| 1067 // No matches found so let's add this one to the list. | 1072 // No matches found so let's add this one to the list. |
| 1068 append_config_index_ = audio_configs_.size(); | 1073 append_config_index_ = audio_configs_.size(); |
| 1069 audio_configs_.resize(audio_configs_.size() + 1); | 1074 audio_configs_.resize(audio_configs_.size() + 1); |
| 1070 audio_configs_[append_config_index_] = new AudioDecoderConfig(); | 1075 audio_configs_[append_config_index_] = new AudioDecoderConfig(); |
| 1071 audio_configs_[append_config_index_]->CopyFrom(config); | 1076 audio_configs_[append_config_index_]->CopyFrom(config); |
| 1072 return true; | 1077 return true; |
| 1073 } | 1078 } |
| 1074 | 1079 |
| 1075 bool SourceBufferStream::UpdateVideoConfig(const VideoDecoderConfig& config) { | 1080 bool SourceBufferStream::UpdateVideoConfig(const VideoDecoderConfig& config) { |
| 1076 DCHECK(!video_configs_.empty()); | 1081 DCHECK(!video_configs_.empty()); |
| 1077 DCHECK(audio_configs_.empty()); | 1082 DCHECK(audio_configs_.empty()); |
| 1078 | 1083 |
| 1079 if (video_configs_[0]->is_encrypted() != config.is_encrypted()) { | 1084 if (video_configs_[0]->is_encrypted() != config.is_encrypted()) { |
| 1080 DVLOG(1) << "UpdateVideoConfig() : Encryption changes not allowed."; | 1085 MEDIA_LOG(log_cb_) <<"Video Encryption changes not allowed."; |
| 1081 return false; | 1086 return false; |
| 1082 } | 1087 } |
| 1083 | 1088 |
| 1084 if (video_configs_[0]->codec() != config.codec()) { | 1089 if (video_configs_[0]->codec() != config.codec()) { |
| 1085 DVLOG(1) << "UpdateVideoConfig() : Codec changes not allowed."; | 1090 MEDIA_LOG(log_cb_) <<"Video codec changes not allowed."; |
| 1086 return false; | 1091 return false; |
| 1087 } | 1092 } |
| 1088 | 1093 |
| 1089 // Check to see if the new config matches an existing one. | 1094 // Check to see if the new config matches an existing one. |
| 1090 for (size_t i = 0; i < video_configs_.size(); ++i) { | 1095 for (size_t i = 0; i < video_configs_.size(); ++i) { |
| 1091 if (config.Matches(*video_configs_[i])) { | 1096 if (config.Matches(*video_configs_[i])) { |
| 1092 append_config_index_ = i; | 1097 append_config_index_ = i; |
| 1093 return true; | 1098 return true; |
| 1094 } | 1099 } |
| 1095 } | 1100 } |
| (...skipping 463 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1559 return ComputeFudgeRoom(GetApproximateDuration()); | 1564 return ComputeFudgeRoom(GetApproximateDuration()); |
| 1560 } | 1565 } |
| 1561 | 1566 |
| 1562 base::TimeDelta SourceBufferRange::GetApproximateDuration() const { | 1567 base::TimeDelta SourceBufferRange::GetApproximateDuration() const { |
| 1563 base::TimeDelta max_interbuffer_distance = interbuffer_distance_cb_.Run(); | 1568 base::TimeDelta max_interbuffer_distance = interbuffer_distance_cb_.Run(); |
| 1564 DCHECK(max_interbuffer_distance != kNoTimestamp()); | 1569 DCHECK(max_interbuffer_distance != kNoTimestamp()); |
| 1565 return max_interbuffer_distance; | 1570 return max_interbuffer_distance; |
| 1566 } | 1571 } |
| 1567 | 1572 |
| 1568 } // namespace media | 1573 } // namespace media |
| OLD | NEW |