1 /* ------------------------------------------------------------------
2 * Copyright (C) 1998-2009 PacketVideo
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
13 * express or implied.
14 * See the License for the specific language governing permissions
15 * and limitations under the License.
16 * -------------------------------------------------------------------
17 */
18 /*********************************************************************************/
19 /* ------------------------------------------------------------------- */
20 /* MPEG-4 TimeToSampleAtom Class */
21 /* ------------------------------------------------------------------- */
22 /*********************************************************************************/
23 /*
24 This TimeToSampleAtom Class contains a compact version of a table that allows
25 indexing from decoding to sample number.
26 */
27
28
29 #define IMPLEMENT_TimeToSampleAtom
30
31 #include "timetosampleatom.h"
32 #include "atomutils.h"
33 #include "atomdefs.h"
34
35 // Stream-in ctor
TimeToSampleAtom(MP4_FF_FILE * fp,uint32 mediaType,uint32 size,uint32 type,OSCL_wString & filename,uint32 parsingMode)36 TimeToSampleAtom::TimeToSampleAtom(MP4_FF_FILE *fp,
37 uint32 mediaType,
38 uint32 size,
39 uint32 type,
40 OSCL_wString& filename,
41 uint32 parsingMode)
42 : FullAtom(fp, size, type)
43 {
44
45 _psampleCountVec = NULL;
46 _psampleDeltaVec = NULL;
47
48 _currGetSampleCount = 0;
49 _currGetIndex = -1;
50 _currGetTimeDelta = 0;
51 _currPeekSampleCount = 0;
52 _currPeekIndex = -1;
53 _currPeekTimeDelta = 0;
54
55 _mediaType = mediaType;
56 _parsed_entry_cnt = 0;
57 _fileptr = NULL;
58 _parsing_mode = 0;
59 _parsing_mode = parsingMode;
60
61 _stbl_buff_size = MAX_CACHED_TABLE_ENTRIES_FILE;
62 _next_buff_number = 0;
63 _curr_buff_number = 0;
64 _curr_entry_point = 0;
65 _stbl_fptr_vec = NULL;
66
67 iLogger = PVLogger::GetLoggerObject("mp4ffparser");
68 iStateVarLogger = PVLogger::GetLoggerObject("mp4ffparser_mediasamplestats");
69 iParsedDataLogger = PVLogger::GetLoggerObject("mp4ffparser_parseddata");
70
71
72 if (_success)
73 {
74 if (!AtomUtils::read32(fp, _entryCount))
75 {
76 _success = false;
77 }
78 PVMF_MP4FFPARSER_LOGPARSEDINFO((0, "TimeToSampleAtom::TimeToSampleAtom- _entryCount =%d", _entryCount));
79 uint32 dataSize = _size - (DEFAULT_FULL_ATOM_SIZE + 4);
80
81 uint32 entrySize = (4 + 4);
82
83 if ((_entryCount*entrySize) > dataSize)
84 {
85 _success = false;
86 }
87
88 if (_success)
89 {
90 if (_entryCount > 0)
91 {
92
93 if (parsingMode == 1)
94 {
95 // cache size is 4K so that optimization should work if entry_count is greater than 4K
96 if ((_entryCount > _stbl_buff_size))
97 {
98 uint32 fptrBuffSize = (_entryCount / _stbl_buff_size) + 1;
99
100 PV_MP4_FF_ARRAY_NEW(NULL, uint32, (fptrBuffSize), _stbl_fptr_vec);
101 if (_stbl_fptr_vec == NULL)
102 {
103 _success = false;
104 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
105 return;
106 }
107
108 PV_MP4_FF_ARRAY_NEW(NULL, uint32, (_stbl_buff_size), _psampleCountVec);
109 if (_psampleCountVec == NULL)
110 {
111 _success = false;
112 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
113 return;
114 }
115 PV_MP4_FF_ARRAY_NEW(NULL, uint32, (_stbl_buff_size), _psampleDeltaVec);
116 if (_psampleDeltaVec == NULL)
117 {
118 PV_MP4_ARRAY_DELETE(NULL, _psampleDeltaVec);
119 _psampleDeltaVec = NULL;
120 _success = false;
121 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
122 return;
123 }
124 for (uint32 idx = 0; idx < _stbl_buff_size; idx++) //initialization
125 {
126 _psampleCountVec[idx] = 0;
127 _psampleDeltaVec[idx] = 0;
128 }
129
130 OsclAny* ptr = (MP4_FF_FILE *)(oscl_malloc(sizeof(MP4_FF_FILE)));
131 if (ptr == NULL)
132 {
133 _success = false;
134 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
135 return;
136 }
137 _fileptr = OSCL_PLACEMENT_NEW(ptr, MP4_FF_FILE());
138 _fileptr->_fileServSession = fp->_fileServSession;
139 _fileptr->_pvfile.SetCPM(fp->_pvfile.GetCPM());
140 if (AtomUtils::OpenMP4File(filename,
141 Oscl_File::MODE_READ | Oscl_File::MODE_BINARY,
142 _fileptr) != 0)
143 {
144 _success = false;
145 _mp4ErrorCode = FILE_OPEN_FAILED;
146 }
147
148 _fileptr->_fileSize = fp->_fileSize;
149
150 int32 _head_offset = AtomUtils::getCurrentFilePosition(fp);
151 AtomUtils::seekFromCurrPos(fp, dataSize);
152 AtomUtils::seekFromStart(_fileptr, _head_offset);
153 return;
154 }
155 else
156 {
157 _parsing_mode = 0;
158 _stbl_buff_size = _entryCount;
159 }
160 }
161 else
162 {
163 _stbl_buff_size = _entryCount;
164 }
165
166 PV_MP4_FF_ARRAY_NEW(NULL, uint32, (_entryCount), _psampleCountVec);
167 if (_psampleCountVec == NULL)
168 {
169 _success = false;
170 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
171 return;
172 }
173 PV_MP4_FF_ARRAY_NEW(NULL, uint32, (_entryCount), _psampleDeltaVec);
174 if (_psampleDeltaVec == NULL)
175 {
176 PV_MP4_ARRAY_DELETE(NULL, _psampleDeltaVec);
177 _psampleDeltaVec = NULL;
178 _success = false;
179 _mp4ErrorCode = MEMORY_ALLOCATION_FAILED;
180 return;
181 }
182 for (uint32 idx = 0; idx < _entryCount; idx++) //initialization
183 {
184 _psampleCountVec[idx] = 0;
185 _psampleDeltaVec[idx] = 0;
186 }
187
188 uint32 number = 0;
189 uint32 delta = 0;
190 for (_parsed_entry_cnt = 0; _parsed_entry_cnt < _entryCount; _parsed_entry_cnt++)
191 {
192 if (!AtomUtils::read32(fp, number))
193 {
194 _success = false;
195 break;
196 }
197 if (!AtomUtils::read32(fp, delta))
198 {
199 _success = false;
200 break;
201 }
202 _psampleCountVec[_parsed_entry_cnt] = (number);
203 _psampleDeltaVec[_parsed_entry_cnt] = (delta);
204 }
205 }
206 }
207
208 if (!_success)
209 {
210 _mp4ErrorCode = READ_TIME_TO_SAMPLE_ATOM_FAILED;
211 }
212 }
213 else
214 {
215 if (_mp4ErrorCode != ATOM_VERSION_NOT_SUPPORTED)
216 _mp4ErrorCode = READ_TIME_TO_SAMPLE_ATOM_FAILED;
217 }
218 }
219
ParseEntryUnit(uint32 entry_cnt)220 bool TimeToSampleAtom::ParseEntryUnit(uint32 entry_cnt)
221 {
222
223 const uint32 threshold = 1024;
224 entry_cnt += threshold;
225
226 if (entry_cnt > _entryCount)
227 entry_cnt = _entryCount;
228
229 uint32 number, delta;
230 while (_parsed_entry_cnt < entry_cnt)
231 {
232 _curr_entry_point = _parsed_entry_cnt % _stbl_buff_size;
233 _curr_buff_number = _parsed_entry_cnt / _stbl_buff_size;
234
235 if (_curr_buff_number == _next_buff_number)
236 {
237 uint32 currFilePointer = AtomUtils::getCurrentFilePosition(_fileptr);
238 _stbl_fptr_vec[_curr_buff_number] = currFilePointer;
239 _next_buff_number++;
240 }
241
242 if (!_curr_entry_point)
243 {
244 uint32 currFilePointer = _stbl_fptr_vec[_curr_buff_number];
245 AtomUtils::seekFromStart(_fileptr, currFilePointer);
246 }
247
248 if (!AtomUtils::read32(_fileptr, number))
249 {
250 return false;
251 }
252 if (!AtomUtils::read32(_fileptr, delta))
253 {
254 return false;
255 }
256 _psampleCountVec[_curr_entry_point] = (number);
257 _psampleDeltaVec[_curr_entry_point] = (delta);
258 _parsed_entry_cnt++;
259 }
260 return true;
261 }
262
263 // Destructor
~TimeToSampleAtom()264 TimeToSampleAtom::~TimeToSampleAtom()
265 {
266 if (_psampleCountVec != NULL)
267 PV_MP4_ARRAY_DELETE(NULL, _psampleCountVec);
268
269 if (_psampleDeltaVec != NULL)
270 PV_MP4_ARRAY_DELETE(NULL, _psampleDeltaVec);
271
272 if (_stbl_fptr_vec != NULL)
273 PV_MP4_ARRAY_DELETE(NULL, _stbl_fptr_vec);
274
275 if (_fileptr != NULL)
276 {
277 if (_fileptr->IsOpen())
278 {
279 AtomUtils::CloseMP4File(_fileptr);
280 }
281 oscl_free(_fileptr);
282 }
283 }
284
285 // Return the number of samples at index
286 uint32
getSampleCountAt(int32 index)287 TimeToSampleAtom::getSampleCountAt(int32 index)
288 {
289 if (_psampleCountVec == NULL)
290 {
291 return (uint32) PV_ERROR;
292 }
293
294 if (index < (int32)_entryCount)
295 {
296 if (_parsing_mode == 1)
297 CheckAndParseEntry(index);
298
299 return (int32)(_psampleCountVec[index%_stbl_buff_size]);
300 }
301 else
302 {
303 PVMF_MP4FFPARSER_LOGERROR((0, "ERROR =>TimeToSampleAtom::getSampleCountAt index = %d", index));
304 return (uint32) PV_ERROR;
305 }
306 }
307
308 // Return sample delta at index
309 int32
getSampleDeltaAt(int32 index)310 TimeToSampleAtom::getSampleDeltaAt(int32 index)
311 {
312 if (_psampleDeltaVec == NULL)
313 {
314 return PV_ERROR;
315 }
316
317 if (index < (int32)_entryCount)
318 {
319 if (_parsing_mode == 1)
320 CheckAndParseEntry(index);
321
322 return (int32)(_psampleDeltaVec[index%_stbl_buff_size]);
323 }
324 else
325 {
326 PVMF_MP4FFPARSER_LOGERROR((0, "ERROR =>TimeToSampleAtom::getSampleDeltaAt index = %d", index));
327 return PV_ERROR;
328 }
329 }
330
331 // Return the samples corresponding to the timestamp ts. If there is not a sample
332 // exactly at ts, the very next sample is used.
333 // This atom maintains timestamp deltas between samples, i.e. delta[i] is the
334 // timestamp difference between sample[i] and sample[i+1]. It is implicit that
335 // sample[0] occurs at timestamp ts=0.
336 int32
getSampleNumberFromTimestamp(uint32 ts,bool oAlwaysRetSampleCount)337 TimeToSampleAtom::getSampleNumberFromTimestamp(uint32 ts, bool oAlwaysRetSampleCount)
338 {
339 // It is assumed that sample 0 has a ts of 0 - i.e. the first
340 // entry in the table starts with the delta between sample 1 and sample 0
341 uint32 sampleCount = 0;
342 uint32 timeCount = 0;
343
344 if ((_psampleDeltaVec == NULL) ||
345 (_psampleCountVec == NULL) ||
346 (_entryCount == 0))
347 {
348 return PV_ERROR;
349 }
350
351 for (uint32 i = 0; i < _entryCount; i++)
352 {
353 if (_parsing_mode == 1)
354 CheckAndParseEntry(i);
355
356 if (ts < timeCount)
357 { // found range that the sample is in - need to backtrack
358 if (_parsing_mode == 1)
359 CheckAndParseEntry(i - 1);
360
361 uint32 samples = _psampleCountVec[(i-1)%_stbl_buff_size];
362 sampleCount -= samples;
363 timeCount -= _psampleDeltaVec[(i-1)%_stbl_buff_size] * samples;
364 while (timeCount <= ts)
365 {
366 timeCount += _psampleDeltaVec[(i-1)%_stbl_buff_size];
367 sampleCount += 1;
368 }
369
370 if (timeCount > ts)
371 {
372 if (sampleCount > 0)
373 {
374 sampleCount--;
375 }
376 return sampleCount;
377 }
378 }
379 else if (ts == timeCount)
380 { // Found sample at ts
381 return sampleCount;
382 }
383 else
384 { // Sample not yet found - advance
385 uint32 samples = _psampleCountVec[i%_stbl_buff_size]; //number of samples at this index
386 sampleCount += samples;
387 timeCount += _psampleDeltaVec[i%_stbl_buff_size] * samples;
388 }
389 }
390
391 // Timestamp is in last run of samples (or possibly beyond)
392 // - need to backtrack to beginning of last run to find it
393 uint32 samples = _psampleCountVec[(_entryCount-1)%_stbl_buff_size];
394 uint32 delta = _psampleDeltaVec[(_entryCount-1)%_stbl_buff_size];
395 sampleCount -= samples;
396 timeCount -= delta * samples;
397
398 for (uint32 count = 0; count < (samples - 1); count++)
399 {
400 timeCount += delta;
401 sampleCount += 1;
402
403 if (timeCount > ts)
404 {
405 if (sampleCount > 0)
406 {
407 sampleCount--;
408 }
409 return sampleCount;
410 }
411 else if (timeCount == ts)
412 {
413 return sampleCount;
414 }
415 }
416
417
418 sampleCount += 1;
419 if (ts >= timeCount)
420 {
421 if (oAlwaysRetSampleCount)
422 {
423 return sampleCount;
424 }
425 else
426 {
427 if (_mediaType == MEDIA_TYPE_VISUAL)
428 {
429 return sampleCount;
430 }
431 }
432 }
433
434 // Went past last sample in last run of samples - not a valid timestamp
435 return PV_ERROR;
436 }
437
438 // Returns the timestamp (ms) for the current sample given by num. This is used when
439 // randomly accessing a frame and the timestamp has not been accumulated. It is implicit
440 // that sample[0] occurs at timestamp ts=0.
getTimestampForSampleNumber(uint32 num)441 int32 TimeToSampleAtom::getTimestampForSampleNumber(uint32 num)
442 {
443 if ((_psampleDeltaVec == NULL) ||
444 (_psampleCountVec == NULL) ||
445 (_entryCount == 0))
446 {
447 return PV_ERROR;
448 }
449 // It is assumed that sample 0 has a ts of 0 - i.e. the first
450 // entry in the table starts with the delta between sample 1 and sample 0
451 if (num == 0)
452 return 0;
453
454 uint32 sampleCount = 0;
455 int32 ts = 0; // Timestamp value to return
456 for (uint32 i = 0; i < _entryCount; i++)
457 {
458 if (_parsing_mode == 1)
459 CheckAndParseEntry(i);
460
461 if (num <= (sampleCount + _psampleCountVec[i%_stbl_buff_size]))
462 { // Sample num within current entry
463 int32 count = num - sampleCount;
464 ts += _psampleDeltaVec[i%_stbl_buff_size] * count;
465 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimestampForSampleNumber- Time Stamp =%d", ts));
466 return ts;
467 }
468 else
469 {
470 sampleCount += _psampleCountVec[i%_stbl_buff_size];
471 ts += (_psampleDeltaVec[i%_stbl_buff_size] * _psampleCountVec[i%_stbl_buff_size]);
472 }
473 }
474
475 // Went past end of list - not a valid sample number
476 return PV_ERROR;
477 }
478
479 // Returns the timestamp delta (ms) for the current sample given by num. This value
480 // is the difference in timestamps between the sample (num) and the previous sample
481 // in the track. It is implicit that sample[0] occurs at timestamp ts=0.
482 int32
getTimeDeltaForSampleNumber(uint32 num)483 TimeToSampleAtom::getTimeDeltaForSampleNumber(uint32 num)
484 {
485 // It is assumed that sample 0 has a ts of 0 - i.e. the first
486 // entry in the table starts with the delta between sample 1 and sample 0
487 if ((_psampleDeltaVec == NULL) ||
488 (_psampleCountVec == NULL) ||
489 (_entryCount == 0))
490 {
491 return PV_ERROR;
492 }
493
494 if (num == 0)
495 return 0;
496
497 uint32 sampleCount = 0;
498 for (uint32 i = 0; i < _entryCount; i++)
499 {
500 if (_parsing_mode == 1)
501 CheckAndParseEntry(i);
502
503 if (num <= (sampleCount + _psampleCountVec[i%_stbl_buff_size]))
504 { // Sample num within current entry
505 return (_psampleDeltaVec[i%_stbl_buff_size]);
506 }
507 else
508 {
509 sampleCount += _psampleCountVec[i%_stbl_buff_size];
510 }
511 }
512
513 // Went past end of list - not a valid sample number
514 return PV_ERROR;
515 }
516
517
518
519
520 // Returns the timestamp delta (ms) for the current sample given by num. This value
521 // is the difference in timestamps between the sample (num) and the previous sample
522 // in the track. It is implicit that sample[0] occurs at timestamp ts=0.
523 int32
getTimeDeltaForSampleNumberPeek(uint32 sampleNum)524 TimeToSampleAtom::getTimeDeltaForSampleNumberPeek(uint32 sampleNum)
525 {
526 // It is assumed that sample 0 has a ts of 0 - i.e. the first
527 // entry in the table starts with the delta between sample 1 and sample 0
528 if ((_psampleDeltaVec == NULL) ||
529 (_psampleCountVec == NULL) ||
530 (_entryCount == 0))
531 {
532 return PV_ERROR;
533 }
534
535 // note that sampleNum is a zero based index while _currGetSampleCount is 1 based index
536 if (sampleNum < _currPeekSampleCount)
537 {
538 return (_currPeekTimeDelta);
539 }
540 else
541 {
542 do
543 {
544 _currPeekIndex++;
545 if (_parsing_mode)
546 CheckAndParseEntry(_currPeekIndex);
547
548 _currPeekSampleCount += _psampleCountVec[_currPeekIndex%_stbl_buff_size];
549 _currPeekTimeDelta = _psampleDeltaVec[_currPeekIndex%_stbl_buff_size];
550 }
551 while (_currPeekSampleCount == 0);
552
553 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberPeek- _currPeekIndex =%d", _currPeekIndex));
554 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberPeek- _currPeekSampleCount =%d", _currPeekSampleCount));
555 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberPeek- _currPeekTimeDelta =%d", _currPeekTimeDelta));
556
557 if (sampleNum < _currPeekSampleCount)
558 {
559 return (_currPeekTimeDelta);
560 }
561 else
562 {
563 PVMF_MP4FFPARSER_LOGERROR((0, "ERROR =>TimeToSampleAtom::getTimeDeltaForSampleNumberPeek sampleNum = %d", sampleNum));
564 return (PV_ERROR);
565 }
566 }
567
568
569 }
570
571 // Returns the timestamp delta (ms) for the current sample given by num. This value
572 // is the difference in timestamps between the sample (num) and the previous sample
573 // in the track. It is implicit that sample[0] occurs at timestamp ts=0.
574 int32
getTimeDeltaForSampleNumberGet(uint32 sampleNum)575 TimeToSampleAtom::getTimeDeltaForSampleNumberGet(uint32 sampleNum)
576 {
577 // It is assumed that sample 0 has a ts of 0 - i.e. the first
578 // entry in the table starts with the delta between sample 1 and sample 0
579 if ((_psampleDeltaVec == NULL) ||
580 (_psampleCountVec == NULL) ||
581 (_entryCount == 0))
582 {
583 return PV_ERROR;
584 }
585
586 // note that sampleNum is a zero based index while _currGetSampleCount is 1 based index
587 if (sampleNum < _currGetSampleCount)
588 {
589 return (_currGetTimeDelta);
590 }
591 else
592 {
593
594 do
595 {
596 _currGetIndex++;
597 if (_parsing_mode)
598 CheckAndParseEntry(_currGetIndex);
599 _currGetSampleCount += _psampleCountVec[_currGetIndex%_stbl_buff_size];
600 _currGetTimeDelta = _psampleDeltaVec[_currGetIndex%_stbl_buff_size];
601 }
602 while (_currGetSampleCount == 0);
603
604 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberGet- _currGetIndex =%d", _currGetIndex));
605 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberGet- _currGetSampleCount =%d", _currGetSampleCount));
606 PVMF_MP4FFPARSER_LOGMEDIASAMPELSTATEVARIABLES((0, "TimeToSampleAtom::getTimeDeltaForSampleNumberGet- _currGetTimeDelta =%d", _currGetTimeDelta));
607
608 if (sampleNum < _currGetSampleCount)
609 {
610 return (_currGetTimeDelta);
611 }
612 else
613 {
614 PVMF_MP4FFPARSER_LOGERROR((0, "ERROR =>TimeToSampleAtom::getTimeDeltaForSampleNumberGet sampleNum = %d", sampleNum));
615 return (PV_ERROR);
616 }
617 }
618
619
620 }
621
622 int32
resetStateVariables()623 TimeToSampleAtom::resetStateVariables()
624 {
625 uint32 sampleNum = 0;
626 return (resetStateVariables(sampleNum));
627 }
628
629 int32
resetStateVariables(uint32 sampleNum)630 TimeToSampleAtom::resetStateVariables(uint32 sampleNum)
631 {
632 _currGetSampleCount = 0;
633 _currGetIndex = -1;
634 _currGetTimeDelta = 0;
635 _currPeekSampleCount = 0;
636 _currPeekIndex = -1;
637 _currPeekTimeDelta = 0;
638
639 // It is assumed that sample 0 has a ts of 0 - i.e. the first
640 // entry in the table starts with the delta between sample 1 and sample 0
641 if ((_psampleDeltaVec == NULL) ||
642 (_psampleCountVec == NULL) ||
643 (_entryCount == 0))
644 {
645 return PV_ERROR;
646 }
647
648
649 for (uint32 i = 0; i < _entryCount; i++)
650 {
651 if (_parsing_mode)
652 CheckAndParseEntry(i);
653
654 _currPeekIndex++;
655 _currPeekSampleCount += _psampleCountVec[i%_stbl_buff_size];
656 _currPeekTimeDelta = _psampleDeltaVec[i%_stbl_buff_size];
657
658 _currGetIndex++;
659 _currGetSampleCount += _psampleCountVec[i%_stbl_buff_size];
660 _currGetTimeDelta = _psampleDeltaVec[i%_stbl_buff_size];
661
662 if (sampleNum <= _currPeekSampleCount)
663 {
664 return (EVERYTHING_FINE);
665 }
666
667 }
668
669 // Went past end of list - not a valid sample number
670 return PV_ERROR;
671 }
672
resetPeekwithGet()673 int32 TimeToSampleAtom::resetPeekwithGet()
674 {
675 _currPeekSampleCount = _currGetSampleCount;
676 _currPeekIndex = _currGetIndex ;
677 _currPeekTimeDelta = _currGetTimeDelta;
678 return (EVERYTHING_FINE);
679 }
680
CheckAndParseEntry(uint32 i)681 void TimeToSampleAtom::CheckAndParseEntry(uint32 i)
682 {
683 if (i >= _parsed_entry_cnt)
684 {
685 ParseEntryUnit(i);
686 }
687 else
688 {
689 uint32 entryLoc = i / _stbl_buff_size;
690 if (_curr_buff_number != entryLoc)
691 {
692 _parsed_entry_cnt = entryLoc * _stbl_buff_size;
693 while (_parsed_entry_cnt <= i)
694 ParseEntryUnit(_parsed_entry_cnt);
695 }
696 }
697 }
698
699