Chromium Code Reviews| 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 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 50 // stream. Used to estimate the duration of a buffer if its duration is not | 50 // stream. Used to estimate the duration of a buffer if its duration is not |
| 51 // known. | 51 // known. |
| 52 typedef base::Callback<base::TimeDelta()> InterbufferDistanceCB; | 52 typedef base::Callback<base::TimeDelta()> InterbufferDistanceCB; |
| 53 | 53 |
| 54 // Creates a source buffer range with |new_buffers|. |new_buffers| cannot be | 54 // Creates a source buffer range with |new_buffers|. |new_buffers| cannot be |
| 55 // empty and the front of |new_buffers| must be a keyframe. | 55 // empty and the front of |new_buffers| must be a keyframe. |
| 56 // |media_segment_start_time| refers to the starting timestamp for the media | 56 // |media_segment_start_time| refers to the starting timestamp for the media |
| 57 // segment to which these buffers belong. | 57 // segment to which these buffers belong. |
| 58 SourceBufferRange(SourceBufferStream::Type type, | 58 SourceBufferRange(SourceBufferStream::Type type, |
| 59 const BufferQueue& new_buffers, | 59 const BufferQueue& new_buffers, |
| 60 base::TimeDelta media_segment_start_time, | 60 DecodeTimestamp media_segment_start_time, |
| 61 const InterbufferDistanceCB& interbuffer_distance_cb); | 61 const InterbufferDistanceCB& interbuffer_distance_cb); |
| 62 | 62 |
| 63 // Appends |buffers| to the end of the range and updates |keyframe_map_| as | 63 // Appends |buffers| to the end of the range and updates |keyframe_map_| as |
| 64 // it encounters new keyframes. Assumes |buffers| belongs at the end of the | 64 // it encounters new keyframes. Assumes |buffers| belongs at the end of the |
| 65 // range. | 65 // range. |
| 66 void AppendBuffersToEnd(const BufferQueue& buffers); | 66 void AppendBuffersToEnd(const BufferQueue& buffers); |
| 67 bool CanAppendBuffersToEnd(const BufferQueue& buffers) const; | 67 bool CanAppendBuffersToEnd(const BufferQueue& buffers) const; |
| 68 | 68 |
| 69 // Appends the buffers from |range| into this range. | 69 // Appends the buffers from |range| into this range. |
| 70 // The first buffer in |range| must come directly after the last buffer | 70 // The first buffer in |range| must come directly after the last buffer |
| 71 // in this range. | 71 // in this range. |
| 72 // If |transfer_current_position| is true, |range|'s |next_buffer_index_| | 72 // If |transfer_current_position| is true, |range|'s |next_buffer_index_| |
| 73 // is transfered to this SourceBufferRange. | 73 // is transfered to this SourceBufferRange. |
| 74 void AppendRangeToEnd(const SourceBufferRange& range, | 74 void AppendRangeToEnd(const SourceBufferRange& range, |
| 75 bool transfer_current_position); | 75 bool transfer_current_position); |
| 76 bool CanAppendRangeToEnd(const SourceBufferRange& range) const; | 76 bool CanAppendRangeToEnd(const SourceBufferRange& range) const; |
| 77 | 77 |
| 78 // Updates |next_buffer_index_| to point to the Buffer containing |timestamp|. | 78 // Updates |next_buffer_index_| to point to the Buffer containing |timestamp|. |
| 79 // Assumes |timestamp| is valid and in this range. | 79 // Assumes |timestamp| is valid and in this range. |
| 80 void Seek(base::TimeDelta timestamp); | 80 void Seek(DecodeTimestamp timestamp); |
|
wolenetz
2014/08/08 21:30:05
Ditto of .h: If eventual intent is to use PTS, use
acolwell GONE FROM CHROMIUM
2014/08/11 17:05:06
Ditto. These changes document current flow of DTS
wolenetz
2014/08/12 00:09:00
Acknowledged.
| |
| 81 | 81 |
| 82 // Updates |next_buffer_index_| to point to next keyframe after or equal to | 82 // Updates |next_buffer_index_| to point to next keyframe after or equal to |
| 83 // |timestamp|. | 83 // |timestamp|. |
| 84 void SeekAheadTo(base::TimeDelta timestamp); | 84 void SeekAheadTo(DecodeTimestamp timestamp); |
| 85 | 85 |
| 86 // Updates |next_buffer_index_| to point to next keyframe strictly after | 86 // Updates |next_buffer_index_| to point to next keyframe strictly after |
| 87 // |timestamp|. | 87 // |timestamp|. |
| 88 void SeekAheadPast(base::TimeDelta timestamp); | 88 void SeekAheadPast(DecodeTimestamp timestamp); |
| 89 | 89 |
| 90 // Seeks to the beginning of the range. | 90 // Seeks to the beginning of the range. |
| 91 void SeekToStart(); | 91 void SeekToStart(); |
| 92 | 92 |
| 93 // Finds the next keyframe from |buffers_| after |timestamp| (or at | 93 // Finds the next keyframe from |buffers_| after |timestamp| (or at |
| 94 // |timestamp| if |is_exclusive| is false) and creates and returns a new | 94 // |timestamp| if |is_exclusive| is false) and creates and returns a new |
| 95 // SourceBufferRange with the buffers from that keyframe onward. | 95 // SourceBufferRange with the buffers from that keyframe onward. |
| 96 // The buffers in the new SourceBufferRange are moved out of this range. If | 96 // The buffers in the new SourceBufferRange are moved out of this range. If |
| 97 // there is no keyframe after |timestamp|, SplitRange() returns null and this | 97 // there is no keyframe after |timestamp|, SplitRange() returns null and this |
| 98 // range is unmodified. | 98 // range is unmodified. |
| 99 SourceBufferRange* SplitRange(base::TimeDelta timestamp, bool is_exclusive); | 99 SourceBufferRange* SplitRange(DecodeTimestamp timestamp, bool is_exclusive); |
| 100 | 100 |
| 101 // Deletes the buffers from this range starting at |timestamp|, exclusive if | 101 // Deletes the buffers from this range starting at |timestamp|, exclusive if |
| 102 // |is_exclusive| is true, inclusive otherwise. | 102 // |is_exclusive| is true, inclusive otherwise. |
| 103 // Resets |next_buffer_index_| if the buffer at |next_buffer_index_| was | 103 // Resets |next_buffer_index_| if the buffer at |next_buffer_index_| was |
| 104 // deleted, and deletes the |keyframe_map_| entries for the buffers that | 104 // deleted, and deletes the |keyframe_map_| entries for the buffers that |
| 105 // were removed. | 105 // were removed. |
| 106 // |deleted_buffers| contains the buffers that were deleted from this range, | 106 // |deleted_buffers| contains the buffers that were deleted from this range, |
| 107 // starting at the buffer that had been at |next_buffer_index_|. | 107 // starting at the buffer that had been at |next_buffer_index_|. |
| 108 // Returns true if everything in the range was deleted. Otherwise | 108 // Returns true if everything in the range was deleted. Otherwise |
| 109 // returns false. | 109 // returns false. |
| 110 bool TruncateAt(base::TimeDelta timestamp, | 110 bool TruncateAt(DecodeTimestamp timestamp, |
| 111 BufferQueue* deleted_buffers, bool is_exclusive); | 111 BufferQueue* deleted_buffers, bool is_exclusive); |
| 112 // Deletes all buffers in range. | 112 // Deletes all buffers in range. |
| 113 void DeleteAll(BufferQueue* deleted_buffers); | 113 void DeleteAll(BufferQueue* deleted_buffers); |
| 114 | 114 |
| 115 // Deletes a GOP from the front or back of the range and moves these | 115 // Deletes a GOP from the front or back of the range and moves these |
| 116 // buffers into |deleted_buffers|. Returns the number of bytes deleted from | 116 // buffers into |deleted_buffers|. Returns the number of bytes deleted from |
| 117 // the range (i.e. the size in bytes of |deleted_buffers|). | 117 // the range (i.e. the size in bytes of |deleted_buffers|). |
| 118 int DeleteGOPFromFront(BufferQueue* deleted_buffers); | 118 int DeleteGOPFromFront(BufferQueue* deleted_buffers); |
| 119 int DeleteGOPFromBack(BufferQueue* deleted_buffers); | 119 int DeleteGOPFromBack(BufferQueue* deleted_buffers); |
| 120 | 120 |
| 121 // Gets the range of GOP to secure at least |bytes_to_free| from | 121 // Gets the range of GOP to secure at least |bytes_to_free| from |
| 122 // [|start_timestamp|, |end_timestamp|). | 122 // [|start_timestamp|, |end_timestamp|). |
| 123 // Returns the size of the buffers to secure if the buffers of | 123 // Returns the size of the buffers to secure if the buffers of |
| 124 // [|start_timestamp|, |end_removal_timestamp|) is removed. | 124 // [|start_timestamp|, |end_removal_timestamp|) is removed. |
| 125 // Will not update |end_removal_timestamp| if the returned size is 0. | 125 // Will not update |end_removal_timestamp| if the returned size is 0. |
| 126 int GetRemovalGOP( | 126 int GetRemovalGOP( |
| 127 base::TimeDelta start_timestamp, base::TimeDelta end_timestamp, | 127 DecodeTimestamp start_timestamp, DecodeTimestamp end_timestamp, |
| 128 int bytes_to_free, base::TimeDelta* end_removal_timestamp); | 128 int bytes_to_free, DecodeTimestamp* end_removal_timestamp); |
| 129 | 129 |
| 130 // Indicates whether the GOP at the beginning or end of the range contains the | 130 // Indicates whether the GOP at the beginning or end of the range contains the |
| 131 // next buffer position. | 131 // next buffer position. |
| 132 bool FirstGOPContainsNextBufferPosition() const; | 132 bool FirstGOPContainsNextBufferPosition() const; |
| 133 bool LastGOPContainsNextBufferPosition() const; | 133 bool LastGOPContainsNextBufferPosition() const; |
| 134 | 134 |
| 135 // Updates |out_buffer| with the next buffer in presentation order. Seek() | 135 // Updates |out_buffer| with the next buffer in presentation order. Seek() |
| 136 // must be called before calls to GetNextBuffer(), and buffers are returned | 136 // must be called before calls to GetNextBuffer(), and buffers are returned |
| 137 // in order from the last call to Seek(). Returns true if |out_buffer| is | 137 // in order from the last call to Seek(). Returns true if |out_buffer| is |
| 138 // filled with a valid buffer, false if there is not enough data to fulfill | 138 // filled with a valid buffer, false if there is not enough data to fulfill |
| 139 // the request. | 139 // the request. |
| 140 bool GetNextBuffer(scoped_refptr<StreamParserBuffer>* out_buffer); | 140 bool GetNextBuffer(scoped_refptr<StreamParserBuffer>* out_buffer); |
| 141 bool HasNextBuffer() const; | 141 bool HasNextBuffer() const; |
| 142 | 142 |
| 143 // Returns the config ID for the buffer that will be returned by | 143 // Returns the config ID for the buffer that will be returned by |
| 144 // GetNextBuffer(). | 144 // GetNextBuffer(). |
| 145 int GetNextConfigId() const; | 145 int GetNextConfigId() const; |
| 146 | 146 |
| 147 // Returns true if the range knows the position of the next buffer it should | 147 // Returns true if the range knows the position of the next buffer it should |
| 148 // return, i.e. it has been Seek()ed. This does not necessarily mean that it | 148 // return, i.e. it has been Seek()ed. This does not necessarily mean that it |
| 149 // has the next buffer yet. | 149 // has the next buffer yet. |
| 150 bool HasNextBufferPosition() const; | 150 bool HasNextBufferPosition() const; |
| 151 | 151 |
| 152 // Resets this range to an "unseeked" state. | 152 // Resets this range to an "unseeked" state. |
| 153 void ResetNextBufferPosition(); | 153 void ResetNextBufferPosition(); |
| 154 | 154 |
| 155 // Returns the timestamp of the next buffer that will be returned from | 155 // Returns the timestamp of the next buffer that will be returned from |
| 156 // GetNextBuffer(), or kNoTimestamp() if the timestamp is unknown. | 156 // GetNextBuffer(), or kNoTimestamp() if the timestamp is unknown. |
| 157 base::TimeDelta GetNextTimestamp() const; | 157 DecodeTimestamp GetNextTimestamp() const; |
| 158 | 158 |
| 159 // Returns the start timestamp of the range. | 159 // Returns the start timestamp of the range. |
| 160 base::TimeDelta GetStartTimestamp() const; | 160 DecodeTimestamp GetStartTimestamp() const; |
| 161 | 161 |
| 162 // Returns the timestamp of the last buffer in the range. | 162 // Returns the timestamp of the last buffer in the range. |
| 163 base::TimeDelta GetEndTimestamp() const; | 163 DecodeTimestamp GetEndTimestamp() const; |
| 164 | 164 |
| 165 // Returns the timestamp for the end of the buffered region in this range. | 165 // Returns the timestamp for the end of the buffered region in this range. |
| 166 // This is an approximation if the duration for the last buffer in the range | 166 // This is an approximation if the duration for the last buffer in the range |
| 167 // is unset. | 167 // is unset. |
| 168 base::TimeDelta GetBufferedEndTimestamp() const; | 168 DecodeTimestamp GetBufferedEndTimestamp() const; |
| 169 | 169 |
| 170 // Gets the timestamp for the keyframe that is after |timestamp|. If | 170 // Gets the timestamp for the keyframe that is after |timestamp|. If |
| 171 // there isn't a keyframe in the range after |timestamp| then kNoTimestamp() | 171 // there isn't a keyframe in the range after |timestamp| then kNoTimestamp() |
| 172 // is returned. If |timestamp| is in the "gap" between the value returned by | 172 // is returned. If |timestamp| is in the "gap" between the value returned by |
| 173 // GetStartTimestamp() and the timestamp on the first buffer in |buffers_|, | 173 // GetStartTimestamp() and the timestamp on the first buffer in |buffers_|, |
| 174 // then |timestamp| is returned. | 174 // then |timestamp| is returned. |
| 175 base::TimeDelta NextKeyframeTimestamp(base::TimeDelta timestamp); | 175 DecodeTimestamp NextKeyframeTimestamp(DecodeTimestamp timestamp); |
| 176 | 176 |
| 177 // Gets the timestamp for the closest keyframe that is <= |timestamp|. If | 177 // Gets the timestamp for the closest keyframe that is <= |timestamp|. If |
| 178 // there isn't a keyframe before |timestamp| or |timestamp| is outside | 178 // there isn't a keyframe before |timestamp| or |timestamp| is outside |
| 179 // this range, then kNoTimestamp() is returned. | 179 // this range, then kNoTimestamp() is returned. |
| 180 base::TimeDelta KeyframeBeforeTimestamp(base::TimeDelta timestamp); | 180 DecodeTimestamp KeyframeBeforeTimestamp(DecodeTimestamp timestamp); |
| 181 | 181 |
| 182 // Returns whether a buffer with a starting timestamp of |timestamp| would | 182 // Returns whether a buffer with a starting timestamp of |timestamp| would |
| 183 // belong in this range. This includes a buffer that would be appended to | 183 // belong in this range. This includes a buffer that would be appended to |
| 184 // the end of the range. | 184 // the end of the range. |
| 185 bool BelongsToRange(base::TimeDelta timestamp) const; | 185 bool BelongsToRange(DecodeTimestamp timestamp) const; |
| 186 | 186 |
| 187 // Returns true if the range has enough data to seek to the specified | 187 // Returns true if the range has enough data to seek to the specified |
| 188 // |timestamp|, false otherwise. | 188 // |timestamp|, false otherwise. |
| 189 bool CanSeekTo(base::TimeDelta timestamp) const; | 189 bool CanSeekTo(DecodeTimestamp timestamp) const; |
| 190 | 190 |
| 191 // Returns true if this range's buffered timespan completely overlaps the | 191 // Returns true if this range's buffered timespan completely overlaps the |
| 192 // buffered timespan of |range|. | 192 // buffered timespan of |range|. |
| 193 bool CompletelyOverlaps(const SourceBufferRange& range) const; | 193 bool CompletelyOverlaps(const SourceBufferRange& range) const; |
| 194 | 194 |
| 195 // Returns true if the end of this range contains buffers that overlaps with | 195 // Returns true if the end of this range contains buffers that overlaps with |
| 196 // the beginning of |range|. | 196 // the beginning of |range|. |
| 197 bool EndOverlaps(const SourceBufferRange& range) const; | 197 bool EndOverlaps(const SourceBufferRange& range) const; |
| 198 | 198 |
| 199 // Returns true if |timestamp| is the timestamp of the next buffer in | 199 // Returns true if |timestamp| is the timestamp of the next buffer in |
| 200 // sequence after |buffers_.back()|, false otherwise. | 200 // sequence after |buffers_.back()|, false otherwise. |
| 201 bool IsNextInSequence(base::TimeDelta timestamp, bool is_keyframe) const; | 201 bool IsNextInSequence(DecodeTimestamp timestamp, bool is_keyframe) const; |
| 202 | 202 |
| 203 // Adds all buffers which overlap [start, end) to the end of |buffers|. If | 203 // Adds all buffers which overlap [start, end) to the end of |buffers|. If |
| 204 // no buffers exist in the range returns false, true otherwise. | 204 // no buffers exist in the range returns false, true otherwise. |
| 205 bool GetBuffersInRange(base::TimeDelta start, base::TimeDelta end, | 205 bool GetBuffersInRange(DecodeTimestamp start, DecodeTimestamp end, |
| 206 BufferQueue* buffers); | 206 BufferQueue* buffers); |
| 207 | 207 |
| 208 int size_in_bytes() const { return size_in_bytes_; } | 208 int size_in_bytes() const { return size_in_bytes_; } |
| 209 | 209 |
| 210 private: | 210 private: |
| 211 typedef std::map<base::TimeDelta, int> KeyframeMap; | 211 typedef std::map<DecodeTimestamp, int> KeyframeMap; |
| 212 | 212 |
| 213 // Seeks the range to the next keyframe after |timestamp|. If | 213 // Seeks the range to the next keyframe after |timestamp|. If |
| 214 // |skip_given_timestamp| is true, the seek will go to a keyframe with a | 214 // |skip_given_timestamp| is true, the seek will go to a keyframe with a |
| 215 // timestamp strictly greater than |timestamp|. | 215 // timestamp strictly greater than |timestamp|. |
| 216 void SeekAhead(base::TimeDelta timestamp, bool skip_given_timestamp); | 216 void SeekAhead(DecodeTimestamp timestamp, bool skip_given_timestamp); |
| 217 | 217 |
| 218 // Returns an iterator in |buffers_| pointing to the buffer at |timestamp|. | 218 // Returns an iterator in |buffers_| pointing to the buffer at |timestamp|. |
| 219 // If |skip_given_timestamp| is true, this returns the first buffer with | 219 // If |skip_given_timestamp| is true, this returns the first buffer with |
| 220 // timestamp greater than |timestamp|. | 220 // timestamp greater than |timestamp|. |
| 221 BufferQueue::iterator GetBufferItrAt( | 221 BufferQueue::iterator GetBufferItrAt( |
| 222 base::TimeDelta timestamp, bool skip_given_timestamp); | 222 DecodeTimestamp timestamp, bool skip_given_timestamp); |
| 223 | 223 |
| 224 // Returns an iterator in |keyframe_map_| pointing to the next keyframe after | 224 // Returns an iterator in |keyframe_map_| pointing to the next keyframe after |
| 225 // |timestamp|. If |skip_given_timestamp| is true, this returns the first | 225 // |timestamp|. If |skip_given_timestamp| is true, this returns the first |
| 226 // keyframe with a timestamp strictly greater than |timestamp|. | 226 // keyframe with a timestamp strictly greater than |timestamp|. |
| 227 KeyframeMap::iterator GetFirstKeyframeAt( | 227 KeyframeMap::iterator GetFirstKeyframeAt( |
| 228 base::TimeDelta timestamp, bool skip_given_timestamp); | 228 DecodeTimestamp timestamp, bool skip_given_timestamp); |
| 229 | 229 |
| 230 // Returns an iterator in |keyframe_map_| pointing to the first keyframe | 230 // Returns an iterator in |keyframe_map_| pointing to the first keyframe |
| 231 // before or at |timestamp|. | 231 // before or at |timestamp|. |
| 232 KeyframeMap::iterator GetFirstKeyframeBefore(base::TimeDelta timestamp); | 232 KeyframeMap::iterator GetFirstKeyframeBefore(DecodeTimestamp timestamp); |
| 233 | 233 |
| 234 // Helper method to delete buffers in |buffers_| starting at | 234 // Helper method to delete buffers in |buffers_| starting at |
| 235 // |starting_point|, an iterator in |buffers_|. | 235 // |starting_point|, an iterator in |buffers_|. |
| 236 // Returns true if everything in the range was removed. Returns | 236 // Returns true if everything in the range was removed. Returns |
| 237 // false if the range still contains buffers. | 237 // false if the range still contains buffers. |
| 238 bool TruncateAt(const BufferQueue::iterator& starting_point, | 238 bool TruncateAt(const BufferQueue::iterator& starting_point, |
| 239 BufferQueue* deleted_buffers); | 239 BufferQueue* deleted_buffers); |
| 240 | 240 |
| 241 // Frees the buffers in |buffers_| from [|start_point|,|ending_point|) and | 241 // Frees the buffers in |buffers_| from [|start_point|,|ending_point|) and |
| 242 // updates the |size_in_bytes_| accordingly. Does not update |keyframe_map_|. | 242 // updates the |size_in_bytes_| accordingly. Does not update |keyframe_map_|. |
| (...skipping 26 matching lines...) Expand all Loading... | |
| 269 int next_buffer_index_; | 269 int next_buffer_index_; |
| 270 | 270 |
| 271 // If the first buffer in this range is the beginning of a media segment, | 271 // If the first buffer in this range is the beginning of a media segment, |
| 272 // |media_segment_start_time_| is the time when the media segment begins. | 272 // |media_segment_start_time_| is the time when the media segment begins. |
| 273 // |media_segment_start_time_| may be <= the timestamp of the first buffer in | 273 // |media_segment_start_time_| may be <= the timestamp of the first buffer in |
| 274 // |buffers_|. |media_segment_start_time_| is kNoTimestamp() if this range | 274 // |buffers_|. |media_segment_start_time_| is kNoTimestamp() if this range |
| 275 // does not start at the beginning of a media segment, which can only happen | 275 // does not start at the beginning of a media segment, which can only happen |
| 276 // garbage collection or after an end overlap that results in a split range | 276 // garbage collection or after an end overlap that results in a split range |
| 277 // (we don't have a way of knowing the media segment timestamp for the new | 277 // (we don't have a way of knowing the media segment timestamp for the new |
| 278 // range). | 278 // range). |
| 279 base::TimeDelta media_segment_start_time_; | 279 DecodeTimestamp media_segment_start_time_; |
| 280 | 280 |
| 281 // Called to get the largest interbuffer distance seen so far in the stream. | 281 // Called to get the largest interbuffer distance seen so far in the stream. |
| 282 InterbufferDistanceCB interbuffer_distance_cb_; | 282 InterbufferDistanceCB interbuffer_distance_cb_; |
| 283 | 283 |
| 284 // Stores the amount of memory taken up by the data in |buffers_|. | 284 // Stores the amount of memory taken up by the data in |buffers_|. |
| 285 int size_in_bytes_; | 285 int size_in_bytes_; |
| 286 | 286 |
| 287 DISALLOW_COPY_AND_ASSIGN(SourceBufferRange); | 287 DISALLOW_COPY_AND_ASSIGN(SourceBufferRange); |
| 288 }; | 288 }; |
| 289 | 289 |
| 290 } // namespace media | |
| 291 | |
| 292 // Helper method that returns true if |ranges| is sorted in increasing order, | 290 // Helper method that returns true if |ranges| is sorted in increasing order, |
| 293 // false otherwise. | 291 // false otherwise. |
| 294 static bool IsRangeListSorted( | 292 static bool IsRangeListSorted( |
| 295 const std::list<media::SourceBufferRange*>& ranges) { | 293 const std::list<media::SourceBufferRange*>& ranges) { |
| 296 base::TimeDelta prev = media::kNoTimestamp(); | 294 DecodeTimestamp prev = kNoDecodeTimestamp(); |
| 297 for (std::list<media::SourceBufferRange*>::const_iterator itr = | 295 for (std::list<SourceBufferRange*>::const_iterator itr = |
| 298 ranges.begin(); itr != ranges.end(); ++itr) { | 296 ranges.begin(); itr != ranges.end(); ++itr) { |
| 299 if (prev != media::kNoTimestamp() && prev >= (*itr)->GetStartTimestamp()) | 297 if (prev != kNoDecodeTimestamp() && prev >= (*itr)->GetStartTimestamp()) |
| 300 return false; | 298 return false; |
| 301 prev = (*itr)->GetEndTimestamp(); | 299 prev = (*itr)->GetEndTimestamp(); |
| 302 } | 300 } |
| 303 return true; | 301 return true; |
| 304 } | 302 } |
| 305 | 303 |
| 306 // Comparison operators for std::upper_bound() and std::lower_bound(). | 304 // Comparison operators for std::upper_bound() and std::lower_bound(). |
| 307 static bool CompareTimeDeltaToStreamParserBuffer( | 305 static bool CompareTimeDeltaToStreamParserBuffer( |
| 308 const base::TimeDelta& decode_timestamp, | 306 const media::DecodeTimestamp& decode_timestamp, |
| 309 const scoped_refptr<media::StreamParserBuffer>& buffer) { | 307 const scoped_refptr<StreamParserBuffer>& buffer) { |
| 310 return decode_timestamp < buffer->GetDecodeTimestamp(); | 308 return decode_timestamp < buffer->GetDecodeTimestamp(); |
| 311 } | 309 } |
| 312 static bool CompareStreamParserBufferToTimeDelta( | 310 static bool CompareStreamParserBufferToTimeDelta( |
| 313 const scoped_refptr<media::StreamParserBuffer>& buffer, | 311 const scoped_refptr<StreamParserBuffer>& buffer, |
| 314 const base::TimeDelta& decode_timestamp) { | 312 const DecodeTimestamp& decode_timestamp) { |
| 315 return buffer->GetDecodeTimestamp() < decode_timestamp; | 313 return buffer->GetDecodeTimestamp() < decode_timestamp; |
| 316 } | 314 } |
| 317 | 315 |
| 318 // Returns an estimate of how far from the beginning or end of a range a buffer | 316 // Returns an estimate of how far from the beginning or end of a range a buffer |
| 319 // can be to still be considered in the range, given the |approximate_duration| | 317 // can be to still be considered in the range, given the |approximate_duration| |
| 320 // of a buffer in the stream. | 318 // of a buffer in the stream. |
| 321 static base::TimeDelta ComputeFudgeRoom(base::TimeDelta approximate_duration) { | 319 static base::TimeDelta ComputeFudgeRoom(base::TimeDelta approximate_duration) { |
| 322 // Because we do not know exactly when is the next timestamp, any buffer | 320 // Because we do not know exactly when is the next timestamp, any buffer |
| 323 // that starts within 2x the approximate duration of a buffer is considered | 321 // that starts within 2x the approximate duration of a buffer is considered |
| 324 // within this range. | 322 // within this range. |
| 325 return 2 * approximate_duration; | 323 return 2 * approximate_duration; |
| 326 } | 324 } |
| 327 | 325 |
| 328 // An arbitrarily-chosen number to estimate the duration of a buffer if none | 326 // An arbitrarily-chosen number to estimate the duration of a buffer if none |
| 329 // is set and there's not enough information to get a better estimate. | 327 // is set and there's not enough information to get a better estimate. |
| 330 static int kDefaultBufferDurationInMs = 125; | 328 static int kDefaultBufferDurationInMs = 125; |
| 331 | 329 |
| 332 // The amount of time the beginning of the buffered data can differ from the | 330 // The amount of time the beginning of the buffered data can differ from the |
| 333 // start time in order to still be considered the start of stream. | 331 // start time in order to still be considered the start of stream. |
| 334 static base::TimeDelta kSeekToStartFudgeRoom() { | 332 static base::TimeDelta kSeekToStartFudgeRoom() { |
| 335 return base::TimeDelta::FromMilliseconds(1000); | 333 return base::TimeDelta::FromMilliseconds(1000); |
| 336 } | 334 } |
| 337 | 335 |
| 338 namespace media { | |
| 339 | |
| 340 SourceBufferStream::SourceBufferStream(const AudioDecoderConfig& audio_config, | 336 SourceBufferStream::SourceBufferStream(const AudioDecoderConfig& audio_config, |
| 341 const LogCB& log_cb, | 337 const LogCB& log_cb, |
| 342 bool splice_frames_enabled) | 338 bool splice_frames_enabled) |
| 343 : log_cb_(log_cb), | 339 : log_cb_(log_cb), |
| 344 current_config_index_(0), | 340 current_config_index_(0), |
| 345 append_config_index_(0), | 341 append_config_index_(0), |
| 346 seek_pending_(false), | 342 seek_pending_(false), |
| 347 end_of_stream_(false), | 343 end_of_stream_(false), |
| 348 seek_buffer_timestamp_(kNoTimestamp()), | 344 seek_buffer_timestamp_(kNoTimestamp()), |
| 349 selected_range_(NULL), | 345 selected_range_(NULL), |
| 350 media_segment_start_time_(kNoTimestamp()), | 346 media_segment_start_time_(kNoDecodeTimestamp()), |
| 351 range_for_next_append_(ranges_.end()), | 347 range_for_next_append_(ranges_.end()), |
| 352 new_media_segment_(false), | 348 new_media_segment_(false), |
| 353 last_appended_buffer_timestamp_(kNoTimestamp()), | 349 last_appended_buffer_timestamp_(kNoDecodeTimestamp()), |
| 354 last_appended_buffer_is_keyframe_(false), | 350 last_appended_buffer_is_keyframe_(false), |
| 355 last_output_buffer_timestamp_(kNoTimestamp()), | 351 last_output_buffer_timestamp_(kNoDecodeTimestamp()), |
| 356 max_interbuffer_distance_(kNoTimestamp()), | 352 max_interbuffer_distance_(kNoTimestamp()), |
| 357 memory_limit_(kSourceBufferAudioMemoryLimit), | 353 memory_limit_(kSourceBufferAudioMemoryLimit), |
| 358 config_change_pending_(false), | 354 config_change_pending_(false), |
| 359 splice_buffers_index_(0), | 355 splice_buffers_index_(0), |
| 360 pending_buffers_complete_(false), | 356 pending_buffers_complete_(false), |
| 361 splice_frames_enabled_(splice_frames_enabled) { | 357 splice_frames_enabled_(splice_frames_enabled) { |
| 362 DCHECK(audio_config.IsValidConfig()); | 358 DCHECK(audio_config.IsValidConfig()); |
| 363 audio_configs_.push_back(audio_config); | 359 audio_configs_.push_back(audio_config); |
| 364 } | 360 } |
| 365 | 361 |
| 366 SourceBufferStream::SourceBufferStream(const VideoDecoderConfig& video_config, | 362 SourceBufferStream::SourceBufferStream(const VideoDecoderConfig& video_config, |
| 367 const LogCB& log_cb, | 363 const LogCB& log_cb, |
| 368 bool splice_frames_enabled) | 364 bool splice_frames_enabled) |
| 369 : log_cb_(log_cb), | 365 : log_cb_(log_cb), |
| 370 current_config_index_(0), | 366 current_config_index_(0), |
| 371 append_config_index_(0), | 367 append_config_index_(0), |
| 372 seek_pending_(false), | 368 seek_pending_(false), |
| 373 end_of_stream_(false), | 369 end_of_stream_(false), |
| 374 seek_buffer_timestamp_(kNoTimestamp()), | 370 seek_buffer_timestamp_(kNoTimestamp()), |
| 375 selected_range_(NULL), | 371 selected_range_(NULL), |
| 376 media_segment_start_time_(kNoTimestamp()), | 372 media_segment_start_time_(kNoDecodeTimestamp()), |
| 377 range_for_next_append_(ranges_.end()), | 373 range_for_next_append_(ranges_.end()), |
| 378 new_media_segment_(false), | 374 new_media_segment_(false), |
| 379 last_appended_buffer_timestamp_(kNoTimestamp()), | 375 last_appended_buffer_timestamp_(kNoDecodeTimestamp()), |
| 380 last_appended_buffer_is_keyframe_(false), | 376 last_appended_buffer_is_keyframe_(false), |
| 381 last_output_buffer_timestamp_(kNoTimestamp()), | 377 last_output_buffer_timestamp_(kNoDecodeTimestamp()), |
| 382 max_interbuffer_distance_(kNoTimestamp()), | 378 max_interbuffer_distance_(kNoTimestamp()), |
| 383 memory_limit_(kSourceBufferVideoMemoryLimit), | 379 memory_limit_(kSourceBufferVideoMemoryLimit), |
| 384 config_change_pending_(false), | 380 config_change_pending_(false), |
| 385 splice_buffers_index_(0), | 381 splice_buffers_index_(0), |
| 386 pending_buffers_complete_(false), | 382 pending_buffers_complete_(false), |
| 387 splice_frames_enabled_(splice_frames_enabled) { | 383 splice_frames_enabled_(splice_frames_enabled) { |
| 388 DCHECK(video_config.IsValidConfig()); | 384 DCHECK(video_config.IsValidConfig()); |
| 389 video_configs_.push_back(video_config); | 385 video_configs_.push_back(video_config); |
| 390 } | 386 } |
| 391 | 387 |
| 392 SourceBufferStream::SourceBufferStream(const TextTrackConfig& text_config, | 388 SourceBufferStream::SourceBufferStream(const TextTrackConfig& text_config, |
| 393 const LogCB& log_cb, | 389 const LogCB& log_cb, |
| 394 bool splice_frames_enabled) | 390 bool splice_frames_enabled) |
| 395 : log_cb_(log_cb), | 391 : log_cb_(log_cb), |
| 396 current_config_index_(0), | 392 current_config_index_(0), |
| 397 append_config_index_(0), | 393 append_config_index_(0), |
| 398 text_track_config_(text_config), | 394 text_track_config_(text_config), |
| 399 seek_pending_(false), | 395 seek_pending_(false), |
| 400 end_of_stream_(false), | 396 end_of_stream_(false), |
| 401 seek_buffer_timestamp_(kNoTimestamp()), | 397 seek_buffer_timestamp_(kNoTimestamp()), |
| 402 selected_range_(NULL), | 398 selected_range_(NULL), |
| 403 media_segment_start_time_(kNoTimestamp()), | 399 media_segment_start_time_(kNoDecodeTimestamp()), |
| 404 range_for_next_append_(ranges_.end()), | 400 range_for_next_append_(ranges_.end()), |
| 405 new_media_segment_(false), | 401 new_media_segment_(false), |
| 406 last_appended_buffer_timestamp_(kNoTimestamp()), | 402 last_appended_buffer_timestamp_(kNoDecodeTimestamp()), |
| 407 last_appended_buffer_is_keyframe_(false), | 403 last_appended_buffer_is_keyframe_(false), |
| 408 last_output_buffer_timestamp_(kNoTimestamp()), | 404 last_output_buffer_timestamp_(kNoDecodeTimestamp()), |
| 409 max_interbuffer_distance_(kNoTimestamp()), | 405 max_interbuffer_distance_(kNoTimestamp()), |
| 410 memory_limit_(kSourceBufferAudioMemoryLimit), | 406 memory_limit_(kSourceBufferAudioMemoryLimit), |
| 411 config_change_pending_(false), | 407 config_change_pending_(false), |
| 412 splice_buffers_index_(0), | 408 splice_buffers_index_(0), |
| 413 pending_buffers_complete_(false), | 409 pending_buffers_complete_(false), |
| 414 splice_frames_enabled_(splice_frames_enabled) {} | 410 splice_frames_enabled_(splice_frames_enabled) {} |
| 415 | 411 |
| 416 SourceBufferStream::~SourceBufferStream() { | 412 SourceBufferStream::~SourceBufferStream() { |
| 417 while (!ranges_.empty()) { | 413 while (!ranges_.empty()) { |
| 418 delete ranges_.front(); | 414 delete ranges_.front(); |
| 419 ranges_.pop_front(); | 415 ranges_.pop_front(); |
| 420 } | 416 } |
| 421 } | 417 } |
| 422 | 418 |
| 423 void SourceBufferStream::OnNewMediaSegment( | 419 void SourceBufferStream::OnNewMediaSegment( |
| 424 base::TimeDelta media_segment_start_time) { | 420 DecodeTimestamp media_segment_start_time) { |
| 425 DCHECK(!end_of_stream_); | 421 DCHECK(!end_of_stream_); |
| 426 media_segment_start_time_ = media_segment_start_time; | 422 media_segment_start_time_ = media_segment_start_time; |
| 427 new_media_segment_ = true; | 423 new_media_segment_ = true; |
| 428 | 424 |
| 429 RangeList::iterator last_range = range_for_next_append_; | 425 RangeList::iterator last_range = range_for_next_append_; |
| 430 range_for_next_append_ = FindExistingRangeFor(media_segment_start_time); | 426 range_for_next_append_ = FindExistingRangeFor(media_segment_start_time); |
| 431 | 427 |
| 432 // Only reset |last_appended_buffer_timestamp_| if this new media segment is | 428 // Only reset |last_appended_buffer_timestamp_| if this new media segment is |
| 433 // not adjacent to the previous media segment appended to the stream. | 429 // not adjacent to the previous media segment appended to the stream. |
| 434 if (range_for_next_append_ == ranges_.end() || | 430 if (range_for_next_append_ == ranges_.end() || |
| 435 !AreAdjacentInSequence(last_appended_buffer_timestamp_, | 431 !AreAdjacentInSequence(last_appended_buffer_timestamp_, |
| 436 media_segment_start_time)) { | 432 media_segment_start_time)) { |
| 437 last_appended_buffer_timestamp_ = kNoTimestamp(); | 433 last_appended_buffer_timestamp_ = kNoDecodeTimestamp(); |
| 438 last_appended_buffer_is_keyframe_ = false; | 434 last_appended_buffer_is_keyframe_ = false; |
| 439 } else if (last_range != ranges_.end()) { | 435 } else if (last_range != ranges_.end()) { |
| 440 DCHECK(last_range == range_for_next_append_); | 436 DCHECK(last_range == range_for_next_append_); |
| 441 } | 437 } |
| 442 } | 438 } |
| 443 | 439 |
| 444 bool SourceBufferStream::Append(const BufferQueue& buffers) { | 440 bool SourceBufferStream::Append(const BufferQueue& buffers) { |
| 445 TRACE_EVENT2("media", "SourceBufferStream::Append", | 441 TRACE_EVENT2("media", "SourceBufferStream::Append", |
| 446 "stream type", GetStreamTypeName(), | 442 "stream type", GetStreamTypeName(), |
| 447 "buffers to append", buffers.size()); | 443 "buffers to append", buffers.size()); |
| 448 | 444 |
| 449 DCHECK(!buffers.empty()); | 445 DCHECK(!buffers.empty()); |
| 450 DCHECK(media_segment_start_time_ != kNoTimestamp()); | 446 DCHECK(media_segment_start_time_ != kNoDecodeTimestamp()); |
| 451 DCHECK(media_segment_start_time_ <= buffers.front()->GetDecodeTimestamp()); | 447 DCHECK(media_segment_start_time_ <= buffers.front()->GetDecodeTimestamp()); |
| 452 DCHECK(!end_of_stream_); | 448 DCHECK(!end_of_stream_); |
| 453 | 449 |
| 454 // New media segments must begin with a keyframe. | 450 // New media segments must begin with a keyframe. |
| 455 if (new_media_segment_ && !buffers.front()->IsKeyframe()) { | 451 if (new_media_segment_ && !buffers.front()->IsKeyframe()) { |
| 456 MEDIA_LOG(log_cb_) << "Media segment did not begin with keyframe."; | 452 MEDIA_LOG(log_cb_) << "Media segment did not begin with keyframe."; |
| 457 return false; | 453 return false; |
| 458 } | 454 } |
| 459 | 455 |
| 460 // Buffers within a media segment should be monotonically increasing. | 456 // Buffers within a media segment should be monotonically increasing. |
| 461 if (!IsMonotonicallyIncreasing(buffers)) | 457 if (!IsMonotonicallyIncreasing(buffers)) |
| 462 return false; | 458 return false; |
| 463 | 459 |
| 464 if (media_segment_start_time_ < base::TimeDelta() || | 460 if (media_segment_start_time_ < DecodeTimestamp() || |
| 465 buffers.front()->GetDecodeTimestamp() < base::TimeDelta()) { | 461 buffers.front()->GetDecodeTimestamp() < DecodeTimestamp()) { |
| 466 MEDIA_LOG(log_cb_) | 462 MEDIA_LOG(log_cb_) |
| 467 << "Cannot append a media segment with negative timestamps."; | 463 << "Cannot append a media segment with negative timestamps."; |
| 468 return false; | 464 return false; |
| 469 } | 465 } |
| 470 | 466 |
| 471 if (!IsNextTimestampValid(buffers.front()->GetDecodeTimestamp(), | 467 if (!IsNextTimestampValid(buffers.front()->GetDecodeTimestamp(), |
| 472 buffers.front()->IsKeyframe())) { | 468 buffers.front()->IsKeyframe())) { |
| 473 MEDIA_LOG(log_cb_) << "Invalid same timestamp construct detected at time " | 469 MEDIA_LOG(log_cb_) << "Invalid same timestamp construct detected at time " |
| 474 << buffers.front()->GetDecodeTimestamp().InSecondsF(); | 470 << buffers.front()->GetDecodeTimestamp().InSecondsF(); |
| 475 | 471 |
| 476 return false; | 472 return false; |
| 477 } | 473 } |
| 478 | 474 |
| 479 UpdateMaxInterbufferDistance(buffers); | 475 UpdateMaxInterbufferDistance(buffers); |
| 480 SetConfigIds(buffers); | 476 SetConfigIds(buffers); |
| 481 | 477 |
| 482 // Save a snapshot of stream state before range modifications are made. | 478 // Save a snapshot of stream state before range modifications are made. |
| 483 base::TimeDelta next_buffer_timestamp = GetNextBufferTimestamp(); | 479 DecodeTimestamp next_buffer_timestamp = GetNextBufferTimestamp(); |
| 484 BufferQueue deleted_buffers; | 480 BufferQueue deleted_buffers; |
| 485 | 481 |
| 486 PrepareRangesForNextAppend(buffers, &deleted_buffers); | 482 PrepareRangesForNextAppend(buffers, &deleted_buffers); |
| 487 | 483 |
| 488 // If there's a range for |buffers|, insert |buffers| accordingly. Otherwise, | 484 // If there's a range for |buffers|, insert |buffers| accordingly. Otherwise, |
| 489 // create a new range with |buffers|. | 485 // create a new range with |buffers|. |
| 490 if (range_for_next_append_ != ranges_.end()) { | 486 if (range_for_next_append_ != ranges_.end()) { |
| 491 (*range_for_next_append_)->AppendBuffersToEnd(buffers); | 487 (*range_for_next_append_)->AppendBuffersToEnd(buffers); |
| 492 last_appended_buffer_timestamp_ = buffers.back()->GetDecodeTimestamp(); | 488 last_appended_buffer_timestamp_ = buffers.back()->GetDecodeTimestamp(); |
| 493 last_appended_buffer_is_keyframe_ = buffers.back()->IsKeyframe(); | 489 last_appended_buffer_is_keyframe_ = buffers.back()->IsKeyframe(); |
| 494 } else { | 490 } else { |
| 495 base::TimeDelta new_range_start_time = std::min( | 491 DecodeTimestamp new_range_start_time = std::min( |
| 496 media_segment_start_time_, buffers.front()->GetDecodeTimestamp()); | 492 media_segment_start_time_, buffers.front()->GetDecodeTimestamp()); |
| 497 const BufferQueue* buffers_for_new_range = &buffers; | 493 const BufferQueue* buffers_for_new_range = &buffers; |
| 498 BufferQueue trimmed_buffers; | 494 BufferQueue trimmed_buffers; |
| 499 | 495 |
| 500 // If the new range is not being created because of a new media | 496 // If the new range is not being created because of a new media |
| 501 // segment, then we must make sure that we start with a keyframe. | 497 // segment, then we must make sure that we start with a keyframe. |
| 502 // This can happen if the GOP in the previous append gets destroyed | 498 // This can happen if the GOP in the previous append gets destroyed |
| 503 // by a Remove() call. | 499 // by a Remove() call. |
| 504 if (!new_media_segment_) { | 500 if (!new_media_segment_) { |
| 505 BufferQueue::const_iterator itr = buffers.begin(); | 501 BufferQueue::const_iterator itr = buffers.begin(); |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 542 MergeWithAdjacentRangeIfNecessary(range_for_next_append_); | 538 MergeWithAdjacentRangeIfNecessary(range_for_next_append_); |
| 543 | 539 |
| 544 // Seek to try to fulfill a previous call to Seek(). | 540 // Seek to try to fulfill a previous call to Seek(). |
| 545 if (seek_pending_) { | 541 if (seek_pending_) { |
| 546 DCHECK(!selected_range_); | 542 DCHECK(!selected_range_); |
| 547 DCHECK(deleted_buffers.empty()); | 543 DCHECK(deleted_buffers.empty()); |
| 548 Seek(seek_buffer_timestamp_); | 544 Seek(seek_buffer_timestamp_); |
| 549 } | 545 } |
| 550 | 546 |
| 551 if (!deleted_buffers.empty()) { | 547 if (!deleted_buffers.empty()) { |
| 552 base::TimeDelta start_of_deleted = | 548 DecodeTimestamp start_of_deleted = |
| 553 deleted_buffers.front()->GetDecodeTimestamp(); | 549 deleted_buffers.front()->GetDecodeTimestamp(); |
| 554 | 550 |
| 555 DCHECK(track_buffer_.empty() || | 551 DCHECK(track_buffer_.empty() || |
| 556 track_buffer_.back()->GetDecodeTimestamp() < start_of_deleted) | 552 track_buffer_.back()->GetDecodeTimestamp() < start_of_deleted) |
| 557 << "decode timestamp " | 553 << "decode timestamp " |
| 558 << track_buffer_.back()->GetDecodeTimestamp().InSecondsF() << " sec" | 554 << track_buffer_.back()->GetDecodeTimestamp().InSecondsF() << " sec" |
| 559 << ", start_of_deleted " << start_of_deleted.InSecondsF()<< " sec"; | 555 << ", start_of_deleted " << start_of_deleted.InSecondsF()<< " sec"; |
| 560 | 556 |
| 561 track_buffer_.insert(track_buffer_.end(), deleted_buffers.begin(), | 557 track_buffer_.insert(track_buffer_.end(), deleted_buffers.begin(), |
| 562 deleted_buffers.end()); | 558 deleted_buffers.end()); |
| 563 } | 559 } |
| 564 | 560 |
| 565 // Prune any extra buffers in |track_buffer_| if new keyframes | 561 // Prune any extra buffers in |track_buffer_| if new keyframes |
| 566 // are appended to the range covered by |track_buffer_|. | 562 // are appended to the range covered by |track_buffer_|. |
| 567 if (!track_buffer_.empty()) { | 563 if (!track_buffer_.empty()) { |
| 568 base::TimeDelta keyframe_timestamp = | 564 DecodeTimestamp keyframe_timestamp = |
| 569 FindKeyframeAfterTimestamp(track_buffer_.front()->GetDecodeTimestamp()); | 565 FindKeyframeAfterTimestamp(track_buffer_.front()->GetDecodeTimestamp()); |
| 570 if (keyframe_timestamp != kNoTimestamp()) | 566 if (keyframe_timestamp != kNoDecodeTimestamp()) |
| 571 PruneTrackBuffer(keyframe_timestamp); | 567 PruneTrackBuffer(keyframe_timestamp); |
| 572 } | 568 } |
| 573 | 569 |
| 574 SetSelectedRangeIfNeeded(next_buffer_timestamp); | 570 SetSelectedRangeIfNeeded(next_buffer_timestamp); |
| 575 | 571 |
| 576 GarbageCollectIfNeeded(); | 572 GarbageCollectIfNeeded(); |
| 577 | 573 |
| 578 DCHECK(IsRangeListSorted(ranges_)); | 574 DCHECK(IsRangeListSorted(ranges_)); |
| 579 DCHECK(OnlySelectedRangeIsSeeked()); | 575 DCHECK(OnlySelectedRangeIsSeeked()); |
| 580 return true; | 576 return true; |
| 581 } | 577 } |
| 582 | 578 |
| 583 void SourceBufferStream::Remove(base::TimeDelta start, base::TimeDelta end, | 579 void SourceBufferStream::Remove(base::TimeDelta start, base::TimeDelta end, |
| 584 base::TimeDelta duration) { | 580 base::TimeDelta duration) { |
| 585 DVLOG(1) << __FUNCTION__ << "(" << start.InSecondsF() | 581 DVLOG(1) << __FUNCTION__ << "(" << start.InSecondsF() |
| 586 << ", " << end.InSecondsF() | 582 << ", " << end.InSecondsF() |
| 587 << ", " << duration.InSecondsF() << ")"; | 583 << ", " << duration.InSecondsF() << ")"; |
| 588 DCHECK(start >= base::TimeDelta()) << start.InSecondsF(); | 584 DCHECK(start >= base::TimeDelta()) << start.InSecondsF(); |
| 589 DCHECK(start < end) << "start " << start.InSecondsF() | 585 DCHECK(start < end) << "start " << start.InSecondsF() |
| 590 << " end " << end.InSecondsF(); | 586 << " end " << end.InSecondsF(); |
| 591 DCHECK(duration != kNoTimestamp()); | 587 DCHECK(duration != kNoTimestamp()); |
| 592 | 588 |
| 593 base::TimeDelta remove_end_timestamp = duration; | 589 DecodeTimestamp start_dts = DecodeTimestamp::FromPresentationTime(start); |
| 594 base::TimeDelta keyframe_timestamp = FindKeyframeAfterTimestamp(end); | 590 DecodeTimestamp end_dts = DecodeTimestamp::FromPresentationTime(end); |
| 595 if (keyframe_timestamp != kNoTimestamp()) { | 591 DecodeTimestamp remove_end_timestamp = |
| 592 DecodeTimestamp::FromPresentationTime(duration); | |
| 593 DecodeTimestamp keyframe_timestamp = FindKeyframeAfterTimestamp(end_dts); | |
| 594 if (keyframe_timestamp != kNoDecodeTimestamp()) { | |
| 596 remove_end_timestamp = keyframe_timestamp; | 595 remove_end_timestamp = keyframe_timestamp; |
| 597 } else if (end < remove_end_timestamp) { | 596 } else if (end_dts < remove_end_timestamp) { |
| 598 remove_end_timestamp = end; | 597 remove_end_timestamp = end_dts; |
| 599 } | 598 } |
| 600 | 599 |
| 601 BufferQueue deleted_buffers; | 600 BufferQueue deleted_buffers; |
| 602 RemoveInternal(start, remove_end_timestamp, false, &deleted_buffers); | 601 RemoveInternal(start_dts, remove_end_timestamp, false, &deleted_buffers); |
| 603 | 602 |
| 604 if (!deleted_buffers.empty()) | 603 if (!deleted_buffers.empty()) |
| 605 SetSelectedRangeIfNeeded(deleted_buffers.front()->GetDecodeTimestamp()); | 604 SetSelectedRangeIfNeeded(deleted_buffers.front()->GetDecodeTimestamp()); |
| 606 } | 605 } |
| 607 | 606 |
| 608 void SourceBufferStream::RemoveInternal( | 607 void SourceBufferStream::RemoveInternal( |
| 609 base::TimeDelta start, base::TimeDelta end, bool is_exclusive, | 608 DecodeTimestamp start, DecodeTimestamp end, bool is_exclusive, |
| 610 BufferQueue* deleted_buffers) { | 609 BufferQueue* deleted_buffers) { |
| 611 DVLOG(1) << __FUNCTION__ << "(" << start.InSecondsF() | 610 DVLOG(1) << __FUNCTION__ << "(" << start.InSecondsF() |
| 612 << ", " << end.InSecondsF() | 611 << ", " << end.InSecondsF() |
| 613 << ", " << is_exclusive << ")"; | 612 << ", " << is_exclusive << ")"; |
| 614 | 613 |
| 615 DCHECK(start >= base::TimeDelta()); | 614 DCHECK(start >= DecodeTimestamp()); |
| 616 DCHECK(start < end) << "start " << start.InSecondsF() | 615 DCHECK(start < end) << "start " << start.InSecondsF() |
| 617 << " end " << end.InSecondsF(); | 616 << " end " << end.InSecondsF(); |
| 618 DCHECK(deleted_buffers); | 617 DCHECK(deleted_buffers); |
| 619 | 618 |
| 620 RangeList::iterator itr = ranges_.begin(); | 619 RangeList::iterator itr = ranges_.begin(); |
| 621 | 620 |
| 622 while (itr != ranges_.end()) { | 621 while (itr != ranges_.end()) { |
| 623 SourceBufferRange* range = *itr; | 622 SourceBufferRange* range = *itr; |
| 624 if (range->GetStartTimestamp() >= end) | 623 if (range->GetStartTimestamp() >= end) |
| 625 break; | 624 break; |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 658 if (delete_range) { | 657 if (delete_range) { |
| 659 DeleteAndRemoveRange(&itr); | 658 DeleteAndRemoveRange(&itr); |
| 660 continue; | 659 continue; |
| 661 } | 660 } |
| 662 | 661 |
| 663 // Clear |range_for_next_append_| if we determine that the removal | 662 // Clear |range_for_next_append_| if we determine that the removal |
| 664 // operation makes it impossible for the next append to be added | 663 // operation makes it impossible for the next append to be added |
| 665 // to the current range. | 664 // to the current range. |
| 666 if (range_for_next_append_ != ranges_.end() && | 665 if (range_for_next_append_ != ranges_.end() && |
| 667 *range_for_next_append_ == range && | 666 *range_for_next_append_ == range && |
| 668 last_appended_buffer_timestamp_ != kNoTimestamp()) { | 667 last_appended_buffer_timestamp_ != kNoDecodeTimestamp()) { |
| 669 base::TimeDelta potential_next_append_timestamp = | 668 DecodeTimestamp potential_next_append_timestamp = |
| 670 last_appended_buffer_timestamp_ + | 669 last_appended_buffer_timestamp_ + |
| 671 base::TimeDelta::FromInternalValue(1); | 670 base::TimeDelta::FromInternalValue(1); |
| 672 | 671 |
| 673 if (!range->BelongsToRange(potential_next_append_timestamp)) { | 672 if (!range->BelongsToRange(potential_next_append_timestamp)) { |
| 674 DVLOG(1) << "Resetting range_for_next_append_ since the next append" | 673 DVLOG(1) << "Resetting range_for_next_append_ since the next append" |
| 675 << " can't add to the current range."; | 674 << " can't add to the current range."; |
| 676 range_for_next_append_ = | 675 range_for_next_append_ = |
| 677 FindExistingRangeFor(potential_next_append_timestamp); | 676 FindExistingRangeFor(potential_next_append_timestamp); |
| 678 } | 677 } |
| 679 } | 678 } |
| 680 | 679 |
| 681 // Move on to the next range. | 680 // Move on to the next range. |
| 682 ++itr; | 681 ++itr; |
| 683 } | 682 } |
| 684 | 683 |
| 685 DCHECK(IsRangeListSorted(ranges_)); | 684 DCHECK(IsRangeListSorted(ranges_)); |
| 686 DCHECK(OnlySelectedRangeIsSeeked()); | 685 DCHECK(OnlySelectedRangeIsSeeked()); |
| 687 DVLOG(1) << __FUNCTION__ << " : done"; | 686 DVLOG(1) << __FUNCTION__ << " : done"; |
| 688 } | 687 } |
| 689 | 688 |
| 690 void SourceBufferStream::ResetSeekState() { | 689 void SourceBufferStream::ResetSeekState() { |
| 691 SetSelectedRange(NULL); | 690 SetSelectedRange(NULL); |
| 692 track_buffer_.clear(); | 691 track_buffer_.clear(); |
| 693 config_change_pending_ = false; | 692 config_change_pending_ = false; |
| 694 last_output_buffer_timestamp_ = kNoTimestamp(); | 693 last_output_buffer_timestamp_ = kNoDecodeTimestamp(); |
| 695 splice_buffers_index_ = 0; | 694 splice_buffers_index_ = 0; |
| 696 pending_buffer_ = NULL; | 695 pending_buffer_ = NULL; |
| 697 pending_buffers_complete_ = false; | 696 pending_buffers_complete_ = false; |
| 698 } | 697 } |
| 699 | 698 |
| 700 bool SourceBufferStream::ShouldSeekToStartOfBuffered( | 699 bool SourceBufferStream::ShouldSeekToStartOfBuffered( |
| 701 base::TimeDelta seek_timestamp) const { | 700 base::TimeDelta seek_timestamp) const { |
| 702 if (ranges_.empty()) | 701 if (ranges_.empty()) |
| 703 return false; | 702 return false; |
| 704 base::TimeDelta beginning_of_buffered = | 703 base::TimeDelta beginning_of_buffered = |
| 705 ranges_.front()->GetStartTimestamp(); | 704 ranges_.front()->GetStartTimestamp().ToPresentationTime(); |
| 706 return (seek_timestamp <= beginning_of_buffered && | 705 return (seek_timestamp <= beginning_of_buffered && |
| 707 beginning_of_buffered < kSeekToStartFudgeRoom()); | 706 beginning_of_buffered < kSeekToStartFudgeRoom()); |
| 708 } | 707 } |
| 709 | 708 |
| 710 bool SourceBufferStream::IsMonotonicallyIncreasing( | 709 bool SourceBufferStream::IsMonotonicallyIncreasing( |
| 711 const BufferQueue& buffers) const { | 710 const BufferQueue& buffers) const { |
| 712 DCHECK(!buffers.empty()); | 711 DCHECK(!buffers.empty()); |
| 713 base::TimeDelta prev_timestamp = last_appended_buffer_timestamp_; | 712 DecodeTimestamp prev_timestamp = last_appended_buffer_timestamp_; |
| 714 bool prev_is_keyframe = last_appended_buffer_is_keyframe_; | 713 bool prev_is_keyframe = last_appended_buffer_is_keyframe_; |
| 715 for (BufferQueue::const_iterator itr = buffers.begin(); | 714 for (BufferQueue::const_iterator itr = buffers.begin(); |
| 716 itr != buffers.end(); ++itr) { | 715 itr != buffers.end(); ++itr) { |
| 717 base::TimeDelta current_timestamp = (*itr)->GetDecodeTimestamp(); | 716 DecodeTimestamp current_timestamp = (*itr)->GetDecodeTimestamp(); |
| 718 bool current_is_keyframe = (*itr)->IsKeyframe(); | 717 bool current_is_keyframe = (*itr)->IsKeyframe(); |
| 719 DCHECK(current_timestamp != kNoTimestamp()); | 718 DCHECK(current_timestamp != kNoDecodeTimestamp()); |
| 720 DCHECK((*itr)->duration() >= base::TimeDelta()) | 719 DCHECK((*itr)->duration() >= base::TimeDelta()) |
| 721 << "Packet with invalid duration." | 720 << "Packet with invalid duration." |
| 722 << " pts " << (*itr)->timestamp().InSecondsF() | 721 << " pts " << (*itr)->timestamp().InSecondsF() |
| 723 << " dts " << (*itr)->GetDecodeTimestamp().InSecondsF() | 722 << " dts " << (*itr)->GetDecodeTimestamp().InSecondsF() |
| 724 << " dur " << (*itr)->duration().InSecondsF(); | 723 << " dur " << (*itr)->duration().InSecondsF(); |
| 725 | 724 |
| 726 if (prev_timestamp != kNoTimestamp()) { | 725 if (prev_timestamp != kNoDecodeTimestamp()) { |
| 727 if (current_timestamp < prev_timestamp) { | 726 if (current_timestamp < prev_timestamp) { |
| 728 MEDIA_LOG(log_cb_) << "Buffers were not monotonically increasing."; | 727 MEDIA_LOG(log_cb_) << "Buffers were not monotonically increasing."; |
| 729 return false; | 728 return false; |
| 730 } | 729 } |
| 731 | 730 |
| 732 if (current_timestamp == prev_timestamp && | 731 if (current_timestamp == prev_timestamp && |
| 733 !AllowSameTimestamp(prev_is_keyframe, current_is_keyframe, | 732 !AllowSameTimestamp(prev_is_keyframe, current_is_keyframe, |
| 734 GetType())) { | 733 GetType())) { |
| 735 MEDIA_LOG(log_cb_) << "Unexpected combination of buffers with the" | 734 MEDIA_LOG(log_cb_) << "Unexpected combination of buffers with the" |
| 736 << " same timestamp detected at " | 735 << " same timestamp detected at " |
| 737 << current_timestamp.InSecondsF(); | 736 << current_timestamp.InSecondsF(); |
| 738 return false; | 737 return false; |
| 739 } | 738 } |
| 740 } | 739 } |
| 741 | 740 |
| 742 prev_timestamp = current_timestamp; | 741 prev_timestamp = current_timestamp; |
| 743 prev_is_keyframe = current_is_keyframe; | 742 prev_is_keyframe = current_is_keyframe; |
| 744 } | 743 } |
| 745 return true; | 744 return true; |
| 746 } | 745 } |
| 747 | 746 |
| 748 bool SourceBufferStream::IsNextTimestampValid( | 747 bool SourceBufferStream::IsNextTimestampValid( |
| 749 base::TimeDelta next_timestamp, bool next_is_keyframe) const { | 748 DecodeTimestamp next_timestamp, bool next_is_keyframe) const { |
| 750 return (last_appended_buffer_timestamp_ != next_timestamp) || | 749 return (last_appended_buffer_timestamp_ != next_timestamp) || |
| 751 new_media_segment_ || | 750 new_media_segment_ || |
| 752 AllowSameTimestamp(last_appended_buffer_is_keyframe_, next_is_keyframe, | 751 AllowSameTimestamp(last_appended_buffer_is_keyframe_, next_is_keyframe, |
| 753 GetType()); | 752 GetType()); |
| 754 } | 753 } |
| 755 | 754 |
| 756 | 755 |
| 757 bool SourceBufferStream::OnlySelectedRangeIsSeeked() const { | 756 bool SourceBufferStream::OnlySelectedRangeIsSeeked() const { |
| 758 for (RangeList::const_iterator itr = ranges_.begin(); | 757 for (RangeList::const_iterator itr = ranges_.begin(); |
| 759 itr != ranges_.end(); ++itr) { | 758 itr != ranges_.end(); ++itr) { |
| 760 if ((*itr)->HasNextBufferPosition() && (*itr) != selected_range_) | 759 if ((*itr)->HasNextBufferPosition() && (*itr) != selected_range_) |
| 761 return false; | 760 return false; |
| 762 } | 761 } |
| 763 return !selected_range_ || selected_range_->HasNextBufferPosition(); | 762 return !selected_range_ || selected_range_->HasNextBufferPosition(); |
| 764 } | 763 } |
| 765 | 764 |
| 766 void SourceBufferStream::UpdateMaxInterbufferDistance( | 765 void SourceBufferStream::UpdateMaxInterbufferDistance( |
| 767 const BufferQueue& buffers) { | 766 const BufferQueue& buffers) { |
| 768 DCHECK(!buffers.empty()); | 767 DCHECK(!buffers.empty()); |
| 769 base::TimeDelta prev_timestamp = last_appended_buffer_timestamp_; | 768 DecodeTimestamp prev_timestamp = last_appended_buffer_timestamp_; |
| 770 for (BufferQueue::const_iterator itr = buffers.begin(); | 769 for (BufferQueue::const_iterator itr = buffers.begin(); |
| 771 itr != buffers.end(); ++itr) { | 770 itr != buffers.end(); ++itr) { |
| 772 base::TimeDelta current_timestamp = (*itr)->GetDecodeTimestamp(); | 771 DecodeTimestamp current_timestamp = (*itr)->GetDecodeTimestamp(); |
| 773 DCHECK(current_timestamp != kNoTimestamp()); | 772 DCHECK(current_timestamp != kNoDecodeTimestamp()); |
| 774 | 773 |
| 775 if (prev_timestamp != kNoTimestamp()) { | 774 if (prev_timestamp != kNoDecodeTimestamp()) { |
| 776 base::TimeDelta interbuffer_distance = current_timestamp - prev_timestamp; | 775 base::TimeDelta interbuffer_distance = current_timestamp - prev_timestamp; |
| 777 if (max_interbuffer_distance_ == kNoTimestamp()) { | 776 if (max_interbuffer_distance_ == kNoTimestamp()) { |
| 778 max_interbuffer_distance_ = interbuffer_distance; | 777 max_interbuffer_distance_ = interbuffer_distance; |
| 779 } else { | 778 } else { |
| 780 max_interbuffer_distance_ = | 779 max_interbuffer_distance_ = |
| 781 std::max(max_interbuffer_distance_, interbuffer_distance); | 780 std::max(max_interbuffer_distance_, interbuffer_distance); |
| 782 } | 781 } |
| 783 } | 782 } |
| 784 prev_timestamp = current_timestamp; | 783 prev_timestamp = current_timestamp; |
| 785 } | 784 } |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 810 // Begin deleting from the front. | 809 // Begin deleting from the front. |
| 811 if (bytes_to_free - bytes_freed > 0) | 810 if (bytes_to_free - bytes_freed > 0) |
| 812 bytes_freed += FreeBuffers(bytes_to_free - bytes_freed, false); | 811 bytes_freed += FreeBuffers(bytes_to_free - bytes_freed, false); |
| 813 | 812 |
| 814 // Begin deleting from the back. | 813 // Begin deleting from the back. |
| 815 if (bytes_to_free - bytes_freed > 0) | 814 if (bytes_to_free - bytes_freed > 0) |
| 816 FreeBuffers(bytes_to_free - bytes_freed, true); | 815 FreeBuffers(bytes_to_free - bytes_freed, true); |
| 817 } | 816 } |
| 818 | 817 |
| 819 int SourceBufferStream::FreeBuffersAfterLastAppended(int total_bytes_to_free) { | 818 int SourceBufferStream::FreeBuffersAfterLastAppended(int total_bytes_to_free) { |
| 820 base::TimeDelta next_buffer_timestamp = GetNextBufferTimestamp(); | 819 DecodeTimestamp next_buffer_timestamp = GetNextBufferTimestamp(); |
| 821 if (last_appended_buffer_timestamp_ == kNoTimestamp() || | 820 if (last_appended_buffer_timestamp_ == kNoDecodeTimestamp() || |
| 822 next_buffer_timestamp == kNoTimestamp() || | 821 next_buffer_timestamp == kNoDecodeTimestamp() || |
| 823 last_appended_buffer_timestamp_ >= next_buffer_timestamp) { | 822 last_appended_buffer_timestamp_ >= next_buffer_timestamp) { |
| 824 return 0; | 823 return 0; |
| 825 } | 824 } |
| 826 | 825 |
| 827 base::TimeDelta remove_range_start = last_appended_buffer_timestamp_; | 826 DecodeTimestamp remove_range_start = last_appended_buffer_timestamp_; |
| 828 if (last_appended_buffer_is_keyframe_) | 827 if (last_appended_buffer_is_keyframe_) |
| 829 remove_range_start += GetMaxInterbufferDistance(); | 828 remove_range_start += GetMaxInterbufferDistance(); |
| 830 | 829 |
| 831 base::TimeDelta remove_range_start_keyframe = FindKeyframeAfterTimestamp( | 830 DecodeTimestamp remove_range_start_keyframe = FindKeyframeAfterTimestamp( |
| 832 remove_range_start); | 831 remove_range_start); |
| 833 if (remove_range_start_keyframe != kNoTimestamp()) | 832 if (remove_range_start_keyframe != kNoDecodeTimestamp()) |
| 834 remove_range_start = remove_range_start_keyframe; | 833 remove_range_start = remove_range_start_keyframe; |
| 835 if (remove_range_start >= next_buffer_timestamp) | 834 if (remove_range_start >= next_buffer_timestamp) |
| 836 return 0; | 835 return 0; |
| 837 | 836 |
| 838 base::TimeDelta remove_range_end; | 837 DecodeTimestamp remove_range_end; |
| 839 int bytes_freed = GetRemovalRange( | 838 int bytes_freed = GetRemovalRange( |
| 840 remove_range_start, next_buffer_timestamp, total_bytes_to_free, | 839 remove_range_start, next_buffer_timestamp, total_bytes_to_free, |
| 841 &remove_range_end); | 840 &remove_range_end); |
| 842 if (bytes_freed > 0) | 841 if (bytes_freed > 0) { |
| 843 Remove(remove_range_start, remove_range_end, next_buffer_timestamp); | 842 Remove(remove_range_start.ToPresentationTime(), |
| 843 remove_range_end.ToPresentationTime(), | |
| 844 next_buffer_timestamp.ToPresentationTime()); | |
| 845 } | |
| 846 | |
| 844 return bytes_freed; | 847 return bytes_freed; |
| 845 } | 848 } |
| 846 | 849 |
| 847 int SourceBufferStream::GetRemovalRange( | 850 int SourceBufferStream::GetRemovalRange( |
| 848 base::TimeDelta start_timestamp, base::TimeDelta end_timestamp, | 851 DecodeTimestamp start_timestamp, DecodeTimestamp end_timestamp, |
| 849 int total_bytes_to_free, base::TimeDelta* removal_end_timestamp) { | 852 int total_bytes_to_free, DecodeTimestamp* removal_end_timestamp) { |
| 850 DCHECK(start_timestamp >= base::TimeDelta()) << start_timestamp.InSecondsF(); | 853 DCHECK(start_timestamp >= DecodeTimestamp()) << start_timestamp.InSecondsF(); |
| 851 DCHECK(start_timestamp < end_timestamp) | 854 DCHECK(start_timestamp < end_timestamp) |
| 852 << "start " << start_timestamp.InSecondsF() | 855 << "start " << start_timestamp.InSecondsF() |
| 853 << ", end " << end_timestamp.InSecondsF(); | 856 << ", end " << end_timestamp.InSecondsF(); |
| 854 | 857 |
| 855 int bytes_to_free = total_bytes_to_free; | 858 int bytes_to_free = total_bytes_to_free; |
| 856 int bytes_freed = 0; | 859 int bytes_freed = 0; |
| 857 | 860 |
| 858 for (RangeList::iterator itr = ranges_.begin(); | 861 for (RangeList::iterator itr = ranges_.begin(); |
| 859 itr != ranges_.end() && bytes_to_free > 0; ++itr) { | 862 itr != ranges_.end() && bytes_to_free > 0; ++itr) { |
| 860 SourceBufferRange* range = *itr; | 863 SourceBufferRange* range = *itr; |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 900 } else { | 903 } else { |
| 901 current_range = ranges_.front(); | 904 current_range = ranges_.front(); |
| 902 if (current_range->FirstGOPContainsNextBufferPosition()) { | 905 if (current_range->FirstGOPContainsNextBufferPosition()) { |
| 903 DCHECK_EQ(current_range, selected_range_); | 906 DCHECK_EQ(current_range, selected_range_); |
| 904 break; | 907 break; |
| 905 } | 908 } |
| 906 bytes_deleted = current_range->DeleteGOPFromFront(&buffers); | 909 bytes_deleted = current_range->DeleteGOPFromFront(&buffers); |
| 907 } | 910 } |
| 908 | 911 |
| 909 // Check to see if we've just deleted the GOP that was last appended. | 912 // Check to see if we've just deleted the GOP that was last appended. |
| 910 base::TimeDelta end_timestamp = buffers.back()->GetDecodeTimestamp(); | 913 DecodeTimestamp end_timestamp = buffers.back()->GetDecodeTimestamp(); |
| 911 if (end_timestamp == last_appended_buffer_timestamp_) { | 914 if (end_timestamp == last_appended_buffer_timestamp_) { |
| 912 DCHECK(last_appended_buffer_timestamp_ != kNoTimestamp()); | 915 DCHECK(last_appended_buffer_timestamp_ != kNoDecodeTimestamp()); |
| 913 DCHECK(!new_range_for_append); | 916 DCHECK(!new_range_for_append); |
| 914 // Create a new range containing these buffers. | 917 // Create a new range containing these buffers. |
| 915 new_range_for_append = new SourceBufferRange( | 918 new_range_for_append = new SourceBufferRange( |
| 916 GetType(), buffers, kNoTimestamp(), | 919 GetType(), buffers, kNoDecodeTimestamp(), |
| 917 base::Bind(&SourceBufferStream::GetMaxInterbufferDistance, | 920 base::Bind(&SourceBufferStream::GetMaxInterbufferDistance, |
| 918 base::Unretained(this))); | 921 base::Unretained(this))); |
| 919 range_for_next_append_ = ranges_.end(); | 922 range_for_next_append_ = ranges_.end(); |
| 920 } else { | 923 } else { |
| 921 bytes_to_free -= bytes_deleted; | 924 bytes_to_free -= bytes_deleted; |
| 922 bytes_freed += bytes_deleted; | 925 bytes_freed += bytes_deleted; |
| 923 } | 926 } |
| 924 | 927 |
| 925 if (current_range->size_in_bytes() == 0) { | 928 if (current_range->size_in_bytes() == 0) { |
| 926 DCHECK_NE(current_range, selected_range_); | 929 DCHECK_NE(current_range, selected_range_); |
| (...skipping 23 matching lines...) Expand all Loading... | |
| 950 } | 953 } |
| 951 return bytes_freed; | 954 return bytes_freed; |
| 952 } | 955 } |
| 953 | 956 |
| 954 void SourceBufferStream::PrepareRangesForNextAppend( | 957 void SourceBufferStream::PrepareRangesForNextAppend( |
| 955 const BufferQueue& new_buffers, BufferQueue* deleted_buffers) { | 958 const BufferQueue& new_buffers, BufferQueue* deleted_buffers) { |
| 956 DCHECK(deleted_buffers); | 959 DCHECK(deleted_buffers); |
| 957 | 960 |
| 958 bool temporarily_select_range = false; | 961 bool temporarily_select_range = false; |
| 959 if (!track_buffer_.empty()) { | 962 if (!track_buffer_.empty()) { |
| 960 base::TimeDelta tb_timestamp = track_buffer_.back()->GetDecodeTimestamp(); | 963 DecodeTimestamp tb_timestamp = track_buffer_.back()->GetDecodeTimestamp(); |
| 961 base::TimeDelta seek_timestamp = FindKeyframeAfterTimestamp(tb_timestamp); | 964 DecodeTimestamp seek_timestamp = FindKeyframeAfterTimestamp(tb_timestamp); |
| 962 if (seek_timestamp != kNoTimestamp() && | 965 if (seek_timestamp != kNoDecodeTimestamp() && |
| 963 seek_timestamp < new_buffers.front()->GetDecodeTimestamp() && | 966 seek_timestamp < new_buffers.front()->GetDecodeTimestamp() && |
| 964 range_for_next_append_ != ranges_.end() && | 967 range_for_next_append_ != ranges_.end() && |
| 965 (*range_for_next_append_)->BelongsToRange(seek_timestamp)) { | 968 (*range_for_next_append_)->BelongsToRange(seek_timestamp)) { |
| 966 DCHECK(tb_timestamp < seek_timestamp); | 969 DCHECK(tb_timestamp < seek_timestamp); |
| 967 DCHECK(!selected_range_); | 970 DCHECK(!selected_range_); |
| 968 DCHECK(!(*range_for_next_append_)->HasNextBufferPosition()); | 971 DCHECK(!(*range_for_next_append_)->HasNextBufferPosition()); |
| 969 | 972 |
| 970 // If there are GOPs between the end of the track buffer and the | 973 // If there are GOPs between the end of the track buffer and the |
| 971 // beginning of the new buffers, then temporarily seek the range | 974 // beginning of the new buffers, then temporarily seek the range |
| 972 // so that the buffers between these two times will be deposited in | 975 // so that the buffers between these two times will be deposited in |
| 973 // |deleted_buffers| as if they were part of the current playback | 976 // |deleted_buffers| as if they were part of the current playback |
| 974 // position. | 977 // position. |
| 975 // TODO(acolwell): Figure out a more elegant way to do this. | 978 // TODO(acolwell): Figure out a more elegant way to do this. |
| 976 SeekAndSetSelectedRange(*range_for_next_append_, seek_timestamp); | 979 SeekAndSetSelectedRange(*range_for_next_append_, seek_timestamp); |
| 977 temporarily_select_range = true; | 980 temporarily_select_range = true; |
| 978 } | 981 } |
| 979 } | 982 } |
| 980 | 983 |
| 981 // Handle splices between the existing buffers and the new buffers. If a | 984 // Handle splices between the existing buffers and the new buffers. If a |
| 982 // splice is generated the timestamp and duration of the first buffer in | 985 // splice is generated the timestamp and duration of the first buffer in |
| 983 // |new_buffers| will be modified. | 986 // |new_buffers| will be modified. |
| 984 if (splice_frames_enabled_) | 987 if (splice_frames_enabled_) |
| 985 GenerateSpliceFrame(new_buffers); | 988 GenerateSpliceFrame(new_buffers); |
| 986 | 989 |
| 987 base::TimeDelta prev_timestamp = last_appended_buffer_timestamp_; | 990 DecodeTimestamp prev_timestamp = last_appended_buffer_timestamp_; |
| 988 bool prev_is_keyframe = last_appended_buffer_is_keyframe_; | 991 bool prev_is_keyframe = last_appended_buffer_is_keyframe_; |
| 989 base::TimeDelta next_timestamp = new_buffers.front()->GetDecodeTimestamp(); | 992 DecodeTimestamp next_timestamp = new_buffers.front()->GetDecodeTimestamp(); |
| 990 bool next_is_keyframe = new_buffers.front()->IsKeyframe(); | 993 bool next_is_keyframe = new_buffers.front()->IsKeyframe(); |
| 991 | 994 |
| 992 if (prev_timestamp != kNoTimestamp() && prev_timestamp != next_timestamp) { | 995 if (prev_timestamp != kNoDecodeTimestamp() && |
| 996 prev_timestamp != next_timestamp) { | |
| 993 // Clean up the old buffers between the last appended buffer and the | 997 // Clean up the old buffers between the last appended buffer and the |
| 994 // beginning of |new_buffers|. | 998 // beginning of |new_buffers|. |
| 995 RemoveInternal(prev_timestamp, next_timestamp, true, deleted_buffers); | 999 RemoveInternal(prev_timestamp, next_timestamp, true, deleted_buffers); |
| 996 } | 1000 } |
| 997 | 1001 |
| 998 // Make the delete range exclusive if we are dealing with an allowed same | 1002 // Make the delete range exclusive if we are dealing with an allowed same |
| 999 // timestamp situation. This prevents the first buffer in the current append | 1003 // timestamp situation. This prevents the first buffer in the current append |
| 1000 // from deleting the last buffer in the previous append if both buffers | 1004 // from deleting the last buffer in the previous append if both buffers |
| 1001 // have the same timestamp. | 1005 // have the same timestamp. |
| 1002 // | 1006 // |
| 1003 // The delete range should never be exclusive if a splice frame was generated | 1007 // The delete range should never be exclusive if a splice frame was generated |
| 1004 // because we don't generate splice frames for same timestamp situations. | 1008 // because we don't generate splice frames for same timestamp situations. |
| 1005 DCHECK(new_buffers.front()->splice_timestamp() != | 1009 DCHECK(new_buffers.front()->splice_timestamp() != |
| 1006 new_buffers.front()->timestamp()); | 1010 new_buffers.front()->timestamp()); |
| 1007 const bool is_exclusive = | 1011 const bool is_exclusive = |
| 1008 new_buffers.front()->splice_buffers().empty() && | 1012 new_buffers.front()->splice_buffers().empty() && |
| 1009 prev_timestamp == next_timestamp && | 1013 prev_timestamp == next_timestamp && |
| 1010 AllowSameTimestamp(prev_is_keyframe, next_is_keyframe, GetType()); | 1014 AllowSameTimestamp(prev_is_keyframe, next_is_keyframe, GetType()); |
| 1011 | 1015 |
| 1012 // Delete the buffers that |new_buffers| overlaps. | 1016 // Delete the buffers that |new_buffers| overlaps. |
| 1013 base::TimeDelta start = new_buffers.front()->GetDecodeTimestamp(); | 1017 DecodeTimestamp start = new_buffers.front()->GetDecodeTimestamp(); |
| 1014 base::TimeDelta end = new_buffers.back()->GetDecodeTimestamp(); | 1018 DecodeTimestamp end = new_buffers.back()->GetDecodeTimestamp(); |
| 1015 base::TimeDelta duration = new_buffers.back()->duration(); | 1019 base::TimeDelta duration = new_buffers.back()->duration(); |
| 1016 | 1020 |
| 1017 if (duration != kNoTimestamp() && duration > base::TimeDelta()) { | 1021 if (duration != kNoTimestamp() && duration > base::TimeDelta()) { |
| 1018 end += duration; | 1022 end += duration; |
| 1019 } else { | 1023 } else { |
| 1020 // TODO(acolwell): Ensure all buffers actually have proper | 1024 // TODO(acolwell): Ensure all buffers actually have proper |
| 1021 // duration info so that this hack isn't needed. | 1025 // duration info so that this hack isn't needed. |
| 1022 // http://crbug.com/312836 | 1026 // http://crbug.com/312836 |
| 1023 end += base::TimeDelta::FromInternalValue(1); | 1027 end += base::TimeDelta::FromInternalValue(1); |
| 1024 } | 1028 } |
| 1025 | 1029 |
| 1026 RemoveInternal(start, end, is_exclusive, deleted_buffers); | 1030 RemoveInternal(start, end, is_exclusive, deleted_buffers); |
| 1027 | 1031 |
| 1028 // Restore the range seek state if necessary. | 1032 // Restore the range seek state if necessary. |
| 1029 if (temporarily_select_range) | 1033 if (temporarily_select_range) |
| 1030 SetSelectedRange(NULL); | 1034 SetSelectedRange(NULL); |
| 1031 } | 1035 } |
| 1032 | 1036 |
| 1033 bool SourceBufferStream::AreAdjacentInSequence( | 1037 bool SourceBufferStream::AreAdjacentInSequence( |
| 1034 base::TimeDelta first_timestamp, base::TimeDelta second_timestamp) const { | 1038 DecodeTimestamp first_timestamp, DecodeTimestamp second_timestamp) const { |
| 1035 return first_timestamp < second_timestamp && | 1039 return first_timestamp < second_timestamp && |
| 1036 second_timestamp <= | 1040 second_timestamp <= |
| 1037 first_timestamp + ComputeFudgeRoom(GetMaxInterbufferDistance()); | 1041 first_timestamp + ComputeFudgeRoom(GetMaxInterbufferDistance()); |
| 1038 } | 1042 } |
| 1039 | 1043 |
| 1040 void SourceBufferStream::PruneTrackBuffer(const base::TimeDelta timestamp) { | 1044 void SourceBufferStream::PruneTrackBuffer(const DecodeTimestamp timestamp) { |
| 1041 // If we don't have the next timestamp, we don't have anything to delete. | 1045 // If we don't have the next timestamp, we don't have anything to delete. |
| 1042 if (timestamp == kNoTimestamp()) | 1046 if (timestamp == kNoDecodeTimestamp()) |
| 1043 return; | 1047 return; |
| 1044 | 1048 |
| 1045 while (!track_buffer_.empty() && | 1049 while (!track_buffer_.empty() && |
| 1046 track_buffer_.back()->GetDecodeTimestamp() >= timestamp) { | 1050 track_buffer_.back()->GetDecodeTimestamp() >= timestamp) { |
| 1047 track_buffer_.pop_back(); | 1051 track_buffer_.pop_back(); |
| 1048 } | 1052 } |
| 1049 } | 1053 } |
| 1050 | 1054 |
| 1051 void SourceBufferStream::MergeWithAdjacentRangeIfNecessary( | 1055 void SourceBufferStream::MergeWithAdjacentRangeIfNecessary( |
| 1052 const RangeList::iterator& range_with_new_buffers_itr) { | 1056 const RangeList::iterator& range_with_new_buffers_itr) { |
| (...skipping 29 matching lines...) Expand all Loading... | |
| 1082 if (ShouldSeekToStartOfBuffered(timestamp)) { | 1086 if (ShouldSeekToStartOfBuffered(timestamp)) { |
| 1083 ranges_.front()->SeekToStart(); | 1087 ranges_.front()->SeekToStart(); |
| 1084 SetSelectedRange(ranges_.front()); | 1088 SetSelectedRange(ranges_.front()); |
| 1085 seek_pending_ = false; | 1089 seek_pending_ = false; |
| 1086 return; | 1090 return; |
| 1087 } | 1091 } |
| 1088 | 1092 |
| 1089 seek_buffer_timestamp_ = timestamp; | 1093 seek_buffer_timestamp_ = timestamp; |
| 1090 seek_pending_ = true; | 1094 seek_pending_ = true; |
| 1091 | 1095 |
| 1096 DecodeTimestamp seek_dts = DecodeTimestamp::FromPresentationTime(timestamp); | |
| 1097 | |
| 1092 RangeList::iterator itr = ranges_.end(); | 1098 RangeList::iterator itr = ranges_.end(); |
| 1093 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { | 1099 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { |
| 1094 if ((*itr)->CanSeekTo(timestamp)) | 1100 if ((*itr)->CanSeekTo(seek_dts)) |
| 1095 break; | 1101 break; |
| 1096 } | 1102 } |
| 1097 | 1103 |
| 1098 if (itr == ranges_.end()) | 1104 if (itr == ranges_.end()) |
| 1099 return; | 1105 return; |
| 1100 | 1106 |
| 1101 SeekAndSetSelectedRange(*itr, timestamp); | 1107 SeekAndSetSelectedRange(*itr, seek_dts); |
| 1102 seek_pending_ = false; | 1108 seek_pending_ = false; |
| 1103 } | 1109 } |
| 1104 | 1110 |
| 1105 bool SourceBufferStream::IsSeekPending() const { | 1111 bool SourceBufferStream::IsSeekPending() const { |
| 1106 return !(end_of_stream_ && IsEndSelected()) && seek_pending_; | 1112 return !(end_of_stream_ && IsEndSelected()) && seek_pending_; |
| 1107 } | 1113 } |
| 1108 | 1114 |
| 1109 void SourceBufferStream::OnSetDuration(base::TimeDelta duration) { | 1115 void SourceBufferStream::OnSetDuration(base::TimeDelta duration) { |
| 1116 DecodeTimestamp duration_dts = | |
| 1117 DecodeTimestamp::FromPresentationTime(duration); | |
| 1118 | |
| 1110 RangeList::iterator itr = ranges_.end(); | 1119 RangeList::iterator itr = ranges_.end(); |
| 1111 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { | 1120 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { |
| 1112 if ((*itr)->GetEndTimestamp() > duration) | 1121 if ((*itr)->GetEndTimestamp() > duration_dts) |
| 1113 break; | 1122 break; |
| 1114 } | 1123 } |
| 1115 if (itr == ranges_.end()) | 1124 if (itr == ranges_.end()) |
| 1116 return; | 1125 return; |
| 1117 | 1126 |
| 1118 // Need to partially truncate this range. | 1127 // Need to partially truncate this range. |
| 1119 if ((*itr)->GetStartTimestamp() < duration) { | 1128 if ((*itr)->GetStartTimestamp() < duration_dts) { |
| 1120 bool delete_range = (*itr)->TruncateAt(duration, NULL, false); | 1129 bool delete_range = (*itr)->TruncateAt(duration_dts, NULL, false); |
| 1121 if ((*itr == selected_range_) && !selected_range_->HasNextBufferPosition()) | 1130 if ((*itr == selected_range_) && !selected_range_->HasNextBufferPosition()) |
| 1122 SetSelectedRange(NULL); | 1131 SetSelectedRange(NULL); |
| 1123 | 1132 |
| 1124 if (delete_range) { | 1133 if (delete_range) { |
| 1125 DeleteAndRemoveRange(&itr); | 1134 DeleteAndRemoveRange(&itr); |
| 1126 } else { | 1135 } else { |
| 1127 ++itr; | 1136 ++itr; |
| 1128 } | 1137 } |
| 1129 } | 1138 } |
| 1130 | 1139 |
| 1131 // Delete all ranges that begin after |duration|. | 1140 // Delete all ranges that begin after |duration|. |
| 1132 while (itr != ranges_.end()) { | 1141 while (itr != ranges_.end()) { |
| 1133 // If we're about to delete the selected range, also reset the seek state. | 1142 // If we're about to delete the selected range, also reset the seek state. |
| 1134 DCHECK((*itr)->GetStartTimestamp() >= duration); | 1143 DCHECK((*itr)->GetStartTimestamp() >= duration_dts); |
| 1135 if (*itr == selected_range_) | 1144 if (*itr == selected_range_) |
| 1136 ResetSeekState(); | 1145 ResetSeekState(); |
| 1137 DeleteAndRemoveRange(&itr); | 1146 DeleteAndRemoveRange(&itr); |
| 1138 } | 1147 } |
| 1139 } | 1148 } |
| 1140 | 1149 |
| 1141 SourceBufferStream::Status SourceBufferStream::GetNextBuffer( | 1150 SourceBufferStream::Status SourceBufferStream::GetNextBuffer( |
| 1142 scoped_refptr<StreamParserBuffer>* out_buffer) { | 1151 scoped_refptr<StreamParserBuffer>* out_buffer) { |
| 1143 if (!pending_buffer_) { | 1152 if (!pending_buffer_) { |
| 1144 const SourceBufferStream::Status status = GetNextBufferInternal(out_buffer); | 1153 const SourceBufferStream::Status status = GetNextBufferInternal(out_buffer); |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1260 config_change_pending_ = true; | 1269 config_change_pending_ = true; |
| 1261 DVLOG(1) << "Config change (selected range config ID does not match)."; | 1270 DVLOG(1) << "Config change (selected range config ID does not match)."; |
| 1262 return kConfigChange; | 1271 return kConfigChange; |
| 1263 } | 1272 } |
| 1264 | 1273 |
| 1265 CHECK(selected_range_->GetNextBuffer(out_buffer)); | 1274 CHECK(selected_range_->GetNextBuffer(out_buffer)); |
| 1266 last_output_buffer_timestamp_ = (*out_buffer)->GetDecodeTimestamp(); | 1275 last_output_buffer_timestamp_ = (*out_buffer)->GetDecodeTimestamp(); |
| 1267 return kSuccess; | 1276 return kSuccess; |
| 1268 } | 1277 } |
| 1269 | 1278 |
| 1270 base::TimeDelta SourceBufferStream::GetNextBufferTimestamp() { | 1279 DecodeTimestamp SourceBufferStream::GetNextBufferTimestamp() { |
| 1271 if (!track_buffer_.empty()) | 1280 if (!track_buffer_.empty()) |
| 1272 return track_buffer_.front()->GetDecodeTimestamp(); | 1281 return track_buffer_.front()->GetDecodeTimestamp(); |
| 1273 | 1282 |
| 1274 if (!selected_range_) | 1283 if (!selected_range_) |
| 1275 return kNoTimestamp(); | 1284 return kNoDecodeTimestamp(); |
| 1276 | 1285 |
| 1277 DCHECK(selected_range_->HasNextBufferPosition()); | 1286 DCHECK(selected_range_->HasNextBufferPosition()); |
| 1278 return selected_range_->GetNextTimestamp(); | 1287 return selected_range_->GetNextTimestamp(); |
| 1279 } | 1288 } |
| 1280 | 1289 |
| 1281 base::TimeDelta SourceBufferStream::GetEndBufferTimestamp() { | |
| 1282 if (!selected_range_) | |
| 1283 return kNoTimestamp(); | |
| 1284 return selected_range_->GetEndTimestamp(); | |
| 1285 } | |
| 1286 | |
| 1287 SourceBufferStream::RangeList::iterator | 1290 SourceBufferStream::RangeList::iterator |
| 1288 SourceBufferStream::FindExistingRangeFor(base::TimeDelta start_timestamp) { | 1291 SourceBufferStream::FindExistingRangeFor(DecodeTimestamp start_timestamp) { |
| 1289 for (RangeList::iterator itr = ranges_.begin(); itr != ranges_.end(); ++itr) { | 1292 for (RangeList::iterator itr = ranges_.begin(); itr != ranges_.end(); ++itr) { |
| 1290 if ((*itr)->BelongsToRange(start_timestamp)) | 1293 if ((*itr)->BelongsToRange(start_timestamp)) |
| 1291 return itr; | 1294 return itr; |
| 1292 } | 1295 } |
| 1293 return ranges_.end(); | 1296 return ranges_.end(); |
| 1294 } | 1297 } |
| 1295 | 1298 |
| 1296 SourceBufferStream::RangeList::iterator | 1299 SourceBufferStream::RangeList::iterator |
| 1297 SourceBufferStream::AddToRanges(SourceBufferRange* new_range) { | 1300 SourceBufferStream::AddToRanges(SourceBufferRange* new_range) { |
| 1298 base::TimeDelta start_timestamp = new_range->GetStartTimestamp(); | 1301 DecodeTimestamp start_timestamp = new_range->GetStartTimestamp(); |
| 1299 RangeList::iterator itr = ranges_.end(); | 1302 RangeList::iterator itr = ranges_.end(); |
| 1300 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { | 1303 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { |
| 1301 if ((*itr)->GetStartTimestamp() > start_timestamp) | 1304 if ((*itr)->GetStartTimestamp() > start_timestamp) |
| 1302 break; | 1305 break; |
| 1303 } | 1306 } |
| 1304 return ranges_.insert(itr, new_range); | 1307 return ranges_.insert(itr, new_range); |
| 1305 } | 1308 } |
| 1306 | 1309 |
| 1307 SourceBufferStream::RangeList::iterator | 1310 SourceBufferStream::RangeList::iterator |
| 1308 SourceBufferStream::GetSelectedRangeItr() { | 1311 SourceBufferStream::GetSelectedRangeItr() { |
| 1309 DCHECK(selected_range_); | 1312 DCHECK(selected_range_); |
| 1310 RangeList::iterator itr = ranges_.end(); | 1313 RangeList::iterator itr = ranges_.end(); |
| 1311 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { | 1314 for (itr = ranges_.begin(); itr != ranges_.end(); ++itr) { |
| 1312 if (*itr == selected_range_) | 1315 if (*itr == selected_range_) |
| 1313 break; | 1316 break; |
| 1314 } | 1317 } |
| 1315 DCHECK(itr != ranges_.end()); | 1318 DCHECK(itr != ranges_.end()); |
| 1316 return itr; | 1319 return itr; |
| 1317 } | 1320 } |
| 1318 | 1321 |
| 1319 void SourceBufferStream::SeekAndSetSelectedRange( | 1322 void SourceBufferStream::SeekAndSetSelectedRange( |
| 1320 SourceBufferRange* range, base::TimeDelta seek_timestamp) { | 1323 SourceBufferRange* range, DecodeTimestamp seek_timestamp) { |
| 1321 if (range) | 1324 if (range) |
| 1322 range->Seek(seek_timestamp); | 1325 range->Seek(seek_timestamp); |
| 1323 SetSelectedRange(range); | 1326 SetSelectedRange(range); |
| 1324 } | 1327 } |
| 1325 | 1328 |
| 1326 void SourceBufferStream::SetSelectedRange(SourceBufferRange* range) { | 1329 void SourceBufferStream::SetSelectedRange(SourceBufferRange* range) { |
| 1327 DVLOG(1) << __FUNCTION__ << " : " << selected_range_ << " -> " << range; | 1330 DVLOG(1) << __FUNCTION__ << " : " << selected_range_ << " -> " << range; |
| 1328 if (selected_range_) | 1331 if (selected_range_) |
| 1329 selected_range_->ResetNextBufferPosition(); | 1332 selected_range_->ResetNextBufferPosition(); |
| 1330 DCHECK(!range || range->HasNextBufferPosition()); | 1333 DCHECK(!range || range->HasNextBufferPosition()); |
| 1331 selected_range_ = range; | 1334 selected_range_ = range; |
| 1332 } | 1335 } |
| 1333 | 1336 |
| 1334 Ranges<base::TimeDelta> SourceBufferStream::GetBufferedTime() const { | 1337 Ranges<base::TimeDelta> SourceBufferStream::GetBufferedTime() const { |
| 1335 Ranges<base::TimeDelta> ranges; | 1338 Ranges<base::TimeDelta> ranges; |
| 1336 for (RangeList::const_iterator itr = ranges_.begin(); | 1339 for (RangeList::const_iterator itr = ranges_.begin(); |
| 1337 itr != ranges_.end(); ++itr) { | 1340 itr != ranges_.end(); ++itr) { |
| 1338 ranges.Add((*itr)->GetStartTimestamp(), (*itr)->GetBufferedEndTimestamp()); | 1341 ranges.Add((*itr)->GetStartTimestamp().ToPresentationTime(), |
| 1342 (*itr)->GetBufferedEndTimestamp().ToPresentationTime()); | |
| 1339 } | 1343 } |
| 1340 return ranges; | 1344 return ranges; |
| 1341 } | 1345 } |
| 1342 | 1346 |
| 1343 base::TimeDelta SourceBufferStream::GetBufferedDuration() const { | 1347 base::TimeDelta SourceBufferStream::GetBufferedDuration() const { |
| 1344 if (ranges_.empty()) | 1348 if (ranges_.empty()) |
| 1345 return base::TimeDelta(); | 1349 return base::TimeDelta(); |
| 1346 | 1350 |
| 1347 return ranges_.back()->GetBufferedEndTimestamp(); | 1351 return ranges_.back()->GetBufferedEndTimestamp().ToPresentationTime(); |
| 1348 } | 1352 } |
| 1349 | 1353 |
| 1350 void SourceBufferStream::MarkEndOfStream() { | 1354 void SourceBufferStream::MarkEndOfStream() { |
| 1351 DCHECK(!end_of_stream_); | 1355 DCHECK(!end_of_stream_); |
| 1352 end_of_stream_ = true; | 1356 end_of_stream_ = true; |
| 1353 } | 1357 } |
| 1354 | 1358 |
| 1355 void SourceBufferStream::UnmarkEndOfStream() { | 1359 void SourceBufferStream::UnmarkEndOfStream() { |
| 1356 DCHECK(end_of_stream_); | 1360 DCHECK(end_of_stream_); |
| 1357 end_of_stream_ = false; | 1361 end_of_stream_ = false; |
| 1358 } | 1362 } |
| 1359 | 1363 |
| 1360 bool SourceBufferStream::IsEndSelected() const { | 1364 bool SourceBufferStream::IsEndSelected() const { |
| 1361 if (ranges_.empty()) | 1365 if (ranges_.empty()) |
| 1362 return true; | 1366 return true; |
| 1363 | 1367 |
| 1364 if (seek_pending_) | 1368 if (seek_pending_) { |
| 1365 return seek_buffer_timestamp_ >= ranges_.back()->GetBufferedEndTimestamp(); | 1369 base::TimeDelta last_range_end_time = |
| 1370 ranges_.back()->GetBufferedEndTimestamp().ToPresentationTime();; | |
|
wolenetz
2014/08/08 21:30:04
lint nit: s/;;/;/
acolwell GONE FROM CHROMIUM
2014/08/11 17:05:05
Done.
| |
| 1371 return seek_buffer_timestamp_ >= last_range_end_time; | |
| 1372 } | |
| 1366 | 1373 |
| 1367 return selected_range_ == ranges_.back(); | 1374 return selected_range_ == ranges_.back(); |
| 1368 } | 1375 } |
| 1369 | 1376 |
| 1370 const AudioDecoderConfig& SourceBufferStream::GetCurrentAudioDecoderConfig() { | 1377 const AudioDecoderConfig& SourceBufferStream::GetCurrentAudioDecoderConfig() { |
| 1371 if (config_change_pending_) | 1378 if (config_change_pending_) |
| 1372 CompleteConfigChange(); | 1379 CompleteConfigChange(); |
| 1373 return audio_configs_[current_config_index_]; | 1380 return audio_configs_[current_config_index_]; |
| 1374 } | 1381 } |
| 1375 | 1382 |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1463 if (!track_buffer_.empty()) { | 1470 if (!track_buffer_.empty()) { |
| 1464 current_config_index_ = GetConfigId(track_buffer_.front(), 0); | 1471 current_config_index_ = GetConfigId(track_buffer_.front(), 0); |
| 1465 return; | 1472 return; |
| 1466 } | 1473 } |
| 1467 | 1474 |
| 1468 if (selected_range_ && selected_range_->HasNextBuffer()) | 1475 if (selected_range_ && selected_range_->HasNextBuffer()) |
| 1469 current_config_index_ = selected_range_->GetNextConfigId(); | 1476 current_config_index_ = selected_range_->GetNextConfigId(); |
| 1470 } | 1477 } |
| 1471 | 1478 |
| 1472 void SourceBufferStream::SetSelectedRangeIfNeeded( | 1479 void SourceBufferStream::SetSelectedRangeIfNeeded( |
| 1473 const base::TimeDelta timestamp) { | 1480 const DecodeTimestamp timestamp) { |
| 1474 DVLOG(1) << __FUNCTION__ << "(" << timestamp.InSecondsF() << ")"; | 1481 DVLOG(1) << __FUNCTION__ << "(" << timestamp.InSecondsF() << ")"; |
| 1475 | 1482 |
| 1476 if (selected_range_) { | 1483 if (selected_range_) { |
| 1477 DCHECK(track_buffer_.empty()); | 1484 DCHECK(track_buffer_.empty()); |
| 1478 return; | 1485 return; |
| 1479 } | 1486 } |
| 1480 | 1487 |
| 1481 if (!track_buffer_.empty()) { | 1488 if (!track_buffer_.empty()) { |
| 1482 DCHECK(!selected_range_); | 1489 DCHECK(!selected_range_); |
| 1483 return; | 1490 return; |
| 1484 } | 1491 } |
| 1485 | 1492 |
| 1486 base::TimeDelta start_timestamp = timestamp; | 1493 DecodeTimestamp start_timestamp = timestamp; |
| 1487 | 1494 |
| 1488 // If the next buffer timestamp is not known then use a timestamp just after | 1495 // If the next buffer timestamp is not known then use a timestamp just after |
| 1489 // the timestamp on the last buffer returned by GetNextBuffer(). | 1496 // the timestamp on the last buffer returned by GetNextBuffer(). |
| 1490 if (start_timestamp == kNoTimestamp()) { | 1497 if (start_timestamp == kNoDecodeTimestamp()) { |
| 1491 if (last_output_buffer_timestamp_ == kNoTimestamp()) | 1498 if (last_output_buffer_timestamp_ == kNoDecodeTimestamp()) |
| 1492 return; | 1499 return; |
| 1493 | 1500 |
| 1494 start_timestamp = last_output_buffer_timestamp_ + | 1501 start_timestamp = last_output_buffer_timestamp_ + |
| 1495 base::TimeDelta::FromInternalValue(1); | 1502 base::TimeDelta::FromInternalValue(1); |
| 1496 } | 1503 } |
| 1497 | 1504 |
| 1498 base::TimeDelta seek_timestamp = | 1505 DecodeTimestamp seek_timestamp = |
| 1499 FindNewSelectedRangeSeekTimestamp(start_timestamp); | 1506 FindNewSelectedRangeSeekTimestamp(start_timestamp); |
| 1500 | 1507 |
| 1501 // If we don't have buffered data to seek to, then return. | 1508 // If we don't have buffered data to seek to, then return. |
| 1502 if (seek_timestamp == kNoTimestamp()) | 1509 if (seek_timestamp == kNoDecodeTimestamp()) |
| 1503 return; | 1510 return; |
| 1504 | 1511 |
| 1505 DCHECK(track_buffer_.empty()); | 1512 DCHECK(track_buffer_.empty()); |
| 1506 SeekAndSetSelectedRange(*FindExistingRangeFor(seek_timestamp), | 1513 SeekAndSetSelectedRange(*FindExistingRangeFor(seek_timestamp), |
| 1507 seek_timestamp); | 1514 seek_timestamp); |
| 1508 } | 1515 } |
| 1509 | 1516 |
| 1510 base::TimeDelta SourceBufferStream::FindNewSelectedRangeSeekTimestamp( | 1517 DecodeTimestamp SourceBufferStream::FindNewSelectedRangeSeekTimestamp( |
| 1511 const base::TimeDelta start_timestamp) { | 1518 const DecodeTimestamp start_timestamp) { |
| 1512 DCHECK(start_timestamp != kNoTimestamp()); | 1519 DCHECK(start_timestamp != kNoDecodeTimestamp()); |
| 1513 DCHECK(start_timestamp >= base::TimeDelta()); | 1520 DCHECK(start_timestamp >= DecodeTimestamp()); |
| 1514 | 1521 |
| 1515 RangeList::iterator itr = ranges_.begin(); | 1522 RangeList::iterator itr = ranges_.begin(); |
| 1516 | 1523 |
| 1517 for (; itr != ranges_.end(); ++itr) { | 1524 for (; itr != ranges_.end(); ++itr) { |
| 1518 if ((*itr)->GetEndTimestamp() >= start_timestamp) { | 1525 if ((*itr)->GetEndTimestamp() >= start_timestamp) { |
| 1519 break; | 1526 break; |
| 1520 } | 1527 } |
| 1521 } | 1528 } |
| 1522 | 1529 |
| 1523 if (itr == ranges_.end()) | 1530 if (itr == ranges_.end()) |
| 1524 return kNoTimestamp(); | 1531 return kNoDecodeTimestamp(); |
| 1525 | 1532 |
| 1526 // First check for a keyframe timestamp >= |start_timestamp| | 1533 // First check for a keyframe timestamp >= |start_timestamp| |
| 1527 // in the current range. | 1534 // in the current range. |
| 1528 base::TimeDelta keyframe_timestamp = | 1535 DecodeTimestamp keyframe_timestamp = |
| 1529 (*itr)->NextKeyframeTimestamp(start_timestamp); | 1536 (*itr)->NextKeyframeTimestamp(start_timestamp); |
| 1530 | 1537 |
| 1531 if (keyframe_timestamp != kNoTimestamp()) | 1538 if (keyframe_timestamp != kNoDecodeTimestamp()) |
| 1532 return keyframe_timestamp; | 1539 return keyframe_timestamp; |
| 1533 | 1540 |
| 1534 // If a keyframe was not found then look for a keyframe that is | 1541 // If a keyframe was not found then look for a keyframe that is |
| 1535 // "close enough" in the current or next range. | 1542 // "close enough" in the current or next range. |
| 1536 base::TimeDelta end_timestamp = | 1543 DecodeTimestamp end_timestamp = |
| 1537 start_timestamp + ComputeFudgeRoom(GetMaxInterbufferDistance()); | 1544 start_timestamp + ComputeFudgeRoom(GetMaxInterbufferDistance()); |
| 1538 DCHECK(start_timestamp < end_timestamp); | 1545 DCHECK(start_timestamp < end_timestamp); |
| 1539 | 1546 |
| 1540 // Make sure the current range doesn't start beyond |end_timestamp|. | 1547 // Make sure the current range doesn't start beyond |end_timestamp|. |
| 1541 if ((*itr)->GetStartTimestamp() >= end_timestamp) | 1548 if ((*itr)->GetStartTimestamp() >= end_timestamp) |
| 1542 return kNoTimestamp(); | 1549 return kNoDecodeTimestamp(); |
| 1543 | 1550 |
| 1544 keyframe_timestamp = (*itr)->KeyframeBeforeTimestamp(end_timestamp); | 1551 keyframe_timestamp = (*itr)->KeyframeBeforeTimestamp(end_timestamp); |
| 1545 | 1552 |
| 1546 // Check to see if the keyframe is within the acceptable range | 1553 // Check to see if the keyframe is within the acceptable range |
| 1547 // (|start_timestamp|, |end_timestamp|]. | 1554 // (|start_timestamp|, |end_timestamp|]. |
| 1548 if (keyframe_timestamp != kNoTimestamp() && | 1555 if (keyframe_timestamp != kNoDecodeTimestamp() && |
| 1549 start_timestamp < keyframe_timestamp && | 1556 start_timestamp < keyframe_timestamp && |
| 1550 keyframe_timestamp <= end_timestamp) { | 1557 keyframe_timestamp <= end_timestamp) { |
| 1551 return keyframe_timestamp; | 1558 return keyframe_timestamp; |
| 1552 } | 1559 } |
| 1553 | 1560 |
| 1554 // If |end_timestamp| is within this range, then no other checks are | 1561 // If |end_timestamp| is within this range, then no other checks are |
| 1555 // necessary. | 1562 // necessary. |
| 1556 if (end_timestamp <= (*itr)->GetEndTimestamp()) | 1563 if (end_timestamp <= (*itr)->GetEndTimestamp()) |
| 1557 return kNoTimestamp(); | 1564 return kNoDecodeTimestamp(); |
| 1558 | 1565 |
| 1559 // Move on to the next range. | 1566 // Move on to the next range. |
| 1560 ++itr; | 1567 ++itr; |
| 1561 | 1568 |
| 1562 // Return early if the next range does not contain |end_timestamp|. | 1569 // Return early if the next range does not contain |end_timestamp|. |
| 1563 if (itr == ranges_.end() || (*itr)->GetStartTimestamp() >= end_timestamp) | 1570 if (itr == ranges_.end() || (*itr)->GetStartTimestamp() >= end_timestamp) |
| 1564 return kNoTimestamp(); | 1571 return kNoDecodeTimestamp(); |
| 1565 | 1572 |
| 1566 keyframe_timestamp = (*itr)->KeyframeBeforeTimestamp(end_timestamp); | 1573 keyframe_timestamp = (*itr)->KeyframeBeforeTimestamp(end_timestamp); |
| 1567 | 1574 |
| 1568 // Check to see if the keyframe is within the acceptable range | 1575 // Check to see if the keyframe is within the acceptable range |
| 1569 // (|start_timestamp|, |end_timestamp|]. | 1576 // (|start_timestamp|, |end_timestamp|]. |
| 1570 if (keyframe_timestamp != kNoTimestamp() && | 1577 if (keyframe_timestamp != kNoDecodeTimestamp() && |
| 1571 start_timestamp < keyframe_timestamp && | 1578 start_timestamp < keyframe_timestamp && |
| 1572 keyframe_timestamp <= end_timestamp) { | 1579 keyframe_timestamp <= end_timestamp) { |
| 1573 return keyframe_timestamp; | 1580 return keyframe_timestamp; |
| 1574 } | 1581 } |
| 1575 | 1582 |
| 1576 return kNoTimestamp(); | 1583 return kNoDecodeTimestamp(); |
| 1577 } | 1584 } |
| 1578 | 1585 |
| 1579 base::TimeDelta SourceBufferStream::FindKeyframeAfterTimestamp( | 1586 DecodeTimestamp SourceBufferStream::FindKeyframeAfterTimestamp( |
| 1580 const base::TimeDelta timestamp) { | 1587 const DecodeTimestamp timestamp) { |
| 1581 DCHECK(timestamp != kNoTimestamp()); | 1588 DCHECK(timestamp != kNoDecodeTimestamp()); |
| 1582 | 1589 |
| 1583 RangeList::iterator itr = FindExistingRangeFor(timestamp); | 1590 RangeList::iterator itr = FindExistingRangeFor(timestamp); |
| 1584 | 1591 |
| 1585 if (itr == ranges_.end()) | 1592 if (itr == ranges_.end()) |
| 1586 return kNoTimestamp(); | 1593 return kNoDecodeTimestamp(); |
| 1587 | 1594 |
| 1588 // First check for a keyframe timestamp >= |timestamp| | 1595 // First check for a keyframe timestamp >= |timestamp| |
| 1589 // in the current range. | 1596 // in the current range. |
| 1590 return (*itr)->NextKeyframeTimestamp(timestamp); | 1597 return (*itr)->NextKeyframeTimestamp(timestamp); |
| 1591 } | 1598 } |
| 1592 | 1599 |
| 1593 std::string SourceBufferStream::GetStreamTypeName() const { | 1600 std::string SourceBufferStream::GetStreamTypeName() const { |
| 1594 switch (GetType()) { | 1601 switch (GetType()) { |
| 1595 case kAudio: | 1602 case kAudio: |
| 1596 return "AUDIO"; | 1603 return "AUDIO"; |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 1617 | 1624 |
| 1618 DCHECK(*itr != ranges_.end()); | 1625 DCHECK(*itr != ranges_.end()); |
| 1619 if (**itr == selected_range_) { | 1626 if (**itr == selected_range_) { |
| 1620 DVLOG(1) << __FUNCTION__ << " deleting selected range."; | 1627 DVLOG(1) << __FUNCTION__ << " deleting selected range."; |
| 1621 SetSelectedRange(NULL); | 1628 SetSelectedRange(NULL); |
| 1622 } | 1629 } |
| 1623 | 1630 |
| 1624 if (*itr == range_for_next_append_) { | 1631 if (*itr == range_for_next_append_) { |
| 1625 DVLOG(1) << __FUNCTION__ << " deleting range_for_next_append_."; | 1632 DVLOG(1) << __FUNCTION__ << " deleting range_for_next_append_."; |
| 1626 range_for_next_append_ = ranges_.end(); | 1633 range_for_next_append_ = ranges_.end(); |
| 1627 last_appended_buffer_timestamp_ = kNoTimestamp(); | 1634 last_appended_buffer_timestamp_ = kNoDecodeTimestamp(); |
| 1628 last_appended_buffer_is_keyframe_ = false; | 1635 last_appended_buffer_is_keyframe_ = false; |
| 1629 } | 1636 } |
| 1630 | 1637 |
| 1631 delete **itr; | 1638 delete **itr; |
| 1632 *itr = ranges_.erase(*itr); | 1639 *itr = ranges_.erase(*itr); |
| 1633 } | 1640 } |
| 1634 | 1641 |
| 1635 void SourceBufferStream::GenerateSpliceFrame(const BufferQueue& new_buffers) { | 1642 void SourceBufferStream::GenerateSpliceFrame(const BufferQueue& new_buffers) { |
| 1636 DCHECK(!new_buffers.empty()); | 1643 DCHECK(!new_buffers.empty()); |
| 1637 | 1644 |
| 1638 // Splice frames are only supported for audio. | 1645 // Splice frames are only supported for audio. |
| 1639 if (GetType() != kAudio) | 1646 if (GetType() != kAudio) |
| 1640 return; | 1647 return; |
| 1641 | 1648 |
| 1642 // Find the overlapped range (if any). | 1649 // Find the overlapped range (if any). |
| 1643 const base::TimeDelta splice_timestamp = new_buffers.front()->timestamp(); | 1650 const base::TimeDelta splice_timestamp = new_buffers.front()->timestamp(); |
| 1644 RangeList::iterator range_itr = FindExistingRangeFor(splice_timestamp); | 1651 const DecodeTimestamp splice_dts = |
| 1652 DecodeTimestamp::FromPresentationTime(splice_timestamp); | |
| 1653 RangeList::iterator range_itr = FindExistingRangeFor(splice_dts); | |
| 1645 if (range_itr == ranges_.end()) | 1654 if (range_itr == ranges_.end()) |
| 1646 return; | 1655 return; |
| 1647 | 1656 |
| 1648 const base::TimeDelta max_splice_end_timestamp = | 1657 const DecodeTimestamp max_splice_end_dts = |
| 1649 splice_timestamp + base::TimeDelta::FromMilliseconds( | 1658 splice_dts + base::TimeDelta::FromMilliseconds( |
| 1650 AudioSplicer::kCrossfadeDurationInMilliseconds); | 1659 AudioSplicer::kCrossfadeDurationInMilliseconds); |
| 1651 | 1660 |
| 1652 // Find all buffers involved before the splice point. | 1661 // Find all buffers involved before the splice point. |
| 1653 BufferQueue pre_splice_buffers; | 1662 BufferQueue pre_splice_buffers; |
| 1654 if (!(*range_itr)->GetBuffersInRange( | 1663 if (!(*range_itr)->GetBuffersInRange( |
| 1655 splice_timestamp, max_splice_end_timestamp, &pre_splice_buffers)) { | 1664 splice_dts, max_splice_end_dts, &pre_splice_buffers)) { |
| 1656 return; | 1665 return; |
| 1657 } | 1666 } |
| 1658 | 1667 |
| 1659 // If there are gaps in the timeline, it's possible that we only find buffers | 1668 // If there are gaps in the timeline, it's possible that we only find buffers |
| 1660 // after the splice point but within the splice range. For simplicity, we do | 1669 // after the splice point but within the splice range. For simplicity, we do |
| 1661 // not generate splice frames in this case. | 1670 // not generate splice frames in this case. |
| 1662 // | 1671 // |
| 1663 // We also do not want to generate splices if the first new buffer replaces an | 1672 // We also do not want to generate splices if the first new buffer replaces an |
| 1664 // existing buffer exactly. | 1673 // existing buffer exactly. |
| 1665 if (pre_splice_buffers.front()->timestamp() >= splice_timestamp) | 1674 if (pre_splice_buffers.front()->timestamp() >= splice_timestamp) |
| (...skipping 29 matching lines...) Expand all Loading... | |
| 1695 << splice_duration.InMicroseconds() << " us, but need " | 1704 << splice_duration.InMicroseconds() << " us, but need " |
| 1696 << minimum_splice_duration.InMicroseconds() << " us."; | 1705 << minimum_splice_duration.InMicroseconds() << " us."; |
| 1697 return; | 1706 return; |
| 1698 } | 1707 } |
| 1699 | 1708 |
| 1700 new_buffers.front()->ConvertToSpliceBuffer(pre_splice_buffers); | 1709 new_buffers.front()->ConvertToSpliceBuffer(pre_splice_buffers); |
| 1701 } | 1710 } |
| 1702 | 1711 |
| 1703 SourceBufferRange::SourceBufferRange( | 1712 SourceBufferRange::SourceBufferRange( |
| 1704 SourceBufferStream::Type type, const BufferQueue& new_buffers, | 1713 SourceBufferStream::Type type, const BufferQueue& new_buffers, |
| 1705 base::TimeDelta media_segment_start_time, | 1714 DecodeTimestamp media_segment_start_time, |
| 1706 const InterbufferDistanceCB& interbuffer_distance_cb) | 1715 const InterbufferDistanceCB& interbuffer_distance_cb) |
| 1707 : type_(type), | 1716 : type_(type), |
| 1708 keyframe_map_index_base_(0), | 1717 keyframe_map_index_base_(0), |
| 1709 next_buffer_index_(-1), | 1718 next_buffer_index_(-1), |
| 1710 media_segment_start_time_(media_segment_start_time), | 1719 media_segment_start_time_(media_segment_start_time), |
| 1711 interbuffer_distance_cb_(interbuffer_distance_cb), | 1720 interbuffer_distance_cb_(interbuffer_distance_cb), |
| 1712 size_in_bytes_(0) { | 1721 size_in_bytes_(0) { |
| 1713 CHECK(!new_buffers.empty()); | 1722 CHECK(!new_buffers.empty()); |
| 1714 DCHECK(new_buffers.front()->IsKeyframe()); | 1723 DCHECK(new_buffers.front()->IsKeyframe()); |
| 1715 DCHECK(!interbuffer_distance_cb.is_null()); | 1724 DCHECK(!interbuffer_distance_cb.is_null()); |
| 1716 AppendBuffersToEnd(new_buffers); | 1725 AppendBuffersToEnd(new_buffers); |
| 1717 } | 1726 } |
| 1718 | 1727 |
| 1719 void SourceBufferRange::AppendBuffersToEnd(const BufferQueue& new_buffers) { | 1728 void SourceBufferRange::AppendBuffersToEnd(const BufferQueue& new_buffers) { |
| 1720 DCHECK(buffers_.empty() || CanAppendBuffersToEnd(new_buffers)); | 1729 DCHECK(buffers_.empty() || CanAppendBuffersToEnd(new_buffers)); |
| 1721 DCHECK(media_segment_start_time_ == kNoTimestamp() || | 1730 DCHECK(media_segment_start_time_ == kNoDecodeTimestamp() || |
| 1722 media_segment_start_time_ <= | 1731 media_segment_start_time_ <= |
| 1723 new_buffers.front()->GetDecodeTimestamp()); | 1732 new_buffers.front()->GetDecodeTimestamp()); |
| 1724 for (BufferQueue::const_iterator itr = new_buffers.begin(); | 1733 for (BufferQueue::const_iterator itr = new_buffers.begin(); |
| 1725 itr != new_buffers.end(); | 1734 itr != new_buffers.end(); |
| 1726 ++itr) { | 1735 ++itr) { |
| 1727 DCHECK((*itr)->GetDecodeTimestamp() != kNoTimestamp()); | 1736 DCHECK((*itr)->GetDecodeTimestamp() != kNoDecodeTimestamp()); |
| 1728 buffers_.push_back(*itr); | 1737 buffers_.push_back(*itr); |
| 1729 size_in_bytes_ += (*itr)->data_size(); | 1738 size_in_bytes_ += (*itr)->data_size(); |
| 1730 | 1739 |
| 1731 if ((*itr)->IsKeyframe()) { | 1740 if ((*itr)->IsKeyframe()) { |
| 1732 keyframe_map_.insert( | 1741 keyframe_map_.insert( |
| 1733 std::make_pair((*itr)->GetDecodeTimestamp(), | 1742 std::make_pair((*itr)->GetDecodeTimestamp(), |
| 1734 buffers_.size() - 1 + keyframe_map_index_base_)); | 1743 buffers_.size() - 1 + keyframe_map_index_base_)); |
| 1735 } | 1744 } |
| 1736 } | 1745 } |
| 1737 } | 1746 } |
| 1738 | 1747 |
| 1739 void SourceBufferRange::Seek(base::TimeDelta timestamp) { | 1748 void SourceBufferRange::Seek(DecodeTimestamp timestamp) { |
| 1740 DCHECK(CanSeekTo(timestamp)); | 1749 DCHECK(CanSeekTo(timestamp)); |
| 1741 DCHECK(!keyframe_map_.empty()); | 1750 DCHECK(!keyframe_map_.empty()); |
| 1742 | 1751 |
| 1743 KeyframeMap::iterator result = GetFirstKeyframeBefore(timestamp); | 1752 KeyframeMap::iterator result = GetFirstKeyframeBefore(timestamp); |
| 1744 next_buffer_index_ = result->second - keyframe_map_index_base_; | 1753 next_buffer_index_ = result->second - keyframe_map_index_base_; |
| 1745 DCHECK_LT(next_buffer_index_, static_cast<int>(buffers_.size())); | 1754 DCHECK_LT(next_buffer_index_, static_cast<int>(buffers_.size())); |
| 1746 } | 1755 } |
| 1747 | 1756 |
| 1748 void SourceBufferRange::SeekAheadTo(base::TimeDelta timestamp) { | 1757 void SourceBufferRange::SeekAheadTo(DecodeTimestamp timestamp) { |
| 1749 SeekAhead(timestamp, false); | 1758 SeekAhead(timestamp, false); |
| 1750 } | 1759 } |
| 1751 | 1760 |
| 1752 void SourceBufferRange::SeekAheadPast(base::TimeDelta timestamp) { | 1761 void SourceBufferRange::SeekAheadPast(DecodeTimestamp timestamp) { |
| 1753 SeekAhead(timestamp, true); | 1762 SeekAhead(timestamp, true); |
| 1754 } | 1763 } |
| 1755 | 1764 |
| 1756 void SourceBufferRange::SeekAhead(base::TimeDelta timestamp, | 1765 void SourceBufferRange::SeekAhead(DecodeTimestamp timestamp, |
| 1757 bool skip_given_timestamp) { | 1766 bool skip_given_timestamp) { |
| 1758 DCHECK(!keyframe_map_.empty()); | 1767 DCHECK(!keyframe_map_.empty()); |
| 1759 | 1768 |
| 1760 KeyframeMap::iterator result = | 1769 KeyframeMap::iterator result = |
| 1761 GetFirstKeyframeAt(timestamp, skip_given_timestamp); | 1770 GetFirstKeyframeAt(timestamp, skip_given_timestamp); |
| 1762 | 1771 |
| 1763 // If there isn't a keyframe after |timestamp|, then seek to end and return | 1772 // If there isn't a keyframe after |timestamp|, then seek to end and return |
| 1764 // kNoTimestamp to signal such. | 1773 // kNoTimestamp to signal such. |
| 1765 if (result == keyframe_map_.end()) { | 1774 if (result == keyframe_map_.end()) { |
| 1766 next_buffer_index_ = -1; | 1775 next_buffer_index_ = -1; |
| 1767 return; | 1776 return; |
| 1768 } | 1777 } |
| 1769 next_buffer_index_ = result->second - keyframe_map_index_base_; | 1778 next_buffer_index_ = result->second - keyframe_map_index_base_; |
| 1770 DCHECK_LT(next_buffer_index_, static_cast<int>(buffers_.size())); | 1779 DCHECK_LT(next_buffer_index_, static_cast<int>(buffers_.size())); |
| 1771 } | 1780 } |
| 1772 | 1781 |
| 1773 void SourceBufferRange::SeekToStart() { | 1782 void SourceBufferRange::SeekToStart() { |
| 1774 DCHECK(!buffers_.empty()); | 1783 DCHECK(!buffers_.empty()); |
| 1775 next_buffer_index_ = 0; | 1784 next_buffer_index_ = 0; |
| 1776 } | 1785 } |
| 1777 | 1786 |
| 1778 SourceBufferRange* SourceBufferRange::SplitRange( | 1787 SourceBufferRange* SourceBufferRange::SplitRange( |
| 1779 base::TimeDelta timestamp, bool is_exclusive) { | 1788 DecodeTimestamp timestamp, bool is_exclusive) { |
| 1780 CHECK(!buffers_.empty()); | 1789 CHECK(!buffers_.empty()); |
| 1781 | 1790 |
| 1782 // Find the first keyframe after |timestamp|. If |is_exclusive|, do not | 1791 // Find the first keyframe after |timestamp|. If |is_exclusive|, do not |
| 1783 // include keyframes at |timestamp|. | 1792 // include keyframes at |timestamp|. |
| 1784 KeyframeMap::iterator new_beginning_keyframe = | 1793 KeyframeMap::iterator new_beginning_keyframe = |
| 1785 GetFirstKeyframeAt(timestamp, is_exclusive); | 1794 GetFirstKeyframeAt(timestamp, is_exclusive); |
| 1786 | 1795 |
| 1787 // If there is no keyframe after |timestamp|, we can't split the range. | 1796 // If there is no keyframe after |timestamp|, we can't split the range. |
| 1788 if (new_beginning_keyframe == keyframe_map_.end()) | 1797 if (new_beginning_keyframe == keyframe_map_.end()) |
| 1789 return NULL; | 1798 return NULL; |
| 1790 | 1799 |
| 1791 // Remove the data beginning at |keyframe_index| from |buffers_| and save it | 1800 // Remove the data beginning at |keyframe_index| from |buffers_| and save it |
| 1792 // into |removed_buffers|. | 1801 // into |removed_buffers|. |
| 1793 int keyframe_index = | 1802 int keyframe_index = |
| 1794 new_beginning_keyframe->second - keyframe_map_index_base_; | 1803 new_beginning_keyframe->second - keyframe_map_index_base_; |
| 1795 DCHECK_LT(keyframe_index, static_cast<int>(buffers_.size())); | 1804 DCHECK_LT(keyframe_index, static_cast<int>(buffers_.size())); |
| 1796 BufferQueue::iterator starting_point = buffers_.begin() + keyframe_index; | 1805 BufferQueue::iterator starting_point = buffers_.begin() + keyframe_index; |
| 1797 BufferQueue removed_buffers(starting_point, buffers_.end()); | 1806 BufferQueue removed_buffers(starting_point, buffers_.end()); |
| 1798 | 1807 |
| 1799 base::TimeDelta new_range_start_timestamp = kNoTimestamp(); | 1808 DecodeTimestamp new_range_start_timestamp = kNoDecodeTimestamp(); |
| 1800 if (GetStartTimestamp() < buffers_.front()->GetDecodeTimestamp() && | 1809 if (GetStartTimestamp() < buffers_.front()->GetDecodeTimestamp() && |
| 1801 timestamp < removed_buffers.front()->GetDecodeTimestamp()) { | 1810 timestamp < removed_buffers.front()->GetDecodeTimestamp()) { |
| 1802 // The split is in the gap between |media_segment_start_time_| and | 1811 // The split is in the gap between |media_segment_start_time_| and |
| 1803 // the first buffer of the new range so we should set the start | 1812 // the first buffer of the new range so we should set the start |
| 1804 // time of the new range to |timestamp| so we preserve part of the | 1813 // time of the new range to |timestamp| so we preserve part of the |
| 1805 // gap in the new range. | 1814 // gap in the new range. |
| 1806 new_range_start_timestamp = timestamp; | 1815 new_range_start_timestamp = timestamp; |
| 1807 } | 1816 } |
| 1808 | 1817 |
| 1809 keyframe_map_.erase(new_beginning_keyframe, keyframe_map_.end()); | 1818 keyframe_map_.erase(new_beginning_keyframe, keyframe_map_.end()); |
| 1810 FreeBufferRange(starting_point, buffers_.end()); | 1819 FreeBufferRange(starting_point, buffers_.end()); |
| 1811 | 1820 |
| 1812 // Create a new range with |removed_buffers|. | 1821 // Create a new range with |removed_buffers|. |
| 1813 SourceBufferRange* split_range = | 1822 SourceBufferRange* split_range = |
| 1814 new SourceBufferRange( | 1823 new SourceBufferRange( |
| 1815 type_, removed_buffers, new_range_start_timestamp, | 1824 type_, removed_buffers, new_range_start_timestamp, |
| 1816 interbuffer_distance_cb_); | 1825 interbuffer_distance_cb_); |
| 1817 | 1826 |
| 1818 // If the next buffer position is now in |split_range|, update the state of | 1827 // If the next buffer position is now in |split_range|, update the state of |
| 1819 // this range and |split_range| accordingly. | 1828 // this range and |split_range| accordingly. |
| 1820 if (next_buffer_index_ >= static_cast<int>(buffers_.size())) { | 1829 if (next_buffer_index_ >= static_cast<int>(buffers_.size())) { |
| 1821 split_range->next_buffer_index_ = next_buffer_index_ - keyframe_index; | 1830 split_range->next_buffer_index_ = next_buffer_index_ - keyframe_index; |
| 1822 ResetNextBufferPosition(); | 1831 ResetNextBufferPosition(); |
| 1823 } | 1832 } |
| 1824 | 1833 |
| 1825 return split_range; | 1834 return split_range; |
| 1826 } | 1835 } |
| 1827 | 1836 |
| 1828 BufferQueue::iterator SourceBufferRange::GetBufferItrAt( | 1837 BufferQueue::iterator SourceBufferRange::GetBufferItrAt( |
| 1829 base::TimeDelta timestamp, | 1838 DecodeTimestamp timestamp, |
| 1830 bool skip_given_timestamp) { | 1839 bool skip_given_timestamp) { |
| 1831 return skip_given_timestamp | 1840 return skip_given_timestamp |
| 1832 ? std::upper_bound(buffers_.begin(), | 1841 ? std::upper_bound(buffers_.begin(), |
| 1833 buffers_.end(), | 1842 buffers_.end(), |
| 1834 timestamp, | 1843 timestamp, |
| 1835 CompareTimeDeltaToStreamParserBuffer) | 1844 CompareTimeDeltaToStreamParserBuffer) |
| 1836 : std::lower_bound(buffers_.begin(), | 1845 : std::lower_bound(buffers_.begin(), |
| 1837 buffers_.end(), | 1846 buffers_.end(), |
| 1838 timestamp, | 1847 timestamp, |
| 1839 CompareStreamParserBufferToTimeDelta); | 1848 CompareStreamParserBufferToTimeDelta); |
| 1840 } | 1849 } |
| 1841 | 1850 |
| 1842 SourceBufferRange::KeyframeMap::iterator | 1851 SourceBufferRange::KeyframeMap::iterator |
| 1843 SourceBufferRange::GetFirstKeyframeAt(base::TimeDelta timestamp, | 1852 SourceBufferRange::GetFirstKeyframeAt(DecodeTimestamp timestamp, |
| 1844 bool skip_given_timestamp) { | 1853 bool skip_given_timestamp) { |
| 1845 return skip_given_timestamp ? | 1854 return skip_given_timestamp ? |
| 1846 keyframe_map_.upper_bound(timestamp) : | 1855 keyframe_map_.upper_bound(timestamp) : |
| 1847 keyframe_map_.lower_bound(timestamp); | 1856 keyframe_map_.lower_bound(timestamp); |
| 1848 } | 1857 } |
| 1849 | 1858 |
| 1850 SourceBufferRange::KeyframeMap::iterator | 1859 SourceBufferRange::KeyframeMap::iterator |
| 1851 SourceBufferRange::GetFirstKeyframeBefore(base::TimeDelta timestamp) { | 1860 SourceBufferRange::GetFirstKeyframeBefore(DecodeTimestamp timestamp) { |
| 1852 KeyframeMap::iterator result = keyframe_map_.lower_bound(timestamp); | 1861 KeyframeMap::iterator result = keyframe_map_.lower_bound(timestamp); |
| 1853 // lower_bound() returns the first element >= |timestamp|, so we want the | 1862 // lower_bound() returns the first element >= |timestamp|, so we want the |
| 1854 // previous element if it did not return the element exactly equal to | 1863 // previous element if it did not return the element exactly equal to |
| 1855 // |timestamp|. | 1864 // |timestamp|. |
| 1856 if (result != keyframe_map_.begin() && | 1865 if (result != keyframe_map_.begin() && |
| 1857 (result == keyframe_map_.end() || result->first != timestamp)) { | 1866 (result == keyframe_map_.end() || result->first != timestamp)) { |
| 1858 --result; | 1867 --result; |
| 1859 } | 1868 } |
| 1860 return result; | 1869 return result; |
| 1861 } | 1870 } |
| 1862 | 1871 |
| 1863 void SourceBufferRange::DeleteAll(BufferQueue* removed_buffers) { | 1872 void SourceBufferRange::DeleteAll(BufferQueue* removed_buffers) { |
| 1864 TruncateAt(buffers_.begin(), removed_buffers); | 1873 TruncateAt(buffers_.begin(), removed_buffers); |
| 1865 } | 1874 } |
| 1866 | 1875 |
| 1867 bool SourceBufferRange::TruncateAt( | 1876 bool SourceBufferRange::TruncateAt( |
| 1868 base::TimeDelta timestamp, BufferQueue* removed_buffers, | 1877 DecodeTimestamp timestamp, BufferQueue* removed_buffers, |
| 1869 bool is_exclusive) { | 1878 bool is_exclusive) { |
| 1870 // Find the place in |buffers_| where we will begin deleting data. | 1879 // Find the place in |buffers_| where we will begin deleting data. |
| 1871 BufferQueue::iterator starting_point = | 1880 BufferQueue::iterator starting_point = |
| 1872 GetBufferItrAt(timestamp, is_exclusive); | 1881 GetBufferItrAt(timestamp, is_exclusive); |
| 1873 return TruncateAt(starting_point, removed_buffers); | 1882 return TruncateAt(starting_point, removed_buffers); |
| 1874 } | 1883 } |
| 1875 | 1884 |
| 1876 int SourceBufferRange::DeleteGOPFromFront(BufferQueue* deleted_buffers) { | 1885 int SourceBufferRange::DeleteGOPFromFront(BufferQueue* deleted_buffers) { |
| 1877 DCHECK(!FirstGOPContainsNextBufferPosition()); | 1886 DCHECK(!FirstGOPContainsNextBufferPosition()); |
| 1878 DCHECK(deleted_buffers); | 1887 DCHECK(deleted_buffers); |
| (...skipping 28 matching lines...) Expand all Loading... | |
| 1907 keyframe_map_index_base_ += buffers_deleted; | 1916 keyframe_map_index_base_ += buffers_deleted; |
| 1908 | 1917 |
| 1909 if (next_buffer_index_ > -1) { | 1918 if (next_buffer_index_ > -1) { |
| 1910 next_buffer_index_ -= buffers_deleted; | 1919 next_buffer_index_ -= buffers_deleted; |
| 1911 DCHECK_GE(next_buffer_index_, 0); | 1920 DCHECK_GE(next_buffer_index_, 0); |
| 1912 } | 1921 } |
| 1913 | 1922 |
| 1914 // Invalidate media segment start time if we've deleted the first buffer of | 1923 // Invalidate media segment start time if we've deleted the first buffer of |
| 1915 // the range. | 1924 // the range. |
| 1916 if (buffers_deleted > 0) | 1925 if (buffers_deleted > 0) |
| 1917 media_segment_start_time_ = kNoTimestamp(); | 1926 media_segment_start_time_ = kNoDecodeTimestamp(); |
| 1918 | 1927 |
| 1919 return total_bytes_deleted; | 1928 return total_bytes_deleted; |
| 1920 } | 1929 } |
| 1921 | 1930 |
| 1922 int SourceBufferRange::DeleteGOPFromBack(BufferQueue* deleted_buffers) { | 1931 int SourceBufferRange::DeleteGOPFromBack(BufferQueue* deleted_buffers) { |
| 1923 DCHECK(!LastGOPContainsNextBufferPosition()); | 1932 DCHECK(!LastGOPContainsNextBufferPosition()); |
| 1924 DCHECK(deleted_buffers); | 1933 DCHECK(deleted_buffers); |
| 1925 | 1934 |
| 1926 // Remove the last GOP's keyframe from the |keyframe_map_|. | 1935 // Remove the last GOP's keyframe from the |keyframe_map_|. |
| 1927 KeyframeMap::iterator back = keyframe_map_.end(); | 1936 KeyframeMap::iterator back = keyframe_map_.end(); |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 1942 // front of |deleted_buffers| so that |deleted_buffers| are in nondecreasing | 1951 // front of |deleted_buffers| so that |deleted_buffers| are in nondecreasing |
| 1943 // order. | 1952 // order. |
| 1944 deleted_buffers->push_front(buffers_.back()); | 1953 deleted_buffers->push_front(buffers_.back()); |
| 1945 buffers_.pop_back(); | 1954 buffers_.pop_back(); |
| 1946 } | 1955 } |
| 1947 | 1956 |
| 1948 return total_bytes_deleted; | 1957 return total_bytes_deleted; |
| 1949 } | 1958 } |
| 1950 | 1959 |
| 1951 int SourceBufferRange::GetRemovalGOP( | 1960 int SourceBufferRange::GetRemovalGOP( |
| 1952 base::TimeDelta start_timestamp, base::TimeDelta end_timestamp, | 1961 DecodeTimestamp start_timestamp, DecodeTimestamp end_timestamp, |
| 1953 int total_bytes_to_free, base::TimeDelta* removal_end_timestamp) { | 1962 int total_bytes_to_free, DecodeTimestamp* removal_end_timestamp) { |
| 1954 int bytes_to_free = total_bytes_to_free; | 1963 int bytes_to_free = total_bytes_to_free; |
| 1955 int bytes_removed = 0; | 1964 int bytes_removed = 0; |
| 1956 | 1965 |
| 1957 KeyframeMap::iterator gop_itr = GetFirstKeyframeAt(start_timestamp, false); | 1966 KeyframeMap::iterator gop_itr = GetFirstKeyframeAt(start_timestamp, false); |
| 1958 if (gop_itr == keyframe_map_.end()) | 1967 if (gop_itr == keyframe_map_.end()) |
| 1959 return 0; | 1968 return 0; |
| 1960 int keyframe_index = gop_itr->second - keyframe_map_index_base_; | 1969 int keyframe_index = gop_itr->second - keyframe_map_index_base_; |
| 1961 BufferQueue::iterator buffer_itr = buffers_.begin() + keyframe_index; | 1970 BufferQueue::iterator buffer_itr = buffers_.begin() + keyframe_index; |
| 1962 KeyframeMap::iterator gop_end = keyframe_map_.end(); | 1971 KeyframeMap::iterator gop_end = keyframe_map_.end(); |
| 1963 if (end_timestamp < GetBufferedEndTimestamp()) | 1972 if (end_timestamp < GetBufferedEndTimestamp()) |
| (...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2030 const BufferQueue::iterator& starting_point, BufferQueue* removed_buffers) { | 2039 const BufferQueue::iterator& starting_point, BufferQueue* removed_buffers) { |
| 2031 DCHECK(!removed_buffers || removed_buffers->empty()); | 2040 DCHECK(!removed_buffers || removed_buffers->empty()); |
| 2032 | 2041 |
| 2033 // Return if we're not deleting anything. | 2042 // Return if we're not deleting anything. |
| 2034 if (starting_point == buffers_.end()) | 2043 if (starting_point == buffers_.end()) |
| 2035 return buffers_.empty(); | 2044 return buffers_.empty(); |
| 2036 | 2045 |
| 2037 // Reset the next buffer index if we will be deleting the buffer that's next | 2046 // Reset the next buffer index if we will be deleting the buffer that's next |
| 2038 // in sequence. | 2047 // in sequence. |
| 2039 if (HasNextBufferPosition()) { | 2048 if (HasNextBufferPosition()) { |
| 2040 base::TimeDelta next_buffer_timestamp = GetNextTimestamp(); | 2049 DecodeTimestamp next_buffer_timestamp = GetNextTimestamp(); |
| 2041 if (next_buffer_timestamp == kNoTimestamp() || | 2050 if (next_buffer_timestamp == kNoDecodeTimestamp() || |
| 2042 next_buffer_timestamp >= (*starting_point)->GetDecodeTimestamp()) { | 2051 next_buffer_timestamp >= (*starting_point)->GetDecodeTimestamp()) { |
| 2043 if (HasNextBuffer() && removed_buffers) { | 2052 if (HasNextBuffer() && removed_buffers) { |
| 2044 int starting_offset = starting_point - buffers_.begin(); | 2053 int starting_offset = starting_point - buffers_.begin(); |
| 2045 int next_buffer_offset = next_buffer_index_ - starting_offset; | 2054 int next_buffer_offset = next_buffer_index_ - starting_offset; |
| 2046 DCHECK_GE(next_buffer_offset, 0); | 2055 DCHECK_GE(next_buffer_offset, 0); |
| 2047 BufferQueue saved(starting_point + next_buffer_offset, buffers_.end()); | 2056 BufferQueue saved(starting_point + next_buffer_offset, buffers_.end()); |
| 2048 removed_buffers->swap(saved); | 2057 removed_buffers->swap(saved); |
| 2049 } | 2058 } |
| 2050 ResetNextBufferPosition(); | 2059 ResetNextBufferPosition(); |
| 2051 } | 2060 } |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 2076 next_buffer_index_ < static_cast<int>(buffers_.size()); | 2085 next_buffer_index_ < static_cast<int>(buffers_.size()); |
| 2077 } | 2086 } |
| 2078 | 2087 |
| 2079 int SourceBufferRange::GetNextConfigId() const { | 2088 int SourceBufferRange::GetNextConfigId() const { |
| 2080 DCHECK(HasNextBuffer()); | 2089 DCHECK(HasNextBuffer()); |
| 2081 // If the next buffer is an audio splice frame, the next effective config id | 2090 // If the next buffer is an audio splice frame, the next effective config id |
| 2082 // comes from the first fade out preroll buffer. | 2091 // comes from the first fade out preroll buffer. |
| 2083 return GetConfigId(buffers_[next_buffer_index_], 0); | 2092 return GetConfigId(buffers_[next_buffer_index_], 0); |
| 2084 } | 2093 } |
| 2085 | 2094 |
| 2086 base::TimeDelta SourceBufferRange::GetNextTimestamp() const { | 2095 DecodeTimestamp SourceBufferRange::GetNextTimestamp() const { |
| 2087 DCHECK(!buffers_.empty()); | 2096 DCHECK(!buffers_.empty()); |
| 2088 DCHECK(HasNextBufferPosition()); | 2097 DCHECK(HasNextBufferPosition()); |
| 2089 | 2098 |
| 2090 if (next_buffer_index_ >= static_cast<int>(buffers_.size())) { | 2099 if (next_buffer_index_ >= static_cast<int>(buffers_.size())) { |
| 2091 return kNoTimestamp(); | 2100 return kNoDecodeTimestamp(); |
| 2092 } | 2101 } |
| 2093 | 2102 |
| 2094 return buffers_[next_buffer_index_]->GetDecodeTimestamp(); | 2103 return buffers_[next_buffer_index_]->GetDecodeTimestamp(); |
| 2095 } | 2104 } |
| 2096 | 2105 |
| 2097 bool SourceBufferRange::HasNextBufferPosition() const { | 2106 bool SourceBufferRange::HasNextBufferPosition() const { |
| 2098 return next_buffer_index_ >= 0; | 2107 return next_buffer_index_ >= 0; |
| 2099 } | 2108 } |
| 2100 | 2109 |
| 2101 void SourceBufferRange::ResetNextBufferPosition() { | 2110 void SourceBufferRange::ResetNextBufferPosition() { |
| (...skipping 16 matching lines...) Expand all Loading... | |
| 2118 return CanAppendBuffersToEnd(range.buffers_); | 2127 return CanAppendBuffersToEnd(range.buffers_); |
| 2119 } | 2128 } |
| 2120 | 2129 |
| 2121 bool SourceBufferRange::CanAppendBuffersToEnd( | 2130 bool SourceBufferRange::CanAppendBuffersToEnd( |
| 2122 const BufferQueue& buffers) const { | 2131 const BufferQueue& buffers) const { |
| 2123 DCHECK(!buffers_.empty()); | 2132 DCHECK(!buffers_.empty()); |
| 2124 return IsNextInSequence(buffers.front()->GetDecodeTimestamp(), | 2133 return IsNextInSequence(buffers.front()->GetDecodeTimestamp(), |
| 2125 buffers.front()->IsKeyframe()); | 2134 buffers.front()->IsKeyframe()); |
| 2126 } | 2135 } |
| 2127 | 2136 |
| 2128 bool SourceBufferRange::BelongsToRange(base::TimeDelta timestamp) const { | 2137 bool SourceBufferRange::BelongsToRange(DecodeTimestamp timestamp) const { |
| 2129 DCHECK(!buffers_.empty()); | 2138 DCHECK(!buffers_.empty()); |
| 2130 | 2139 |
| 2131 return (IsNextInSequence(timestamp, false) || | 2140 return (IsNextInSequence(timestamp, false) || |
| 2132 (GetStartTimestamp() <= timestamp && timestamp <= GetEndTimestamp())); | 2141 (GetStartTimestamp() <= timestamp && timestamp <= GetEndTimestamp())); |
| 2133 } | 2142 } |
| 2134 | 2143 |
| 2135 bool SourceBufferRange::CanSeekTo(base::TimeDelta timestamp) const { | 2144 bool SourceBufferRange::CanSeekTo(DecodeTimestamp timestamp) const { |
| 2136 base::TimeDelta start_timestamp = | 2145 DecodeTimestamp start_timestamp = |
| 2137 std::max(base::TimeDelta(), GetStartTimestamp() - GetFudgeRoom()); | 2146 std::max(DecodeTimestamp(), GetStartTimestamp() - GetFudgeRoom()); |
| 2138 return !keyframe_map_.empty() && start_timestamp <= timestamp && | 2147 return !keyframe_map_.empty() && start_timestamp <= timestamp && |
| 2139 timestamp < GetBufferedEndTimestamp(); | 2148 timestamp < GetBufferedEndTimestamp(); |
| 2140 } | 2149 } |
| 2141 | 2150 |
| 2142 bool SourceBufferRange::CompletelyOverlaps( | 2151 bool SourceBufferRange::CompletelyOverlaps( |
| 2143 const SourceBufferRange& range) const { | 2152 const SourceBufferRange& range) const { |
| 2144 return GetStartTimestamp() <= range.GetStartTimestamp() && | 2153 return GetStartTimestamp() <= range.GetStartTimestamp() && |
| 2145 GetEndTimestamp() >= range.GetEndTimestamp(); | 2154 GetEndTimestamp() >= range.GetEndTimestamp(); |
| 2146 } | 2155 } |
| 2147 | 2156 |
| 2148 bool SourceBufferRange::EndOverlaps(const SourceBufferRange& range) const { | 2157 bool SourceBufferRange::EndOverlaps(const SourceBufferRange& range) const { |
| 2149 return range.GetStartTimestamp() <= GetEndTimestamp() && | 2158 return range.GetStartTimestamp() <= GetEndTimestamp() && |
| 2150 GetEndTimestamp() < range.GetEndTimestamp(); | 2159 GetEndTimestamp() < range.GetEndTimestamp(); |
| 2151 } | 2160 } |
| 2152 | 2161 |
| 2153 base::TimeDelta SourceBufferRange::GetStartTimestamp() const { | 2162 DecodeTimestamp SourceBufferRange::GetStartTimestamp() const { |
| 2154 DCHECK(!buffers_.empty()); | 2163 DCHECK(!buffers_.empty()); |
| 2155 base::TimeDelta start_timestamp = media_segment_start_time_; | 2164 DecodeTimestamp start_timestamp = media_segment_start_time_; |
| 2156 if (start_timestamp == kNoTimestamp()) | 2165 if (start_timestamp == kNoDecodeTimestamp()) |
| 2157 start_timestamp = buffers_.front()->GetDecodeTimestamp(); | 2166 start_timestamp = buffers_.front()->GetDecodeTimestamp(); |
| 2158 return start_timestamp; | 2167 return start_timestamp; |
| 2159 } | 2168 } |
| 2160 | 2169 |
| 2161 base::TimeDelta SourceBufferRange::GetEndTimestamp() const { | 2170 DecodeTimestamp SourceBufferRange::GetEndTimestamp() const { |
| 2162 DCHECK(!buffers_.empty()); | 2171 DCHECK(!buffers_.empty()); |
| 2163 return buffers_.back()->GetDecodeTimestamp(); | 2172 return buffers_.back()->GetDecodeTimestamp(); |
| 2164 } | 2173 } |
| 2165 | 2174 |
| 2166 base::TimeDelta SourceBufferRange::GetBufferedEndTimestamp() const { | 2175 DecodeTimestamp SourceBufferRange::GetBufferedEndTimestamp() const { |
| 2167 DCHECK(!buffers_.empty()); | 2176 DCHECK(!buffers_.empty()); |
| 2168 base::TimeDelta duration = buffers_.back()->duration(); | 2177 base::TimeDelta duration = buffers_.back()->duration(); |
| 2169 if (duration == kNoTimestamp() || duration == base::TimeDelta()) | 2178 if (duration == kNoTimestamp() || duration == base::TimeDelta()) |
| 2170 duration = GetApproximateDuration(); | 2179 duration = GetApproximateDuration(); |
| 2171 return GetEndTimestamp() + duration; | 2180 return GetEndTimestamp() + duration; |
| 2172 } | 2181 } |
| 2173 | 2182 |
| 2174 base::TimeDelta SourceBufferRange::NextKeyframeTimestamp( | 2183 DecodeTimestamp SourceBufferRange::NextKeyframeTimestamp( |
| 2175 base::TimeDelta timestamp) { | 2184 DecodeTimestamp timestamp) { |
| 2176 DCHECK(!keyframe_map_.empty()); | 2185 DCHECK(!keyframe_map_.empty()); |
| 2177 | 2186 |
| 2178 if (timestamp < GetStartTimestamp() || timestamp >= GetBufferedEndTimestamp()) | 2187 if (timestamp < GetStartTimestamp() || timestamp >= GetBufferedEndTimestamp()) |
| 2179 return kNoTimestamp(); | 2188 return kNoDecodeTimestamp(); |
| 2180 | 2189 |
| 2181 KeyframeMap::iterator itr = GetFirstKeyframeAt(timestamp, false); | 2190 KeyframeMap::iterator itr = GetFirstKeyframeAt(timestamp, false); |
| 2182 if (itr == keyframe_map_.end()) | 2191 if (itr == keyframe_map_.end()) |
| 2183 return kNoTimestamp(); | 2192 return kNoDecodeTimestamp(); |
| 2184 | 2193 |
| 2185 // If the timestamp is inside the gap between the start of the media | 2194 // If the timestamp is inside the gap between the start of the media |
| 2186 // segment and the first buffer, then just pretend there is a | 2195 // segment and the first buffer, then just pretend there is a |
| 2187 // keyframe at the specified timestamp. | 2196 // keyframe at the specified timestamp. |
| 2188 if (itr == keyframe_map_.begin() && | 2197 if (itr == keyframe_map_.begin() && |
| 2189 timestamp > media_segment_start_time_ && | 2198 timestamp > media_segment_start_time_ && |
| 2190 timestamp < itr->first) { | 2199 timestamp < itr->first) { |
| 2191 return timestamp; | 2200 return timestamp; |
| 2192 } | 2201 } |
| 2193 | 2202 |
| 2194 return itr->first; | 2203 return itr->first; |
| 2195 } | 2204 } |
| 2196 | 2205 |
| 2197 base::TimeDelta SourceBufferRange::KeyframeBeforeTimestamp( | 2206 DecodeTimestamp SourceBufferRange::KeyframeBeforeTimestamp( |
| 2198 base::TimeDelta timestamp) { | 2207 DecodeTimestamp timestamp) { |
| 2199 DCHECK(!keyframe_map_.empty()); | 2208 DCHECK(!keyframe_map_.empty()); |
| 2200 | 2209 |
| 2201 if (timestamp < GetStartTimestamp() || timestamp >= GetBufferedEndTimestamp()) | 2210 if (timestamp < GetStartTimestamp() || timestamp >= GetBufferedEndTimestamp()) |
| 2202 return kNoTimestamp(); | 2211 return kNoDecodeTimestamp(); |
| 2203 | 2212 |
| 2204 return GetFirstKeyframeBefore(timestamp)->first; | 2213 return GetFirstKeyframeBefore(timestamp)->first; |
| 2205 } | 2214 } |
| 2206 | 2215 |
| 2207 bool SourceBufferRange::IsNextInSequence( | 2216 bool SourceBufferRange::IsNextInSequence( |
| 2208 base::TimeDelta timestamp, bool is_keyframe) const { | 2217 DecodeTimestamp timestamp, bool is_keyframe) const { |
| 2209 base::TimeDelta end = buffers_.back()->GetDecodeTimestamp(); | 2218 DecodeTimestamp end = buffers_.back()->GetDecodeTimestamp(); |
| 2210 if (end < timestamp && | 2219 if (end < timestamp && |
| 2211 (type_ == SourceBufferStream::kText || | 2220 (type_ == SourceBufferStream::kText || |
| 2212 timestamp <= end + GetFudgeRoom())) { | 2221 timestamp <= end + GetFudgeRoom())) { |
| 2213 return true; | 2222 return true; |
| 2214 } | 2223 } |
| 2215 | 2224 |
| 2216 return timestamp == end && AllowSameTimestamp( | 2225 return timestamp == end && AllowSameTimestamp( |
| 2217 buffers_.back()->IsKeyframe(), is_keyframe, type_); | 2226 buffers_.back()->IsKeyframe(), is_keyframe, type_); |
| 2218 } | 2227 } |
| 2219 | 2228 |
| 2220 base::TimeDelta SourceBufferRange::GetFudgeRoom() const { | 2229 base::TimeDelta SourceBufferRange::GetFudgeRoom() const { |
| 2221 return ComputeFudgeRoom(GetApproximateDuration()); | 2230 return ComputeFudgeRoom(GetApproximateDuration()); |
| 2222 } | 2231 } |
| 2223 | 2232 |
| 2224 base::TimeDelta SourceBufferRange::GetApproximateDuration() const { | 2233 base::TimeDelta SourceBufferRange::GetApproximateDuration() const { |
| 2225 base::TimeDelta max_interbuffer_distance = interbuffer_distance_cb_.Run(); | 2234 base::TimeDelta max_interbuffer_distance = interbuffer_distance_cb_.Run(); |
| 2226 DCHECK(max_interbuffer_distance != kNoTimestamp()); | 2235 DCHECK(max_interbuffer_distance != kNoTimestamp()); |
| 2227 return max_interbuffer_distance; | 2236 return max_interbuffer_distance; |
| 2228 } | 2237 } |
| 2229 | 2238 |
| 2230 bool SourceBufferRange::GetBuffersInRange(base::TimeDelta start, | 2239 bool SourceBufferRange::GetBuffersInRange(DecodeTimestamp start, |
| 2231 base::TimeDelta end, | 2240 DecodeTimestamp end, |
| 2232 BufferQueue* buffers) { | 2241 BufferQueue* buffers) { |
| 2233 // Find the nearest buffer with a decode timestamp <= start. | 2242 // Find the nearest buffer with a decode timestamp <= start. |
| 2234 const base::TimeDelta first_timestamp = KeyframeBeforeTimestamp(start); | 2243 const DecodeTimestamp first_timestamp = KeyframeBeforeTimestamp(start); |
| 2235 if (first_timestamp == kNoTimestamp()) | 2244 if (first_timestamp == kNoDecodeTimestamp()) |
| 2236 return false; | 2245 return false; |
| 2237 | 2246 |
| 2238 // Find all buffers involved in the range. | 2247 // Find all buffers involved in the range. |
| 2239 const size_t previous_size = buffers->size(); | 2248 const size_t previous_size = buffers->size(); |
| 2240 for (BufferQueue::iterator it = GetBufferItrAt(first_timestamp, false); | 2249 for (BufferQueue::iterator it = GetBufferItrAt(first_timestamp, false); |
| 2241 it != buffers_.end(); | 2250 it != buffers_.end(); |
| 2242 ++it) { | 2251 ++it) { |
| 2243 const scoped_refptr<StreamParserBuffer>& buffer = *it; | 2252 const scoped_refptr<StreamParserBuffer>& buffer = *it; |
| 2244 // Buffers without duration are not supported, so bail if we encounter any. | 2253 // Buffers without duration are not supported, so bail if we encounter any. |
| 2245 if (buffer->duration() == kNoTimestamp() || | 2254 if (buffer->duration() == kNoTimestamp() || |
| 2246 buffer->duration() <= base::TimeDelta()) { | 2255 buffer->duration() <= base::TimeDelta()) { |
| 2247 return false; | 2256 return false; |
| 2248 } | 2257 } |
| 2249 if (buffer->end_of_stream() || buffer->timestamp() >= end) | 2258 if (buffer->end_of_stream() || |
| 2259 buffer->timestamp() >= end.ToPresentationTime()) { | |
| 2250 break; | 2260 break; |
| 2251 if (buffer->timestamp() + buffer->duration() <= start) | 2261 } |
| 2262 | |
| 2263 if (buffer->timestamp() + buffer->duration() <= start.ToPresentationTime()) | |
| 2252 continue; | 2264 continue; |
| 2253 buffers->push_back(buffer); | 2265 buffers->push_back(buffer); |
| 2254 } | 2266 } |
| 2255 return previous_size < buffers->size(); | 2267 return previous_size < buffers->size(); |
| 2256 } | 2268 } |
| 2257 | 2269 |
| 2258 bool SourceBufferStream::SetPendingBuffer( | 2270 bool SourceBufferStream::SetPendingBuffer( |
| 2259 scoped_refptr<StreamParserBuffer>* out_buffer) { | 2271 scoped_refptr<StreamParserBuffer>* out_buffer) { |
| 2260 DCHECK(*out_buffer); | 2272 DCHECK(*out_buffer); |
| 2261 DCHECK(!pending_buffer_); | 2273 DCHECK(!pending_buffer_); |
| 2262 | 2274 |
| 2263 const bool have_splice_buffers = !(*out_buffer)->splice_buffers().empty(); | 2275 const bool have_splice_buffers = !(*out_buffer)->splice_buffers().empty(); |
| 2264 const bool have_preroll_buffer = !!(*out_buffer)->preroll_buffer(); | 2276 const bool have_preroll_buffer = !!(*out_buffer)->preroll_buffer(); |
| 2265 | 2277 |
| 2266 if (!have_splice_buffers && !have_preroll_buffer) | 2278 if (!have_splice_buffers && !have_preroll_buffer) |
| 2267 return false; | 2279 return false; |
| 2268 | 2280 |
| 2269 DCHECK_NE(have_splice_buffers, have_preroll_buffer); | 2281 DCHECK_NE(have_splice_buffers, have_preroll_buffer); |
| 2270 splice_buffers_index_ = 0; | 2282 splice_buffers_index_ = 0; |
| 2271 pending_buffer_.swap(*out_buffer); | 2283 pending_buffer_.swap(*out_buffer); |
| 2272 pending_buffers_complete_ = false; | 2284 pending_buffers_complete_ = false; |
| 2273 return true; | 2285 return true; |
| 2274 } | 2286 } |
| 2275 | 2287 |
| 2276 } // namespace media | 2288 } // namespace media |
| OLD | NEW |