]> git.sesse.net Git - ffmpeg/blob - ffplay.c
lut3d: Fix reading 3dl files with leading comments.
[ffmpeg] / ffplay.c
1 /*
2  * Copyright (c) 2003 Fabrice Bellard
3  *
4  * This file is part of FFmpeg.
5  *
6  * FFmpeg is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * FFmpeg is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with FFmpeg; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20
21 /**
22  * @file
23  * simple media player based on the FFmpeg libraries
24  */
25
26 #include "config.h"
27 #include <inttypes.h>
28 #include <math.h>
29 #include <limits.h>
30 #include <signal.h>
31 #include "libavutil/avstring.h"
32 #include "libavutil/colorspace.h"
33 #include "libavutil/mathematics.h"
34 #include "libavutil/pixdesc.h"
35 #include "libavutil/imgutils.h"
36 #include "libavutil/dict.h"
37 #include "libavutil/parseutils.h"
38 #include "libavutil/samplefmt.h"
39 #include "libavutil/avassert.h"
40 #include "libavutil/time.h"
41 #include "libavformat/avformat.h"
42 #include "libavdevice/avdevice.h"
43 #include "libswscale/swscale.h"
44 #include "libavutil/opt.h"
45 #include "libavcodec/avfft.h"
46 #include "libswresample/swresample.h"
47
48 #if CONFIG_AVFILTER
49 # include "libavfilter/avcodec.h"
50 # include "libavfilter/avfilter.h"
51 # include "libavfilter/buffersink.h"
52 # include "libavfilter/buffersrc.h"
53 #endif
54
55 #include <SDL.h>
56 #include <SDL_thread.h>
57
58 #include "cmdutils.h"
59
60 #include <assert.h>
61
62 const char program_name[] = "ffplay";
63 const int program_birth_year = 2003;
64
65 #define MAX_QUEUE_SIZE (15 * 1024 * 1024)
66 #define MIN_FRAMES 5
67
68 /* SDL audio buffer size, in samples. Should be small to have precise
69    A/V sync as SDL does not have hardware buffer fullness info. */
70 #define SDL_AUDIO_BUFFER_SIZE 1024
71
72 /* no AV sync correction is done if below the minimum AV sync threshold */
73 #define AV_SYNC_THRESHOLD_MIN 0.01
74 /* AV sync correction is done if above the maximum AV sync threshold */
75 #define AV_SYNC_THRESHOLD_MAX 0.1
76 /* If a frame duration is longer than this, it will not be duplicated to compensate AV sync */
77 #define AV_SYNC_FRAMEDUP_THRESHOLD 0.1
78 /* no AV correction is done if too big error */
79 #define AV_NOSYNC_THRESHOLD 10.0
80
81 /* maximum audio speed change to get correct sync */
82 #define SAMPLE_CORRECTION_PERCENT_MAX 10
83
84 /* external clock speed adjustment constants for realtime sources based on buffer fullness */
85 #define EXTERNAL_CLOCK_SPEED_MIN  0.900
86 #define EXTERNAL_CLOCK_SPEED_MAX  1.010
87 #define EXTERNAL_CLOCK_SPEED_STEP 0.001
88
89 /* we use about AUDIO_DIFF_AVG_NB A-V differences to make the average */
90 #define AUDIO_DIFF_AVG_NB   20
91
92 /* polls for possible required screen refresh at least this often, should be less than 1/fps */
93 #define REFRESH_RATE 0.01
94
95 /* NOTE: the size must be big enough to compensate the hardware audio buffersize size */
96 /* TODO: We assume that a decoded and resampled frame fits into this buffer */
97 #define SAMPLE_ARRAY_SIZE (8 * 65536)
98
99 #define CURSOR_HIDE_DELAY 1000000
100
101 static int64_t sws_flags = SWS_BICUBIC;
102
103 typedef struct MyAVPacketList {
104     AVPacket pkt;
105     struct MyAVPacketList *next;
106     int serial;
107 } MyAVPacketList;
108
109 typedef struct PacketQueue {
110     MyAVPacketList *first_pkt, *last_pkt;
111     int nb_packets;
112     int size;
113     int abort_request;
114     int serial;
115     SDL_mutex *mutex;
116     SDL_cond *cond;
117 } PacketQueue;
118
119 #define VIDEO_PICTURE_QUEUE_SIZE 3
120 #define SUBPICTURE_QUEUE_SIZE 4
121
122 typedef struct VideoPicture {
123     double pts;             // presentation timestamp for this picture
124     int64_t pos;            // byte position in file
125     SDL_Overlay *bmp;
126     int width, height; /* source height & width */
127     int allocated;
128     int reallocate;
129     int serial;
130
131     AVRational sar;
132 } VideoPicture;
133
134 typedef struct SubPicture {
135     double pts; /* presentation time stamp for this picture */
136     AVSubtitle sub;
137     int serial;
138 } SubPicture;
139
140 typedef struct AudioParams {
141     int freq;
142     int channels;
143     int64_t channel_layout;
144     enum AVSampleFormat fmt;
145 } AudioParams;
146
147 typedef struct Clock {
148     double pts;           /* clock base */
149     double pts_drift;     /* clock base minus time at which we updated the clock */
150     double last_updated;
151     double speed;
152     int serial;           /* clock is based on a packet with this serial */
153     int paused;
154     int *queue_serial;    /* pointer to the current packet queue serial, used for obsolete clock detection */
155 } Clock;
156
157 enum {
158     AV_SYNC_AUDIO_MASTER, /* default choice */
159     AV_SYNC_VIDEO_MASTER,
160     AV_SYNC_EXTERNAL_CLOCK, /* synchronize to an external clock */
161 };
162
163 typedef struct VideoState {
164     SDL_Thread *read_tid;
165     SDL_Thread *video_tid;
166     AVInputFormat *iformat;
167     int no_background;
168     int abort_request;
169     int force_refresh;
170     int paused;
171     int last_paused;
172     int queue_attachments_req;
173     int seek_req;
174     int seek_flags;
175     int64_t seek_pos;
176     int64_t seek_rel;
177     int read_pause_return;
178     AVFormatContext *ic;
179     int realtime;
180
181     Clock audclk;
182     Clock vidclk;
183     Clock extclk;
184
185     int audio_stream;
186
187     int av_sync_type;
188
189     double audio_clock;
190     int audio_clock_serial;
191     double audio_diff_cum; /* used for AV difference average computation */
192     double audio_diff_avg_coef;
193     double audio_diff_threshold;
194     int audio_diff_avg_count;
195     AVStream *audio_st;
196     PacketQueue audioq;
197     int audio_hw_buf_size;
198     uint8_t silence_buf[SDL_AUDIO_BUFFER_SIZE];
199     uint8_t *audio_buf;
200     uint8_t *audio_buf1;
201     unsigned int audio_buf_size; /* in bytes */
202     unsigned int audio_buf1_size;
203     int audio_buf_index; /* in bytes */
204     int audio_write_buf_size;
205     int audio_buf_frames_pending;
206     AVPacket audio_pkt_temp;
207     AVPacket audio_pkt;
208     int audio_pkt_temp_serial;
209     int audio_last_serial;
210     struct AudioParams audio_src;
211 #if CONFIG_AVFILTER
212     struct AudioParams audio_filter_src;
213 #endif
214     struct AudioParams audio_tgt;
215     struct SwrContext *swr_ctx;
216     int frame_drops_early;
217     int frame_drops_late;
218     AVFrame *frame;
219
220     enum ShowMode {
221         SHOW_MODE_NONE = -1, SHOW_MODE_VIDEO = 0, SHOW_MODE_WAVES, SHOW_MODE_RDFT, SHOW_MODE_NB
222     } show_mode;
223     int16_t sample_array[SAMPLE_ARRAY_SIZE];
224     int sample_array_index;
225     int last_i_start;
226     RDFTContext *rdft;
227     int rdft_bits;
228     FFTSample *rdft_data;
229     int xpos;
230     double last_vis_time;
231
232     SDL_Thread *subtitle_tid;
233     int subtitle_stream;
234     AVStream *subtitle_st;
235     PacketQueue subtitleq;
236     SubPicture subpq[SUBPICTURE_QUEUE_SIZE];
237     int subpq_size, subpq_rindex, subpq_windex;
238     SDL_mutex *subpq_mutex;
239     SDL_cond *subpq_cond;
240
241     double frame_timer;
242     double frame_last_pts;
243     double frame_last_duration;
244     double frame_last_dropped_pts;
245     double frame_last_returned_time;
246     double frame_last_filter_delay;
247     int64_t frame_last_dropped_pos;
248     int frame_last_dropped_serial;
249     int video_stream;
250     AVStream *video_st;
251     PacketQueue videoq;
252     int64_t video_current_pos;      // current displayed file pos
253     double max_frame_duration;      // maximum duration of a frame - above this, we consider the jump a timestamp discontinuity
254     VideoPicture pictq[VIDEO_PICTURE_QUEUE_SIZE];
255     int pictq_size, pictq_rindex, pictq_windex;
256     SDL_mutex *pictq_mutex;
257     SDL_cond *pictq_cond;
258 #if !CONFIG_AVFILTER
259     struct SwsContext *img_convert_ctx;
260 #endif
261     SDL_Rect last_display_rect;
262
263     char filename[1024];
264     int width, height, xleft, ytop;
265     int step;
266
267 #if CONFIG_AVFILTER
268     AVFilterContext *in_video_filter;   // the first filter in the video chain
269     AVFilterContext *out_video_filter;  // the last filter in the video chain
270     AVFilterContext *in_audio_filter;   // the first filter in the audio chain
271     AVFilterContext *out_audio_filter;  // the last filter in the audio chain
272     AVFilterGraph *agraph;              // audio filter graph
273 #endif
274
275     int last_video_stream, last_audio_stream, last_subtitle_stream;
276
277     SDL_cond *continue_read_thread;
278 } VideoState;
279
280 /* options specified by the user */
281 static AVInputFormat *file_iformat;
282 static const char *input_filename;
283 static const char *window_title;
284 static int fs_screen_width;
285 static int fs_screen_height;
286 static int default_width  = 640;
287 static int default_height = 480;
288 static int screen_width  = 0;
289 static int screen_height = 0;
290 static int audio_disable;
291 static int video_disable;
292 static int subtitle_disable;
293 static int wanted_stream[AVMEDIA_TYPE_NB] = {
294     [AVMEDIA_TYPE_AUDIO]    = -1,
295     [AVMEDIA_TYPE_VIDEO]    = -1,
296     [AVMEDIA_TYPE_SUBTITLE] = -1,
297 };
298 static int seek_by_bytes = -1;
299 static int display_disable;
300 static int show_status = 1;
301 static int av_sync_type = AV_SYNC_AUDIO_MASTER;
302 static int64_t start_time = AV_NOPTS_VALUE;
303 static int64_t duration = AV_NOPTS_VALUE;
304 static int workaround_bugs = 1;
305 static int fast = 0;
306 static int genpts = 0;
307 static int lowres = 0;
308 static int error_concealment = 3;
309 static int decoder_reorder_pts = -1;
310 static int autoexit;
311 static int exit_on_keydown;
312 static int exit_on_mousedown;
313 static int loop = 1;
314 static int framedrop = -1;
315 static int infinite_buffer = -1;
316 static enum ShowMode show_mode = SHOW_MODE_NONE;
317 static const char *audio_codec_name;
318 static const char *subtitle_codec_name;
319 static const char *video_codec_name;
320 double rdftspeed = 0.02;
321 static int64_t cursor_last_shown;
322 static int cursor_hidden = 0;
323 #if CONFIG_AVFILTER
324 static char *vfilters = NULL;
325 static char *afilters = NULL;
326 #endif
327
328 /* current context */
329 static int is_full_screen;
330 static int64_t audio_callback_time;
331
332 static AVPacket flush_pkt;
333
334 #define FF_ALLOC_EVENT   (SDL_USEREVENT)
335 #define FF_QUIT_EVENT    (SDL_USEREVENT + 2)
336
337 static SDL_Surface *screen;
338
339 static inline
340 int cmp_audio_fmts(enum AVSampleFormat fmt1, int64_t channel_count1,
341                    enum AVSampleFormat fmt2, int64_t channel_count2)
342 {
343     /* If channel count == 1, planar and non-planar formats are the same */
344     if (channel_count1 == 1 && channel_count2 == 1)
345         return av_get_packed_sample_fmt(fmt1) != av_get_packed_sample_fmt(fmt2);
346     else
347         return channel_count1 != channel_count2 || fmt1 != fmt2;
348 }
349
350 static inline
351 int64_t get_valid_channel_layout(int64_t channel_layout, int channels)
352 {
353     if (channel_layout && av_get_channel_layout_nb_channels(channel_layout) == channels)
354         return channel_layout;
355     else
356         return 0;
357 }
358
359 static int packet_queue_put(PacketQueue *q, AVPacket *pkt);
360
361 static int packet_queue_put_private(PacketQueue *q, AVPacket *pkt)
362 {
363     MyAVPacketList *pkt1;
364
365     if (q->abort_request)
366        return -1;
367
368     pkt1 = av_malloc(sizeof(MyAVPacketList));
369     if (!pkt1)
370         return -1;
371     pkt1->pkt = *pkt;
372     pkt1->next = NULL;
373     if (pkt == &flush_pkt)
374         q->serial++;
375     pkt1->serial = q->serial;
376
377     if (!q->last_pkt)
378         q->first_pkt = pkt1;
379     else
380         q->last_pkt->next = pkt1;
381     q->last_pkt = pkt1;
382     q->nb_packets++;
383     q->size += pkt1->pkt.size + sizeof(*pkt1);
384     /* XXX: should duplicate packet data in DV case */
385     SDL_CondSignal(q->cond);
386     return 0;
387 }
388
389 static int packet_queue_put(PacketQueue *q, AVPacket *pkt)
390 {
391     int ret;
392
393     /* duplicate the packet */
394     if (pkt != &flush_pkt && av_dup_packet(pkt) < 0)
395         return -1;
396
397     SDL_LockMutex(q->mutex);
398     ret = packet_queue_put_private(q, pkt);
399     SDL_UnlockMutex(q->mutex);
400
401     if (pkt != &flush_pkt && ret < 0)
402         av_free_packet(pkt);
403
404     return ret;
405 }
406
407 /* packet queue handling */
408 static void packet_queue_init(PacketQueue *q)
409 {
410     memset(q, 0, sizeof(PacketQueue));
411     q->mutex = SDL_CreateMutex();
412     q->cond = SDL_CreateCond();
413     q->abort_request = 1;
414 }
415
416 static void packet_queue_flush(PacketQueue *q)
417 {
418     MyAVPacketList *pkt, *pkt1;
419
420     SDL_LockMutex(q->mutex);
421     for (pkt = q->first_pkt; pkt != NULL; pkt = pkt1) {
422         pkt1 = pkt->next;
423         av_free_packet(&pkt->pkt);
424         av_freep(&pkt);
425     }
426     q->last_pkt = NULL;
427     q->first_pkt = NULL;
428     q->nb_packets = 0;
429     q->size = 0;
430     SDL_UnlockMutex(q->mutex);
431 }
432
433 static void packet_queue_destroy(PacketQueue *q)
434 {
435     packet_queue_flush(q);
436     SDL_DestroyMutex(q->mutex);
437     SDL_DestroyCond(q->cond);
438 }
439
440 static void packet_queue_abort(PacketQueue *q)
441 {
442     SDL_LockMutex(q->mutex);
443
444     q->abort_request = 1;
445
446     SDL_CondSignal(q->cond);
447
448     SDL_UnlockMutex(q->mutex);
449 }
450
451 static void packet_queue_start(PacketQueue *q)
452 {
453     SDL_LockMutex(q->mutex);
454     q->abort_request = 0;
455     packet_queue_put_private(q, &flush_pkt);
456     SDL_UnlockMutex(q->mutex);
457 }
458
459 /* return < 0 if aborted, 0 if no packet and > 0 if packet.  */
460 static int packet_queue_get(PacketQueue *q, AVPacket *pkt, int block, int *serial)
461 {
462     MyAVPacketList *pkt1;
463     int ret;
464
465     SDL_LockMutex(q->mutex);
466
467     for (;;) {
468         if (q->abort_request) {
469             ret = -1;
470             break;
471         }
472
473         pkt1 = q->first_pkt;
474         if (pkt1) {
475             q->first_pkt = pkt1->next;
476             if (!q->first_pkt)
477                 q->last_pkt = NULL;
478             q->nb_packets--;
479             q->size -= pkt1->pkt.size + sizeof(*pkt1);
480             *pkt = pkt1->pkt;
481             if (serial)
482                 *serial = pkt1->serial;
483             av_free(pkt1);
484             ret = 1;
485             break;
486         } else if (!block) {
487             ret = 0;
488             break;
489         } else {
490             SDL_CondWait(q->cond, q->mutex);
491         }
492     }
493     SDL_UnlockMutex(q->mutex);
494     return ret;
495 }
496
497 static inline void fill_rectangle(SDL_Surface *screen,
498                                   int x, int y, int w, int h, int color, int update)
499 {
500     SDL_Rect rect;
501     rect.x = x;
502     rect.y = y;
503     rect.w = w;
504     rect.h = h;
505     SDL_FillRect(screen, &rect, color);
506     if (update && w > 0 && h > 0)
507         SDL_UpdateRect(screen, x, y, w, h);
508 }
509
510 /* draw only the border of a rectangle */
511 static void fill_border(int xleft, int ytop, int width, int height, int x, int y, int w, int h, int color, int update)
512 {
513     int w1, w2, h1, h2;
514
515     /* fill the background */
516     w1 = x;
517     if (w1 < 0)
518         w1 = 0;
519     w2 = width - (x + w);
520     if (w2 < 0)
521         w2 = 0;
522     h1 = y;
523     if (h1 < 0)
524         h1 = 0;
525     h2 = height - (y + h);
526     if (h2 < 0)
527         h2 = 0;
528     fill_rectangle(screen,
529                    xleft, ytop,
530                    w1, height,
531                    color, update);
532     fill_rectangle(screen,
533                    xleft + width - w2, ytop,
534                    w2, height,
535                    color, update);
536     fill_rectangle(screen,
537                    xleft + w1, ytop,
538                    width - w1 - w2, h1,
539                    color, update);
540     fill_rectangle(screen,
541                    xleft + w1, ytop + height - h2,
542                    width - w1 - w2, h2,
543                    color, update);
544 }
545
546 #define ALPHA_BLEND(a, oldp, newp, s)\
547 ((((oldp << s) * (255 - (a))) + (newp * (a))) / (255 << s))
548
549 #define RGBA_IN(r, g, b, a, s)\
550 {\
551     unsigned int v = ((const uint32_t *)(s))[0];\
552     a = (v >> 24) & 0xff;\
553     r = (v >> 16) & 0xff;\
554     g = (v >> 8) & 0xff;\
555     b = v & 0xff;\
556 }
557
558 #define YUVA_IN(y, u, v, a, s, pal)\
559 {\
560     unsigned int val = ((const uint32_t *)(pal))[*(const uint8_t*)(s)];\
561     a = (val >> 24) & 0xff;\
562     y = (val >> 16) & 0xff;\
563     u = (val >> 8) & 0xff;\
564     v = val & 0xff;\
565 }
566
567 #define YUVA_OUT(d, y, u, v, a)\
568 {\
569     ((uint32_t *)(d))[0] = (a << 24) | (y << 16) | (u << 8) | v;\
570 }
571
572
573 #define BPP 1
574
575 static void blend_subrect(AVPicture *dst, const AVSubtitleRect *rect, int imgw, int imgh)
576 {
577     int wrap, wrap3, width2, skip2;
578     int y, u, v, a, u1, v1, a1, w, h;
579     uint8_t *lum, *cb, *cr;
580     const uint8_t *p;
581     const uint32_t *pal;
582     int dstx, dsty, dstw, dsth;
583
584     dstw = av_clip(rect->w, 0, imgw);
585     dsth = av_clip(rect->h, 0, imgh);
586     dstx = av_clip(rect->x, 0, imgw - dstw);
587     dsty = av_clip(rect->y, 0, imgh - dsth);
588     lum = dst->data[0] + dsty * dst->linesize[0];
589     cb  = dst->data[1] + (dsty >> 1) * dst->linesize[1];
590     cr  = dst->data[2] + (dsty >> 1) * dst->linesize[2];
591
592     width2 = ((dstw + 1) >> 1) + (dstx & ~dstw & 1);
593     skip2 = dstx >> 1;
594     wrap = dst->linesize[0];
595     wrap3 = rect->pict.linesize[0];
596     p = rect->pict.data[0];
597     pal = (const uint32_t *)rect->pict.data[1];  /* Now in YCrCb! */
598
599     if (dsty & 1) {
600         lum += dstx;
601         cb += skip2;
602         cr += skip2;
603
604         if (dstx & 1) {
605             YUVA_IN(y, u, v, a, p, pal);
606             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
607             cb[0] = ALPHA_BLEND(a >> 2, cb[0], u, 0);
608             cr[0] = ALPHA_BLEND(a >> 2, cr[0], v, 0);
609             cb++;
610             cr++;
611             lum++;
612             p += BPP;
613         }
614         for (w = dstw - (dstx & 1); w >= 2; w -= 2) {
615             YUVA_IN(y, u, v, a, p, pal);
616             u1 = u;
617             v1 = v;
618             a1 = a;
619             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
620
621             YUVA_IN(y, u, v, a, p + BPP, pal);
622             u1 += u;
623             v1 += v;
624             a1 += a;
625             lum[1] = ALPHA_BLEND(a, lum[1], y, 0);
626             cb[0] = ALPHA_BLEND(a1 >> 2, cb[0], u1, 1);
627             cr[0] = ALPHA_BLEND(a1 >> 2, cr[0], v1, 1);
628             cb++;
629             cr++;
630             p += 2 * BPP;
631             lum += 2;
632         }
633         if (w) {
634             YUVA_IN(y, u, v, a, p, pal);
635             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
636             cb[0] = ALPHA_BLEND(a >> 2, cb[0], u, 0);
637             cr[0] = ALPHA_BLEND(a >> 2, cr[0], v, 0);
638             p++;
639             lum++;
640         }
641         p += wrap3 - dstw * BPP;
642         lum += wrap - dstw - dstx;
643         cb += dst->linesize[1] - width2 - skip2;
644         cr += dst->linesize[2] - width2 - skip2;
645     }
646     for (h = dsth - (dsty & 1); h >= 2; h -= 2) {
647         lum += dstx;
648         cb += skip2;
649         cr += skip2;
650
651         if (dstx & 1) {
652             YUVA_IN(y, u, v, a, p, pal);
653             u1 = u;
654             v1 = v;
655             a1 = a;
656             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
657             p += wrap3;
658             lum += wrap;
659             YUVA_IN(y, u, v, a, p, pal);
660             u1 += u;
661             v1 += v;
662             a1 += a;
663             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
664             cb[0] = ALPHA_BLEND(a1 >> 2, cb[0], u1, 1);
665             cr[0] = ALPHA_BLEND(a1 >> 2, cr[0], v1, 1);
666             cb++;
667             cr++;
668             p += -wrap3 + BPP;
669             lum += -wrap + 1;
670         }
671         for (w = dstw - (dstx & 1); w >= 2; w -= 2) {
672             YUVA_IN(y, u, v, a, p, pal);
673             u1 = u;
674             v1 = v;
675             a1 = a;
676             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
677
678             YUVA_IN(y, u, v, a, p + BPP, pal);
679             u1 += u;
680             v1 += v;
681             a1 += a;
682             lum[1] = ALPHA_BLEND(a, lum[1], y, 0);
683             p += wrap3;
684             lum += wrap;
685
686             YUVA_IN(y, u, v, a, p, pal);
687             u1 += u;
688             v1 += v;
689             a1 += a;
690             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
691
692             YUVA_IN(y, u, v, a, p + BPP, pal);
693             u1 += u;
694             v1 += v;
695             a1 += a;
696             lum[1] = ALPHA_BLEND(a, lum[1], y, 0);
697
698             cb[0] = ALPHA_BLEND(a1 >> 2, cb[0], u1, 2);
699             cr[0] = ALPHA_BLEND(a1 >> 2, cr[0], v1, 2);
700
701             cb++;
702             cr++;
703             p += -wrap3 + 2 * BPP;
704             lum += -wrap + 2;
705         }
706         if (w) {
707             YUVA_IN(y, u, v, a, p, pal);
708             u1 = u;
709             v1 = v;
710             a1 = a;
711             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
712             p += wrap3;
713             lum += wrap;
714             YUVA_IN(y, u, v, a, p, pal);
715             u1 += u;
716             v1 += v;
717             a1 += a;
718             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
719             cb[0] = ALPHA_BLEND(a1 >> 2, cb[0], u1, 1);
720             cr[0] = ALPHA_BLEND(a1 >> 2, cr[0], v1, 1);
721             cb++;
722             cr++;
723             p += -wrap3 + BPP;
724             lum += -wrap + 1;
725         }
726         p += wrap3 + (wrap3 - dstw * BPP);
727         lum += wrap + (wrap - dstw - dstx);
728         cb += dst->linesize[1] - width2 - skip2;
729         cr += dst->linesize[2] - width2 - skip2;
730     }
731     /* handle odd height */
732     if (h) {
733         lum += dstx;
734         cb += skip2;
735         cr += skip2;
736
737         if (dstx & 1) {
738             YUVA_IN(y, u, v, a, p, pal);
739             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
740             cb[0] = ALPHA_BLEND(a >> 2, cb[0], u, 0);
741             cr[0] = ALPHA_BLEND(a >> 2, cr[0], v, 0);
742             cb++;
743             cr++;
744             lum++;
745             p += BPP;
746         }
747         for (w = dstw - (dstx & 1); w >= 2; w -= 2) {
748             YUVA_IN(y, u, v, a, p, pal);
749             u1 = u;
750             v1 = v;
751             a1 = a;
752             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
753
754             YUVA_IN(y, u, v, a, p + BPP, pal);
755             u1 += u;
756             v1 += v;
757             a1 += a;
758             lum[1] = ALPHA_BLEND(a, lum[1], y, 0);
759             cb[0] = ALPHA_BLEND(a1 >> 2, cb[0], u, 1);
760             cr[0] = ALPHA_BLEND(a1 >> 2, cr[0], v, 1);
761             cb++;
762             cr++;
763             p += 2 * BPP;
764             lum += 2;
765         }
766         if (w) {
767             YUVA_IN(y, u, v, a, p, pal);
768             lum[0] = ALPHA_BLEND(a, lum[0], y, 0);
769             cb[0] = ALPHA_BLEND(a >> 2, cb[0], u, 0);
770             cr[0] = ALPHA_BLEND(a >> 2, cr[0], v, 0);
771         }
772     }
773 }
774
775 static void free_subpicture(SubPicture *sp)
776 {
777     avsubtitle_free(&sp->sub);
778 }
779
780 static void calculate_display_rect(SDL_Rect *rect, int scr_xleft, int scr_ytop, int scr_width, int scr_height, VideoPicture *vp)
781 {
782     float aspect_ratio;
783     int width, height, x, y;
784
785     if (vp->sar.num == 0)
786         aspect_ratio = 0;
787     else
788         aspect_ratio = av_q2d(vp->sar);
789
790     if (aspect_ratio <= 0.0)
791         aspect_ratio = 1.0;
792     aspect_ratio *= (float)vp->width / (float)vp->height;
793
794     /* XXX: we suppose the screen has a 1.0 pixel ratio */
795     height = scr_height;
796     width = ((int)rint(height * aspect_ratio)) & ~1;
797     if (width > scr_width) {
798         width = scr_width;
799         height = ((int)rint(width / aspect_ratio)) & ~1;
800     }
801     x = (scr_width - width) / 2;
802     y = (scr_height - height) / 2;
803     rect->x = scr_xleft + x;
804     rect->y = scr_ytop  + y;
805     rect->w = FFMAX(width,  1);
806     rect->h = FFMAX(height, 1);
807 }
808
809 static void video_image_display(VideoState *is)
810 {
811     VideoPicture *vp;
812     SubPicture *sp;
813     AVPicture pict;
814     SDL_Rect rect;
815     int i;
816
817     vp = &is->pictq[is->pictq_rindex];
818     if (vp->bmp) {
819         if (is->subtitle_st) {
820             if (is->subpq_size > 0) {
821                 sp = &is->subpq[is->subpq_rindex];
822
823                 if (vp->pts >= sp->pts + ((float) sp->sub.start_display_time / 1000)) {
824                     SDL_LockYUVOverlay (vp->bmp);
825
826                     pict.data[0] = vp->bmp->pixels[0];
827                     pict.data[1] = vp->bmp->pixels[2];
828                     pict.data[2] = vp->bmp->pixels[1];
829
830                     pict.linesize[0] = vp->bmp->pitches[0];
831                     pict.linesize[1] = vp->bmp->pitches[2];
832                     pict.linesize[2] = vp->bmp->pitches[1];
833
834                     for (i = 0; i < sp->sub.num_rects; i++)
835                         blend_subrect(&pict, sp->sub.rects[i],
836                                       vp->bmp->w, vp->bmp->h);
837
838                     SDL_UnlockYUVOverlay (vp->bmp);
839                 }
840             }
841         }
842
843         calculate_display_rect(&rect, is->xleft, is->ytop, is->width, is->height, vp);
844
845         SDL_DisplayYUVOverlay(vp->bmp, &rect);
846
847         if (rect.x != is->last_display_rect.x || rect.y != is->last_display_rect.y || rect.w != is->last_display_rect.w || rect.h != is->last_display_rect.h || is->force_refresh) {
848             int bgcolor = SDL_MapRGB(screen->format, 0x00, 0x00, 0x00);
849             fill_border(is->xleft, is->ytop, is->width, is->height, rect.x, rect.y, rect.w, rect.h, bgcolor, 1);
850             is->last_display_rect = rect;
851         }
852     }
853 }
854
855 static inline int compute_mod(int a, int b)
856 {
857     return a < 0 ? a%b + b : a%b;
858 }
859
860 static void video_audio_display(VideoState *s)
861 {
862     int i, i_start, x, y1, y, ys, delay, n, nb_display_channels;
863     int ch, channels, h, h2, bgcolor, fgcolor;
864     int64_t time_diff;
865     int rdft_bits, nb_freq;
866
867     for (rdft_bits = 1; (1 << rdft_bits) < 2 * s->height; rdft_bits++)
868         ;
869     nb_freq = 1 << (rdft_bits - 1);
870
871     /* compute display index : center on currently output samples */
872     channels = s->audio_tgt.channels;
873     nb_display_channels = channels;
874     if (!s->paused) {
875         int data_used= s->show_mode == SHOW_MODE_WAVES ? s->width : (2*nb_freq);
876         n = 2 * channels;
877         delay = s->audio_write_buf_size;
878         delay /= n;
879
880         /* to be more precise, we take into account the time spent since
881            the last buffer computation */
882         if (audio_callback_time) {
883             time_diff = av_gettime() - audio_callback_time;
884             delay -= (time_diff * s->audio_tgt.freq) / 1000000;
885         }
886
887         delay += 2 * data_used;
888         if (delay < data_used)
889             delay = data_used;
890
891         i_start= x = compute_mod(s->sample_array_index - delay * channels, SAMPLE_ARRAY_SIZE);
892         if (s->show_mode == SHOW_MODE_WAVES) {
893             h = INT_MIN;
894             for (i = 0; i < 1000; i += channels) {
895                 int idx = (SAMPLE_ARRAY_SIZE + x - i) % SAMPLE_ARRAY_SIZE;
896                 int a = s->sample_array[idx];
897                 int b = s->sample_array[(idx + 4 * channels) % SAMPLE_ARRAY_SIZE];
898                 int c = s->sample_array[(idx + 5 * channels) % SAMPLE_ARRAY_SIZE];
899                 int d = s->sample_array[(idx + 9 * channels) % SAMPLE_ARRAY_SIZE];
900                 int score = a - d;
901                 if (h < score && (b ^ c) < 0) {
902                     h = score;
903                     i_start = idx;
904                 }
905             }
906         }
907
908         s->last_i_start = i_start;
909     } else {
910         i_start = s->last_i_start;
911     }
912
913     bgcolor = SDL_MapRGB(screen->format, 0x00, 0x00, 0x00);
914     if (s->show_mode == SHOW_MODE_WAVES) {
915         fill_rectangle(screen,
916                        s->xleft, s->ytop, s->width, s->height,
917                        bgcolor, 0);
918
919         fgcolor = SDL_MapRGB(screen->format, 0xff, 0xff, 0xff);
920
921         /* total height for one channel */
922         h = s->height / nb_display_channels;
923         /* graph height / 2 */
924         h2 = (h * 9) / 20;
925         for (ch = 0; ch < nb_display_channels; ch++) {
926             i = i_start + ch;
927             y1 = s->ytop + ch * h + (h / 2); /* position of center line */
928             for (x = 0; x < s->width; x++) {
929                 y = (s->sample_array[i] * h2) >> 15;
930                 if (y < 0) {
931                     y = -y;
932                     ys = y1 - y;
933                 } else {
934                     ys = y1;
935                 }
936                 fill_rectangle(screen,
937                                s->xleft + x, ys, 1, y,
938                                fgcolor, 0);
939                 i += channels;
940                 if (i >= SAMPLE_ARRAY_SIZE)
941                     i -= SAMPLE_ARRAY_SIZE;
942             }
943         }
944
945         fgcolor = SDL_MapRGB(screen->format, 0x00, 0x00, 0xff);
946
947         for (ch = 1; ch < nb_display_channels; ch++) {
948             y = s->ytop + ch * h;
949             fill_rectangle(screen,
950                            s->xleft, y, s->width, 1,
951                            fgcolor, 0);
952         }
953         SDL_UpdateRect(screen, s->xleft, s->ytop, s->width, s->height);
954     } else {
955         nb_display_channels= FFMIN(nb_display_channels, 2);
956         if (rdft_bits != s->rdft_bits) {
957             av_rdft_end(s->rdft);
958             av_free(s->rdft_data);
959             s->rdft = av_rdft_init(rdft_bits, DFT_R2C);
960             s->rdft_bits = rdft_bits;
961             s->rdft_data = av_malloc(4 * nb_freq * sizeof(*s->rdft_data));
962         }
963         {
964             FFTSample *data[2];
965             for (ch = 0; ch < nb_display_channels; ch++) {
966                 data[ch] = s->rdft_data + 2 * nb_freq * ch;
967                 i = i_start + ch;
968                 for (x = 0; x < 2 * nb_freq; x++) {
969                     double w = (x-nb_freq) * (1.0 / nb_freq);
970                     data[ch][x] = s->sample_array[i] * (1.0 - w * w);
971                     i += channels;
972                     if (i >= SAMPLE_ARRAY_SIZE)
973                         i -= SAMPLE_ARRAY_SIZE;
974                 }
975                 av_rdft_calc(s->rdft, data[ch]);
976             }
977             // least efficient way to do this, we should of course directly access it but its more than fast enough
978             for (y = 0; y < s->height; y++) {
979                 double w = 1 / sqrt(nb_freq);
980                 int a = sqrt(w * sqrt(data[0][2 * y + 0] * data[0][2 * y + 0] + data[0][2 * y + 1] * data[0][2 * y + 1]));
981                 int b = (nb_display_channels == 2 ) ? sqrt(w * sqrt(data[1][2 * y + 0] * data[1][2 * y + 0]
982                        + data[1][2 * y + 1] * data[1][2 * y + 1])) : a;
983                 a = FFMIN(a, 255);
984                 b = FFMIN(b, 255);
985                 fgcolor = SDL_MapRGB(screen->format, a, b, (a + b) / 2);
986
987                 fill_rectangle(screen,
988                             s->xpos, s->height-y, 1, 1,
989                             fgcolor, 0);
990             }
991         }
992         SDL_UpdateRect(screen, s->xpos, s->ytop, 1, s->height);
993         if (!s->paused)
994             s->xpos++;
995         if (s->xpos >= s->width)
996             s->xpos= s->xleft;
997     }
998 }
999
1000 static void stream_close(VideoState *is)
1001 {
1002     VideoPicture *vp;
1003     int i;
1004     /* XXX: use a special url_shutdown call to abort parse cleanly */
1005     is->abort_request = 1;
1006     SDL_WaitThread(is->read_tid, NULL);
1007     packet_queue_destroy(&is->videoq);
1008     packet_queue_destroy(&is->audioq);
1009     packet_queue_destroy(&is->subtitleq);
1010
1011     /* free all pictures */
1012     for (i = 0; i < VIDEO_PICTURE_QUEUE_SIZE; i++) {
1013         vp = &is->pictq[i];
1014         if (vp->bmp) {
1015             SDL_FreeYUVOverlay(vp->bmp);
1016             vp->bmp = NULL;
1017         }
1018     }
1019     SDL_DestroyMutex(is->pictq_mutex);
1020     SDL_DestroyCond(is->pictq_cond);
1021     SDL_DestroyMutex(is->subpq_mutex);
1022     SDL_DestroyCond(is->subpq_cond);
1023     SDL_DestroyCond(is->continue_read_thread);
1024 #if !CONFIG_AVFILTER
1025     sws_freeContext(is->img_convert_ctx);
1026 #endif
1027     av_free(is);
1028 }
1029
1030 static void do_exit(VideoState *is)
1031 {
1032     if (is) {
1033         stream_close(is);
1034     }
1035     av_lockmgr_register(NULL);
1036     uninit_opts();
1037 #if CONFIG_AVFILTER
1038     av_freep(&vfilters);
1039 #endif
1040     avformat_network_deinit();
1041     if (show_status)
1042         printf("\n");
1043     SDL_Quit();
1044     av_log(NULL, AV_LOG_QUIET, "%s", "");
1045     exit(0);
1046 }
1047
1048 static void sigterm_handler(int sig)
1049 {
1050     exit(123);
1051 }
1052
1053 static int video_open(VideoState *is, int force_set_video_mode, VideoPicture *vp)
1054 {
1055     int flags = SDL_HWSURFACE | SDL_ASYNCBLIT | SDL_HWACCEL;
1056     int w,h;
1057     SDL_Rect rect;
1058
1059     if (is_full_screen) flags |= SDL_FULLSCREEN;
1060     else                flags |= SDL_RESIZABLE;
1061
1062     if (vp && vp->width) {
1063         calculate_display_rect(&rect, 0, 0, INT_MAX, vp->height, vp);
1064         default_width  = rect.w;
1065         default_height = rect.h;
1066     }
1067
1068     if (is_full_screen && fs_screen_width) {
1069         w = fs_screen_width;
1070         h = fs_screen_height;
1071     } else if (!is_full_screen && screen_width) {
1072         w = screen_width;
1073         h = screen_height;
1074     } else {
1075         w = default_width;
1076         h = default_height;
1077     }
1078     w = FFMIN(16383, w);
1079     if (screen && is->width == screen->w && screen->w == w
1080        && is->height== screen->h && screen->h == h && !force_set_video_mode)
1081         return 0;
1082     screen = SDL_SetVideoMode(w, h, 0, flags);
1083     if (!screen) {
1084         av_log(NULL, AV_LOG_FATAL, "SDL: could not set video mode - exiting\n");
1085         do_exit(is);
1086     }
1087     if (!window_title)
1088         window_title = input_filename;
1089     SDL_WM_SetCaption(window_title, window_title);
1090
1091     is->width  = screen->w;
1092     is->height = screen->h;
1093
1094     return 0;
1095 }
1096
1097 /* display the current picture, if any */
1098 static void video_display(VideoState *is)
1099 {
1100     if (!screen)
1101         video_open(is, 0, NULL);
1102     if (is->audio_st && is->show_mode != SHOW_MODE_VIDEO)
1103         video_audio_display(is);
1104     else if (is->video_st)
1105         video_image_display(is);
1106 }
1107
1108 static double get_clock(Clock *c)
1109 {
1110     if (*c->queue_serial != c->serial)
1111         return NAN;
1112     if (c->paused) {
1113         return c->pts;
1114     } else {
1115         double time = av_gettime() / 1000000.0;
1116         return c->pts_drift + time - (time - c->last_updated) * (1.0 - c->speed);
1117     }
1118 }
1119
1120 static void set_clock_at(Clock *c, double pts, int serial, double time)
1121 {
1122     c->pts = pts;
1123     c->last_updated = time;
1124     c->pts_drift = c->pts - time;
1125     c->serial = serial;
1126 }
1127
1128 static void set_clock(Clock *c, double pts, int serial)
1129 {
1130     double time = av_gettime() / 1000000.0;
1131     set_clock_at(c, pts, serial, time);
1132 }
1133
1134 static void set_clock_speed(Clock *c, double speed)
1135 {
1136     set_clock(c, get_clock(c), c->serial);
1137     c->speed = speed;
1138 }
1139
1140 static void init_clock(Clock *c, int *queue_serial)
1141 {
1142     c->speed = 1.0;
1143     c->paused = 0;
1144     c->queue_serial = queue_serial;
1145     set_clock(c, NAN, -1);
1146 }
1147
1148 static void sync_clock_to_slave(Clock *c, Clock *slave)
1149 {
1150     double clock = get_clock(c);
1151     double slave_clock = get_clock(slave);
1152     if (!isnan(slave_clock) && (isnan(clock) || fabs(clock - slave_clock) > AV_NOSYNC_THRESHOLD))
1153         set_clock(c, slave_clock, slave->serial);
1154 }
1155
1156 static int get_master_sync_type(VideoState *is) {
1157     if (is->av_sync_type == AV_SYNC_VIDEO_MASTER) {
1158         if (is->video_st)
1159             return AV_SYNC_VIDEO_MASTER;
1160         else
1161             return AV_SYNC_AUDIO_MASTER;
1162     } else if (is->av_sync_type == AV_SYNC_AUDIO_MASTER) {
1163         if (is->audio_st)
1164             return AV_SYNC_AUDIO_MASTER;
1165         else
1166             return AV_SYNC_EXTERNAL_CLOCK;
1167     } else {
1168         return AV_SYNC_EXTERNAL_CLOCK;
1169     }
1170 }
1171
1172 /* get the current master clock value */
1173 static double get_master_clock(VideoState *is)
1174 {
1175     double val;
1176
1177     switch (get_master_sync_type(is)) {
1178         case AV_SYNC_VIDEO_MASTER:
1179             val = get_clock(&is->vidclk);
1180             break;
1181         case AV_SYNC_AUDIO_MASTER:
1182             val = get_clock(&is->audclk);
1183             break;
1184         default:
1185             val = get_clock(&is->extclk);
1186             break;
1187     }
1188     return val;
1189 }
1190
1191 static void check_external_clock_speed(VideoState *is) {
1192    if (is->video_stream >= 0 && is->videoq.nb_packets <= MIN_FRAMES / 2 ||
1193        is->audio_stream >= 0 && is->audioq.nb_packets <= MIN_FRAMES / 2) {
1194        set_clock_speed(&is->extclk, FFMAX(EXTERNAL_CLOCK_SPEED_MIN, is->extclk.speed - EXTERNAL_CLOCK_SPEED_STEP));
1195    } else if ((is->video_stream < 0 || is->videoq.nb_packets > MIN_FRAMES * 2) &&
1196               (is->audio_stream < 0 || is->audioq.nb_packets > MIN_FRAMES * 2)) {
1197        set_clock_speed(&is->extclk, FFMIN(EXTERNAL_CLOCK_SPEED_MAX, is->extclk.speed + EXTERNAL_CLOCK_SPEED_STEP));
1198    } else {
1199        double speed = is->extclk.speed;
1200        if (speed != 1.0)
1201            set_clock_speed(&is->extclk, speed + EXTERNAL_CLOCK_SPEED_STEP * (1.0 - speed) / fabs(1.0 - speed));
1202    }
1203 }
1204
1205 /* seek in the stream */
1206 static void stream_seek(VideoState *is, int64_t pos, int64_t rel, int seek_by_bytes)
1207 {
1208     if (!is->seek_req) {
1209         is->seek_pos = pos;
1210         is->seek_rel = rel;
1211         is->seek_flags &= ~AVSEEK_FLAG_BYTE;
1212         if (seek_by_bytes)
1213             is->seek_flags |= AVSEEK_FLAG_BYTE;
1214         is->seek_req = 1;
1215         SDL_CondSignal(is->continue_read_thread);
1216     }
1217 }
1218
1219 /* pause or resume the video */
1220 static void stream_toggle_pause(VideoState *is)
1221 {
1222     if (is->paused) {
1223         is->frame_timer += av_gettime() / 1000000.0 + is->vidclk.pts_drift - is->vidclk.pts;
1224         if (is->read_pause_return != AVERROR(ENOSYS)) {
1225             is->vidclk.paused = 0;
1226         }
1227         set_clock(&is->vidclk, get_clock(&is->vidclk), is->vidclk.serial);
1228     }
1229     set_clock(&is->extclk, get_clock(&is->extclk), is->extclk.serial);
1230     is->paused = is->audclk.paused = is->vidclk.paused = is->extclk.paused = !is->paused;
1231 }
1232
1233 static void toggle_pause(VideoState *is)
1234 {
1235     stream_toggle_pause(is);
1236     is->step = 0;
1237 }
1238
1239 static void step_to_next_frame(VideoState *is)
1240 {
1241     /* if the stream is paused unpause it, then step */
1242     if (is->paused)
1243         stream_toggle_pause(is);
1244     is->step = 1;
1245 }
1246
1247 static double compute_target_delay(double delay, VideoState *is)
1248 {
1249     double sync_threshold, diff;
1250
1251     /* update delay to follow master synchronisation source */
1252     if (get_master_sync_type(is) != AV_SYNC_VIDEO_MASTER) {
1253         /* if video is slave, we try to correct big delays by
1254            duplicating or deleting a frame */
1255         diff = get_clock(&is->vidclk) - get_master_clock(is);
1256
1257         /* skip or repeat frame. We take into account the
1258            delay to compute the threshold. I still don't know
1259            if it is the best guess */
1260         sync_threshold = FFMAX(AV_SYNC_THRESHOLD_MIN, FFMIN(AV_SYNC_THRESHOLD_MAX, delay));
1261         if (!isnan(diff) && fabs(diff) < is->max_frame_duration) {
1262             if (diff <= -sync_threshold)
1263                 delay = FFMAX(0, delay + diff);
1264             else if (diff >= sync_threshold && delay > AV_SYNC_FRAMEDUP_THRESHOLD)
1265                 delay = delay + diff;
1266             else if (diff >= sync_threshold)
1267                 delay = 2 * delay;
1268         }
1269     }
1270
1271     av_dlog(NULL, "video: delay=%0.3f A-V=%f\n",
1272             delay, -diff);
1273
1274     return delay;
1275 }
1276
1277 static void pictq_next_picture(VideoState *is) {
1278     /* update queue size and signal for next picture */
1279     if (++is->pictq_rindex == VIDEO_PICTURE_QUEUE_SIZE)
1280         is->pictq_rindex = 0;
1281
1282     SDL_LockMutex(is->pictq_mutex);
1283     is->pictq_size--;
1284     SDL_CondSignal(is->pictq_cond);
1285     SDL_UnlockMutex(is->pictq_mutex);
1286 }
1287
1288 static int pictq_prev_picture(VideoState *is) {
1289     VideoPicture *prevvp;
1290     int ret = 0;
1291     /* update queue size and signal for the previous picture */
1292     prevvp = &is->pictq[(is->pictq_rindex + VIDEO_PICTURE_QUEUE_SIZE - 1) % VIDEO_PICTURE_QUEUE_SIZE];
1293     if (prevvp->allocated && prevvp->serial == is->videoq.serial) {
1294         SDL_LockMutex(is->pictq_mutex);
1295         if (is->pictq_size < VIDEO_PICTURE_QUEUE_SIZE) {
1296             if (--is->pictq_rindex == -1)
1297                 is->pictq_rindex = VIDEO_PICTURE_QUEUE_SIZE - 1;
1298             is->pictq_size++;
1299             ret = 1;
1300         }
1301         SDL_CondSignal(is->pictq_cond);
1302         SDL_UnlockMutex(is->pictq_mutex);
1303     }
1304     return ret;
1305 }
1306
1307 static void update_video_pts(VideoState *is, double pts, int64_t pos, int serial) {
1308     /* update current video pts */
1309     set_clock(&is->vidclk, pts, serial);
1310     sync_clock_to_slave(&is->extclk, &is->vidclk);
1311     is->video_current_pos = pos;
1312     is->frame_last_pts = pts;
1313 }
1314
1315 /* called to display each frame */
1316 static void video_refresh(void *opaque, double *remaining_time)
1317 {
1318     VideoState *is = opaque;
1319     VideoPicture *vp;
1320     double time;
1321
1322     SubPicture *sp, *sp2;
1323
1324     if (!is->paused && get_master_sync_type(is) == AV_SYNC_EXTERNAL_CLOCK && is->realtime)
1325         check_external_clock_speed(is);
1326
1327     if (!display_disable && is->show_mode != SHOW_MODE_VIDEO && is->audio_st) {
1328         time = av_gettime() / 1000000.0;
1329         if (is->force_refresh || is->last_vis_time + rdftspeed < time) {
1330             video_display(is);
1331             is->last_vis_time = time;
1332         }
1333         *remaining_time = FFMIN(*remaining_time, is->last_vis_time + rdftspeed - time);
1334     }
1335
1336     if (is->video_st) {
1337         int redisplay = 0;
1338         if (is->force_refresh)
1339             redisplay = pictq_prev_picture(is);
1340 retry:
1341         if (is->pictq_size == 0) {
1342             SDL_LockMutex(is->pictq_mutex);
1343             if (is->frame_last_dropped_pts != AV_NOPTS_VALUE && is->frame_last_dropped_pts > is->frame_last_pts) {
1344                 update_video_pts(is, is->frame_last_dropped_pts, is->frame_last_dropped_pos, is->frame_last_dropped_serial);
1345                 is->frame_last_dropped_pts = AV_NOPTS_VALUE;
1346             }
1347             SDL_UnlockMutex(is->pictq_mutex);
1348             // nothing to do, no picture to display in the queue
1349         } else {
1350             double last_duration, duration, delay;
1351             /* dequeue the picture */
1352             vp = &is->pictq[is->pictq_rindex];
1353
1354             if (vp->serial != is->videoq.serial) {
1355                 pictq_next_picture(is);
1356                 redisplay = 0;
1357                 goto retry;
1358             }
1359
1360             if (is->paused)
1361                 goto display;
1362
1363             /* compute nominal last_duration */
1364             last_duration = vp->pts - is->frame_last_pts;
1365             if (!isnan(last_duration) && last_duration > 0 && last_duration < is->max_frame_duration) {
1366                 /* if duration of the last frame was sane, update last_duration in video state */
1367                 is->frame_last_duration = last_duration;
1368             }
1369             if (redisplay)
1370                 delay = 0.0;
1371             else
1372                 delay = compute_target_delay(is->frame_last_duration, is);
1373
1374             time= av_gettime()/1000000.0;
1375             if (time < is->frame_timer + delay && !redisplay) {
1376                 *remaining_time = FFMIN(is->frame_timer + delay - time, *remaining_time);
1377                 return;
1378             }
1379
1380             is->frame_timer += delay;
1381             if (delay > 0 && time - is->frame_timer > AV_SYNC_THRESHOLD_MAX)
1382                 is->frame_timer = time;
1383
1384             SDL_LockMutex(is->pictq_mutex);
1385             if (!redisplay && !isnan(vp->pts))
1386                 update_video_pts(is, vp->pts, vp->pos, vp->serial);
1387             SDL_UnlockMutex(is->pictq_mutex);
1388
1389             if (is->pictq_size > 1) {
1390                 VideoPicture *nextvp = &is->pictq[(is->pictq_rindex + 1) % VIDEO_PICTURE_QUEUE_SIZE];
1391                 duration = nextvp->pts - vp->pts;
1392                 if(!is->step && (redisplay || framedrop>0 || (framedrop && get_master_sync_type(is) != AV_SYNC_VIDEO_MASTER)) && time > is->frame_timer + duration){
1393                     if (!redisplay)
1394                         is->frame_drops_late++;
1395                     pictq_next_picture(is);
1396                     redisplay = 0;
1397                     goto retry;
1398                 }
1399             }
1400
1401             if (is->subtitle_st) {
1402                     while (is->subpq_size > 0) {
1403                         sp = &is->subpq[is->subpq_rindex];
1404
1405                         if (is->subpq_size > 1)
1406                             sp2 = &is->subpq[(is->subpq_rindex + 1) % SUBPICTURE_QUEUE_SIZE];
1407                         else
1408                             sp2 = NULL;
1409
1410                         if (sp->serial != is->subtitleq.serial
1411                                 || (is->vidclk.pts > (sp->pts + ((float) sp->sub.end_display_time / 1000)))
1412                                 || (sp2 && is->vidclk.pts > (sp2->pts + ((float) sp2->sub.start_display_time / 1000))))
1413                         {
1414                             free_subpicture(sp);
1415
1416                             /* update queue size and signal for next picture */
1417                             if (++is->subpq_rindex == SUBPICTURE_QUEUE_SIZE)
1418                                 is->subpq_rindex = 0;
1419
1420                             SDL_LockMutex(is->subpq_mutex);
1421                             is->subpq_size--;
1422                             SDL_CondSignal(is->subpq_cond);
1423                             SDL_UnlockMutex(is->subpq_mutex);
1424                         } else {
1425                             break;
1426                         }
1427                     }
1428             }
1429
1430 display:
1431             /* display picture */
1432             if (!display_disable && is->show_mode == SHOW_MODE_VIDEO)
1433                 video_display(is);
1434
1435             pictq_next_picture(is);
1436
1437             if (is->step && !is->paused)
1438                 stream_toggle_pause(is);
1439         }
1440     }
1441     is->force_refresh = 0;
1442     if (show_status) {
1443         static int64_t last_time;
1444         int64_t cur_time;
1445         int aqsize, vqsize, sqsize;
1446         double av_diff;
1447
1448         cur_time = av_gettime();
1449         if (!last_time || (cur_time - last_time) >= 30000) {
1450             aqsize = 0;
1451             vqsize = 0;
1452             sqsize = 0;
1453             if (is->audio_st)
1454                 aqsize = is->audioq.size;
1455             if (is->video_st)
1456                 vqsize = is->videoq.size;
1457             if (is->subtitle_st)
1458                 sqsize = is->subtitleq.size;
1459             av_diff = 0;
1460             if (is->audio_st && is->video_st)
1461                 av_diff = get_clock(&is->audclk) - get_clock(&is->vidclk);
1462             else if (is->video_st)
1463                 av_diff = get_master_clock(is) - get_clock(&is->vidclk);
1464             else if (is->audio_st)
1465                 av_diff = get_master_clock(is) - get_clock(&is->audclk);
1466             av_log(NULL, AV_LOG_INFO,
1467                    "%7.2f %s:%7.3f fd=%4d aq=%5dKB vq=%5dKB sq=%5dB f=%"PRId64"/%"PRId64"   \r",
1468                    get_master_clock(is),
1469                    (is->audio_st && is->video_st) ? "A-V" : (is->video_st ? "M-V" : (is->audio_st ? "M-A" : "   ")),
1470                    av_diff,
1471                    is->frame_drops_early + is->frame_drops_late,
1472                    aqsize / 1024,
1473                    vqsize / 1024,
1474                    sqsize,
1475                    is->video_st ? is->video_st->codec->pts_correction_num_faulty_dts : 0,
1476                    is->video_st ? is->video_st->codec->pts_correction_num_faulty_pts : 0);
1477             fflush(stdout);
1478             last_time = cur_time;
1479         }
1480     }
1481 }
1482
1483 /* allocate a picture (needs to do that in main thread to avoid
1484    potential locking problems */
1485 static void alloc_picture(VideoState *is)
1486 {
1487     VideoPicture *vp;
1488     int64_t bufferdiff;
1489
1490     vp = &is->pictq[is->pictq_windex];
1491
1492     if (vp->bmp)
1493         SDL_FreeYUVOverlay(vp->bmp);
1494
1495     video_open(is, 0, vp);
1496
1497     vp->bmp = SDL_CreateYUVOverlay(vp->width, vp->height,
1498                                    SDL_YV12_OVERLAY,
1499                                    screen);
1500     bufferdiff = vp->bmp ? FFMAX(vp->bmp->pixels[0], vp->bmp->pixels[1]) - FFMIN(vp->bmp->pixels[0], vp->bmp->pixels[1]) : 0;
1501     if (!vp->bmp || vp->bmp->pitches[0] < vp->width || bufferdiff < (int64_t)vp->height * vp->bmp->pitches[0]) {
1502         /* SDL allocates a buffer smaller than requested if the video
1503          * overlay hardware is unable to support the requested size. */
1504         av_log(NULL, AV_LOG_FATAL,
1505                "Error: the video system does not support an image\n"
1506                         "size of %dx%d pixels. Try using -lowres or -vf \"scale=w:h\"\n"
1507                         "to reduce the image size.\n", vp->width, vp->height );
1508         do_exit(is);
1509     }
1510
1511     SDL_LockMutex(is->pictq_mutex);
1512     vp->allocated = 1;
1513     SDL_CondSignal(is->pictq_cond);
1514     SDL_UnlockMutex(is->pictq_mutex);
1515 }
1516
1517 static void duplicate_right_border_pixels(SDL_Overlay *bmp) {
1518     int i, width, height;
1519     Uint8 *p, *maxp;
1520     for (i = 0; i < 3; i++) {
1521         width  = bmp->w;
1522         height = bmp->h;
1523         if (i > 0) {
1524             width  >>= 1;
1525             height >>= 1;
1526         }
1527         if (bmp->pitches[i] > width) {
1528             maxp = bmp->pixels[i] + bmp->pitches[i] * height - 1;
1529             for (p = bmp->pixels[i] + width - 1; p < maxp; p += bmp->pitches[i])
1530                 *(p+1) = *p;
1531         }
1532     }
1533 }
1534
1535 static int queue_picture(VideoState *is, AVFrame *src_frame, double pts, int64_t pos, int serial)
1536 {
1537     VideoPicture *vp;
1538
1539 #if defined(DEBUG_SYNC) && 0
1540     printf("frame_type=%c pts=%0.3f\n",
1541            av_get_picture_type_char(src_frame->pict_type), pts);
1542 #endif
1543
1544     /* wait until we have space to put a new picture */
1545     SDL_LockMutex(is->pictq_mutex);
1546
1547     /* keep the last already displayed picture in the queue */
1548     while (is->pictq_size >= VIDEO_PICTURE_QUEUE_SIZE - 1 &&
1549            !is->videoq.abort_request) {
1550         SDL_CondWait(is->pictq_cond, is->pictq_mutex);
1551     }
1552     SDL_UnlockMutex(is->pictq_mutex);
1553
1554     if (is->videoq.abort_request)
1555         return -1;
1556
1557     vp = &is->pictq[is->pictq_windex];
1558
1559     vp->sar = src_frame->sample_aspect_ratio;
1560
1561     /* alloc or resize hardware picture buffer */
1562     if (!vp->bmp || vp->reallocate || !vp->allocated ||
1563         vp->width  != src_frame->width ||
1564         vp->height != src_frame->height) {
1565         SDL_Event event;
1566
1567         vp->allocated  = 0;
1568         vp->reallocate = 0;
1569         vp->width = src_frame->width;
1570         vp->height = src_frame->height;
1571
1572         /* the allocation must be done in the main thread to avoid
1573            locking problems. */
1574         event.type = FF_ALLOC_EVENT;
1575         event.user.data1 = is;
1576         SDL_PushEvent(&event);
1577
1578         /* wait until the picture is allocated */
1579         SDL_LockMutex(is->pictq_mutex);
1580         while (!vp->allocated && !is->videoq.abort_request) {
1581             SDL_CondWait(is->pictq_cond, is->pictq_mutex);
1582         }
1583         /* if the queue is aborted, we have to pop the pending ALLOC event or wait for the allocation to complete */
1584         if (is->videoq.abort_request && SDL_PeepEvents(&event, 1, SDL_GETEVENT, SDL_EVENTMASK(FF_ALLOC_EVENT)) != 1) {
1585             while (!vp->allocated) {
1586                 SDL_CondWait(is->pictq_cond, is->pictq_mutex);
1587             }
1588         }
1589         SDL_UnlockMutex(is->pictq_mutex);
1590
1591         if (is->videoq.abort_request)
1592             return -1;
1593     }
1594
1595     /* if the frame is not skipped, then display it */
1596     if (vp->bmp) {
1597         AVPicture pict = { { 0 } };
1598
1599         /* get a pointer on the bitmap */
1600         SDL_LockYUVOverlay (vp->bmp);
1601
1602         pict.data[0] = vp->bmp->pixels[0];
1603         pict.data[1] = vp->bmp->pixels[2];
1604         pict.data[2] = vp->bmp->pixels[1];
1605
1606         pict.linesize[0] = vp->bmp->pitches[0];
1607         pict.linesize[1] = vp->bmp->pitches[2];
1608         pict.linesize[2] = vp->bmp->pitches[1];
1609
1610 #if CONFIG_AVFILTER
1611         // FIXME use direct rendering
1612         av_picture_copy(&pict, (AVPicture *)src_frame,
1613                         src_frame->format, vp->width, vp->height);
1614 #else
1615         av_opt_get_int(sws_opts, "sws_flags", 0, &sws_flags);
1616         is->img_convert_ctx = sws_getCachedContext(is->img_convert_ctx,
1617             vp->width, vp->height, src_frame->format, vp->width, vp->height,
1618             AV_PIX_FMT_YUV420P, sws_flags, NULL, NULL, NULL);
1619         if (is->img_convert_ctx == NULL) {
1620             av_log(NULL, AV_LOG_FATAL, "Cannot initialize the conversion context\n");
1621             exit(1);
1622         }
1623         sws_scale(is->img_convert_ctx, src_frame->data, src_frame->linesize,
1624                   0, vp->height, pict.data, pict.linesize);
1625 #endif
1626         /* workaround SDL PITCH_WORKAROUND */
1627         duplicate_right_border_pixels(vp->bmp);
1628         /* update the bitmap content */
1629         SDL_UnlockYUVOverlay(vp->bmp);
1630
1631         vp->pts = pts;
1632         vp->pos = pos;
1633         vp->serial = serial;
1634
1635         /* now we can update the picture count */
1636         if (++is->pictq_windex == VIDEO_PICTURE_QUEUE_SIZE)
1637             is->pictq_windex = 0;
1638         SDL_LockMutex(is->pictq_mutex);
1639         is->pictq_size++;
1640         SDL_UnlockMutex(is->pictq_mutex);
1641     }
1642     return 0;
1643 }
1644
1645 static int get_video_frame(VideoState *is, AVFrame *frame, AVPacket *pkt, int *serial)
1646 {
1647     int got_picture;
1648
1649     if (packet_queue_get(&is->videoq, pkt, 1, serial) < 0)
1650         return -1;
1651
1652     if (pkt->data == flush_pkt.data) {
1653         avcodec_flush_buffers(is->video_st->codec);
1654
1655         SDL_LockMutex(is->pictq_mutex);
1656         // Make sure there are no long delay timers (ideally we should just flush the queue but that's harder)
1657         while (is->pictq_size && !is->videoq.abort_request) {
1658             SDL_CondWait(is->pictq_cond, is->pictq_mutex);
1659         }
1660         is->video_current_pos = -1;
1661         is->frame_last_pts = AV_NOPTS_VALUE;
1662         is->frame_last_duration = 0;
1663         is->frame_timer = (double)av_gettime() / 1000000.0;
1664         is->frame_last_dropped_pts = AV_NOPTS_VALUE;
1665         SDL_UnlockMutex(is->pictq_mutex);
1666         return 0;
1667     }
1668
1669     if(avcodec_decode_video2(is->video_st->codec, frame, &got_picture, pkt) < 0)
1670         return 0;
1671
1672     if (got_picture) {
1673         int ret = 1;
1674         double dpts = NAN;
1675
1676         if (decoder_reorder_pts == -1) {
1677             frame->pts = av_frame_get_best_effort_timestamp(frame);
1678         } else if (decoder_reorder_pts) {
1679             frame->pts = frame->pkt_pts;
1680         } else {
1681             frame->pts = frame->pkt_dts;
1682         }
1683
1684         if (frame->pts != AV_NOPTS_VALUE)
1685             dpts = av_q2d(is->video_st->time_base) * frame->pts;
1686
1687         frame->sample_aspect_ratio = av_guess_sample_aspect_ratio(is->ic, is->video_st, frame);
1688
1689         if (framedrop>0 || (framedrop && get_master_sync_type(is) != AV_SYNC_VIDEO_MASTER)) {
1690             SDL_LockMutex(is->pictq_mutex);
1691             if (is->frame_last_pts != AV_NOPTS_VALUE && frame->pts != AV_NOPTS_VALUE) {
1692                 double clockdiff = get_clock(&is->vidclk) - get_master_clock(is);
1693                 double ptsdiff = dpts - is->frame_last_pts;
1694                 if (!isnan(clockdiff) && fabs(clockdiff) < AV_NOSYNC_THRESHOLD &&
1695                     !isnan(ptsdiff) && ptsdiff > 0 && ptsdiff < AV_NOSYNC_THRESHOLD &&
1696                     clockdiff + ptsdiff - is->frame_last_filter_delay < 0 &&
1697                     is->videoq.nb_packets) {
1698                     is->frame_last_dropped_pos = pkt->pos;
1699                     is->frame_last_dropped_pts = dpts;
1700                     is->frame_last_dropped_serial = *serial;
1701                     is->frame_drops_early++;
1702                     av_frame_unref(frame);
1703                     ret = 0;
1704                 }
1705             }
1706             SDL_UnlockMutex(is->pictq_mutex);
1707         }
1708
1709         return ret;
1710     }
1711     return 0;
1712 }
1713
1714 #if CONFIG_AVFILTER
1715 static int configure_filtergraph(AVFilterGraph *graph, const char *filtergraph,
1716                                  AVFilterContext *source_ctx, AVFilterContext *sink_ctx)
1717 {
1718     int ret;
1719     AVFilterInOut *outputs = NULL, *inputs = NULL;
1720
1721     if (filtergraph) {
1722         outputs = avfilter_inout_alloc();
1723         inputs  = avfilter_inout_alloc();
1724         if (!outputs || !inputs) {
1725             ret = AVERROR(ENOMEM);
1726             goto fail;
1727         }
1728
1729         outputs->name       = av_strdup("in");
1730         outputs->filter_ctx = source_ctx;
1731         outputs->pad_idx    = 0;
1732         outputs->next       = NULL;
1733
1734         inputs->name        = av_strdup("out");
1735         inputs->filter_ctx  = sink_ctx;
1736         inputs->pad_idx     = 0;
1737         inputs->next        = NULL;
1738
1739         if ((ret = avfilter_graph_parse_ptr(graph, filtergraph, &inputs, &outputs, NULL)) < 0)
1740             goto fail;
1741     } else {
1742         if ((ret = avfilter_link(source_ctx, 0, sink_ctx, 0)) < 0)
1743             goto fail;
1744     }
1745
1746     ret = avfilter_graph_config(graph, NULL);
1747 fail:
1748     avfilter_inout_free(&outputs);
1749     avfilter_inout_free(&inputs);
1750     return ret;
1751 }
1752
1753 static int configure_video_filters(AVFilterGraph *graph, VideoState *is, const char *vfilters, AVFrame *frame)
1754 {
1755     static const enum AVPixelFormat pix_fmts[] = { AV_PIX_FMT_YUV420P, AV_PIX_FMT_NONE };
1756     char sws_flags_str[128];
1757     char buffersrc_args[256];
1758     int ret;
1759     AVFilterContext *filt_src = NULL, *filt_out = NULL, *filt_crop;
1760     AVCodecContext *codec = is->video_st->codec;
1761     AVRational fr = av_guess_frame_rate(is->ic, is->video_st, NULL);
1762
1763     av_opt_get_int(sws_opts, "sws_flags", 0, &sws_flags);
1764     snprintf(sws_flags_str, sizeof(sws_flags_str), "flags=%"PRId64, sws_flags);
1765     graph->scale_sws_opts = av_strdup(sws_flags_str);
1766
1767     snprintf(buffersrc_args, sizeof(buffersrc_args),
1768              "video_size=%dx%d:pix_fmt=%d:time_base=%d/%d:pixel_aspect=%d/%d",
1769              frame->width, frame->height, frame->format,
1770              is->video_st->time_base.num, is->video_st->time_base.den,
1771              codec->sample_aspect_ratio.num, FFMAX(codec->sample_aspect_ratio.den, 1));
1772     if (fr.num && fr.den)
1773         av_strlcatf(buffersrc_args, sizeof(buffersrc_args), ":frame_rate=%d/%d", fr.num, fr.den);
1774
1775     if ((ret = avfilter_graph_create_filter(&filt_src,
1776                                             avfilter_get_by_name("buffer"),
1777                                             "ffplay_buffer", buffersrc_args, NULL,
1778                                             graph)) < 0)
1779         goto fail;
1780
1781     ret = avfilter_graph_create_filter(&filt_out,
1782                                        avfilter_get_by_name("buffersink"),
1783                                        "ffplay_buffersink", NULL, NULL, graph);
1784     if (ret < 0)
1785         goto fail;
1786
1787     if ((ret = av_opt_set_int_list(filt_out, "pix_fmts", pix_fmts,  AV_PIX_FMT_NONE, AV_OPT_SEARCH_CHILDREN)) < 0)
1788         goto fail;
1789
1790     /* SDL YUV code is not handling odd width/height for some driver
1791      * combinations, therefore we crop the picture to an even width/height. */
1792     if ((ret = avfilter_graph_create_filter(&filt_crop,
1793                                             avfilter_get_by_name("crop"),
1794                                             "ffplay_crop", "floor(in_w/2)*2:floor(in_h/2)*2", NULL, graph)) < 0)
1795         goto fail;
1796     if ((ret = avfilter_link(filt_crop, 0, filt_out, 0)) < 0)
1797         goto fail;
1798
1799     if ((ret = configure_filtergraph(graph, vfilters, filt_src, filt_crop)) < 0)
1800         goto fail;
1801
1802     is->in_video_filter  = filt_src;
1803     is->out_video_filter = filt_out;
1804
1805 fail:
1806     return ret;
1807 }
1808
1809 static int configure_audio_filters(VideoState *is, const char *afilters, int force_output_format)
1810 {
1811     static const enum AVSampleFormat sample_fmts[] = { AV_SAMPLE_FMT_S16, AV_SAMPLE_FMT_NONE };
1812     int sample_rates[2] = { 0, -1 };
1813     int64_t channel_layouts[2] = { 0, -1 };
1814     int channels[2] = { 0, -1 };
1815     AVFilterContext *filt_asrc = NULL, *filt_asink = NULL;
1816     char asrc_args[256];
1817     int ret;
1818
1819     avfilter_graph_free(&is->agraph);
1820     if (!(is->agraph = avfilter_graph_alloc()))
1821         return AVERROR(ENOMEM);
1822
1823     ret = snprintf(asrc_args, sizeof(asrc_args),
1824                    "sample_rate=%d:sample_fmt=%s:channels=%d:time_base=%d/%d",
1825                    is->audio_filter_src.freq, av_get_sample_fmt_name(is->audio_filter_src.fmt),
1826                    is->audio_filter_src.channels,
1827                    1, is->audio_filter_src.freq);
1828     if (is->audio_filter_src.channel_layout)
1829         snprintf(asrc_args + ret, sizeof(asrc_args) - ret,
1830                  ":channel_layout=0x%"PRIx64,  is->audio_filter_src.channel_layout);
1831
1832     ret = avfilter_graph_create_filter(&filt_asrc,
1833                                        avfilter_get_by_name("abuffer"), "ffplay_abuffer",
1834                                        asrc_args, NULL, is->agraph);
1835     if (ret < 0)
1836         goto end;
1837
1838
1839     ret = avfilter_graph_create_filter(&filt_asink,
1840                                        avfilter_get_by_name("abuffersink"), "ffplay_abuffersink",
1841                                        NULL, NULL, is->agraph);
1842     if (ret < 0)
1843         goto end;
1844
1845     if ((ret = av_opt_set_int_list(filt_asink, "sample_fmts", sample_fmts,  AV_SAMPLE_FMT_NONE, AV_OPT_SEARCH_CHILDREN)) < 0)
1846         goto end;
1847     if ((ret = av_opt_set_int(filt_asink, "all_channel_counts", 1, AV_OPT_SEARCH_CHILDREN)) < 0)
1848         goto end;
1849
1850     if (force_output_format) {
1851         channel_layouts[0] = is->audio_tgt.channel_layout;
1852         channels       [0] = is->audio_tgt.channels;
1853         sample_rates   [0] = is->audio_tgt.freq;
1854         if ((ret = av_opt_set_int(filt_asink, "all_channel_counts", 0, AV_OPT_SEARCH_CHILDREN)) < 0)
1855             goto end;
1856         if ((ret = av_opt_set_int_list(filt_asink, "channel_layouts", channel_layouts,  -1, AV_OPT_SEARCH_CHILDREN)) < 0)
1857             goto end;
1858         if ((ret = av_opt_set_int_list(filt_asink, "channel_counts" , channels       ,  -1, AV_OPT_SEARCH_CHILDREN)) < 0)
1859             goto end;
1860         if ((ret = av_opt_set_int_list(filt_asink, "sample_rates"   , sample_rates   ,  -1, AV_OPT_SEARCH_CHILDREN)) < 0)
1861             goto end;
1862     }
1863
1864
1865     if ((ret = configure_filtergraph(is->agraph, afilters, filt_asrc, filt_asink)) < 0)
1866         goto end;
1867
1868     is->in_audio_filter  = filt_asrc;
1869     is->out_audio_filter = filt_asink;
1870
1871 end:
1872     if (ret < 0)
1873         avfilter_graph_free(&is->agraph);
1874     return ret;
1875 }
1876 #endif  /* CONFIG_AVFILTER */
1877
1878 static int video_thread(void *arg)
1879 {
1880     AVPacket pkt = { 0 };
1881     VideoState *is = arg;
1882     AVFrame *frame = av_frame_alloc();
1883     double pts;
1884     int ret;
1885     int serial = 0;
1886
1887 #if CONFIG_AVFILTER
1888     AVFilterGraph *graph = avfilter_graph_alloc();
1889     AVFilterContext *filt_out = NULL, *filt_in = NULL;
1890     int last_w = 0;
1891     int last_h = 0;
1892     enum AVPixelFormat last_format = -2;
1893     int last_serial = -1;
1894 #endif
1895
1896     for (;;) {
1897         while (is->paused && !is->videoq.abort_request)
1898             SDL_Delay(10);
1899
1900         avcodec_get_frame_defaults(frame);
1901         av_free_packet(&pkt);
1902
1903         ret = get_video_frame(is, frame, &pkt, &serial);
1904         if (ret < 0)
1905             goto the_end;
1906         if (!ret)
1907             continue;
1908
1909 #if CONFIG_AVFILTER
1910         if (   last_w != frame->width
1911             || last_h != frame->height
1912             || last_format != frame->format
1913             || last_serial != serial) {
1914             av_log(NULL, AV_LOG_DEBUG,
1915                    "Video frame changed from size:%dx%d format:%s serial:%d to size:%dx%d format:%s serial:%d\n",
1916                    last_w, last_h,
1917                    (const char *)av_x_if_null(av_get_pix_fmt_name(last_format), "none"), last_serial,
1918                    frame->width, frame->height,
1919                    (const char *)av_x_if_null(av_get_pix_fmt_name(frame->format), "none"), serial);
1920             avfilter_graph_free(&graph);
1921             graph = avfilter_graph_alloc();
1922             if ((ret = configure_video_filters(graph, is, vfilters, frame)) < 0) {
1923                 SDL_Event event;
1924                 event.type = FF_QUIT_EVENT;
1925                 event.user.data1 = is;
1926                 SDL_PushEvent(&event);
1927                 av_free_packet(&pkt);
1928                 goto the_end;
1929             }
1930             filt_in  = is->in_video_filter;
1931             filt_out = is->out_video_filter;
1932             last_w = frame->width;
1933             last_h = frame->height;
1934             last_format = frame->format;
1935             last_serial = serial;
1936         }
1937
1938         ret = av_buffersrc_add_frame(filt_in, frame);
1939         if (ret < 0)
1940             goto the_end;
1941         av_frame_unref(frame);
1942         avcodec_get_frame_defaults(frame);
1943         av_free_packet(&pkt);
1944
1945         while (ret >= 0) {
1946             is->frame_last_returned_time = av_gettime() / 1000000.0;
1947
1948             ret = av_buffersink_get_frame_flags(filt_out, frame, 0);
1949             if (ret < 0) {
1950                 ret = 0;
1951                 break;
1952             }
1953
1954             is->frame_last_filter_delay = av_gettime() / 1000000.0 - is->frame_last_returned_time;
1955             if (fabs(is->frame_last_filter_delay) > AV_NOSYNC_THRESHOLD / 10.0)
1956                 is->frame_last_filter_delay = 0;
1957
1958             pts = (frame->pts == AV_NOPTS_VALUE) ? NAN : frame->pts * av_q2d(filt_out->inputs[0]->time_base);
1959             ret = queue_picture(is, frame, pts, av_frame_get_pkt_pos(frame), serial);
1960             av_frame_unref(frame);
1961         }
1962 #else
1963         pts = (frame->pts == AV_NOPTS_VALUE) ? NAN : frame->pts * av_q2d(is->video_st->time_base);
1964         ret = queue_picture(is, frame, pts, pkt.pos, serial);
1965         av_frame_unref(frame);
1966 #endif
1967
1968         if (ret < 0)
1969             goto the_end;
1970     }
1971  the_end:
1972     avcodec_flush_buffers(is->video_st->codec);
1973 #if CONFIG_AVFILTER
1974     avfilter_graph_free(&graph);
1975 #endif
1976     av_free_packet(&pkt);
1977     av_frame_free(&frame);
1978     return 0;
1979 }
1980
1981 static int subtitle_thread(void *arg)
1982 {
1983     VideoState *is = arg;
1984     SubPicture *sp;
1985     AVPacket pkt1, *pkt = &pkt1;
1986     int got_subtitle;
1987     int serial;
1988     double pts;
1989     int i, j;
1990     int r, g, b, y, u, v, a;
1991
1992     for (;;) {
1993         while (is->paused && !is->subtitleq.abort_request) {
1994             SDL_Delay(10);
1995         }
1996         if (packet_queue_get(&is->subtitleq, pkt, 1, &serial) < 0)
1997             break;
1998
1999         if (pkt->data == flush_pkt.data) {
2000             avcodec_flush_buffers(is->subtitle_st->codec);
2001             continue;
2002         }
2003         SDL_LockMutex(is->subpq_mutex);
2004         while (is->subpq_size >= SUBPICTURE_QUEUE_SIZE &&
2005                !is->subtitleq.abort_request) {
2006             SDL_CondWait(is->subpq_cond, is->subpq_mutex);
2007         }
2008         SDL_UnlockMutex(is->subpq_mutex);
2009
2010         if (is->subtitleq.abort_request)
2011             return 0;
2012
2013         sp = &is->subpq[is->subpq_windex];
2014
2015        /* NOTE: ipts is the PTS of the _first_ picture beginning in
2016            this packet, if any */
2017         pts = 0;
2018         if (pkt->pts != AV_NOPTS_VALUE)
2019             pts = av_q2d(is->subtitle_st->time_base) * pkt->pts;
2020
2021         avcodec_decode_subtitle2(is->subtitle_st->codec, &sp->sub,
2022                                  &got_subtitle, pkt);
2023         if (got_subtitle && sp->sub.format == 0) {
2024             if (sp->sub.pts != AV_NOPTS_VALUE)
2025                 pts = sp->sub.pts / (double)AV_TIME_BASE;
2026             sp->pts = pts;
2027             sp->serial = serial;
2028
2029             for (i = 0; i < sp->sub.num_rects; i++)
2030             {
2031                 for (j = 0; j < sp->sub.rects[i]->nb_colors; j++)
2032                 {
2033                     RGBA_IN(r, g, b, a, (uint32_t*)sp->sub.rects[i]->pict.data[1] + j);
2034                     y = RGB_TO_Y_CCIR(r, g, b);
2035                     u = RGB_TO_U_CCIR(r, g, b, 0);
2036                     v = RGB_TO_V_CCIR(r, g, b, 0);
2037                     YUVA_OUT((uint32_t*)sp->sub.rects[i]->pict.data[1] + j, y, u, v, a);
2038                 }
2039             }
2040
2041             /* now we can update the picture count */
2042             if (++is->subpq_windex == SUBPICTURE_QUEUE_SIZE)
2043                 is->subpq_windex = 0;
2044             SDL_LockMutex(is->subpq_mutex);
2045             is->subpq_size++;
2046             SDL_UnlockMutex(is->subpq_mutex);
2047         }
2048         av_free_packet(pkt);
2049     }
2050     return 0;
2051 }
2052
2053 /* copy samples for viewing in editor window */
2054 static void update_sample_display(VideoState *is, short *samples, int samples_size)
2055 {
2056     int size, len;
2057
2058     size = samples_size / sizeof(short);
2059     while (size > 0) {
2060         len = SAMPLE_ARRAY_SIZE - is->sample_array_index;
2061         if (len > size)
2062             len = size;
2063         memcpy(is->sample_array + is->sample_array_index, samples, len * sizeof(short));
2064         samples += len;
2065         is->sample_array_index += len;
2066         if (is->sample_array_index >= SAMPLE_ARRAY_SIZE)
2067             is->sample_array_index = 0;
2068         size -= len;
2069     }
2070 }
2071
2072 /* return the wanted number of samples to get better sync if sync_type is video
2073  * or external master clock */
2074 static int synchronize_audio(VideoState *is, int nb_samples)
2075 {
2076     int wanted_nb_samples = nb_samples;
2077
2078     /* if not master, then we try to remove or add samples to correct the clock */
2079     if (get_master_sync_type(is) != AV_SYNC_AUDIO_MASTER) {
2080         double diff, avg_diff;
2081         int min_nb_samples, max_nb_samples;
2082
2083         diff = get_clock(&is->audclk) - get_master_clock(is);
2084
2085         if (!isnan(diff) && fabs(diff) < AV_NOSYNC_THRESHOLD) {
2086             is->audio_diff_cum = diff + is->audio_diff_avg_coef * is->audio_diff_cum;
2087             if (is->audio_diff_avg_count < AUDIO_DIFF_AVG_NB) {
2088                 /* not enough measures to have a correct estimate */
2089                 is->audio_diff_avg_count++;
2090             } else {
2091                 /* estimate the A-V difference */
2092                 avg_diff = is->audio_diff_cum * (1.0 - is->audio_diff_avg_coef);
2093
2094                 if (fabs(avg_diff) >= is->audio_diff_threshold) {
2095                     wanted_nb_samples = nb_samples + (int)(diff * is->audio_src.freq);
2096                     min_nb_samples = ((nb_samples * (100 - SAMPLE_CORRECTION_PERCENT_MAX) / 100));
2097                     max_nb_samples = ((nb_samples * (100 + SAMPLE_CORRECTION_PERCENT_MAX) / 100));
2098                     wanted_nb_samples = FFMIN(FFMAX(wanted_nb_samples, min_nb_samples), max_nb_samples);
2099                 }
2100                 av_dlog(NULL, "diff=%f adiff=%f sample_diff=%d apts=%0.3f %f\n",
2101                         diff, avg_diff, wanted_nb_samples - nb_samples,
2102                         is->audio_clock, is->audio_diff_threshold);
2103             }
2104         } else {
2105             /* too big difference : may be initial PTS errors, so
2106                reset A-V filter */
2107             is->audio_diff_avg_count = 0;
2108             is->audio_diff_cum       = 0;
2109         }
2110     }
2111
2112     return wanted_nb_samples;
2113 }
2114
2115 /**
2116  * Decode one audio frame and return its uncompressed size.
2117  *
2118  * The processed audio frame is decoded, converted if required, and
2119  * stored in is->audio_buf, with size in bytes given by the return
2120  * value.
2121  */
2122 static int audio_decode_frame(VideoState *is)
2123 {
2124     AVPacket *pkt_temp = &is->audio_pkt_temp;
2125     AVPacket *pkt = &is->audio_pkt;
2126     AVCodecContext *dec = is->audio_st->codec;
2127     int len1, data_size, resampled_data_size;
2128     int64_t dec_channel_layout;
2129     int got_frame;
2130     av_unused double audio_clock0;
2131     int new_packet = 0;
2132     int flush_complete = 0;
2133     int wanted_nb_samples;
2134     AVRational tb;
2135     int ret;
2136     int reconfigure;
2137
2138     for (;;) {
2139         /* NOTE: the audio packet can contain several frames */
2140         while (pkt_temp->size > 0 || (!pkt_temp->data && new_packet) || is->audio_buf_frames_pending) {
2141             if (!is->frame) {
2142                 if (!(is->frame = avcodec_alloc_frame()))
2143                     return AVERROR(ENOMEM);
2144             } else {
2145                 av_frame_unref(is->frame);
2146                 avcodec_get_frame_defaults(is->frame);
2147             }
2148
2149             if (is->audioq.serial != is->audio_pkt_temp_serial)
2150                 break;
2151
2152             if (is->paused)
2153                 return -1;
2154
2155             if (!is->audio_buf_frames_pending) {
2156                 if (flush_complete)
2157                     break;
2158                 new_packet = 0;
2159                 len1 = avcodec_decode_audio4(dec, is->frame, &got_frame, pkt_temp);
2160                 if (len1 < 0) {
2161                     /* if error, we skip the frame */
2162                     pkt_temp->size = 0;
2163                     break;
2164                 }
2165
2166                 pkt_temp->data += len1;
2167                 pkt_temp->size -= len1;
2168
2169                 if (!got_frame) {
2170                     /* stop sending empty packets if the decoder is finished */
2171                     if (!pkt_temp->data && dec->codec->capabilities & CODEC_CAP_DELAY)
2172                         flush_complete = 1;
2173                     continue;
2174                 }
2175
2176                 tb = (AVRational){1, is->frame->sample_rate};
2177                 if (is->frame->pts != AV_NOPTS_VALUE)
2178                     is->frame->pts = av_rescale_q(is->frame->pts, dec->time_base, tb);
2179                 else if (is->frame->pkt_pts != AV_NOPTS_VALUE)
2180                     is->frame->pts = av_rescale_q(is->frame->pkt_pts, is->audio_st->time_base, tb);
2181                 if (pkt_temp->pts != AV_NOPTS_VALUE)
2182                     pkt_temp->pts += (double) is->frame->nb_samples / is->frame->sample_rate / av_q2d(is->audio_st->time_base);
2183
2184 #if CONFIG_AVFILTER
2185                 dec_channel_layout = get_valid_channel_layout(is->frame->channel_layout, av_frame_get_channels(is->frame));
2186
2187                 reconfigure =
2188                     cmp_audio_fmts(is->audio_filter_src.fmt, is->audio_filter_src.channels,
2189                                    is->frame->format, av_frame_get_channels(is->frame))    ||
2190                     is->audio_filter_src.channel_layout != dec_channel_layout ||
2191                     is->audio_filter_src.freq           != is->frame->sample_rate ||
2192                     is->audio_pkt_temp_serial           != is->audio_last_serial;
2193
2194                 if (reconfigure) {
2195                     char buf1[1024], buf2[1024];
2196                     av_get_channel_layout_string(buf1, sizeof(buf1), -1, is->audio_filter_src.channel_layout);
2197                     av_get_channel_layout_string(buf2, sizeof(buf2), -1, dec_channel_layout);
2198                     av_log(NULL, AV_LOG_DEBUG,
2199                            "Audio frame changed from rate:%d ch:%d fmt:%s layout:%s serial:%d to rate:%d ch:%d fmt:%s layout:%s serial:%d\n",
2200                            is->audio_filter_src.freq, is->audio_filter_src.channels, av_get_sample_fmt_name(is->audio_filter_src.fmt), buf1, is->audio_last_serial,
2201                            is->frame->sample_rate, av_frame_get_channels(is->frame), av_get_sample_fmt_name(is->frame->format), buf2, is->audio_pkt_temp_serial);
2202
2203                     is->audio_filter_src.fmt            = is->frame->format;
2204                     is->audio_filter_src.channels       = av_frame_get_channels(is->frame);
2205                     is->audio_filter_src.channel_layout = dec_channel_layout;
2206                     is->audio_filter_src.freq           = is->frame->sample_rate;
2207                     is->audio_last_serial               = is->audio_pkt_temp_serial;
2208
2209                     if ((ret = configure_audio_filters(is, afilters, 1)) < 0)
2210                         return ret;
2211                 }
2212
2213                 if ((ret = av_buffersrc_add_frame(is->in_audio_filter, is->frame)) < 0)
2214                     return ret;
2215                 av_frame_unref(is->frame);
2216 #endif
2217             }
2218 #if CONFIG_AVFILTER
2219             if ((ret = av_buffersink_get_frame_flags(is->out_audio_filter, is->frame, 0)) < 0) {
2220                 if (ret == AVERROR(EAGAIN)) {
2221                     is->audio_buf_frames_pending = 0;
2222                     continue;
2223                 }
2224                 return ret;
2225             }
2226             is->audio_buf_frames_pending = 1;
2227             tb = is->out_audio_filter->inputs[0]->time_base;
2228 #endif
2229
2230             data_size = av_samples_get_buffer_size(NULL, av_frame_get_channels(is->frame),
2231                                                    is->frame->nb_samples,
2232                                                    is->frame->format, 1);
2233
2234             dec_channel_layout =
2235                 (is->frame->channel_layout && av_frame_get_channels(is->frame) == av_get_channel_layout_nb_channels(is->frame->channel_layout)) ?
2236                 is->frame->channel_layout : av_get_default_channel_layout(av_frame_get_channels(is->frame));
2237             wanted_nb_samples = synchronize_audio(is, is->frame->nb_samples);
2238
2239             if (is->frame->format        != is->audio_src.fmt            ||
2240                 dec_channel_layout       != is->audio_src.channel_layout ||
2241                 is->frame->sample_rate   != is->audio_src.freq           ||
2242                 (wanted_nb_samples       != is->frame->nb_samples && !is->swr_ctx)) {
2243                 swr_free(&is->swr_ctx);
2244                 is->swr_ctx = swr_alloc_set_opts(NULL,
2245                                                  is->audio_tgt.channel_layout, is->audio_tgt.fmt, is->audio_tgt.freq,
2246                                                  dec_channel_layout,           is->frame->format, is->frame->sample_rate,
2247                                                  0, NULL);
2248                 if (!is->swr_ctx || swr_init(is->swr_ctx) < 0) {
2249                     av_log(NULL, AV_LOG_ERROR,
2250                            "Cannot create sample rate converter for conversion of %d Hz %s %d channels to %d Hz %s %d channels!\n",
2251                             is->frame->sample_rate, av_get_sample_fmt_name(is->frame->format), av_frame_get_channels(is->frame),
2252                             is->audio_tgt.freq, av_get_sample_fmt_name(is->audio_tgt.fmt), is->audio_tgt.channels);
2253                     break;
2254                 }
2255                 is->audio_src.channel_layout = dec_channel_layout;
2256                 is->audio_src.channels       = av_frame_get_channels(is->frame);
2257                 is->audio_src.freq = is->frame->sample_rate;
2258                 is->audio_src.fmt = is->frame->format;
2259             }
2260
2261             if (is->swr_ctx) {
2262                 const uint8_t **in = (const uint8_t **)is->frame->extended_data;
2263                 uint8_t **out = &is->audio_buf1;
2264                 int out_count = (int64_t)wanted_nb_samples * is->audio_tgt.freq / is->frame->sample_rate + 256;
2265                 int out_size  = av_samples_get_buffer_size(NULL, is->audio_tgt.channels, out_count, is->audio_tgt.fmt, 0);
2266                 int len2;
2267                 if (out_size < 0) {
2268                     av_log(NULL, AV_LOG_ERROR, "av_samples_get_buffer_size() failed\n");
2269                     break;
2270                 }
2271                 if (wanted_nb_samples != is->frame->nb_samples) {
2272                     if (swr_set_compensation(is->swr_ctx, (wanted_nb_samples - is->frame->nb_samples) * is->audio_tgt.freq / is->frame->sample_rate,
2273                                                 wanted_nb_samples * is->audio_tgt.freq / is->frame->sample_rate) < 0) {
2274                         av_log(NULL, AV_LOG_ERROR, "swr_set_compensation() failed\n");
2275                         break;
2276                     }
2277                 }
2278                 av_fast_malloc(&is->audio_buf1, &is->audio_buf1_size, out_size);
2279                 if (!is->audio_buf1)
2280                     return AVERROR(ENOMEM);
2281                 len2 = swr_convert(is->swr_ctx, out, out_count, in, is->frame->nb_samples);
2282                 if (len2 < 0) {
2283                     av_log(NULL, AV_LOG_ERROR, "swr_convert() failed\n");
2284                     break;
2285                 }
2286                 if (len2 == out_count) {
2287                     av_log(NULL, AV_LOG_WARNING, "audio buffer is probably too small\n");
2288                     swr_init(is->swr_ctx);
2289                 }
2290                 is->audio_buf = is->audio_buf1;
2291                 resampled_data_size = len2 * is->audio_tgt.channels * av_get_bytes_per_sample(is->audio_tgt.fmt);
2292             } else {
2293                 is->audio_buf = is->frame->data[0];
2294                 resampled_data_size = data_size;
2295             }
2296
2297             audio_clock0 = is->audio_clock;
2298             /* update the audio clock with the pts */
2299             if (is->frame->pts != AV_NOPTS_VALUE)
2300                 is->audio_clock = is->frame->pts * av_q2d(tb) + (double) is->frame->nb_samples / is->frame->sample_rate;
2301             else
2302                 is->audio_clock = NAN;
2303             is->audio_clock_serial = is->audio_pkt_temp_serial;
2304 #ifdef DEBUG
2305             {
2306                 static double last_clock;
2307                 printf("audio: delay=%0.3f clock=%0.3f clock0=%0.3f\n",
2308                        is->audio_clock - last_clock,
2309                        is->audio_clock, audio_clock0);
2310                 last_clock = is->audio_clock;
2311             }
2312 #endif
2313             return resampled_data_size;
2314         }
2315
2316         /* free the current packet */
2317         if (pkt->data)
2318             av_free_packet(pkt);
2319         memset(pkt_temp, 0, sizeof(*pkt_temp));
2320
2321         if (is->audioq.abort_request) {
2322             return -1;
2323         }
2324
2325         if (is->audioq.nb_packets == 0)
2326             SDL_CondSignal(is->continue_read_thread);
2327
2328         /* read next packet */
2329         if ((new_packet = packet_queue_get(&is->audioq, pkt, 1, &is->audio_pkt_temp_serial)) < 0)
2330             return -1;
2331
2332         if (pkt->data == flush_pkt.data) {
2333             avcodec_flush_buffers(dec);
2334             flush_complete = 0;
2335             is->audio_buf_frames_pending = 0;
2336         }
2337
2338         *pkt_temp = *pkt;
2339     }
2340 }
2341
2342 /* prepare a new audio buffer */
2343 static void sdl_audio_callback(void *opaque, Uint8 *stream, int len)
2344 {
2345     VideoState *is = opaque;
2346     int audio_size, len1;
2347     int bytes_per_sec;
2348     int frame_size = av_samples_get_buffer_size(NULL, is->audio_tgt.channels, 1, is->audio_tgt.fmt, 1);
2349
2350     audio_callback_time = av_gettime();
2351
2352     while (len > 0) {
2353         if (is->audio_buf_index >= is->audio_buf_size) {
2354            audio_size = audio_decode_frame(is);
2355            if (audio_size < 0) {
2356                 /* if error, just output silence */
2357                is->audio_buf      = is->silence_buf;
2358                is->audio_buf_size = sizeof(is->silence_buf) / frame_size * frame_size;
2359            } else {
2360                if (is->show_mode != SHOW_MODE_VIDEO)
2361                    update_sample_display(is, (int16_t *)is->audio_buf, audio_size);
2362                is->audio_buf_size = audio_size;
2363            }
2364            is->audio_buf_index = 0;
2365         }
2366         len1 = is->audio_buf_size - is->audio_buf_index;
2367         if (len1 > len)
2368             len1 = len;
2369         memcpy(stream, (uint8_t *)is->audio_buf + is->audio_buf_index, len1);
2370         len -= len1;
2371         stream += len1;
2372         is->audio_buf_index += len1;
2373     }
2374     bytes_per_sec = is->audio_tgt.freq * is->audio_tgt.channels * av_get_bytes_per_sample(is->audio_tgt.fmt);
2375     is->audio_write_buf_size = is->audio_buf_size - is->audio_buf_index;
2376     /* Let's assume the audio driver that is used by SDL has two periods. */
2377     if (!isnan(is->audio_clock)) {
2378         set_clock_at(&is->audclk, is->audio_clock - (double)(2 * is->audio_hw_buf_size + is->audio_write_buf_size) / bytes_per_sec, is->audio_clock_serial, audio_callback_time / 1000000.0);
2379         sync_clock_to_slave(&is->extclk, &is->audclk);
2380     }
2381 }
2382
2383 static int audio_open(void *opaque, int64_t wanted_channel_layout, int wanted_nb_channels, int wanted_sample_rate, struct AudioParams *audio_hw_params)
2384 {
2385     SDL_AudioSpec wanted_spec, spec;
2386     const char *env;
2387     const int next_nb_channels[] = {0, 0, 1, 6, 2, 6, 4, 6};
2388
2389     env = SDL_getenv("SDL_AUDIO_CHANNELS");
2390     if (env) {
2391         wanted_nb_channels = atoi(env);
2392         wanted_channel_layout = av_get_default_channel_layout(wanted_nb_channels);
2393     }
2394     if (!wanted_channel_layout || wanted_nb_channels != av_get_channel_layout_nb_channels(wanted_channel_layout)) {
2395         wanted_channel_layout = av_get_default_channel_layout(wanted_nb_channels);
2396         wanted_channel_layout &= ~AV_CH_LAYOUT_STEREO_DOWNMIX;
2397     }
2398     wanted_spec.channels = av_get_channel_layout_nb_channels(wanted_channel_layout);
2399     wanted_spec.freq = wanted_sample_rate;
2400     if (wanted_spec.freq <= 0 || wanted_spec.channels <= 0) {
2401         av_log(NULL, AV_LOG_ERROR, "Invalid sample rate or channel count!\n");
2402         return -1;
2403     }
2404     wanted_spec.format = AUDIO_S16SYS;
2405     wanted_spec.silence = 0;
2406     wanted_spec.samples = SDL_AUDIO_BUFFER_SIZE;
2407     wanted_spec.callback = sdl_audio_callback;
2408     wanted_spec.userdata = opaque;
2409     while (SDL_OpenAudio(&wanted_spec, &spec) < 0) {
2410         av_log(NULL, AV_LOG_WARNING, "SDL_OpenAudio (%d channels): %s\n", wanted_spec.channels, SDL_GetError());
2411         wanted_spec.channels = next_nb_channels[FFMIN(7, wanted_spec.channels)];
2412         if (!wanted_spec.channels) {
2413             av_log(NULL, AV_LOG_ERROR,
2414                    "No more channel combinations to try, audio open failed\n");
2415             return -1;
2416         }
2417         wanted_channel_layout = av_get_default_channel_layout(wanted_spec.channels);
2418     }
2419     if (spec.format != AUDIO_S16SYS) {
2420         av_log(NULL, AV_LOG_ERROR,
2421                "SDL advised audio format %d is not supported!\n", spec.format);
2422         return -1;
2423     }
2424     if (spec.channels != wanted_spec.channels) {
2425         wanted_channel_layout = av_get_default_channel_layout(spec.channels);
2426         if (!wanted_channel_layout) {
2427             av_log(NULL, AV_LOG_ERROR,
2428                    "SDL advised channel count %d is not supported!\n", spec.channels);
2429             return -1;
2430         }
2431     }
2432
2433     audio_hw_params->fmt = AV_SAMPLE_FMT_S16;
2434     audio_hw_params->freq = spec.freq;
2435     audio_hw_params->channel_layout = wanted_channel_layout;
2436     audio_hw_params->channels =  spec.channels;
2437     return spec.size;
2438 }
2439
2440 /* open a given stream. Return 0 if OK */
2441 static int stream_component_open(VideoState *is, int stream_index)
2442 {
2443     AVFormatContext *ic = is->ic;
2444     AVCodecContext *avctx;
2445     AVCodec *codec;
2446     const char *forced_codec_name = NULL;
2447     AVDictionary *opts;
2448     AVDictionaryEntry *t = NULL;
2449     int sample_rate, nb_channels;
2450     int64_t channel_layout;
2451     int ret;
2452
2453     if (stream_index < 0 || stream_index >= ic->nb_streams)
2454         return -1;
2455     avctx = ic->streams[stream_index]->codec;
2456
2457     codec = avcodec_find_decoder(avctx->codec_id);
2458
2459     switch(avctx->codec_type){
2460         case AVMEDIA_TYPE_AUDIO   : is->last_audio_stream    = stream_index; forced_codec_name =    audio_codec_name; break;
2461         case AVMEDIA_TYPE_SUBTITLE: is->last_subtitle_stream = stream_index; forced_codec_name = subtitle_codec_name; break;
2462         case AVMEDIA_TYPE_VIDEO   : is->last_video_stream    = stream_index; forced_codec_name =    video_codec_name; break;
2463     }
2464     if (forced_codec_name)
2465         codec = avcodec_find_decoder_by_name(forced_codec_name);
2466     if (!codec) {
2467         if (forced_codec_name) av_log(NULL, AV_LOG_WARNING,
2468                                       "No codec could be found with name '%s'\n", forced_codec_name);
2469         else                   av_log(NULL, AV_LOG_WARNING,
2470                                       "No codec could be found with id %d\n", avctx->codec_id);
2471         return -1;
2472     }
2473
2474     avctx->codec_id = codec->id;
2475     avctx->workaround_bugs   = workaround_bugs;
2476     avctx->lowres            = lowres;
2477     if(avctx->lowres > codec->max_lowres){
2478         av_log(avctx, AV_LOG_WARNING, "The maximum value for lowres supported by the decoder is %d\n",
2479                 codec->max_lowres);
2480         avctx->lowres= codec->max_lowres;
2481     }
2482     avctx->error_concealment = error_concealment;
2483
2484     if(avctx->lowres) avctx->flags |= CODEC_FLAG_EMU_EDGE;
2485     if (fast)   avctx->flags2 |= CODEC_FLAG2_FAST;
2486     if(codec->capabilities & CODEC_CAP_DR1)
2487         avctx->flags |= CODEC_FLAG_EMU_EDGE;
2488
2489     opts = filter_codec_opts(codec_opts, avctx->codec_id, ic, ic->streams[stream_index], codec);
2490     if (!av_dict_get(opts, "threads", NULL, 0))
2491         av_dict_set(&opts, "threads", "auto", 0);
2492     if (avctx->lowres)
2493         av_dict_set(&opts, "lowres", av_asprintf("%d", avctx->lowres), AV_DICT_DONT_STRDUP_VAL);
2494     if (avctx->codec_type == AVMEDIA_TYPE_VIDEO || avctx->codec_type == AVMEDIA_TYPE_AUDIO)
2495         av_dict_set(&opts, "refcounted_frames", "1", 0);
2496     if (avcodec_open2(avctx, codec, &opts) < 0)
2497         return -1;
2498     if ((t = av_dict_get(opts, "", NULL, AV_DICT_IGNORE_SUFFIX))) {
2499         av_log(NULL, AV_LOG_ERROR, "Option %s not found.\n", t->key);
2500         return AVERROR_OPTION_NOT_FOUND;
2501     }
2502
2503     ic->streams[stream_index]->discard = AVDISCARD_DEFAULT;
2504     switch (avctx->codec_type) {
2505     case AVMEDIA_TYPE_AUDIO:
2506 #if CONFIG_AVFILTER
2507         {
2508             AVFilterLink *link;
2509
2510             is->audio_filter_src.freq           = avctx->sample_rate;
2511             is->audio_filter_src.channels       = avctx->channels;
2512             is->audio_filter_src.channel_layout = get_valid_channel_layout(avctx->channel_layout, avctx->channels);
2513             is->audio_filter_src.fmt            = avctx->sample_fmt;
2514             if ((ret = configure_audio_filters(is, afilters, 0)) < 0)
2515                 return ret;
2516             link = is->out_audio_filter->inputs[0];
2517             sample_rate    = link->sample_rate;
2518             nb_channels    = link->channels;
2519             channel_layout = link->channel_layout;
2520         }
2521 #else
2522         sample_rate    = avctx->sample_rate;
2523         nb_channels    = avctx->channels;
2524         channel_layout = avctx->channel_layout;
2525 #endif
2526
2527         /* prepare audio output */
2528         if ((ret = audio_open(is, channel_layout, nb_channels, sample_rate, &is->audio_tgt)) < 0)
2529             return ret;
2530         is->audio_hw_buf_size = ret;
2531         is->audio_src = is->audio_tgt;
2532         is->audio_buf_size  = 0;
2533         is->audio_buf_index = 0;
2534
2535         /* init averaging filter */
2536         is->audio_diff_avg_coef  = exp(log(0.01) / AUDIO_DIFF_AVG_NB);
2537         is->audio_diff_avg_count = 0;
2538         /* since we do not have a precise anough audio fifo fullness,
2539            we correct audio sync only if larger than this threshold */
2540         is->audio_diff_threshold = 2.0 * is->audio_hw_buf_size / av_samples_get_buffer_size(NULL, is->audio_tgt.channels, is->audio_tgt.freq, is->audio_tgt.fmt, 1);
2541
2542         memset(&is->audio_pkt, 0, sizeof(is->audio_pkt));
2543         memset(&is->audio_pkt_temp, 0, sizeof(is->audio_pkt_temp));
2544
2545         is->audio_stream = stream_index;
2546         is->audio_st = ic->streams[stream_index];
2547
2548         packet_queue_start(&is->audioq);
2549         SDL_PauseAudio(0);
2550         break;
2551     case AVMEDIA_TYPE_VIDEO:
2552         is->video_stream = stream_index;
2553         is->video_st = ic->streams[stream_index];
2554
2555         packet_queue_start(&is->videoq);
2556         is->video_tid = SDL_CreateThread(video_thread, is);
2557         is->queue_attachments_req = 1;
2558         break;
2559     case AVMEDIA_TYPE_SUBTITLE:
2560         is->subtitle_stream = stream_index;
2561         is->subtitle_st = ic->streams[stream_index];
2562         packet_queue_start(&is->subtitleq);
2563
2564         is->subtitle_tid = SDL_CreateThread(subtitle_thread, is);
2565         break;
2566     default:
2567         break;
2568     }
2569     return 0;
2570 }
2571
2572 static void stream_component_close(VideoState *is, int stream_index)
2573 {
2574     AVFormatContext *ic = is->ic;
2575     AVCodecContext *avctx;
2576
2577     if (stream_index < 0 || stream_index >= ic->nb_streams)
2578         return;
2579     avctx = ic->streams[stream_index]->codec;
2580
2581     switch (avctx->codec_type) {
2582     case AVMEDIA_TYPE_AUDIO:
2583         packet_queue_abort(&is->audioq);
2584
2585         SDL_CloseAudio();
2586
2587         packet_queue_flush(&is->audioq);
2588         av_free_packet(&is->audio_pkt);
2589         swr_free(&is->swr_ctx);
2590         av_freep(&is->audio_buf1);
2591         is->audio_buf1_size = 0;
2592         is->audio_buf = NULL;
2593         av_frame_free(&is->frame);
2594
2595         if (is->rdft) {
2596             av_rdft_end(is->rdft);
2597             av_freep(&is->rdft_data);
2598             is->rdft = NULL;
2599             is->rdft_bits = 0;
2600         }
2601 #if CONFIG_AVFILTER
2602         avfilter_graph_free(&is->agraph);
2603 #endif
2604         break;
2605     case AVMEDIA_TYPE_VIDEO:
2606         packet_queue_abort(&is->videoq);
2607
2608         /* note: we also signal this mutex to make sure we deblock the
2609            video thread in all cases */
2610         SDL_LockMutex(is->pictq_mutex);
2611         SDL_CondSignal(is->pictq_cond);
2612         SDL_UnlockMutex(is->pictq_mutex);
2613
2614         SDL_WaitThread(is->video_tid, NULL);
2615
2616         packet_queue_flush(&is->videoq);
2617         break;
2618     case AVMEDIA_TYPE_SUBTITLE:
2619         packet_queue_abort(&is->subtitleq);
2620
2621         /* note: we also signal this mutex to make sure we deblock the
2622            video thread in all cases */
2623         SDL_LockMutex(is->subpq_mutex);
2624         SDL_CondSignal(is->subpq_cond);
2625         SDL_UnlockMutex(is->subpq_mutex);
2626
2627         SDL_WaitThread(is->subtitle_tid, NULL);
2628
2629         packet_queue_flush(&is->subtitleq);
2630         break;
2631     default:
2632         break;
2633     }
2634
2635     ic->streams[stream_index]->discard = AVDISCARD_ALL;
2636     avcodec_close(avctx);
2637     switch (avctx->codec_type) {
2638     case AVMEDIA_TYPE_AUDIO:
2639         is->audio_st = NULL;
2640         is->audio_stream = -1;
2641         break;
2642     case AVMEDIA_TYPE_VIDEO:
2643         is->video_st = NULL;
2644         is->video_stream = -1;
2645         break;
2646     case AVMEDIA_TYPE_SUBTITLE:
2647         is->subtitle_st = NULL;
2648         is->subtitle_stream = -1;
2649         break;
2650     default:
2651         break;
2652     }
2653 }
2654
2655 static int decode_interrupt_cb(void *ctx)
2656 {
2657     VideoState *is = ctx;
2658     return is->abort_request;
2659 }
2660
2661 static int is_realtime(AVFormatContext *s)
2662 {
2663     if(   !strcmp(s->iformat->name, "rtp")
2664        || !strcmp(s->iformat->name, "rtsp")
2665        || !strcmp(s->iformat->name, "sdp")
2666     )
2667         return 1;
2668
2669     if(s->pb && (   !strncmp(s->filename, "rtp:", 4)
2670                  || !strncmp(s->filename, "udp:", 4)
2671                 )
2672     )
2673         return 1;
2674     return 0;
2675 }
2676
2677 /* this thread gets the stream from the disk or the network */
2678 static int read_thread(void *arg)
2679 {
2680     VideoState *is = arg;
2681     AVFormatContext *ic = NULL;
2682     int err, i, ret;
2683     int st_index[AVMEDIA_TYPE_NB];
2684     AVPacket pkt1, *pkt = &pkt1;
2685     int eof = 0;
2686     int64_t stream_start_time;
2687     int pkt_in_play_range = 0;
2688     AVDictionaryEntry *t;
2689     AVDictionary **opts;
2690     int orig_nb_streams;
2691     SDL_mutex *wait_mutex = SDL_CreateMutex();
2692
2693     memset(st_index, -1, sizeof(st_index));
2694     is->last_video_stream = is->video_stream = -1;
2695     is->last_audio_stream = is->audio_stream = -1;
2696     is->last_subtitle_stream = is->subtitle_stream = -1;
2697
2698     ic = avformat_alloc_context();
2699     ic->interrupt_callback.callback = decode_interrupt_cb;
2700     ic->interrupt_callback.opaque = is;
2701     err = avformat_open_input(&ic, is->filename, is->iformat, &format_opts);
2702     if (err < 0) {
2703         print_error(is->filename, err);
2704         ret = -1;
2705         goto fail;
2706     }
2707     if ((t = av_dict_get(format_opts, "", NULL, AV_DICT_IGNORE_SUFFIX))) {
2708         av_log(NULL, AV_LOG_ERROR, "Option %s not found.\n", t->key);
2709         ret = AVERROR_OPTION_NOT_FOUND;
2710         goto fail;
2711     }
2712     is->ic = ic;
2713
2714     if (genpts)
2715         ic->flags |= AVFMT_FLAG_GENPTS;
2716
2717     opts = setup_find_stream_info_opts(ic, codec_opts);
2718     orig_nb_streams = ic->nb_streams;
2719
2720     err = avformat_find_stream_info(ic, opts);
2721     if (err < 0) {
2722         av_log(NULL, AV_LOG_WARNING,
2723                "%s: could not find codec parameters\n", is->filename);
2724         ret = -1;
2725         goto fail;
2726     }
2727     for (i = 0; i < orig_nb_streams; i++)
2728         av_dict_free(&opts[i]);
2729     av_freep(&opts);
2730
2731     if (ic->pb)
2732         ic->pb->eof_reached = 0; // FIXME hack, ffplay maybe should not use url_feof() to test for the end
2733
2734     if (seek_by_bytes < 0)
2735         seek_by_bytes = !!(ic->iformat->flags & AVFMT_TS_DISCONT) && strcmp("ogg", ic->iformat->name);
2736
2737     is->max_frame_duration = (ic->iformat->flags & AVFMT_TS_DISCONT) ? 10.0 : 3600.0;
2738
2739     if (!window_title && (t = av_dict_get(ic->metadata, "title", NULL, 0)))
2740         window_title = av_asprintf("%s - %s", t->value, input_filename);
2741
2742     /* if seeking requested, we execute it */
2743     if (start_time != AV_NOPTS_VALUE) {
2744         int64_t timestamp;
2745
2746         timestamp = start_time;
2747         /* add the stream start time */
2748         if (ic->start_time != AV_NOPTS_VALUE)
2749             timestamp += ic->start_time;
2750         ret = avformat_seek_file(ic, -1, INT64_MIN, timestamp, INT64_MAX, 0);
2751         if (ret < 0) {
2752             av_log(NULL, AV_LOG_WARNING, "%s: could not seek to position %0.3f\n",
2753                     is->filename, (double)timestamp / AV_TIME_BASE);
2754         }
2755     }
2756
2757     is->realtime = is_realtime(ic);
2758
2759     for (i = 0; i < ic->nb_streams; i++)
2760         ic->streams[i]->discard = AVDISCARD_ALL;
2761     if (!video_disable)
2762         st_index[AVMEDIA_TYPE_VIDEO] =
2763             av_find_best_stream(ic, AVMEDIA_TYPE_VIDEO,
2764                                 wanted_stream[AVMEDIA_TYPE_VIDEO], -1, NULL, 0);
2765     if (!audio_disable)
2766         st_index[AVMEDIA_TYPE_AUDIO] =
2767             av_find_best_stream(ic, AVMEDIA_TYPE_AUDIO,
2768                                 wanted_stream[AVMEDIA_TYPE_AUDIO],
2769                                 st_index[AVMEDIA_TYPE_VIDEO],
2770                                 NULL, 0);
2771     if (!video_disable && !subtitle_disable)
2772         st_index[AVMEDIA_TYPE_SUBTITLE] =
2773             av_find_best_stream(ic, AVMEDIA_TYPE_SUBTITLE,
2774                                 wanted_stream[AVMEDIA_TYPE_SUBTITLE],
2775                                 (st_index[AVMEDIA_TYPE_AUDIO] >= 0 ?
2776                                  st_index[AVMEDIA_TYPE_AUDIO] :
2777                                  st_index[AVMEDIA_TYPE_VIDEO]),
2778                                 NULL, 0);
2779     if (show_status) {
2780         av_dump_format(ic, 0, is->filename, 0);
2781     }
2782
2783     is->show_mode = show_mode;
2784
2785     /* open the streams */
2786     if (st_index[AVMEDIA_TYPE_AUDIO] >= 0) {
2787         stream_component_open(is, st_index[AVMEDIA_TYPE_AUDIO]);
2788     }
2789
2790     ret = -1;
2791     if (st_index[AVMEDIA_TYPE_VIDEO] >= 0) {
2792         ret = stream_component_open(is, st_index[AVMEDIA_TYPE_VIDEO]);
2793     }
2794     if (is->show_mode == SHOW_MODE_NONE)
2795         is->show_mode = ret >= 0 ? SHOW_MODE_VIDEO : SHOW_MODE_RDFT;
2796
2797     if (st_index[AVMEDIA_TYPE_SUBTITLE] >= 0) {
2798         stream_component_open(is, st_index[AVMEDIA_TYPE_SUBTITLE]);
2799     }
2800
2801     if (is->video_stream < 0 && is->audio_stream < 0) {
2802         av_log(NULL, AV_LOG_FATAL, "%s: could not open codecs\n", is->filename);
2803         ret = -1;
2804         goto fail;
2805     }
2806
2807     if (infinite_buffer < 0 && is->realtime)
2808         infinite_buffer = 1;
2809
2810     for (;;) {
2811         if (is->abort_request)
2812             break;
2813         if (is->paused != is->last_paused) {
2814             is->last_paused = is->paused;
2815             if (is->paused)
2816                 is->read_pause_return = av_read_pause(ic);
2817             else
2818                 av_read_play(ic);
2819         }
2820 #if CONFIG_RTSP_DEMUXER || CONFIG_MMSH_PROTOCOL
2821         if (is->paused &&
2822                 (!strcmp(ic->iformat->name, "rtsp") ||
2823                  (ic->pb && !strncmp(input_filename, "mmsh:", 5)))) {
2824             /* wait 10 ms to avoid trying to get another packet */
2825             /* XXX: horrible */
2826             SDL_Delay(10);
2827             continue;
2828         }
2829 #endif
2830         if (is->seek_req) {
2831             int64_t seek_target = is->seek_pos;
2832             int64_t seek_min    = is->seek_rel > 0 ? seek_target - is->seek_rel + 2: INT64_MIN;
2833             int64_t seek_max    = is->seek_rel < 0 ? seek_target - is->seek_rel - 2: INT64_MAX;
2834 // FIXME the +-2 is due to rounding being not done in the correct direction in generation
2835 //      of the seek_pos/seek_rel variables
2836
2837             ret = avformat_seek_file(is->ic, -1, seek_min, seek_target, seek_max, is->seek_flags);
2838             if (ret < 0) {
2839                 av_log(NULL, AV_LOG_ERROR,
2840                        "%s: error while seeking\n", is->ic->filename);
2841             } else {
2842                 if (is->audio_stream >= 0) {
2843                     packet_queue_flush(&is->audioq);
2844                     packet_queue_put(&is->audioq, &flush_pkt);
2845                 }
2846                 if (is->subtitle_stream >= 0) {
2847                     packet_queue_flush(&is->subtitleq);
2848                     packet_queue_put(&is->subtitleq, &flush_pkt);
2849                 }
2850                 if (is->video_stream >= 0) {
2851                     packet_queue_flush(&is->videoq);
2852                     packet_queue_put(&is->videoq, &flush_pkt);
2853                 }
2854                 if (is->seek_flags & AVSEEK_FLAG_BYTE) {
2855                    set_clock(&is->extclk, NAN, 0);
2856                 } else {
2857                    set_clock(&is->extclk, seek_target / (double)AV_TIME_BASE, 0);
2858                 }
2859             }
2860             is->seek_req = 0;
2861             is->queue_attachments_req = 1;
2862             eof = 0;
2863             if (is->paused)
2864                 step_to_next_frame(is);
2865         }
2866         if (is->queue_attachments_req) {
2867             if (is->video_st && is->video_st->disposition & AV_DISPOSITION_ATTACHED_PIC) {
2868                 AVPacket copy;
2869                 if ((ret = av_copy_packet(&copy, &is->video_st->attached_pic)) < 0)
2870                     goto fail;
2871                 packet_queue_put(&is->videoq, &copy);
2872             }
2873             is->queue_attachments_req = 0;
2874         }
2875
2876         /* if the queue are full, no need to read more */
2877         if (infinite_buffer<1 &&
2878               (is->audioq.size + is->videoq.size + is->subtitleq.size > MAX_QUEUE_SIZE
2879             || (   (is->audioq   .nb_packets > MIN_FRAMES || is->audio_stream < 0 || is->audioq.abort_request)
2880                 && (is->videoq   .nb_packets > MIN_FRAMES || is->video_stream < 0 || is->videoq.abort_request
2881                     || (is->video_st->disposition & AV_DISPOSITION_ATTACHED_PIC))
2882                 && (is->subtitleq.nb_packets > MIN_FRAMES || is->subtitle_stream < 0 || is->subtitleq.abort_request)))) {
2883             /* wait 10 ms */
2884             SDL_LockMutex(wait_mutex);
2885             SDL_CondWaitTimeout(is->continue_read_thread, wait_mutex, 10);
2886             SDL_UnlockMutex(wait_mutex);
2887             continue;
2888         }
2889         if (eof) {
2890             if (is->video_stream >= 0) {
2891                 av_init_packet(pkt);
2892                 pkt->data = NULL;
2893                 pkt->size = 0;
2894                 pkt->stream_index = is->video_stream;
2895                 packet_queue_put(&is->videoq, pkt);
2896             }
2897             if (is->audio_stream >= 0) {
2898                 av_init_packet(pkt);
2899                 pkt->data = NULL;
2900                 pkt->size = 0;
2901                 pkt->stream_index = is->audio_stream;
2902                 packet_queue_put(&is->audioq, pkt);
2903             }
2904             SDL_Delay(10);
2905             if (is->audioq.size + is->videoq.size + is->subtitleq.size == 0) {
2906                 if (loop != 1 && (!loop || --loop)) {
2907                     stream_seek(is, start_time != AV_NOPTS_VALUE ? start_time : 0, 0, 0);
2908                 } else if (autoexit) {
2909                     ret = AVERROR_EOF;
2910                     goto fail;
2911                 }
2912             }
2913             eof=0;
2914             continue;
2915         }
2916         ret = av_read_frame(ic, pkt);
2917         if (ret < 0) {
2918             if (ret == AVERROR_EOF || url_feof(ic->pb))
2919                 eof = 1;
2920             if (ic->pb && ic->pb->error)
2921                 break;
2922             SDL_LockMutex(wait_mutex);
2923             SDL_CondWaitTimeout(is->continue_read_thread, wait_mutex, 10);
2924             SDL_UnlockMutex(wait_mutex);
2925             continue;
2926         }
2927         /* check if packet is in play range specified by user, then queue, otherwise discard */
2928         stream_start_time = ic->streams[pkt->stream_index]->start_time;
2929         pkt_in_play_range = duration == AV_NOPTS_VALUE ||
2930                 (pkt->pts - (stream_start_time != AV_NOPTS_VALUE ? stream_start_time : 0)) *
2931                 av_q2d(ic->streams[pkt->stream_index]->time_base) -
2932                 (double)(start_time != AV_NOPTS_VALUE ? start_time : 0) / 1000000
2933                 <= ((double)duration / 1000000);
2934         if (pkt->stream_index == is->audio_stream && pkt_in_play_range) {
2935             packet_queue_put(&is->audioq, pkt);
2936         } else if (pkt->stream_index == is->video_stream && pkt_in_play_range
2937                    && !(is->video_st->disposition & AV_DISPOSITION_ATTACHED_PIC)) {
2938             packet_queue_put(&is->videoq, pkt);
2939         } else if (pkt->stream_index == is->subtitle_stream && pkt_in_play_range) {
2940             packet_queue_put(&is->subtitleq, pkt);
2941         } else {
2942             av_free_packet(pkt);
2943         }
2944     }
2945     /* wait until the end */
2946     while (!is->abort_request) {
2947         SDL_Delay(100);
2948     }
2949
2950     ret = 0;
2951  fail:
2952     /* close each stream */
2953     if (is->audio_stream >= 0)
2954         stream_component_close(is, is->audio_stream);
2955     if (is->video_stream >= 0)
2956         stream_component_close(is, is->video_stream);
2957     if (is->subtitle_stream >= 0)
2958         stream_component_close(is, is->subtitle_stream);
2959     if (is->ic) {
2960         avformat_close_input(&is->ic);
2961     }
2962
2963     if (ret != 0) {
2964         SDL_Event event;
2965
2966         event.type = FF_QUIT_EVENT;
2967         event.user.data1 = is;
2968         SDL_PushEvent(&event);
2969     }
2970     SDL_DestroyMutex(wait_mutex);
2971     return 0;
2972 }
2973
2974 static VideoState *stream_open(const char *filename, AVInputFormat *iformat)
2975 {
2976     VideoState *is;
2977
2978     is = av_mallocz(sizeof(VideoState));
2979     if (!is)
2980         return NULL;
2981     av_strlcpy(is->filename, filename, sizeof(is->filename));
2982     is->iformat = iformat;
2983     is->ytop    = 0;
2984     is->xleft   = 0;
2985
2986     /* start video display */
2987     is->pictq_mutex = SDL_CreateMutex();
2988     is->pictq_cond  = SDL_CreateCond();
2989
2990     is->subpq_mutex = SDL_CreateMutex();
2991     is->subpq_cond  = SDL_CreateCond();
2992
2993     packet_queue_init(&is->videoq);
2994     packet_queue_init(&is->audioq);
2995     packet_queue_init(&is->subtitleq);
2996
2997     is->continue_read_thread = SDL_CreateCond();
2998
2999     init_clock(&is->vidclk, &is->videoq.serial);
3000     init_clock(&is->audclk, &is->audioq.serial);
3001     init_clock(&is->extclk, &is->extclk.serial);
3002     is->audio_clock_serial = -1;
3003     is->audio_last_serial = -1;
3004     is->av_sync_type = av_sync_type;
3005     is->read_tid     = SDL_CreateThread(read_thread, is);
3006     if (!is->read_tid) {
3007         av_free(is);
3008         return NULL;
3009     }
3010     return is;
3011 }
3012
3013 static void stream_cycle_channel(VideoState *is, int codec_type)
3014 {
3015     AVFormatContext *ic = is->ic;
3016     int start_index, stream_index;
3017     int old_index;
3018     AVStream *st;
3019
3020     if (codec_type == AVMEDIA_TYPE_VIDEO) {
3021         start_index = is->last_video_stream;
3022         old_index = is->video_stream;
3023     } else if (codec_type == AVMEDIA_TYPE_AUDIO) {
3024         start_index = is->last_audio_stream;
3025         old_index = is->audio_stream;
3026     } else {
3027         start_index = is->last_subtitle_stream;
3028         old_index = is->subtitle_stream;
3029     }
3030     stream_index = start_index;
3031     for (;;) {
3032         if (++stream_index >= is->ic->nb_streams)
3033         {
3034             if (codec_type == AVMEDIA_TYPE_SUBTITLE)
3035             {
3036                 stream_index = -1;
3037                 is->last_subtitle_stream = -1;
3038                 goto the_end;
3039             }
3040             if (start_index == -1)
3041                 return;
3042             stream_index = 0;
3043         }
3044         if (stream_index == start_index)
3045             return;
3046         st = ic->streams[stream_index];
3047         if (st->codec->codec_type == codec_type) {
3048             /* check that parameters are OK */
3049             switch (codec_type) {
3050             case AVMEDIA_TYPE_AUDIO:
3051                 if (st->codec->sample_rate != 0 &&
3052                     st->codec->channels != 0)
3053                     goto the_end;
3054                 break;
3055             case AVMEDIA_TYPE_VIDEO:
3056             case AVMEDIA_TYPE_SUBTITLE:
3057                 goto the_end;
3058             default:
3059                 break;
3060             }
3061         }
3062     }
3063  the_end:
3064     stream_component_close(is, old_index);
3065     stream_component_open(is, stream_index);
3066 }
3067
3068
3069 static void toggle_full_screen(VideoState *is)
3070 {
3071 #if defined(__APPLE__) && SDL_VERSION_ATLEAST(1, 2, 14)
3072     /* OS X needs to reallocate the SDL overlays */
3073     int i;
3074     for (i = 0; i < VIDEO_PICTURE_QUEUE_SIZE; i++)
3075         is->pictq[i].reallocate = 1;
3076 #endif
3077     is_full_screen = !is_full_screen;
3078     video_open(is, 1, NULL);
3079 }
3080
3081 static void toggle_audio_display(VideoState *is)
3082 {
3083     int bgcolor = SDL_MapRGB(screen->format, 0x00, 0x00, 0x00);
3084     int next = is->show_mode;
3085     do {
3086         next = (next + 1) % SHOW_MODE_NB;
3087     } while (next != is->show_mode && (next == SHOW_MODE_VIDEO && !is->video_st || next != SHOW_MODE_VIDEO && !is->audio_st));
3088     if (is->show_mode != next) {
3089         fill_rectangle(screen,
3090                     is->xleft, is->ytop, is->width, is->height,
3091                     bgcolor, 1);
3092         is->force_refresh = 1;
3093         is->show_mode = next;
3094     }
3095 }
3096
3097 static void refresh_loop_wait_event(VideoState *is, SDL_Event *event) {
3098     double remaining_time = 0.0;
3099     SDL_PumpEvents();
3100     while (!SDL_PeepEvents(event, 1, SDL_GETEVENT, SDL_ALLEVENTS)) {
3101         if (!cursor_hidden && av_gettime() - cursor_last_shown > CURSOR_HIDE_DELAY) {
3102             SDL_ShowCursor(0);
3103             cursor_hidden = 1;
3104         }
3105         if (remaining_time > 0.0)
3106             av_usleep((int64_t)(remaining_time * 1000000.0));
3107         remaining_time = REFRESH_RATE;
3108         if (is->show_mode != SHOW_MODE_NONE && (!is->paused || is->force_refresh))
3109             video_refresh(is, &remaining_time);
3110         SDL_PumpEvents();
3111     }
3112 }
3113
3114 /* handle an event sent by the GUI */
3115 static void event_loop(VideoState *cur_stream)
3116 {
3117     SDL_Event event;
3118     double incr, pos, frac;
3119
3120     for (;;) {
3121         double x;
3122         refresh_loop_wait_event(cur_stream, &event);
3123         switch (event.type) {
3124         case SDL_KEYDOWN:
3125             if (exit_on_keydown) {
3126                 do_exit(cur_stream);
3127                 break;
3128             }
3129             switch (event.key.keysym.sym) {
3130             case SDLK_ESCAPE:
3131             case SDLK_q:
3132                 do_exit(cur_stream);
3133                 break;
3134             case SDLK_f:
3135                 toggle_full_screen(cur_stream);
3136                 cur_stream->force_refresh = 1;
3137                 break;
3138             case SDLK_p:
3139             case SDLK_SPACE:
3140                 toggle_pause(cur_stream);
3141                 break;
3142             case SDLK_s: // S: Step to next frame
3143                 step_to_next_frame(cur_stream);
3144                 break;
3145             case SDLK_a:
3146                 stream_cycle_channel(cur_stream, AVMEDIA_TYPE_AUDIO);
3147                 break;
3148             case SDLK_v:
3149                 stream_cycle_channel(cur_stream, AVMEDIA_TYPE_VIDEO);
3150                 break;
3151             case SDLK_t:
3152                 stream_cycle_channel(cur_stream, AVMEDIA_TYPE_SUBTITLE);
3153                 break;
3154             case SDLK_w:
3155                 toggle_audio_display(cur_stream);
3156                 break;
3157             case SDLK_PAGEUP:
3158                 incr = 600.0;
3159                 goto do_seek;
3160             case SDLK_PAGEDOWN:
3161                 incr = -600.0;
3162                 goto do_seek;
3163             case SDLK_LEFT:
3164                 incr = -10.0;
3165                 goto do_seek;
3166             case SDLK_RIGHT:
3167                 incr = 10.0;
3168                 goto do_seek;
3169             case SDLK_UP:
3170                 incr = 60.0;
3171                 goto do_seek;
3172             case SDLK_DOWN:
3173                 incr = -60.0;
3174             do_seek:
3175                     if (seek_by_bytes) {
3176                         if (cur_stream->video_stream >= 0 && cur_stream->video_current_pos >= 0) {
3177                             pos = cur_stream->video_current_pos;
3178                         } else if (cur_stream->audio_stream >= 0 && cur_stream->audio_pkt.pos >= 0) {
3179                             pos = cur_stream->audio_pkt.pos;
3180                         } else
3181                             pos = avio_tell(cur_stream->ic->pb);
3182                         if (cur_stream->ic->bit_rate)
3183                             incr *= cur_stream->ic->bit_rate / 8.0;
3184                         else
3185                             incr *= 180000.0;
3186                         pos += incr;
3187                         stream_seek(cur_stream, pos, incr, 1);
3188                     } else {
3189                         pos = get_master_clock(cur_stream);
3190                         if (isnan(pos))
3191                             pos = (double)cur_stream->seek_pos / AV_TIME_BASE;
3192                         pos += incr;
3193                         if (cur_stream->ic->start_time != AV_NOPTS_VALUE && pos < cur_stream->ic->start_time / (double)AV_TIME_BASE)
3194                             pos = cur_stream->ic->start_time / (double)AV_TIME_BASE;
3195                         stream_seek(cur_stream, (int64_t)(pos * AV_TIME_BASE), (int64_t)(incr * AV_TIME_BASE), 0);
3196                     }
3197                 break;
3198             default:
3199                 break;
3200             }
3201             break;
3202         case SDL_VIDEOEXPOSE:
3203             cur_stream->force_refresh = 1;
3204             break;
3205         case SDL_MOUSEBUTTONDOWN:
3206             if (exit_on_mousedown) {
3207                 do_exit(cur_stream);
3208                 break;
3209             }
3210         case SDL_MOUSEMOTION:
3211             if (cursor_hidden) {
3212                 SDL_ShowCursor(1);
3213                 cursor_hidden = 0;
3214             }
3215             cursor_last_shown = av_gettime();
3216             if (event.type == SDL_MOUSEBUTTONDOWN) {
3217                 x = event.button.x;
3218             } else {
3219                 if (event.motion.state != SDL_PRESSED)
3220                     break;
3221                 x = event.motion.x;
3222             }
3223                 if (seek_by_bytes || cur_stream->ic->duration <= 0) {
3224                     uint64_t size =  avio_size(cur_stream->ic->pb);
3225                     stream_seek(cur_stream, size*x/cur_stream->width, 0, 1);
3226                 } else {
3227                     int64_t ts;
3228                     int ns, hh, mm, ss;
3229                     int tns, thh, tmm, tss;
3230                     tns  = cur_stream->ic->duration / 1000000LL;
3231                     thh  = tns / 3600;
3232                     tmm  = (tns % 3600) / 60;
3233                     tss  = (tns % 60);
3234                     frac = x / cur_stream->width;
3235                     ns   = frac * tns;
3236                     hh   = ns / 3600;
3237                     mm   = (ns % 3600) / 60;
3238                     ss   = (ns % 60);
3239                     av_log(NULL, AV_LOG_INFO,
3240                            "Seek to %2.0f%% (%2d:%02d:%02d) of total duration (%2d:%02d:%02d)       \n", frac*100,
3241                             hh, mm, ss, thh, tmm, tss);
3242                     ts = frac * cur_stream->ic->duration;
3243                     if (cur_stream->ic->start_time != AV_NOPTS_VALUE)
3244                         ts += cur_stream->ic->start_time;
3245                     stream_seek(cur_stream, ts, 0, 0);
3246                 }
3247             break;
3248         case SDL_VIDEORESIZE:
3249                 screen = SDL_SetVideoMode(FFMIN(16383, event.resize.w), event.resize.h, 0,
3250                                           SDL_HWSURFACE|SDL_RESIZABLE|SDL_ASYNCBLIT|SDL_HWACCEL);
3251                 if (!screen) {
3252                     av_log(NULL, AV_LOG_FATAL, "Failed to set video mode\n");
3253                     do_exit(cur_stream);
3254                 }
3255                 screen_width  = cur_stream->width  = screen->w;
3256                 screen_height = cur_stream->height = screen->h;
3257                 cur_stream->force_refresh = 1;
3258             break;
3259         case SDL_QUIT:
3260         case FF_QUIT_EVENT:
3261             do_exit(cur_stream);
3262             break;
3263         case FF_ALLOC_EVENT:
3264             alloc_picture(event.user.data1);
3265             break;
3266         default:
3267             break;
3268         }
3269     }
3270 }
3271
3272 static int opt_frame_size(void *optctx, const char *opt, const char *arg)
3273 {
3274     av_log(NULL, AV_LOG_WARNING, "Option -s is deprecated, use -video_size.\n");
3275     return opt_default(NULL, "video_size", arg);
3276 }
3277
3278 static int opt_width(void *optctx, const char *opt, const char *arg)
3279 {
3280     screen_width = parse_number_or_die(opt, arg, OPT_INT64, 1, INT_MAX);
3281     return 0;
3282 }
3283
3284 static int opt_height(void *optctx, const char *opt, const char *arg)
3285 {
3286     screen_height = parse_number_or_die(opt, arg, OPT_INT64, 1, INT_MAX);
3287     return 0;
3288 }
3289
3290 static int opt_format(void *optctx, const char *opt, const char *arg)
3291 {
3292     file_iformat = av_find_input_format(arg);
3293     if (!file_iformat) {
3294         av_log(NULL, AV_LOG_FATAL, "Unknown input format: %s\n", arg);
3295         return AVERROR(EINVAL);
3296     }
3297     return 0;
3298 }
3299
3300 static int opt_frame_pix_fmt(void *optctx, const char *opt, const char *arg)
3301 {
3302     av_log(NULL, AV_LOG_WARNING, "Option -pix_fmt is deprecated, use -pixel_format.\n");
3303     return opt_default(NULL, "pixel_format", arg);
3304 }
3305
3306 static int opt_sync(void *optctx, const char *opt, const char *arg)
3307 {
3308     if (!strcmp(arg, "audio"))
3309         av_sync_type = AV_SYNC_AUDIO_MASTER;
3310     else if (!strcmp(arg, "video"))
3311         av_sync_type = AV_SYNC_VIDEO_MASTER;
3312     else if (!strcmp(arg, "ext"))
3313         av_sync_type = AV_SYNC_EXTERNAL_CLOCK;
3314     else {
3315         av_log(NULL, AV_LOG_ERROR, "Unknown value for %s: %s\n", opt, arg);
3316         exit(1);
3317     }
3318     return 0;
3319 }
3320
3321 static int opt_seek(void *optctx, const char *opt, const char *arg)
3322 {
3323     start_time = parse_time_or_die(opt, arg, 1);
3324     return 0;
3325 }
3326
3327 static int opt_duration(void *optctx, const char *opt, const char *arg)
3328 {
3329     duration = parse_time_or_die(opt, arg, 1);
3330     return 0;
3331 }
3332
3333 static int opt_show_mode(void *optctx, const char *opt, const char *arg)
3334 {
3335     show_mode = !strcmp(arg, "video") ? SHOW_MODE_VIDEO :
3336                 !strcmp(arg, "waves") ? SHOW_MODE_WAVES :
3337                 !strcmp(arg, "rdft" ) ? SHOW_MODE_RDFT  :
3338                 parse_number_or_die(opt, arg, OPT_INT, 0, SHOW_MODE_NB-1);
3339     return 0;
3340 }
3341
3342 static void opt_input_file(void *optctx, const char *filename)
3343 {
3344     if (input_filename) {
3345         av_log(NULL, AV_LOG_FATAL,
3346                "Argument '%s' provided as input filename, but '%s' was already specified.\n",
3347                 filename, input_filename);
3348         exit(1);
3349     }
3350     if (!strcmp(filename, "-"))
3351         filename = "pipe:";
3352     input_filename = filename;
3353 }
3354
3355 static int opt_codec(void *optctx, const char *opt, const char *arg)
3356 {
3357    const char *spec = strchr(opt, ':');
3358    if (!spec) {
3359        av_log(NULL, AV_LOG_ERROR,
3360               "No media specifier was specified in '%s' in option '%s'\n",
3361                arg, opt);
3362        return AVERROR(EINVAL);
3363    }
3364    spec++;
3365    switch (spec[0]) {
3366    case 'a' :    audio_codec_name = arg; break;
3367    case 's' : subtitle_codec_name = arg; break;
3368    case 'v' :    video_codec_name = arg; break;
3369    default:
3370        av_log(NULL, AV_LOG_ERROR,
3371               "Invalid media specifier '%s' in option '%s'\n", spec, opt);
3372        return AVERROR(EINVAL);
3373    }
3374    return 0;
3375 }
3376
3377 static int dummy;
3378
3379 static const OptionDef options[] = {
3380 #include "cmdutils_common_opts.h"
3381     { "x", HAS_ARG, { .func_arg = opt_width }, "force displayed width", "width" },
3382     { "y", HAS_ARG, { .func_arg = opt_height }, "force displayed height", "height" },
3383     { "s", HAS_ARG | OPT_VIDEO, { .func_arg = opt_frame_size }, "set frame size (WxH or abbreviation)", "size" },
3384     { "fs", OPT_BOOL, { &is_full_screen }, "force full screen" },
3385     { "an", OPT_BOOL, { &audio_disable }, "disable audio" },
3386     { "vn", OPT_BOOL, { &video_disable }, "disable video" },
3387     { "sn", OPT_BOOL, { &subtitle_disable }, "disable subtitling" },
3388     { "ast", OPT_INT | HAS_ARG | OPT_EXPERT, { &wanted_stream[AVMEDIA_TYPE_AUDIO] }, "select desired audio stream", "stream_number" },
3389     { "vst", OPT_INT | HAS_ARG | OPT_EXPERT, { &wanted_stream[AVMEDIA_TYPE_VIDEO] }, "select desired video stream", "stream_number" },
3390     { "sst", OPT_INT | HAS_ARG | OPT_EXPERT, { &wanted_stream[AVMEDIA_TYPE_SUBTITLE] }, "select desired subtitle stream", "stream_number" },
3391     { "ss", HAS_ARG, { .func_arg = opt_seek }, "seek to a given position in seconds", "pos" },
3392     { "t", HAS_ARG, { .func_arg = opt_duration }, "play  \"duration\" seconds of audio/video", "duration" },
3393     { "bytes", OPT_INT | HAS_ARG, { &seek_by_bytes }, "seek by bytes 0=off 1=on -1=auto", "val" },
3394     { "nodisp", OPT_BOOL, { &display_disable }, "disable graphical display" },
3395     { "f", HAS_ARG, { .func_arg = opt_format }, "force format", "fmt" },
3396     { "pix_fmt", HAS_ARG | OPT_EXPERT | OPT_VIDEO, { .func_arg = opt_frame_pix_fmt }, "set pixel format", "format" },
3397     { "stats", OPT_BOOL | OPT_EXPERT, { &show_status }, "show status", "" },
3398     { "bug", OPT_INT | HAS_ARG | OPT_EXPERT, { &workaround_bugs }, "workaround bugs", "" },
3399     { "fast", OPT_BOOL | OPT_EXPERT, { &fast }, "non spec compliant optimizations", "" },
3400     { "genpts", OPT_BOOL | OPT_EXPERT, { &genpts }, "generate pts", "" },
3401     { "drp", OPT_INT | HAS_ARG | OPT_EXPERT, { &decoder_reorder_pts }, "let decoder reorder pts 0=off 1=on -1=auto", ""},
3402     { "lowres", OPT_INT | HAS_ARG | OPT_EXPERT, { &lowres }, "", "" },
3403     { "ec", OPT_INT | HAS_ARG | OPT_EXPERT, { &error_concealment }, "set error concealment options",  "bit_mask" },
3404     { "sync", HAS_ARG | OPT_EXPERT, { .func_arg = opt_sync }, "set audio-video sync. type (type=audio/video/ext)", "type" },
3405     { "autoexit", OPT_BOOL | OPT_EXPERT, { &autoexit }, "exit at the end", "" },
3406     { "exitonkeydown", OPT_BOOL | OPT_EXPERT, { &exit_on_keydown }, "exit on key down", "" },
3407     { "exitonmousedown", OPT_BOOL | OPT_EXPERT, { &exit_on_mousedown }, "exit on mouse down", "" },
3408     { "loop", OPT_INT | HAS_ARG | OPT_EXPERT, { &loop }, "set number of times the playback shall be looped", "loop count" },
3409     { "framedrop", OPT_BOOL | OPT_EXPERT, { &framedrop }, "drop frames when cpu is too slow", "" },
3410     { "infbuf", OPT_BOOL | OPT_EXPERT, { &infinite_buffer }, "don't limit the input buffer size (useful with realtime streams)", "" },
3411     { "window_title", OPT_STRING | HAS_ARG, { &window_title }, "set window title", "window title" },
3412 #if CONFIG_AVFILTER
3413     { "vf", OPT_STRING | HAS_ARG, { &vfilters }, "set video filters", "filter_graph" },
3414     { "af", OPT_STRING | HAS_ARG, { &afilters }, "set audio filters", "filter_graph" },
3415 #endif
3416     { "rdftspeed", OPT_INT | HAS_ARG| OPT_AUDIO | OPT_EXPERT, { &rdftspeed }, "rdft speed", "msecs" },
3417     { "showmode", HAS_ARG, { .func_arg = opt_show_mode}, "select show mode (0 = video, 1 = waves, 2 = RDFT)", "mode" },
3418     { "default", HAS_ARG | OPT_AUDIO | OPT_VIDEO | OPT_EXPERT, { .func_arg = opt_default }, "generic catch all option", "" },
3419     { "i", OPT_BOOL, { &dummy}, "read specified file", "input_file"},
3420     { "codec", HAS_ARG, { .func_arg = opt_codec}, "force decoder", "decoder_name" },
3421     { "acodec", HAS_ARG | OPT_STRING | OPT_EXPERT, {    &audio_codec_name }, "force audio decoder",    "decoder_name" },
3422     { "scodec", HAS_ARG | OPT_STRING | OPT_EXPERT, { &subtitle_codec_name }, "force subtitle decoder", "decoder_name" },
3423     { "vcodec", HAS_ARG | OPT_STRING | OPT_EXPERT, {    &video_codec_name }, "force video decoder",    "decoder_name" },
3424     { NULL, },
3425 };
3426
3427 static void show_usage(void)
3428 {
3429     av_log(NULL, AV_LOG_INFO, "Simple media player\n");
3430     av_log(NULL, AV_LOG_INFO, "usage: %s [options] input_file\n", program_name);
3431     av_log(NULL, AV_LOG_INFO, "\n");
3432 }
3433
3434 void show_help_default(const char *opt, const char *arg)
3435 {
3436     av_log_set_callback(log_callback_help);
3437     show_usage();
3438     show_help_options(options, "Main options:", 0, OPT_EXPERT, 0);
3439     show_help_options(options, "Advanced options:", OPT_EXPERT, 0, 0);
3440     printf("\n");
3441     show_help_children(avcodec_get_class(), AV_OPT_FLAG_DECODING_PARAM);
3442     show_help_children(avformat_get_class(), AV_OPT_FLAG_DECODING_PARAM);
3443 #if !CONFIG_AVFILTER
3444     show_help_children(sws_get_class(), AV_OPT_FLAG_ENCODING_PARAM);
3445 #else
3446     show_help_children(avfilter_get_class(), AV_OPT_FLAG_FILTERING_PARAM);
3447 #endif
3448     printf("\nWhile playing:\n"
3449            "q, ESC              quit\n"
3450            "f                   toggle full screen\n"
3451            "p, SPC              pause\n"
3452            "a                   cycle audio channel\n"
3453            "v                   cycle video channel\n"
3454            "t                   cycle subtitle channel\n"
3455            "w                   show audio waves\n"
3456            "s                   activate frame-step mode\n"
3457            "left/right          seek backward/forward 10 seconds\n"
3458            "down/up             seek backward/forward 1 minute\n"
3459            "page down/page up   seek backward/forward 10 minutes\n"
3460            "mouse click         seek to percentage in file corresponding to fraction of width\n"
3461            );
3462 }
3463
3464 static int lockmgr(void **mtx, enum AVLockOp op)
3465 {
3466    switch(op) {
3467       case AV_LOCK_CREATE:
3468           *mtx = SDL_CreateMutex();
3469           if(!*mtx)
3470               return 1;
3471           return 0;
3472       case AV_LOCK_OBTAIN:
3473           return !!SDL_LockMutex(*mtx);
3474       case AV_LOCK_RELEASE:
3475           return !!SDL_UnlockMutex(*mtx);
3476       case AV_LOCK_DESTROY:
3477           SDL_DestroyMutex(*mtx);
3478           return 0;
3479    }
3480    return 1;
3481 }
3482
3483 /* Called from the main */
3484 int main(int argc, char **argv)
3485 {
3486     int flags;
3487     VideoState *is;
3488     char dummy_videodriver[] = "SDL_VIDEODRIVER=dummy";
3489
3490     av_log_set_flags(AV_LOG_SKIP_REPEATED);
3491     parse_loglevel(argc, argv, options);
3492
3493     /* register all codecs, demux and protocols */
3494     avcodec_register_all();
3495 #if CONFIG_AVDEVICE
3496     avdevice_register_all();
3497 #endif
3498 #if CONFIG_AVFILTER
3499     avfilter_register_all();
3500 #endif
3501     av_register_all();
3502     avformat_network_init();
3503
3504     init_opts();
3505
3506     signal(SIGINT , sigterm_handler); /* Interrupt (ANSI).    */
3507     signal(SIGTERM, sigterm_handler); /* Termination (ANSI).  */
3508
3509     show_banner(argc, argv, options);
3510
3511     parse_options(NULL, argc, argv, options, opt_input_file);
3512
3513     if (!input_filename) {
3514         show_usage();
3515         av_log(NULL, AV_LOG_FATAL, "An input file must be specified\n");
3516         av_log(NULL, AV_LOG_FATAL,
3517                "Use -h to get full help or, even better, run 'man %s'\n", program_name);
3518         exit(1);
3519     }
3520
3521     if (display_disable) {
3522         video_disable = 1;
3523     }
3524     flags = SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_TIMER;
3525     if (audio_disable)
3526         flags &= ~SDL_INIT_AUDIO;
3527     if (display_disable)
3528         SDL_putenv(dummy_videodriver); /* For the event queue, we always need a video driver. */
3529 #if !defined(__MINGW32__) && !defined(__APPLE__)
3530     flags |= SDL_INIT_EVENTTHREAD; /* Not supported on Windows or Mac OS X */
3531 #endif
3532     if (SDL_Init (flags)) {
3533         av_log(NULL, AV_LOG_FATAL, "Could not initialize SDL - %s\n", SDL_GetError());
3534         av_log(NULL, AV_LOG_FATAL, "(Did you set the DISPLAY variable?)\n");
3535         exit(1);
3536     }
3537
3538     if (!display_disable) {
3539         const SDL_VideoInfo *vi = SDL_GetVideoInfo();
3540         fs_screen_width = vi->current_w;
3541         fs_screen_height = vi->current_h;
3542     }
3543
3544     SDL_EventState(SDL_ACTIVEEVENT, SDL_IGNORE);
3545     SDL_EventState(SDL_SYSWMEVENT, SDL_IGNORE);
3546     SDL_EventState(SDL_USEREVENT, SDL_IGNORE);
3547
3548     if (av_lockmgr_register(lockmgr)) {
3549         av_log(NULL, AV_LOG_FATAL, "Could not initialize lock manager!\n");
3550         do_exit(NULL);
3551     }
3552
3553     av_init_packet(&flush_pkt);
3554     flush_pkt.data = (uint8_t *)&flush_pkt;
3555
3556     is = stream_open(input_filename, file_iformat);
3557     if (!is) {
3558         av_log(NULL, AV_LOG_FATAL, "Failed to initialize VideoState!\n");
3559         do_exit(NULL);
3560     }
3561
3562     event_loop(is);
3563
3564     /* never returns */
3565
3566     return 0;
3567 }