]> git.sesse.net Git - ffmpeg/blob - libavformat/avisynth.c
lavf/hls: add http_seekable option for HTTP partial requests
[ffmpeg] / libavformat / avisynth.c
1 /*
2  * AviSynth/AvxSynth support
3  * Copyright (c) 2012 AvxSynth Team
4  *
5  * This file is part of FFmpeg
6  *
7  * FFmpeg is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * FFmpeg is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with FFmpeg; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20  */
21
22 #include "libavutil/attributes.h"
23 #include "libavutil/internal.h"
24
25 #include "libavcodec/internal.h"
26
27 #include "avformat.h"
28 #include "internal.h"
29 #include "config.h"
30
31 /* Enable function pointer definitions for runtime loading. */
32 #define AVSC_NO_DECLSPEC
33
34 /* Platform-specific directives for AviSynth vs AvxSynth. */
35 #ifdef _WIN32
36   #include "compat/w32dlfcn.h"
37   #undef EXTERN_C
38   #include "compat/avisynth/avisynth_c.h"
39   #define AVISYNTH_LIB "avisynth"
40   #define USING_AVISYNTH
41 #else
42   #include <dlfcn.h>
43   #include "compat/avisynth/avxsynth_c.h"
44   #define AVISYNTH_NAME "libavxsynth"
45   #define AVISYNTH_LIB AVISYNTH_NAME SLIBSUF
46 #endif
47
48 typedef struct AviSynthLibrary {
49     void *library;
50 #define AVSC_DECLARE_FUNC(name) name ## _func name
51     AVSC_DECLARE_FUNC(avs_bit_blt);
52     AVSC_DECLARE_FUNC(avs_clip_get_error);
53     AVSC_DECLARE_FUNC(avs_create_script_environment);
54     AVSC_DECLARE_FUNC(avs_delete_script_environment);
55     AVSC_DECLARE_FUNC(avs_get_audio);
56     AVSC_DECLARE_FUNC(avs_get_error);
57     AVSC_DECLARE_FUNC(avs_get_frame);
58     AVSC_DECLARE_FUNC(avs_get_version);
59     AVSC_DECLARE_FUNC(avs_get_video_info);
60     AVSC_DECLARE_FUNC(avs_invoke);
61     AVSC_DECLARE_FUNC(avs_release_clip);
62     AVSC_DECLARE_FUNC(avs_release_value);
63     AVSC_DECLARE_FUNC(avs_release_video_frame);
64     AVSC_DECLARE_FUNC(avs_take_clip);
65 #ifdef USING_AVISYNTH
66     AVSC_DECLARE_FUNC(avs_bits_per_pixel);
67     AVSC_DECLARE_FUNC(avs_get_height_p);
68     AVSC_DECLARE_FUNC(avs_get_pitch_p);
69     AVSC_DECLARE_FUNC(avs_get_read_ptr_p);
70     AVSC_DECLARE_FUNC(avs_get_row_size_p);
71     AVSC_DECLARE_FUNC(avs_is_planar_rgb);
72     AVSC_DECLARE_FUNC(avs_is_planar_rgba);
73 #endif
74 #undef AVSC_DECLARE_FUNC
75 } AviSynthLibrary;
76
77 typedef struct AviSynthContext {
78     AVS_ScriptEnvironment *env;
79     AVS_Clip *clip;
80     const AVS_VideoInfo *vi;
81
82     /* avisynth_read_packet_video() iterates over this. */
83     int n_planes;
84     const int *planes;
85
86     int curr_stream;
87     int curr_frame;
88     int64_t curr_sample;
89
90     int error;
91
92     /* Linked list pointers. */
93     struct AviSynthContext *next;
94 } AviSynthContext;
95
96 static const int avs_planes_packed[1] = { 0 };
97 static const int avs_planes_grey[1]   = { AVS_PLANAR_Y };
98 static const int avs_planes_yuv[3]    = { AVS_PLANAR_Y, AVS_PLANAR_U,
99                                           AVS_PLANAR_V };
100 #ifdef USING_AVISYNTH
101 static const int avs_planes_rgb[3]    = { AVS_PLANAR_G, AVS_PLANAR_B,
102                                           AVS_PLANAR_R };
103 static const int avs_planes_yuva[4]   = { AVS_PLANAR_Y, AVS_PLANAR_U,
104                                           AVS_PLANAR_V, AVS_PLANAR_A };
105 static const int avs_planes_rgba[4]   = { AVS_PLANAR_G, AVS_PLANAR_B,
106                                           AVS_PLANAR_R, AVS_PLANAR_A };
107 #endif
108
109 /* A conflict between C++ global objects, atexit, and dynamic loading requires
110  * us to register our own atexit handler to prevent double freeing. */
111 static AviSynthLibrary avs_library;
112 static int avs_atexit_called        = 0;
113
114 /* Linked list of AviSynthContexts. An atexit handler destroys this list. */
115 static AviSynthContext *avs_ctx_list = NULL;
116
117 static av_cold void avisynth_atexit_handler(void);
118
119 static av_cold int avisynth_load_library(void)
120 {
121     avs_library.library = dlopen(AVISYNTH_LIB, RTLD_NOW | RTLD_LOCAL);
122     if (!avs_library.library)
123         return AVERROR_UNKNOWN;
124
125 #define LOAD_AVS_FUNC(name, continue_on_fail)                          \
126         avs_library.name = (name ## _func)                             \
127                            dlsym(avs_library.library, #name);          \
128         if (!continue_on_fail && !avs_library.name)                    \
129             goto fail;
130
131     LOAD_AVS_FUNC(avs_bit_blt, 0);
132     LOAD_AVS_FUNC(avs_clip_get_error, 0);
133     LOAD_AVS_FUNC(avs_create_script_environment, 0);
134     LOAD_AVS_FUNC(avs_delete_script_environment, 0);
135     LOAD_AVS_FUNC(avs_get_audio, 0);
136     LOAD_AVS_FUNC(avs_get_error, 1); // New to AviSynth 2.6
137     LOAD_AVS_FUNC(avs_get_frame, 0);
138     LOAD_AVS_FUNC(avs_get_version, 0);
139     LOAD_AVS_FUNC(avs_get_video_info, 0);
140     LOAD_AVS_FUNC(avs_invoke, 0);
141     LOAD_AVS_FUNC(avs_release_clip, 0);
142     LOAD_AVS_FUNC(avs_release_value, 0);
143     LOAD_AVS_FUNC(avs_release_video_frame, 0);
144     LOAD_AVS_FUNC(avs_take_clip, 0);
145 #ifdef USING_AVISYNTH
146     LOAD_AVS_FUNC(avs_bits_per_pixel, 1);
147     LOAD_AVS_FUNC(avs_get_height_p, 1);
148     LOAD_AVS_FUNC(avs_get_pitch_p, 1);
149     LOAD_AVS_FUNC(avs_get_read_ptr_p, 1);
150     LOAD_AVS_FUNC(avs_get_row_size_p, 1);
151     LOAD_AVS_FUNC(avs_is_planar_rgb, 1);
152     LOAD_AVS_FUNC(avs_is_planar_rgba, 1);
153 #endif
154 #undef LOAD_AVS_FUNC
155
156     atexit(avisynth_atexit_handler);
157     return 0;
158
159 fail:
160     dlclose(avs_library.library);
161     return AVERROR_UNKNOWN;
162 }
163
164 /* Note that avisynth_context_create and avisynth_context_destroy
165  * do not allocate or free the actual context! That is taken care of
166  * by libavformat. */
167 static av_cold int avisynth_context_create(AVFormatContext *s)
168 {
169     AviSynthContext *avs = s->priv_data;
170     int ret;
171
172     if (!avs_library.library)
173         if (ret = avisynth_load_library())
174             return ret;
175
176     avs->env = avs_library.avs_create_script_environment(3);
177     if (avs_library.avs_get_error) {
178         const char *error = avs_library.avs_get_error(avs->env);
179         if (error) {
180             av_log(s, AV_LOG_ERROR, "%s\n", error);
181             return AVERROR_UNKNOWN;
182         }
183     }
184
185     if (!avs_ctx_list) {
186         avs_ctx_list = avs;
187     } else {
188         avs->next    = avs_ctx_list;
189         avs_ctx_list = avs;
190     }
191
192     return 0;
193 }
194
195 static av_cold void avisynth_context_destroy(AviSynthContext *avs)
196 {
197     if (avs_atexit_called)
198         return;
199
200     if (avs == avs_ctx_list) {
201         avs_ctx_list = avs->next;
202     } else {
203         AviSynthContext *prev = avs_ctx_list;
204         while (prev->next != avs)
205             prev = prev->next;
206         prev->next = avs->next;
207     }
208
209     if (avs->clip) {
210         avs_library.avs_release_clip(avs->clip);
211         avs->clip = NULL;
212     }
213     if (avs->env) {
214         avs_library.avs_delete_script_environment(avs->env);
215         avs->env = NULL;
216     }
217 }
218
219 static av_cold void avisynth_atexit_handler(void)
220 {
221     AviSynthContext *avs = avs_ctx_list;
222
223     while (avs) {
224         AviSynthContext *next = avs->next;
225         avisynth_context_destroy(avs);
226         avs = next;
227     }
228     dlclose(avs_library.library);
229
230     avs_atexit_called = 1;
231 }
232
233 /* Create AVStream from audio and video data. */
234 static int avisynth_create_stream_video(AVFormatContext *s, AVStream *st)
235 {
236     AviSynthContext *avs = s->priv_data;
237     int planar = 0; // 0: packed, 1: YUV, 2: Y8, 3: Planar RGB, 4: YUVA, 5: Planar RGBA
238
239     st->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
240     st->codecpar->codec_id   = AV_CODEC_ID_RAWVIDEO;
241     st->codecpar->width      = avs->vi->width;
242     st->codecpar->height     = avs->vi->height;
243
244     st->avg_frame_rate    = (AVRational) { avs->vi->fps_numerator,
245                                            avs->vi->fps_denominator };
246     st->start_time        = 0;
247     st->duration          = avs->vi->num_frames;
248     st->nb_frames         = avs->vi->num_frames;
249     avpriv_set_pts_info(st, 32, avs->vi->fps_denominator, avs->vi->fps_numerator);
250
251     switch (avs->vi->pixel_type) {
252 #ifdef USING_AVISYNTH
253     /* 10~16-bit YUV pix_fmts (AviSynth+) */
254     case AVS_CS_YUV444P10:
255         st->codecpar->format = AV_PIX_FMT_YUV444P10;
256         planar               = 1;
257         break;
258     case AVS_CS_YUV422P10:
259         st->codecpar->format = AV_PIX_FMT_YUV422P10;
260         planar               = 1;
261         break;
262     case AVS_CS_YUV420P10:
263         st->codecpar->format = AV_PIX_FMT_YUV420P10;
264         planar               = 1;
265         break;
266     case AVS_CS_YUV444P12:
267         st->codecpar->format = AV_PIX_FMT_YUV444P12;
268         planar               = 1;
269         break;
270     case AVS_CS_YUV422P12:
271         st->codecpar->format = AV_PIX_FMT_YUV422P12;
272         planar               = 1;
273         break;
274     case AVS_CS_YUV420P12:
275         st->codecpar->format = AV_PIX_FMT_YUV420P12;
276         planar               = 1;
277         break;
278     case AVS_CS_YUV444P14:
279         st->codecpar->format = AV_PIX_FMT_YUV444P14;
280         planar               = 1;
281         break;
282     case AVS_CS_YUV422P14:
283         st->codecpar->format = AV_PIX_FMT_YUV422P14;
284         planar               = 1;
285         break;
286     case AVS_CS_YUV420P14:
287         st->codecpar->format = AV_PIX_FMT_YUV420P14;
288         planar               = 1;
289         break;
290     case AVS_CS_YUV444P16:
291         st->codecpar->format = AV_PIX_FMT_YUV444P16;
292         planar               = 1;
293         break;
294     case AVS_CS_YUV422P16:
295         st->codecpar->format = AV_PIX_FMT_YUV422P16;
296         planar               = 1;
297         break;
298     case AVS_CS_YUV420P16:
299         st->codecpar->format = AV_PIX_FMT_YUV420P16;
300         planar               = 1;
301         break;
302     /* 8~16-bit YUV pix_fmts with Alpha (AviSynth+) */
303     case AVS_CS_YUVA444:
304         st->codecpar->format = AV_PIX_FMT_YUVA444P;
305         planar               = 4;
306         break;
307     case AVS_CS_YUVA422:
308         st->codecpar->format = AV_PIX_FMT_YUVA422P;
309         planar               = 4;
310         break;
311     case AVS_CS_YUVA420:
312         st->codecpar->format = AV_PIX_FMT_YUVA420P;
313         planar               = 4;
314         break;
315     case AVS_CS_YUVA444P10:
316         st->codecpar->format = AV_PIX_FMT_YUVA444P10;
317         planar               = 4;
318         break;
319     case AVS_CS_YUVA422P10:
320         st->codecpar->format = AV_PIX_FMT_YUVA422P10;
321         planar               = 4;
322         break;
323     case AVS_CS_YUVA420P10:
324         st->codecpar->format = AV_PIX_FMT_YUVA420P10;
325         planar               = 4;
326         break;
327     case AVS_CS_YUVA422P12:
328         st->codecpar->format = AV_PIX_FMT_YUVA422P12;
329         planar               = 4;
330         break;
331     case AVS_CS_YUVA444P16:
332         st->codecpar->format = AV_PIX_FMT_YUVA444P16;
333         planar               = 4;
334         break;
335     case AVS_CS_YUVA422P16:
336         st->codecpar->format = AV_PIX_FMT_YUVA422P16;
337         planar               = 4;
338         break;
339     case AVS_CS_YUVA420P16:
340         st->codecpar->format = AV_PIX_FMT_YUVA420P16;
341         planar               = 4;
342         break;
343     /* Planar RGB pix_fmts (AviSynth+) */
344     case AVS_CS_RGBP:
345         st->codecpar->format = AV_PIX_FMT_GBRP;
346         planar               = 3;
347         break;
348     case AVS_CS_RGBP10:
349         st->codecpar->format = AV_PIX_FMT_GBRP10;
350         planar               = 3;
351         break;
352     case AVS_CS_RGBP12:
353         st->codecpar->format = AV_PIX_FMT_GBRP12;
354         planar               = 3;
355         break;
356     case AVS_CS_RGBP14:
357         st->codecpar->format = AV_PIX_FMT_GBRP14;
358         planar               = 3;
359         break;
360     case AVS_CS_RGBP16:
361         st->codecpar->format = AV_PIX_FMT_GBRP16;
362         planar               = 3;
363         break;
364     /* Single precision floating point Planar RGB (AviSynth+) */
365     case AVS_CS_RGBPS:
366         st->codecpar->format = AV_PIX_FMT_GBRPF32;
367         planar               = 3;
368         break;
369     /* Planar RGB pix_fmts with Alpha (AviSynth+) */
370     case AVS_CS_RGBAP:
371         st->codecpar->format = AV_PIX_FMT_GBRAP;
372         planar               = 5;
373         break;
374     case AVS_CS_RGBAP10:
375         st->codecpar->format = AV_PIX_FMT_GBRAP10;
376         planar               = 5;
377         break;
378     case AVS_CS_RGBAP12:
379         st->codecpar->format = AV_PIX_FMT_GBRAP12;
380         planar               = 5;
381         break;
382     case AVS_CS_RGBAP16:
383         st->codecpar->format = AV_PIX_FMT_GBRAP16;
384         planar               = 5;
385         break;
386     /* Single precision floating point Planar RGB with Alpha (AviSynth+) */
387     case AVS_CS_RGBAPS:
388         st->codecpar->format = AV_PIX_FMT_GBRAPF32;
389         planar               = 5;
390         break;
391     /* 10~16-bit gray pix_fmts (AviSynth+) */
392     case AVS_CS_Y10:
393         st->codecpar->format = AV_PIX_FMT_GRAY10;
394         planar               = 2;
395         break;
396     case AVS_CS_Y12:
397         st->codecpar->format = AV_PIX_FMT_GRAY12;
398         planar               = 2;
399         break;
400     case AVS_CS_Y14:
401         st->codecpar->format = AV_PIX_FMT_GRAY14;
402         planar               = 2;
403         break;
404     case AVS_CS_Y16:
405         st->codecpar->format = AV_PIX_FMT_GRAY16;
406         planar               = 2;
407         break;
408     /* Single precision floating point gray (AviSynth+) */
409     case AVS_CS_Y32:
410         st->codecpar->format = AV_PIX_FMT_GRAYF32;
411         planar               = 2;
412         break;
413     /* pix_fmts added in AviSynth 2.6 */
414     case AVS_CS_YV24:
415         st->codecpar->format = AV_PIX_FMT_YUV444P;
416         planar               = 1;
417         break;
418     case AVS_CS_YV16:
419         st->codecpar->format = AV_PIX_FMT_YUV422P;
420         planar               = 1;
421         break;
422     case AVS_CS_YV411:
423         st->codecpar->format = AV_PIX_FMT_YUV411P;
424         planar               = 1;
425         break;
426     case AVS_CS_Y8:
427         st->codecpar->format = AV_PIX_FMT_GRAY8;
428         planar               = 2;
429         break;
430     /* 16-bit packed RGB pix_fmts (AviSynth+) */
431     case AVS_CS_BGR48:
432         st->codecpar->format = AV_PIX_FMT_BGR48;
433         break;
434     case AVS_CS_BGR64:
435         st->codecpar->format = AV_PIX_FMT_BGRA64;
436         break;
437 #endif
438     /* AviSynth 2.5 and AvxSynth pix_fmts */
439     case AVS_CS_BGR24:
440         st->codecpar->format = AV_PIX_FMT_BGR24;
441         break;
442     case AVS_CS_BGR32:
443         st->codecpar->format = AV_PIX_FMT_RGB32;
444         break;
445     case AVS_CS_YUY2:
446         st->codecpar->format = AV_PIX_FMT_YUYV422;
447         break;
448     case AVS_CS_YV12:
449         st->codecpar->format = AV_PIX_FMT_YUV420P;
450         planar               = 1;
451         break;
452     case AVS_CS_I420: // Is this even used anywhere?
453         st->codecpar->format = AV_PIX_FMT_YUV420P;
454         planar               = 1;
455         break;
456     default:
457         av_log(s, AV_LOG_ERROR,
458                "unknown AviSynth colorspace %d\n", avs->vi->pixel_type);
459         avs->error = 1;
460         return AVERROR_UNKNOWN;
461     }
462
463     switch (planar) {
464 #ifdef USING_AVISYNTH
465     case 5: // Planar RGB + Alpha
466         avs->n_planes = 4;
467         avs->planes   = avs_planes_rgba;
468         break;
469     case 4: // YUV + Alpha
470         avs->n_planes = 4;
471         avs->planes   = avs_planes_yuva;
472         break;
473     case 3: // Planar RGB
474         avs->n_planes = 3;
475         avs->planes   = avs_planes_rgb;
476         break;
477 #endif
478     case 2: // Y8
479         avs->n_planes = 1;
480         avs->planes   = avs_planes_grey;
481         break;
482     case 1: // YUV
483         avs->n_planes = 3;
484         avs->planes   = avs_planes_yuv;
485         break;
486     default:
487         avs->n_planes = 1;
488         avs->planes   = avs_planes_packed;
489     }
490     return 0;
491 }
492
493 static int avisynth_create_stream_audio(AVFormatContext *s, AVStream *st)
494 {
495     AviSynthContext *avs = s->priv_data;
496
497     st->codecpar->codec_type  = AVMEDIA_TYPE_AUDIO;
498     st->codecpar->sample_rate = avs->vi->audio_samples_per_second;
499     st->codecpar->channels    = avs->vi->nchannels;
500     st->duration              = avs->vi->num_audio_samples;
501     avpriv_set_pts_info(st, 64, 1, avs->vi->audio_samples_per_second);
502
503     switch (avs->vi->sample_type) {
504     case AVS_SAMPLE_INT8:
505         st->codecpar->codec_id = AV_CODEC_ID_PCM_U8;
506         break;
507     case AVS_SAMPLE_INT16:
508         st->codecpar->codec_id = AV_CODEC_ID_PCM_S16LE;
509         break;
510     case AVS_SAMPLE_INT24:
511         st->codecpar->codec_id = AV_CODEC_ID_PCM_S24LE;
512         break;
513     case AVS_SAMPLE_INT32:
514         st->codecpar->codec_id = AV_CODEC_ID_PCM_S32LE;
515         break;
516     case AVS_SAMPLE_FLOAT:
517         st->codecpar->codec_id = AV_CODEC_ID_PCM_F32LE;
518         break;
519     default:
520         av_log(s, AV_LOG_ERROR,
521                "unknown AviSynth sample type %d\n", avs->vi->sample_type);
522         avs->error = 1;
523         return AVERROR_UNKNOWN;
524     }
525     return 0;
526 }
527
528 static int avisynth_create_stream(AVFormatContext *s)
529 {
530     AviSynthContext *avs = s->priv_data;
531     AVStream *st;
532     int ret;
533     int id = 0;
534
535     if (avs_has_video(avs->vi)) {
536         st = avformat_new_stream(s, NULL);
537         if (!st)
538             return AVERROR_UNKNOWN;
539         st->id = id++;
540         if (ret = avisynth_create_stream_video(s, st))
541             return ret;
542     }
543     if (avs_has_audio(avs->vi)) {
544         st = avformat_new_stream(s, NULL);
545         if (!st)
546             return AVERROR_UNKNOWN;
547         st->id = id++;
548         if (ret = avisynth_create_stream_audio(s, st))
549             return ret;
550     }
551     return 0;
552 }
553
554 static int avisynth_open_file(AVFormatContext *s)
555 {
556     AviSynthContext *avs = s->priv_data;
557     AVS_Value arg, val;
558     int ret;
559 #ifdef USING_AVISYNTH
560     char filename_ansi[MAX_PATH * 4];
561     wchar_t filename_wc[MAX_PATH * 4];
562 #endif
563
564     if (ret = avisynth_context_create(s))
565         return ret;
566
567 #ifdef USING_AVISYNTH
568     /* Convert UTF-8 to ANSI code page */
569     MultiByteToWideChar(CP_UTF8, 0, s->filename, -1, filename_wc, MAX_PATH * 4);
570     WideCharToMultiByte(CP_THREAD_ACP, 0, filename_wc, -1, filename_ansi,
571                         MAX_PATH * 4, NULL, NULL);
572     arg = avs_new_value_string(filename_ansi);
573 #else
574     arg = avs_new_value_string(s->filename);
575 #endif
576     val = avs_library.avs_invoke(avs->env, "Import", arg, 0);
577     if (avs_is_error(val)) {
578         av_log(s, AV_LOG_ERROR, "%s\n", avs_as_error(val));
579         ret = AVERROR_UNKNOWN;
580         goto fail;
581     }
582     if (!avs_is_clip(val)) {
583         av_log(s, AV_LOG_ERROR, "AviSynth script did not return a clip\n");
584         ret = AVERROR_UNKNOWN;
585         goto fail;
586     }
587
588     avs->clip = avs_library.avs_take_clip(val, avs->env);
589     avs->vi   = avs_library.avs_get_video_info(avs->clip);
590
591 #ifdef USING_AVISYNTH
592     /* On Windows, FFmpeg supports AviSynth interface version 6 or higher.
593      * This includes AviSynth 2.6 RC1 or higher, and AviSynth+ r1718 or higher,
594      * and excludes 2.5 and the 2.6 alphas. Since AvxSynth identifies itself
595      * as interface version 3 like 2.5.8, this needs to be special-cased. */
596
597     if (avs_library.avs_get_version(avs->clip) < 6) {
598         av_log(s, AV_LOG_ERROR,
599                "AviSynth version is too old. Please upgrade to either AviSynth 2.6 >= RC1 or AviSynth+ >= r1718.\n");
600         ret = AVERROR_UNKNOWN;
601         goto fail;
602     }
603 #endif
604
605     /* Release the AVS_Value as it will go out of scope. */
606     avs_library.avs_release_value(val);
607
608     if (ret = avisynth_create_stream(s))
609         goto fail;
610
611     return 0;
612
613 fail:
614     avisynth_context_destroy(avs);
615     return ret;
616 }
617
618 static void avisynth_next_stream(AVFormatContext *s, AVStream **st,
619                                  AVPacket *pkt, int *discard)
620 {
621     AviSynthContext *avs = s->priv_data;
622
623     avs->curr_stream++;
624     avs->curr_stream %= s->nb_streams;
625
626     *st = s->streams[avs->curr_stream];
627     if ((*st)->discard == AVDISCARD_ALL)
628         *discard = 1;
629     else
630         *discard = 0;
631
632     return;
633 }
634
635 /* Copy AviSynth clip data into an AVPacket. */
636 static int avisynth_read_packet_video(AVFormatContext *s, AVPacket *pkt,
637                                       int discard)
638 {
639     AviSynthContext *avs = s->priv_data;
640     AVS_VideoFrame *frame;
641     unsigned char *dst_p;
642     const unsigned char *src_p;
643     int n, i, plane, rowsize, planeheight, pitch, bits;
644     const char *error;
645     int avsplus av_unused;
646
647     if (avs->curr_frame >= avs->vi->num_frames)
648         return AVERROR_EOF;
649
650     /* This must happen even if the stream is discarded to prevent desync. */
651     n = avs->curr_frame++;
652     if (discard)
653         return 0;
654
655 #ifdef USING_AVISYNTH
656     /* Detect whether we're using AviSynth 2.6 or AviSynth+ by
657      * looking for whether avs_is_planar_rgb exists. */
658     if (GetProcAddress(avs_library.library, "avs_is_planar_rgb") == NULL)
659         avsplus = 0;
660     else
661         avsplus = 1;
662
663     /* avs_bits_per_pixel changed to AVSC_API with AviSynth 2.6, which
664      * requires going through avs_library, while AvxSynth has it under
665      * the older AVSC_INLINE type, so special-case this. */
666
667     bits = avs_library.avs_bits_per_pixel(avs->vi);
668 #else
669     bits = avs_bits_per_pixel(avs->vi);
670 #endif
671
672     /* Without the cast to int64_t, calculation overflows at about 9k x 9k
673      * resolution. */
674     pkt->size = (((int64_t)avs->vi->width *
675                   (int64_t)avs->vi->height) * bits) / 8;
676     if (!pkt->size)
677         return AVERROR_UNKNOWN;
678
679     if (av_new_packet(pkt, pkt->size) < 0)
680         return AVERROR(ENOMEM);
681
682     pkt->pts      = n;
683     pkt->dts      = n;
684     pkt->duration = 1;
685     pkt->stream_index = avs->curr_stream;
686
687     frame = avs_library.avs_get_frame(avs->clip, n);
688     error = avs_library.avs_clip_get_error(avs->clip);
689     if (error) {
690         av_log(s, AV_LOG_ERROR, "%s\n", error);
691         avs->error = 1;
692         av_packet_unref(pkt);
693         return AVERROR_UNKNOWN;
694     }
695
696     dst_p = pkt->data;
697     for (i = 0; i < avs->n_planes; i++) {
698         plane = avs->planes[i];
699 #ifdef USING_AVISYNTH
700         src_p = avs_library.avs_get_read_ptr_p(frame, plane);
701         pitch = avs_library.avs_get_pitch_p(frame, plane);
702
703         rowsize     = avs_library.avs_get_row_size_p(frame, plane);
704         planeheight = avs_library.avs_get_height_p(frame, plane);
705 #else
706         src_p = avs_get_read_ptr_p(frame, plane);
707         pitch = avs_get_pitch_p(frame, plane);
708
709         rowsize     = avs_get_row_size_p(frame, plane);
710         planeheight = avs_get_height_p(frame, plane);
711 #endif
712
713         /* Flip RGB video. */
714         if (avs_is_rgb24(avs->vi) || avs_is_rgb(avs->vi)) {
715             src_p = src_p + (planeheight - 1) * pitch;
716             pitch = -pitch;
717         }
718
719 #ifdef USING_AVISYNTH
720         /* Flip Planar RGB video */
721         if (avsplus && (avs_library.avs_is_planar_rgb(avs->vi) ||
722                         avs_library.avs_is_planar_rgba(avs->vi))) {
723             src_p = src_p + (planeheight - 1) * pitch;
724             pitch = -pitch;
725         }
726 #endif
727
728         avs_library.avs_bit_blt(avs->env, dst_p, rowsize, src_p, pitch,
729                                  rowsize, planeheight);
730         dst_p += rowsize * planeheight;
731     }
732
733     avs_library.avs_release_video_frame(frame);
734     return 0;
735 }
736
737 static int avisynth_read_packet_audio(AVFormatContext *s, AVPacket *pkt,
738                                       int discard)
739 {
740     AviSynthContext *avs = s->priv_data;
741     AVRational fps, samplerate;
742     int samples;
743     int64_t n;
744     const char *error;
745
746     if (avs->curr_sample >= avs->vi->num_audio_samples)
747         return AVERROR_EOF;
748
749     fps.num        = avs->vi->fps_numerator;
750     fps.den        = avs->vi->fps_denominator;
751     samplerate.num = avs->vi->audio_samples_per_second;
752     samplerate.den = 1;
753
754     if (avs_has_video(avs->vi)) {
755         if (avs->curr_frame < avs->vi->num_frames)
756             samples = av_rescale_q(avs->curr_frame, samplerate, fps) -
757                       avs->curr_sample;
758         else
759             samples = av_rescale_q(1, samplerate, fps);
760     } else {
761         samples = 1000;
762     }
763
764     /* After seeking, audio may catch up with video. */
765     if (samples <= 0) {
766         pkt->size = 0;
767         pkt->data = NULL;
768         return 0;
769     }
770
771     if (avs->curr_sample + samples > avs->vi->num_audio_samples)
772         samples = avs->vi->num_audio_samples - avs->curr_sample;
773
774     /* This must happen even if the stream is discarded to prevent desync. */
775     n                 = avs->curr_sample;
776     avs->curr_sample += samples;
777     if (discard)
778         return 0;
779
780     pkt->size = avs_bytes_per_channel_sample(avs->vi) *
781                 samples * avs->vi->nchannels;
782     if (!pkt->size)
783         return AVERROR_UNKNOWN;
784
785     if (av_new_packet(pkt, pkt->size) < 0)
786         return AVERROR(ENOMEM);
787
788     pkt->pts      = n;
789     pkt->dts      = n;
790     pkt->duration = samples;
791     pkt->stream_index = avs->curr_stream;
792
793     avs_library.avs_get_audio(avs->clip, pkt->data, n, samples);
794     error = avs_library.avs_clip_get_error(avs->clip);
795     if (error) {
796         av_log(s, AV_LOG_ERROR, "%s\n", error);
797         avs->error = 1;
798         av_packet_unref(pkt);
799         return AVERROR_UNKNOWN;
800     }
801     return 0;
802 }
803
804 static av_cold int avisynth_read_header(AVFormatContext *s)
805 {
806     int ret;
807
808     // Calling library must implement a lock for thread-safe opens.
809     if (ret = ff_lock_avformat())
810         return ret;
811
812     if (ret = avisynth_open_file(s)) {
813         ff_unlock_avformat();
814         return ret;
815     }
816
817     ff_unlock_avformat();
818     return 0;
819 }
820
821 static int avisynth_read_packet(AVFormatContext *s, AVPacket *pkt)
822 {
823     AviSynthContext *avs = s->priv_data;
824     AVStream *st;
825     int discard = 0;
826     int ret;
827
828     if (avs->error)
829         return AVERROR_UNKNOWN;
830
831     /* If either stream reaches EOF, try to read the other one before
832      * giving up. */
833     avisynth_next_stream(s, &st, pkt, &discard);
834     if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
835         ret = avisynth_read_packet_video(s, pkt, discard);
836         if (ret == AVERROR_EOF && avs_has_audio(avs->vi)) {
837             avisynth_next_stream(s, &st, pkt, &discard);
838             return avisynth_read_packet_audio(s, pkt, discard);
839         }
840     } else {
841         ret = avisynth_read_packet_audio(s, pkt, discard);
842         if (ret == AVERROR_EOF && avs_has_video(avs->vi)) {
843             avisynth_next_stream(s, &st, pkt, &discard);
844             return avisynth_read_packet_video(s, pkt, discard);
845         }
846     }
847
848     return ret;
849 }
850
851 static av_cold int avisynth_read_close(AVFormatContext *s)
852 {
853     if (ff_lock_avformat())
854         return AVERROR_UNKNOWN;
855
856     avisynth_context_destroy(s->priv_data);
857     ff_unlock_avformat();
858     return 0;
859 }
860
861 static int avisynth_read_seek(AVFormatContext *s, int stream_index,
862                               int64_t timestamp, int flags)
863 {
864     AviSynthContext *avs = s->priv_data;
865     AVStream *st;
866     AVRational fps, samplerate;
867
868     if (avs->error)
869         return AVERROR_UNKNOWN;
870
871     fps        = (AVRational) { avs->vi->fps_numerator,
872                                 avs->vi->fps_denominator };
873     samplerate = (AVRational) { avs->vi->audio_samples_per_second, 1 };
874
875     st = s->streams[stream_index];
876     if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
877         /* AviSynth frame counts are signed int. */
878         if ((timestamp >= avs->vi->num_frames) ||
879             (timestamp > INT_MAX)              ||
880             (timestamp < 0))
881             return AVERROR_EOF;
882         avs->curr_frame = timestamp;
883         if (avs_has_audio(avs->vi))
884             avs->curr_sample = av_rescale_q(timestamp, samplerate, fps);
885     } else {
886         if ((timestamp >= avs->vi->num_audio_samples) || (timestamp < 0))
887             return AVERROR_EOF;
888         /* Force frame granularity for seeking. */
889         if (avs_has_video(avs->vi)) {
890             avs->curr_frame  = av_rescale_q(timestamp, fps, samplerate);
891             avs->curr_sample = av_rescale_q(avs->curr_frame, samplerate, fps);
892         } else {
893             avs->curr_sample = timestamp;
894         }
895     }
896
897     return 0;
898 }
899
900 AVInputFormat ff_avisynth_demuxer = {
901     .name           = "avisynth",
902     .long_name      = NULL_IF_CONFIG_SMALL("AviSynth script"),
903     .priv_data_size = sizeof(AviSynthContext),
904     .read_header    = avisynth_read_header,
905     .read_packet    = avisynth_read_packet,
906     .read_close     = avisynth_read_close,
907     .read_seek      = avisynth_read_seek,
908     .extensions     = "avs",
909 };