1 #include "../mpeg3private.h"
2 #include "../mpeg3protos.h"
3 #include "mpeg3video.h"
7 void mpeg3video_toc_error()
10 "mpeg3video_seek: frame accurate seeking without a table of contents \n"
11 "is no longer supported. Use mpeg3toc <mpeg file> <table of contents>\n"
12 "to generate a table of contents and load the table of contents instead.\n");
15 int mpeg3video_drop_frames(mpeg3video_t
*video
, long frames
, int cache_it
)
18 long frame_number
= video
->framenum
+ frames
;
19 mpeg3_vtrack_t
*track
= video
->track
;
20 /* first 3 frames are garbage as proven by printfs in the read_frame calls */
23 /* Read the selected number of frames and skip b-frames */
24 while(!result
&& frame_number
> video
->framenum
)
28 result
= mpeg3video_read_frame_backend(video
, 0);
29 if(video
->output_src
[0] && drop_count
--)
31 mpeg3_cache_put_frame(track
->frame_cache
,
36 video
->coded_picture_width
* video
->coded_picture_height
,
37 video
->chrom_width
* video
->chrom_height
,
38 video
->chrom_width
* video
->chrom_height
);
39 //printf("mpeg3video_drop_frames 1 %d\n", video->framenum);
44 result
= mpeg3video_read_frame_backend(video
, frame_number
- video
->framenum
);
51 unsigned int mpeg3bits_next_startcode(mpeg3_bits_t
* stream
)
53 /* Perform forwards search */
54 mpeg3bits_byte_align(stream
);
58 * printf("mpeg3bits_next_startcode 1 %lld %lld\n",
59 * stream->demuxer->titles[0]->fs->current_byte,
60 * stream->demuxer->titles[0]->fs->total_bytes);
64 //mpeg3_read_next_packet(stream->demuxer);
65 //printf("mpeg3bits_next_startcode 2 %d %d\n",
66 // stream->demuxer->titles[0]->fs->current_byte,
67 // stream->demuxer->titles[0]->fs->total_bytes);
69 //printf("mpeg3bits_next_startcode 2 %llx\n", mpeg3bits_tell(stream));
73 unsigned int code
= mpeg3bits_showbits32_noptr(stream
);
75 if((code
>> 8) == MPEG3_PACKET_START_CODE_PREFIX
) break;
76 if(mpeg3bits_eof(stream
)) break;
79 mpeg3bits_getbyte_noptr(stream
);
82 * printf("mpeg3bits_next_startcode 3 %08x %d %d\n",
83 * mpeg3bits_showbits32_noptr(stream),
84 * stream->demuxer->titles[0]->fs->current_byte,
85 * stream->demuxer->titles[0]->fs->total_bytes);
89 //printf("mpeg3bits_next_startcode 4 %d %d\n",
90 // stream->demuxer->titles[0]->fs->current_byte,
91 // stream->demuxer->titles[0]->fs->total_bytes);
92 return mpeg3bits_showbits32_noptr(stream
);
95 /* Line up on the beginning of the next code. */
96 int mpeg3video_next_code(mpeg3_bits_t
* stream
, unsigned int code
)
98 while(!mpeg3bits_eof(stream
) &&
99 mpeg3bits_showbits32_noptr(stream
) != code
)
101 mpeg3bits_getbyte_noptr(stream
);
103 return mpeg3bits_eof(stream
);
106 /* Line up on the beginning of the previous code. */
107 int mpeg3video_prev_code(mpeg3_demuxer_t
*demuxer
, unsigned int code
)
109 uint32_t current_code
= 0;
111 #define PREV_CODE_MACRO \
113 current_code >>= 8; \
114 current_code |= ((uint32_t)mpeg3demux_read_prev_char(demuxer)) << 24; \
122 while(!mpeg3demux_bof(demuxer
) && current_code
!= code
)
126 return mpeg3demux_bof(demuxer
);
129 long mpeg3video_goptimecode_to_frame(mpeg3video_t
*video
)
131 /* printf("mpeg3video_goptimecode_to_frame %d %d %d %d %f\n", */
132 /* video->gop_timecode.hour, video->gop_timecode.minute, video->gop_timecode.second, video->gop_timecode.frame, video->frame_rate); */
133 return (long)(video
->gop_timecode
.hour
* 3600 * video
->frame_rate
+
134 video
->gop_timecode
.minute
* 60 * video
->frame_rate
+
135 video
->gop_timecode
.second
* video
->frame_rate
+
136 video
->gop_timecode
.frame
) - 1 - video
->first_frame
;
139 int mpeg3video_match_refframes(mpeg3video_t
*video
)
141 unsigned char *dst
, *src
;
144 for(i
= 0; i
< 3; i
++)
146 if(video
->newframe
[i
])
148 if(video
->newframe
[i
] == video
->refframe
[i
])
150 src
= video
->refframe
[i
];
151 dst
= video
->oldrefframe
[i
];
155 src
= video
->oldrefframe
[i
];
156 dst
= video
->refframe
[i
];
160 size
= video
->coded_picture_width
* video
->coded_picture_height
+ 32 * video
->coded_picture_width
;
162 size
= video
->chrom_width
* video
->chrom_height
+ 32 * video
->chrom_width
;
164 memcpy(dst
, src
, size
);
170 int mpeg3video_seek_byte(mpeg3video_t
*video
, int64_t byte
)
172 mpeg3_t
*file
= video
->file
;
173 mpeg3_bits_t
*vstream
= video
->vstream
;
174 mpeg3_demuxer_t
*demuxer
= vstream
->demuxer
;
176 video
->byte_seek
= byte
;
180 // Need PTS now so audio can be synchronized
181 mpeg3bits_seek_byte(vstream
, byte
);
182 // file->percentage_pts = mpeg3demux_scan_pts(demuxer);
186 int mpeg3video_seek_frame(mpeg3video_t
*video
, long frame
)
188 video
->frame_seek
= frame
;
192 int mpeg3_rewind_video(mpeg3video_t
*video
)
194 mpeg3_vtrack_t
*track
= video
->track
;
195 mpeg3_bits_t
*vstream
= video
->vstream
;
197 if(track
->frame_offsets
)
198 mpeg3bits_seek_byte(vstream
, track
->frame_offsets
[0]);
200 mpeg3bits_seek_byte(vstream
, 0);
205 int mpeg3video_seek(mpeg3video_t
*video
)
211 mpeg3_t
*file
= video
->file
;
212 mpeg3_bits_t
*vstream
= video
->vstream
;
213 mpeg3_vtrack_t
*track
= video
->track
;
214 mpeg3_demuxer_t
*demuxer
= vstream
->demuxer
;
217 int match_refframes
= 1;
221 /* Must do seeking here so files which don't use video don't seek. */
222 /* Seeking is done in the demuxer */
223 /* Seek to absolute byte */
224 if(video
->byte_seek
>= 0)
226 byte
= video
->byte_seek
;
227 video
->byte_seek
= -1;
228 mpeg3demux_seek_byte(demuxer
, byte
);
232 mpeg3_reset_subtitles(file
);
238 //printf("mpeg3video_seek 1\n");
239 mpeg3demux_start_reverse(demuxer
);
241 //printf("mpeg3video_seek 1 %lld\n", mpeg3demux_tell_byte(demuxer));
245 result
= mpeg3video_prev_code(demuxer
, MPEG3_GOP_START_CODE
);
247 result
= mpeg3video_prev_code(demuxer
, MPEG3_SEQUENCE_START_CODE
);
249 //printf("mpeg3video_seek 2 %lld\n", mpeg3demux_tell_byte(demuxer));
254 result
= mpeg3video_prev_code(demuxer
, MPEG3_GOP_START_CODE
);
256 result
= mpeg3video_prev_code(demuxer
, MPEG3_SEQUENCE_START_CODE
);
259 //printf("mpeg3video_seek 3 %lld\n", mpeg3demux_tell_byte(demuxer));
263 mpeg3demux_start_forward(demuxer
);
268 video
->repeat_count
= 0;
269 mpeg3bits_reset(vstream
);
270 mpeg3video_read_frame_backend(video
, 0);
271 mpeg3_rewind_video(video
);
272 video
->repeat_count
= 0;
276 mpeg3bits_reset(vstream
);
278 //printf("mpeg3video_seek 4 %lld\n", mpeg3demux_tell_byte(demuxer));
279 // Read up to the correct byte
281 video
->repeat_count
= 0;
283 !mpeg3demux_eof(demuxer
) &&
284 mpeg3demux_tell_byte(demuxer
) < byte
)
286 result
= mpeg3video_read_frame_backend(video
, 0);
289 //printf("mpeg3video_seek 5 %lld\n", mpeg3demux_tell_byte(demuxer));
294 mpeg3demux_reset_pts(demuxer
);
296 //printf("mpeg3video_seek 10\n");
300 /* Seek to a frame */
301 if(video
->frame_seek
>= 0)
304 mpeg3_reset_subtitles(file
);
307 frame_number
= video
->frame_seek
;
308 video
->frame_seek
= -1;
309 if(frame_number
< 0) frame_number
= 0;
310 if(frame_number
> video
->maxframe
) frame_number
= video
->maxframe
;
312 //printf("mpeg3video_seek 1 %ld %ld\n", frame_number, video->framenum);
314 /* Seek to I frame in table of contents. */
315 /* Determine time between seek position and previous subtitle. */
316 /* Subtract time difference from subtitle display time. */
317 if(track
->frame_offsets
)
319 mpeg3_reset_cache(track
->frame_cache
);
321 if((frame_number
< video
->framenum
||
322 frame_number
- video
->framenum
> MPEG3_SEEK_THRESHOLD
))
325 for(i
= track
->total_keyframe_numbers
- 1; i
>= 0; i
--)
327 if(track
->keyframe_numbers
[i
] <= frame_number
)
332 // Go 2 I-frames before current position
335 frame
= track
->keyframe_numbers
[i
];
337 byte
= track
->frame_offsets
[0];
339 byte
= track
->frame_offsets
[frame
];
340 video
->framenum
= track
->keyframe_numbers
[i
];
342 mpeg3bits_seek_byte(vstream
, byte
);
345 // Get first 2 I-frames
348 mpeg3video_get_firstframe(video
);
349 mpeg3video_read_frame_backend(video
, 0);
354 video
->repeat_count
= 0;
356 // Read up to current frame
357 mpeg3video_drop_frames(video
, frame_number
- video
->framenum
, 1);
364 video
->repeat_count
= 0;
365 mpeg3video_drop_frames(video
, frame_number
- video
->framenum
, 0);
369 /* No support for seeking without table of contents */
371 mpeg3video_toc_error();
376 mpeg3demux_reset_pts(demuxer
);
382 int mpeg3video_previous_frame(mpeg3video_t
*video
)
384 mpeg3_bits_t
*bitstream
= video
->vstream
;
385 mpeg3_demuxer_t
*demuxer
= bitstream
->demuxer
;
387 int64_t target_byte
= 0;
389 if(mpeg3demux_tell_byte(demuxer
) <= 0) return 1;
391 // Get location of end of previous picture
392 mpeg3demux_start_reverse(demuxer
);
393 result
= mpeg3video_prev_code(demuxer
, MPEG3_PICTURE_START_CODE
);
394 if(!result
) result
= mpeg3video_prev_code(demuxer
, MPEG3_PICTURE_START_CODE
);
395 if(!result
) result
= mpeg3video_prev_code(demuxer
, MPEG3_PICTURE_START_CODE
);
396 if(!result
) target_byte
= mpeg3demux_tell_byte(demuxer
);
403 result
= mpeg3video_prev_code(demuxer
, MPEG3_GOP_START_CODE
);
405 result
= mpeg3video_prev_code(demuxer
, MPEG3_SEQUENCE_START_CODE
);
411 result
= mpeg3video_prev_code(demuxer
, MPEG3_GOP_START_CODE
);
413 result
= mpeg3video_prev_code(demuxer
, MPEG3_SEQUENCE_START_CODE
);
416 mpeg3demux_start_forward(demuxer
);
417 mpeg3bits_reset(bitstream
);
419 // Read up to correct byte
421 video
->repeat_count
= 0;
423 !mpeg3demux_eof(demuxer
) &&
424 mpeg3demux_tell_byte(demuxer
) < target_byte
)
426 result
= mpeg3video_read_frame_backend(video
, 0);
429 video
->repeat_count
= 0;