diff options
Diffstat (limited to 'src/combined/ffmpeg')
-rw-r--r-- | src/combined/ffmpeg/Makefile.am | 57 | ||||
-rw-r--r-- | src/combined/ffmpeg/ff_audio_decoder.c | 25 | ||||
-rw-r--r-- | src/combined/ffmpeg/ff_dvaudio_decoder.c | 432 | ||||
-rw-r--r-- | src/combined/ffmpeg/ff_mpeg_parser.h | 2 | ||||
-rw-r--r-- | src/combined/ffmpeg/ff_video_decoder.c | 67 | ||||
-rw-r--r-- | src/combined/ffmpeg/ffmpeg_decoder.c | 284 | ||||
-rw-r--r-- | src/combined/ffmpeg/ffmpeg_decoder.h | 4 | ||||
-rw-r--r-- | src/combined/ffmpeg/ffmpeg_encoder.c | 334 | ||||
-rwxr-xr-x | src/combined/ffmpeg/mkcodeclist.pl | 9 | ||||
-rw-r--r-- | src/combined/ffmpeg/xine_audio.list | 1 | ||||
-rw-r--r-- | src/combined/ffmpeg/xine_video.list | 3 |
11 files changed, 43 insertions, 1175 deletions
diff --git a/src/combined/ffmpeg/Makefile.am b/src/combined/ffmpeg/Makefile.am index 24cab7577..773353096 100644 --- a/src/combined/ffmpeg/Makefile.am +++ b/src/combined/ffmpeg/Makefile.am @@ -1,74 +1,47 @@ +include $(top_srcdir)/misc/Makefile.quiet include $(top_builddir)/misc/Makefile.plugins include $(top_srcdir)/misc/Makefile.common -DEFAULT_INCLUDES = -I. +AM_CFLAGS = $(DEFAULT_OCFLAGS) $(VISIBILITY_FLAG) +AM_CPPFLAGS = $(ZLIB_CPPFLAGS) +AM_LDFLAGS = $(xineplug_ldflags) -if HAVE_FFMPEG -ff_cppflags = $(FFMPEG_CFLAGS) $(FFMPEG_POSTPROC_CFLAGS) -link_ffmpeg = $(FFMPEG_LIBS) $(FFMPEG_UTIL_LIBS) $(FFMPEG_POSTPROC_LIBS) -else -ff_cppflags = -I$(top_builddir)/src/libffmpeg -I$(top_srcdir)/src/libffmpeg/libavcodec -I$(top_srcdir)/src/libffmpeg/libavutil -link_ffmpeg = \ - $(top_builddir)/src/libffmpeg/libavcodec/libavcodec.la \ - $(top_builddir)/src/libffmpeg/libavutil/libavutil.la \ - $(top_builddir)/src/libffmpeg/libavcodec/libpostproc/libpostprocess.la -endif +xineplug_LTLIBRARIES = xineplug_decode_ff.la ff_generated = \ avcodec_video.list avcodec_audio.list \ ff_video_list.h ff_audio_list.h BUILT_SOURCES = $(ff_generated) +DISTCLEANFILES = $(ff_generated) -# ffmpeg_config.h is generated by configure -DISTCLEANFILES = ffmpeg_config.h $(ff_generated) +EXTRA_DIST = xine_video.list xine_audio.list mkcodeclist.pl -# this must always be included, even if the current machine has no DXR3... -EXTRA_DIST = ffmpeg_encoder.c \ - xine_video.list xine_audio.list mkcodeclist.pl - -xineplug_LTLIBRARIES = xineplug_decode_ff.la xineplug_decode_dvaudio.la - -if HAVE_DXR3 -AM_CPPFLAGS = -I$(top_srcdir)/src/dxr3 $(X_CFLAGS) $(ff_cppflags) \ - $(ZLIB_CPPFLAGS) -xineplug_decode_ff_la_SOURCES = ffmpeg_decoder.c ff_audio_decoder.c ff_video_decoder.c \ - ffmpeg_encoder.c ff_mpeg_parser.c ffmpeg_decoder.h \ - ff_mpeg_parser.h -else -AM_CPPFLAGS = $(ff_cppflags) $(ZLIB_CPPFLAGS) xineplug_decode_ff_la_SOURCES = ffmpeg_decoder.c ff_audio_decoder.c ff_video_decoder.c \ ff_mpeg_parser.c ffmpeg_decoder.h ff_mpeg_parser.h -endif -xineplug_decode_ff_la_CFLAGS = $(VISIBILITY_FLAG) $(AM_CFLAGS) -xineplug_decode_ff_la_LDFLAGS = $(xineplug_ldflags) $(IMPURE_TEXT_LDFLAGS) -xineplug_decode_ff_la_LIBADD = $(XINE_LIB) $(MLIB_LIBS) -lm $(ZLIB_LIBS) \ - $(link_ffmpeg) $(PTHREAD_LIBS) $(LTLIBINTL) - -xineplug_decode_dvaudio_la_CFLAGS = $(VISIBILITY_FLAG) $(AM_CFLAGS) -xineplug_decode_dvaudio_la_LDFLAGS = $(xineplug_ldflags) -xineplug_decode_dvaudio_la_SOURCES = ff_dvaudio_decoder.c -xineplug_decode_dvaudio_la_LIBADD = $(XINE_LIB) $(LTLIBINTL) +nodist_xineplug_decode_ff_la_SOURCES = ffmpeg_config.h -$(top_srcdir)/src/libffmpeg/libavcodec/libavcodec.la: - make -C $(top_srcdir)/src/libffmpeg +xineplug_decode_ff_la_CFLAGS = $(AM_CFLAGS) $(FFMPEG_CFLAGS) $(FFMPEG_POSTPROC_CFLAGS) +xineplug_decode_ff_la_LIBADD = $(XINE_LIB) $(MLIB_LIBS) -lm $(ZLIB_LIBS) \ + $(FFMPEG_LIBS) $(AVUTIL_LIBS) $(FFMPEG_POSTPROC_LIBS) $(PTHREAD_LIBS) $(LTLIBINTL) +xineplug_decode_ff_la_LDFLAGS = $(AM_LDFLAGS) $(IMPURE_TEXT_LDFLAGS) # Generation of ffmpeg->xine codec mapping lists (see xine_*.list). -AV_CPP = $(CPP) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) +AV_CPP = $(CPP) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AVUTIL_CFLAGS) # Extract some CODEC_ID_* from avcodec.h. Requires some sed mangling. avcodec_audio.list: AV_CODECS:=/CODEC_ID_PCM_S16LE/,/CODEC_ID_DVD_SUBTITLE/ avcodec_video.list: AV_CODECS:=/CODEC_ID_MPEG1VIDEO/,/CODEC_ID_PCM_S16LE/ avcodec_audio.list avcodec_video.list: - echo '#include "$(srcdir)/ffmpeg_decoder.h"' | $(AV_CPP) - |\ + $(AM_V_GEN)echo '#include "$(srcdir)/ffmpeg_decoder.h"' | $(AV_CPP) - |\ sed -e $(AV_CODECS)'! d; s/^[ \t]*//; s/[=,].*//; /^$$/ d' >$@ # Generate the mappings. These are #included where needed. ff_%_list.h: $(srcdir)/mkcodeclist.pl avcodec_%.list $(srcdir)/xine_%.list - $(PERL) $^ $@ + $(AM_V_GEN)$(PERL) $^ $@ ff_audio_decoder.c: ff_audio_list.h ff_video_decoder.c: ff_video_list.h diff --git a/src/combined/ffmpeg/ff_audio_decoder.c b/src/combined/ffmpeg/ff_audio_decoder.c index e4a9c16bf..a45d57c69 100644 --- a/src/combined/ffmpeg/ff_audio_decoder.c +++ b/src/combined/ffmpeg/ff_audio_decoder.c @@ -22,7 +22,6 @@ #ifdef HAVE_CONFIG_H #include "config.h" -#include "../../libffmpeg/ffmpeg_config.h" #endif #include <stdlib.h> @@ -38,9 +37,9 @@ #define LOG */ -#include "xine_internal.h" -#include "buffer.h" -#include "xineutils.h" +#include <xine/xine_internal.h> +#include <xine/buffer.h> +#include <xine/xineutils.h> #include "bswap.h" #include "ffmpeg_decoder.h" @@ -653,18 +652,6 @@ static audio_decoder_t *ff_audio_open_plugin (audio_decoder_class_t *class_gen, return &this->audio_decoder; } -static char *ff_audio_get_identifier (audio_decoder_class_t *this) { - return "ffmpeg audio"; -} - -static char *ff_audio_get_description (audio_decoder_class_t *this) { - return "ffmpeg based audio decoder plugin"; -} - -static void ff_audio_dispose_class (audio_decoder_class_t *this) { - free (this); -} - void *init_audio_plugin (xine_t *xine, void *data) { ff_audio_class_t *this ; @@ -672,9 +659,9 @@ void *init_audio_plugin (xine_t *xine, void *data) { this = calloc(1, sizeof (ff_audio_class_t)); this->decoder_class.open_plugin = ff_audio_open_plugin; - this->decoder_class.get_identifier = ff_audio_get_identifier; - this->decoder_class.get_description = ff_audio_get_description; - this->decoder_class.dispose = ff_audio_dispose_class; + this->decoder_class.identifier = "ffmpeg audio"; + this->decoder_class.description = N_("ffmpeg based audio decoder plugin"); + this->decoder_class.dispose = default_audio_decoder_class_dispose; pthread_once( &once_control, init_once_routine ); diff --git a/src/combined/ffmpeg/ff_dvaudio_decoder.c b/src/combined/ffmpeg/ff_dvaudio_decoder.c deleted file mode 100644 index 4d78162df..000000000 --- a/src/combined/ffmpeg/ff_dvaudio_decoder.c +++ /dev/null @@ -1,432 +0,0 @@ -/* - * Copyright (C) 2005 the xine project - * - * This file is part of xine, a free video player. - * - * xine is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * xine is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA - * - * dv audio decoder based on patch by Dan Dennedy <dan@dennedy.org> - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include <stdlib.h> -#include <stdio.h> -#include <inttypes.h> -#include <string.h> -#include <math.h> - -#define LOG_MODULE "dvaudio" -#define LOG_VERBOSE -/* -#define LOG -*/ - -#include "xine_internal.h" -#include "buffer.h" -#include "xineutils.h" - -#ifdef _MSC_VER -/* ffmpeg has own definitions of those types */ -# undef int8_t -# undef uint8_t -# undef int16_t -# undef uint16_t -# undef int32_t -# undef uint32_t -# undef int64_t -# undef uint64_t -#endif - -#ifdef HAVE_FFMPEG_AVUTIL_H -# include <avcodec.h> -#elif defined HAVE_FFMPEG -# include <libavcodec/avcodec.h> -#else -# include "../../libffmpeg/libavcodec/avcodec.h" -#endif - -#include "../../libffmpeg/libavcodec/dvdata.h" - -#ifdef _MSC_VER -# undef malloc -# undef free -# undef realloc -#endif - -#define AUDIOBUFSIZE 128*1024 -#define MAXFRAMESIZE 131072 - - -typedef struct { - audio_decoder_class_t decoder_class; -} dvaudio_class_t; - -typedef struct dvaudio_decoder_s { - audio_decoder_t audio_decoder; - - xine_stream_t *stream; - - int output_open; - int audio_channels; - int audio_bits; - int audio_sample_rate; - - unsigned char *buf; - int bufsize; - int size; - - char *decode_buffer; - int decoder_ok; - -} dvaudio_decoder_t; - - -/* - * This is the dumbest implementation of all -- it simply looks at - * a fixed offset and if pack isn't there -- fails. We might want - * to have a fallback mechanism for complete search of missing packs. - */ -static const uint8_t* dv_extract_pack(uint8_t* frame, enum dv_pack_type t) -{ - int offs; - - switch (t) { - case dv_audio_source: - offs = (80*6 + 80*16*3 + 3); - break; - case dv_audio_control: - offs = (80*6 + 80*16*4 + 3); - break; - case dv_video_control: - offs = (80*5 + 48 + 5); - break; - default: - return NULL; - } - - return (frame[offs] == t ? &frame[offs] : NULL); -} - -static inline uint16_t dv_audio_12to16(uint16_t sample) -{ - uint16_t shift, result; - - sample = (sample < 0x800) ? sample : sample | 0xf000; - shift = (sample & 0xf00) >> 8; - - if (shift < 0x2 || shift > 0xd) { - result = sample; - } else if (shift < 0x8) { - shift--; - result = (sample - (256 * shift)) << shift; - } else { - shift = 0xe - shift; - result = ((sample + ((256 * shift) + 1)) << shift) - 1; - } - - return result; -} - -/* - * There's a couple of assumptions being made here: - * 1. By default we silence erroneous (0x8000/16bit 0x800/12bit) audio samples. - * We can pass them upwards when ffmpeg will be ready to deal with them. - * 2. We don't do software emphasis. - * 3. Audio is always returned as 16bit linear samples: 12bit nonlinear samples - * are converted into 16bit linear ones. - */ -static int dv_extract_audio(uint8_t* frame, uint8_t* pcm, uint8_t* pcm2) -{ - int size, i, j, d, of, smpls, freq, quant, half_ch; - uint16_t lc, rc; - const DVprofile* sys; - const uint8_t* as_pack; - - as_pack = dv_extract_pack(frame, dv_audio_source); - if (!as_pack) /* No audio ? */ - return 0; - - sys = dv_frame_profile(frame); - smpls = as_pack[1] & 0x3f; /* samples in this frame - min. samples */ - freq = (as_pack[4] >> 3) & 0x07; /* 0 - 48KHz, 1 - 44,1kHz, 2 - 32 kHz */ - quant = as_pack[4] & 0x07; /* 0 - 16bit linear, 1 - 12bit nonlinear */ - - if (quant > 1) - return -1; /* Unsupported quantization */ - - size = (sys->audio_min_samples[freq] + smpls) * 4; /* 2ch, 2bytes */ - half_ch = sys->difseg_size/2; - - /* for each DIF segment */ - for (i = 0; i < sys->difseg_size; i++) { - frame += 6 * 80; /* skip DIF segment header */ - if (quant == 1 && i == half_ch) { - if (!pcm2) - break; - else - pcm = pcm2; - } - - for (j = 0; j < 9; j++) { - for (d = 8; d < 80; d += 2) { - if (quant == 0) { /* 16bit quantization */ - of = sys->audio_shuffle[i][j] + (d - 8)/2 * sys->audio_stride; - if (of*2 >= size) - continue; - -#ifdef WORDS_BIGENDIAN - pcm[of*2] = frame[d]; - pcm[of*2+1] = frame[d+1]; -#else - pcm[of*2] = frame[d+1]; - pcm[of*2+1] = frame[d]; -#endif - if (pcm[of*2+1] == 0x80 && pcm[of*2] == 0x00) - pcm[of*2+1] = 0; - } else { /* 12bit quantization */ - lc = ((uint16_t)frame[d] << 4) | - ((uint16_t)frame[d+2] >> 4); - rc = ((uint16_t)frame[d+1] << 4) | - ((uint16_t)frame[d+2] & 0x0f); - lc = (lc == 0x800 ? 0 : dv_audio_12to16(lc)); - rc = (rc == 0x800 ? 0 : dv_audio_12to16(rc)); - - of = sys->audio_shuffle[i%half_ch][j] + (d - 8)/3 * sys->audio_stride; - if (of*2 >= size) - continue; - -#ifdef WORDS_BIGENDIAN - pcm[of*2] = lc >> 8; - pcm[of*2+1] = lc & 0xff; -#else - pcm[of*2] = lc & 0xff; - pcm[of*2+1] = lc >> 8; -#endif - of = sys->audio_shuffle[i%half_ch+half_ch][j] + - (d - 8)/3 * sys->audio_stride; -#ifdef WORDS_BIGENDIAN - pcm[of*2] = rc >> 8; - pcm[of*2+1] = rc & 0xff; -#else - pcm[of*2] = rc & 0xff; - pcm[of*2+1] = rc >> 8; -#endif - ++d; - } - } - - frame += 16 * 80; /* 15 Video DIFs + 1 Audio DIF */ - } - } - - return size; -} - -static void dvaudio_decode_data (audio_decoder_t *this_gen, buf_element_t *buf) { - - dvaudio_decoder_t *this = (dvaudio_decoder_t *) this_gen; - int bytes_consumed; - int decode_buffer_size; - int offset; - int out; - audio_buffer_t *audio_buffer; - int bytes_to_send; - - if (buf->decoder_flags & BUF_FLAG_PREVIEW) - return; - - if (buf->decoder_flags & BUF_FLAG_STDHEADER) { - this->buf = calloc(1, AUDIOBUFSIZE); - this->bufsize = AUDIOBUFSIZE; - this->size = 0; - this->decode_buffer = calloc(1, MAXFRAMESIZE); - - this->audio_sample_rate = buf->decoder_info[1]; - this->audio_bits = buf->decoder_info[2]; - this->audio_channels = buf->decoder_info[3]; - - _x_meta_info_set_utf8(this->stream, XINE_META_INFO_AUDIOCODEC, "DV Audio"); - - this->decoder_ok = 1; - - return; - } - - if (this->decoder_ok && !(buf->decoder_flags & (BUF_FLAG_HEADER|BUF_FLAG_SPECIAL))) { - - if (!this->output_open) { - this->output_open = (this->stream->audio_out->open) (this->stream->audio_out, - this->stream, this->audio_bits, this->audio_sample_rate, - _x_ao_channels2mode(this->audio_channels)); - } - - /* if the audio still isn't open, bail */ - if (!this->output_open) - return; - - if( this->size + buf->size > this->bufsize ) { - this->bufsize = this->size + 2 * buf->size; - xprintf(this->stream->xine, XINE_VERBOSITY_LOG, - _("dvaudio: increasing buffer to %d to avoid overflow.\n"), - this->bufsize); - this->buf = realloc( this->buf, this->bufsize ); - } - - xine_fast_memcpy (&this->buf[this->size], buf->content, buf->size); - this->size += buf->size; - - if (buf->decoder_flags & BUF_FLAG_FRAME_END) { /* time to decode a frame */ - - offset = 0; - while (this->size>0) { - decode_buffer_size = dv_extract_audio(&this->buf[offset], this->decode_buffer, NULL); - - if (decode_buffer_size > -1) - bytes_consumed = dv_frame_profile(&this->buf[offset])->frame_size; - else - bytes_consumed = decode_buffer_size; - - /* dispatch the decoded audio */ - out = 0; - while (out < decode_buffer_size) { - audio_buffer = - this->stream->audio_out->get_buffer (this->stream->audio_out); - if (audio_buffer->mem_size == 0) { - xprintf (this->stream->xine, XINE_VERBOSITY_DEBUG, - "dvaudio: Help! Allocated audio buffer with nothing in it!\n"); - return; - } - - if ((decode_buffer_size - out) > audio_buffer->mem_size) - bytes_to_send = audio_buffer->mem_size; - else - bytes_to_send = decode_buffer_size - out; - - /* fill up this buffer */ - xine_fast_memcpy(audio_buffer->mem, &this->decode_buffer[out], - bytes_to_send); - /* byte count / 2 (bytes / sample) / channels */ - audio_buffer->num_frames = bytes_to_send / 2 / this->audio_channels; - - audio_buffer->vpts = buf->pts; - buf->pts = 0; /* only first buffer gets the real pts */ - this->stream->audio_out->put_buffer (this->stream->audio_out, - audio_buffer, this->stream); - - out += bytes_to_send; - } - - this->size -= bytes_consumed; - offset += bytes_consumed; - } - - /* reset internal accumulation buffer */ - this->size = 0; - } - } -} - -static void dvaudio_reset (audio_decoder_t *this_gen) { - dvaudio_decoder_t *this = (dvaudio_decoder_t *) this_gen; - - this->size = 0; -} - -static void dvaudio_discontinuity (audio_decoder_t *this_gen) { -} - -static void dvaudio_dispose (audio_decoder_t *this_gen) { - - dvaudio_decoder_t *this = (dvaudio_decoder_t *) this_gen; - - if (this->output_open) - this->stream->audio_out->close (this->stream->audio_out, this->stream); - this->output_open = 0; - - free(this->buf); - free(this->decode_buffer); - - free (this_gen); -} - -static audio_decoder_t *dvaudio_open_plugin (audio_decoder_class_t *class_gen, xine_stream_t *stream) { - - dvaudio_decoder_t *this ; - - this = calloc(1, sizeof (dvaudio_decoder_t)); - - this->audio_decoder.decode_data = dvaudio_decode_data; - this->audio_decoder.reset = dvaudio_reset; - this->audio_decoder.discontinuity = dvaudio_discontinuity; - this->audio_decoder.dispose = dvaudio_dispose; - - this->output_open = 0; - this->audio_channels = 0; - this->stream = stream; - this->buf = NULL; - this->size = 0; - this->decoder_ok = 0; - - return &this->audio_decoder; -} - -static char *dvaudio_get_identifier (audio_decoder_class_t *this) { - return "dv audio"; -} - -static char *dvaudio_get_description (audio_decoder_class_t *this) { - return "dv audio decoder plugin"; -} - -static void dvaudio_dispose_class (audio_decoder_class_t *this) { - free (this); -} - -static void *init_dvaudio_plugin (xine_t *xine, void *data) { - - dvaudio_class_t *this ; - - this = calloc(1, sizeof (dvaudio_class_t)); - - this->decoder_class.open_plugin = dvaudio_open_plugin; - this->decoder_class.get_identifier = dvaudio_get_identifier; - this->decoder_class.get_description = dvaudio_get_description; - this->decoder_class.dispose = dvaudio_dispose_class; - - return this; -} - -static uint32_t supported_audio_types[] = { - BUF_AUDIO_DV, - 0 -}; - -static const decoder_info_t dec_info_dvaudio = { - supported_audio_types, /* supported types */ - 5 /* priority */ -}; - -/* - * exported plugin catalog entry - */ - -const plugin_info_t xine_plugin_info[] EXPORTED = { - /* type, API, "name", version, special_info, init_function */ - { PLUGIN_AUDIO_DECODER, 15, "dvaudio", XINE_VERSION_CODE, &dec_info_dvaudio, init_dvaudio_plugin }, - { PLUGIN_NONE, 0, "", 0, NULL, NULL } -}; diff --git a/src/combined/ffmpeg/ff_mpeg_parser.h b/src/combined/ffmpeg/ff_mpeg_parser.h index 5797933df..c1ebc326f 100644 --- a/src/combined/ffmpeg/ff_mpeg_parser.h +++ b/src/combined/ffmpeg/ff_mpeg_parser.h @@ -23,7 +23,7 @@ #ifndef HAVE_MPEG_PARSER_H #define HAVE_MPEG_PARSER_H -#include "xine_internal.h" +#include <xine/xine_internal.h> #include "ffmpeg_decoder.h" #define BUFFER_SIZE (1194 * 1024) /* libmpeg2's buffer size */ diff --git a/src/combined/ffmpeg/ff_video_decoder.c b/src/combined/ffmpeg/ff_video_decoder.c index a1d729df4..c75848bee 100644 --- a/src/combined/ffmpeg/ff_video_decoder.c +++ b/src/combined/ffmpeg/ff_video_decoder.c @@ -22,7 +22,6 @@ #ifdef HAVE_CONFIG_H #include "config.h" -#include "../../libffmpeg/ffmpeg_config.h" #endif #include <stdlib.h> @@ -38,10 +37,10 @@ /* #define LOG */ -#include "xine_internal.h" +#include <xine/xine_internal.h> #include "bswap.h" -#include "buffer.h" -#include "xineutils.h" +#include <xine/buffer.h> +#include <xine/xineutils.h> #include "ffmpeg_decoder.h" #include "ff_mpeg_parser.h" @@ -70,12 +69,6 @@ # define DEPRECATED_AVCODEC_THREAD_INIT 1 #endif -/* reordered_opaque appeared in libavcodec 51.68.0 */ -#define AVCODEC_HAS_REORDERED_OPAQUE -#if LIBAVCODEC_VERSION_INT < 0x334400 -# undef AVCODEC_HAS_REORDERED_OPAQUE -#endif - typedef struct ff_video_decoder_s ff_video_decoder_t; typedef struct ff_video_class_s { @@ -96,12 +89,10 @@ struct ff_video_decoder_s { xine_stream_t *stream; int64_t pts; -#ifdef AVCODEC_HAS_REORDERED_OPAQUE uint64_t pts_tag_mask; uint64_t pts_tag; int pts_tag_counter; int pts_tag_stable_counter; -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ int video_step; int reported_video_step; @@ -237,10 +228,8 @@ static int get_buffer(AVCodecContext *context, AVFrame *av_frame){ av_frame->type= FF_BUFFER_TYPE_USER; -#ifdef AVCODEC_HAS_REORDERED_OPAQUE /* take over pts for this frame to have it reordered */ av_frame->reordered_opaque = context->reordered_opaque; -#endif xine_list_push_back(this->dr1_frames, av_frame); @@ -1225,7 +1214,6 @@ static void ff_handle_mpeg12_buffer (ff_video_decoder_t *this, buf_element_t *bu } } -#ifdef AVCODEC_HAS_REORDERED_OPAQUE static uint64_t ff_tag_pts(ff_video_decoder_t *this, uint64_t pts) { return pts | this->pts_tag; @@ -1271,7 +1259,6 @@ static void ff_check_pts_tagging(ff_video_decoder_t *this, uint64_t pts) } } } -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { uint8_t *chunk_buf = this->buf; @@ -1300,7 +1287,6 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { this->size = 0; } -#ifdef AVCODEC_HAS_REORDERED_OPAQUE if (this->size == 0) { /* take over pts when we are about to buffer a frame */ this->av_frame->reordered_opaque = ff_tag_pts(this, this->pts); @@ -1308,7 +1294,6 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { this->context->reordered_opaque = ff_tag_pts(this, this->pts); this->pts = 0; } -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ /* data accumulation */ if (buf->size > 0) { @@ -1375,10 +1360,8 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { &got_picture, &chunk_buf[offset], this->size); #endif -#ifdef AVCODEC_HAS_REORDERED_OPAQUE /* reset consumed pts value */ this->context->reordered_opaque = ff_tag_pts(this, 0); -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ lprintf("consumed size: %d, got_picture: %d\n", len, got_picture); if ((len <= 0) || (len > this->size)) { @@ -1396,12 +1379,10 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { memmove (this->buf, &chunk_buf[offset], this->size); chunk_buf = this->buf; -#ifdef AVCODEC_HAS_REORDERED_OPAQUE /* take over pts for next access unit */ this->av_frame->reordered_opaque = ff_tag_pts(this, this->pts); this->context->reordered_opaque = ff_tag_pts(this, this->pts); this->pts = 0; -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ } } } @@ -1410,11 +1391,7 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { video_step_to_use = (this->video_step || !this->context->time_base.den) ? this->video_step : (int)(90000ll -#if LIBAVCODEC_VERSION_INT >= 0x341400 * this->context->ticks_per_frame -#elif LIBAVCODEC_VERSION_INT >= 0x340000 -# warning Building without avcodec ticks_per_frame support; you should upgrade your libavcodec and recompile -#endif * this->context->time_base.num / this->context->time_base.den); /* aspect ratio provided by ffmpeg, override previous setting */ @@ -1504,14 +1481,9 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { ff_convert_frame(this, img); } -#ifndef AVCODEC_HAS_REORDERED_OPAQUE - img->pts = this->pts; - this->pts = 0; -#else /* AVCODEC_HAS_REORDERED_OPAQUE */ img->pts = ff_untag_pts(this, this->av_frame->reordered_opaque); ff_check_pts_tagging(this, this->av_frame->reordered_opaque); /* only check for valid frames */ this->av_frame->reordered_opaque = 0; -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ /* workaround for weird 120fps streams */ if( video_step_to_use == 750 ) { @@ -1554,13 +1526,8 @@ static void ff_handle_buffer (ff_video_decoder_t *this, buf_element_t *buf) { this->output_format, VO_BOTH_FIELDS|this->frame_flags); /* set PTS to allow early syncing */ -#ifndef AVCODEC_HAS_REORDERED_OPAQUE - img->pts = this->pts; - this->pts = 0; -#else /* AVCODEC_HAS_REORDERED_OPAQUE */ img->pts = ff_untag_pts(this, this->av_frame->reordered_opaque); this->av_frame->reordered_opaque = 0; -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ img->duration = video_step_to_use; @@ -1614,6 +1581,8 @@ static void ff_decode_data (video_decoder_t *this_gen, buf_element_t *buf) { } } else { + if (this->decoder_init_mode && !this->is_mpeg12) + ff_handle_preview_buffer(this, buf); /* decode */ if (buf->pts) @@ -1646,12 +1615,10 @@ static void ff_reset (video_decoder_t *this_gen) { if (this->is_mpeg12) mpeg_parser_reset(this->mpeg_parser); -#ifdef AVCODEC_HAS_REORDERED_OPAQUE this->pts_tag_mask = 0; this->pts_tag = 0; this->pts_tag_counter = 0; this->pts_tag_stable_counter = 0; -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ } static void ff_discontinuity (video_decoder_t *this_gen) { @@ -1660,7 +1627,6 @@ static void ff_discontinuity (video_decoder_t *this_gen) { lprintf ("ff_discontinuity\n"); this->pts = 0; -#ifdef AVCODEC_HAS_REORDERED_OPAQUE /* * there is currently no way to reset all the pts which are stored in the decoder. * therefore, we add a unique tag (generated from pts_tag_counter) to pts (see @@ -1693,7 +1659,6 @@ static void ff_discontinuity (video_decoder_t *this_gen) { counter_mask <<= 1; } } -#endif /* AVCODEC_HAS_REORDERED_OPAQUE */ } static void ff_dispose (video_decoder_t *this_gen) { @@ -1799,18 +1764,6 @@ static video_decoder_t *ff_video_open_plugin (video_decoder_class_t *class_gen, return &this->video_decoder; } -static char *ff_video_get_identifier (video_decoder_class_t *this) { - return "ffmpeg video"; -} - -static char *ff_video_get_description (video_decoder_class_t *this) { - return "ffmpeg based video decoder plugin"; -} - -static void ff_video_dispose_class (video_decoder_class_t *this) { - free (this); -} - void *init_video_plugin (xine_t *xine, void *data) { ff_video_class_t *this; @@ -1819,9 +1772,9 @@ void *init_video_plugin (xine_t *xine, void *data) { this = calloc(1, sizeof (ff_video_class_t)); this->decoder_class.open_plugin = ff_video_open_plugin; - this->decoder_class.get_identifier = ff_video_get_identifier; - this->decoder_class.get_description = ff_video_get_description; - this->decoder_class.dispose = ff_video_dispose_class; + this->decoder_class.identifier = "ffmpeg video"; + this->decoder_class.description = N_("ffmpeg based video decoder plugin"); + this->decoder_class.dispose = default_video_decoder_class_dispose; this->xine = xine; pthread_once( &once_control, init_once_routine ); @@ -1870,12 +1823,12 @@ void *init_video_plugin (xine_t *xine, void *data) { return this; } -static uint32_t wmv8_video_types[] = { +static const uint32_t wmv8_video_types[] = { BUF_VIDEO_WMV8, 0 }; -static uint32_t wmv9_video_types[] = { +static const uint32_t wmv9_video_types[] = { BUF_VIDEO_WMV9, 0 }; diff --git a/src/combined/ffmpeg/ffmpeg_decoder.c b/src/combined/ffmpeg/ffmpeg_decoder.c index b50633053..4f9a0f7a4 100644 --- a/src/combined/ffmpeg/ffmpeg_decoder.c +++ b/src/combined/ffmpeg/ffmpeg_decoder.c @@ -22,10 +22,9 @@ #ifdef HAVE_CONFIG_H #include "config.h" -#include "../../libffmpeg/ffmpeg_config.h" #endif -#include "xine_internal.h" +#include <xine/xine_internal.h> #include "ffmpeg_decoder.h" @@ -36,279 +35,6 @@ pthread_once_t once_control = PTHREAD_ONCE_INIT; pthread_mutex_t ffmpeg_lock; -#ifndef HAVE_FFMPEG - -#define REGISTER_ENCODER(X,x) \ - if(ENABLE_##X##_ENCODER) register_avcodec(&x##_encoder) -#define REGISTER_DECODER(X,x) \ - if(ENABLE_##X##_DECODER) register_avcodec(&x##_decoder) -#define REGISTER_ENCDEC(X,x) REGISTER_ENCODER(X,x); REGISTER_DECODER(X,x) - -#define REGISTER_PARSER(X,x) \ - if(ENABLE_##X##_PARSER) av_register_codec_parser(&x##_parser) - -/* If you do not call this function, then you can select exactly which - formats you want to support */ - -/** - * simple call to register all the codecs. - */ -void avcodec_register_all(void) -{ - static int inited = 0; - - if (inited != 0) - return; - inited = 1; - - /* video codecs */ - REGISTER_DECODER(AASC, aasc); - REGISTER_ENCDEC (ASV1, asv1); - REGISTER_ENCDEC (ASV2, asv2); - REGISTER_DECODER(AVS, avs); - REGISTER_DECODER(BMP, bmp); - REGISTER_DECODER(CAVS, cavs); - REGISTER_DECODER(CINEPAK, cinepak); - REGISTER_DECODER(CLJR, cljr); - REGISTER_DECODER(CSCD, cscd); - REGISTER_DECODER(CYUV, cyuv); - REGISTER_DECODER(DSICINVIDEO, dsicinvideo); - REGISTER_ENCDEC (DVVIDEO, dvvideo); - REGISTER_DECODER(EIGHTBPS, eightbps); - REGISTER_ENCDEC (FFV1, ffv1); - REGISTER_ENCDEC (FFVHUFF, ffvhuff); - REGISTER_DECODER(FLASHSV, flashsv); - REGISTER_DECODER(FLIC, flic); - REGISTER_ENCDEC (FLV, flv); - REGISTER_DECODER(FOURXM, fourxm); - REGISTER_DECODER(FRAPS, fraps); - REGISTER_ENCDEC (GIF, gif); - REGISTER_ENCDEC (H261, h261); - REGISTER_ENCDEC (H263, h263); - REGISTER_DECODER(H263I, h263i); - REGISTER_ENCODER(H263P, h263p); - REGISTER_DECODER(H264, h264); - REGISTER_ENCDEC (HUFFYUV, huffyuv); - REGISTER_DECODER(IDCIN, idcin); - REGISTER_DECODER(INDEO2, indeo2); - REGISTER_DECODER(INDEO3, indeo3); - REGISTER_DECODER(INTERPLAY_VIDEO, interplay_video); - REGISTER_ENCODER(JPEGLS, jpegls); - REGISTER_DECODER(KMVC, kmvc); - REGISTER_ENCODER(LJPEG, ljpeg); - REGISTER_DECODER(LOCO, loco); - REGISTER_DECODER(MDEC, mdec); - REGISTER_ENCDEC (MJPEG, mjpeg); - REGISTER_DECODER(MJPEGB, mjpegb); - REGISTER_DECODER(MMVIDEO, mmvideo); -#ifdef HAVE_XVMC - REGISTER_DECODER(MPEG_XVMC, mpeg_xvmc); -#endif - REGISTER_ENCDEC (MPEG1VIDEO, mpeg1video); - REGISTER_ENCDEC (MPEG2VIDEO, mpeg2video); - REGISTER_ENCDEC (MPEG4, mpeg4); - REGISTER_DECODER(MPEGVIDEO, mpegvideo); - REGISTER_ENCDEC (MSMPEG4V1, msmpeg4v1); - REGISTER_ENCDEC (MSMPEG4V2, msmpeg4v2); - REGISTER_ENCDEC (MSMPEG4V3, msmpeg4v3); - REGISTER_DECODER(MSRLE, msrle); - REGISTER_DECODER(MSVIDEO1, msvideo1); - REGISTER_DECODER(MSZH, mszh); - REGISTER_DECODER(NUV, nuv); - REGISTER_ENCODER(PAM, pam); - REGISTER_ENCODER(PBM, pbm); - REGISTER_ENCODER(PGM, pgm); - REGISTER_ENCODER(PGMYUV, pgmyuv); -#ifdef CONFIG_ZLIB - REGISTER_ENCDEC (PNG, png); -#endif - REGISTER_ENCODER(PPM, ppm); - REGISTER_DECODER(QDRAW, qdraw); - REGISTER_DECODER(QPEG, qpeg); - REGISTER_DECODER(QTRLE, qtrle); - REGISTER_ENCDEC (RAWVIDEO, rawvideo); - REGISTER_DECODER(ROQ, roq); - REGISTER_DECODER(RPZA, rpza); - REGISTER_ENCDEC (RV10, rv10); - REGISTER_ENCDEC (RV20, rv20); - REGISTER_DECODER(SMACKER, smacker); - REGISTER_DECODER(SMC, smc); - REGISTER_ENCDEC (SNOW, snow); - REGISTER_DECODER(SP5X, sp5x); - REGISTER_ENCDEC (SVQ1, svq1); - REGISTER_DECODER(SVQ3, svq3); - REGISTER_DECODER(TARGA, targa); - REGISTER_DECODER(THEORA, theora); - REGISTER_DECODER(TIERTEXSEQVIDEO, tiertexseqvideo); - REGISTER_DECODER(TIFF, tiff); - REGISTER_DECODER(TRUEMOTION1, truemotion1); - REGISTER_DECODER(TRUEMOTION2, truemotion2); - REGISTER_DECODER(TSCC, tscc); - REGISTER_DECODER(ULTI, ulti); - REGISTER_DECODER(VC1, vc1); - REGISTER_DECODER(VCR1, vcr1); - REGISTER_DECODER(VMDVIDEO, vmdvideo); - REGISTER_DECODER(VMNC, vmnc); - REGISTER_DECODER(VP3, vp3); - REGISTER_DECODER(VP5, vp5); - REGISTER_DECODER(VP6, vp6); - REGISTER_DECODER(VP6F, vp6f); - REGISTER_DECODER(VQA, vqa); - REGISTER_ENCDEC (WMV1, wmv1); - REGISTER_ENCDEC (WMV2, wmv2); - REGISTER_DECODER(WMV3, wmv3); - REGISTER_DECODER(WNV1, wnv1); -#ifdef CONFIG_X264 - REGISTER_ENCODER(X264, x264); -#endif - REGISTER_DECODER(XAN_WC3, xan_wc3); - REGISTER_DECODER(XL, xl); -#ifdef CONFIG_XVID - REGISTER_ENCODER(XVID, xvid); -#endif - REGISTER_ENCDEC (ZLIB, zlib); -#ifdef CONFIG_ZLIB - REGISTER_ENCDEC (ZMBV, zmbv); -#endif - - /* audio codecs */ -#ifdef CONFIG_LIBFAAD - REGISTER_DECODER(AAC, aac); - REGISTER_DECODER(MPEG4AAC, mpeg4aac); -#endif -#ifdef CONFIG_LIBA52 - REGISTER_DECODER(AC3, ac3); -#endif - REGISTER_ENCODER(AC3, ac3); -#ifdef CODEC_ID_EAC3 - REGISTER_DECODER(EAC3, eac3); -#endif - REGISTER_DECODER(ALAC, alac); -#if defined(CONFIG_AMR_NB) || defined(CONFIG_AMR_NB_FIXED) - REGISTER_ENCDEC (AMR_NB, amr_nb); -#endif -#ifdef CONFIG_AMR_WB - REGISTER_ENCDEC (AMR_WB, amr_wb); -#endif - REGISTER_DECODER(COOK, cook); - REGISTER_DECODER(DSICINAUDIO, dsicinaudio); -#ifdef CONFIG_LIBDTS - REGISTER_DECODER(DTS, dts); -#endif -#ifdef CONFIG_LIBFAAC - REGISTER_ENCODER(FAAC, faac); -#endif - REGISTER_ENCDEC (FLAC, flac); - REGISTER_DECODER(IMC, imc); -#ifdef CONFIG_LIBGSM - REGISTER_ENCDEC (LIBGSM, libgsm); -#endif - REGISTER_DECODER(MACE3, mace3); - REGISTER_DECODER(MACE6, mace6); - REGISTER_ENCDEC (MP2, mp2); - REGISTER_DECODER(MP3, mp3); - REGISTER_DECODER(MP3ADU, mp3adu); -#ifdef CONFIG_LIBMP3LAME - REGISTER_ENCODER(MP3LAME, mp3lame); -#endif - REGISTER_DECODER(MP3ON4, mp3on4); - REGISTER_DECODER(MPC7, mpc7); -#ifdef CONFIG_LIBVORBIS - if (!ENABLE_VORBIS_ENCODER) REGISTER_ENCODER(OGGVORBIS, oggvorbis); - if (!ENABLE_VORBIS_DECODER) REGISTER_DECODER(OGGVORBIS, oggvorbis); -#endif - REGISTER_DECODER(QDM2, qdm2); - REGISTER_DECODER(RA_144, ra_144); - REGISTER_DECODER(RA_288, ra_288); - REGISTER_DECODER(SHORTEN, shorten); - REGISTER_DECODER(SMACKAUD, smackaud); - REGISTER_ENCDEC (SONIC, sonic); - REGISTER_ENCODER(SONIC_LS, sonic_ls); - REGISTER_DECODER(TRUESPEECH, truespeech); - REGISTER_DECODER(TTA, tta); - REGISTER_DECODER(VMDAUDIO, vmdaudio); - REGISTER_ENCDEC (VORBIS, vorbis); - REGISTER_DECODER(WAVPACK, wavpack); - REGISTER_DECODER(WMAV1, wmav1); - REGISTER_DECODER(WMAV2, wmav2); - REGISTER_DECODER(WS_SND1, ws_snd1); - - /* pcm codecs */ - REGISTER_ENCDEC (PCM_ALAW, pcm_alaw); - REGISTER_ENCDEC (PCM_MULAW, pcm_mulaw); - REGISTER_ENCDEC (PCM_S8, pcm_s8); - REGISTER_ENCDEC (PCM_S16BE, pcm_s16be); - REGISTER_ENCDEC (PCM_S16LE, pcm_s16le); - REGISTER_ENCDEC (PCM_S24BE, pcm_s24be); - REGISTER_ENCDEC (PCM_S24DAUD, pcm_s24daud); - REGISTER_ENCDEC (PCM_S24LE, pcm_s24le); - REGISTER_ENCDEC (PCM_S32BE, pcm_s32be); - REGISTER_ENCDEC (PCM_S32LE, pcm_s32le); - REGISTER_ENCDEC (PCM_U8, pcm_u8); - REGISTER_ENCDEC (PCM_U16BE, pcm_u16be); - REGISTER_ENCDEC (PCM_U16LE, pcm_u16le); - REGISTER_ENCDEC (PCM_U24BE, pcm_u24be); - REGISTER_ENCDEC (PCM_U24LE, pcm_u24le); - REGISTER_ENCDEC (PCM_U32BE, pcm_u32be); - REGISTER_ENCDEC (PCM_U32LE, pcm_u32le); - - /* dpcm codecs */ - REGISTER_DECODER(INTERPLAY_DPCM, interplay_dpcm); - REGISTER_DECODER(ROQ_DPCM, roq_dpcm); - REGISTER_DECODER(SOL_DPCM, sol_dpcm); - REGISTER_DECODER(XAN_DPCM, xan_dpcm); - - /* adpcm codecs */ - REGISTER_ENCDEC (ADPCM_4XM, adpcm_4xm); - REGISTER_ENCDEC (ADPCM_ADX, adpcm_adx); - REGISTER_ENCDEC (ADPCM_CT, adpcm_ct); - REGISTER_ENCDEC (ADPCM_EA, adpcm_ea); - REGISTER_ENCDEC (ADPCM_G726, adpcm_g726); - REGISTER_ENCDEC (ADPCM_IMA_DK3, adpcm_ima_dk3); - REGISTER_ENCDEC (ADPCM_IMA_DK4, adpcm_ima_dk4); - REGISTER_ENCDEC (ADPCM_IMA_QT, adpcm_ima_qt); - REGISTER_ENCDEC (ADPCM_IMA_SMJPEG, adpcm_ima_smjpeg); - REGISTER_ENCDEC (ADPCM_IMA_WAV, adpcm_ima_wav); - REGISTER_ENCDEC (ADPCM_IMA_WS, adpcm_ima_ws); - REGISTER_ENCDEC (ADPCM_MS, adpcm_ms); - REGISTER_ENCDEC (ADPCM_SBPRO_2, adpcm_sbpro_2); - REGISTER_ENCDEC (ADPCM_SBPRO_3, adpcm_sbpro_3); - REGISTER_ENCDEC (ADPCM_SBPRO_4, adpcm_sbpro_4); - REGISTER_ENCDEC (ADPCM_SWF, adpcm_swf); - REGISTER_ENCDEC (ADPCM_XA, adpcm_xa); - REGISTER_ENCDEC (ADPCM_YAMAHA, adpcm_yamaha); - - /* subtitles */ - REGISTER_ENCDEC (DVBSUB, dvbsub); - REGISTER_ENCDEC (DVDSUB, dvdsub); - - /* parsers */ - REGISTER_PARSER (AAC, aac); - REGISTER_PARSER (AC3, ac3); - REGISTER_PARSER (CAVSVIDEO, cavsvideo); - REGISTER_PARSER (DVBSUB, dvbsub); - REGISTER_PARSER (DVDSUB, dvdsub); - REGISTER_PARSER (H261, h261); - REGISTER_PARSER (H263, h263); - REGISTER_PARSER (H264, h264); - REGISTER_PARSER (MJPEG, mjpeg); - REGISTER_PARSER (MPEG4VIDEO, mpeg4video); - REGISTER_PARSER (MPEGAUDIO, mpegaudio); - REGISTER_PARSER (MPEGVIDEO, mpegvideo); - REGISTER_PARSER (PNM, pnm); - - /* - av_register_bitstream_filter(&dump_extradata_bsf); - av_register_bitstream_filter(&remove_extradata_bsf); - av_register_bitstream_filter(&noise_bsf); - av_register_bitstream_filter(&mp3_header_compress_bsf); - av_register_bitstream_filter(&mp3_header_decompress_bsf); - av_register_bitstream_filter(&mjpega_dump_header_bsf); - */ -} - -#endif - void init_once_routine(void) { pthread_mutex_init(&ffmpeg_lock, NULL); avcodec_init(); @@ -321,9 +47,9 @@ void init_once_routine(void) { const plugin_info_t xine_plugin_info[] EXPORTED = { /* type, API, "name", version, special_info, init_function */ - { PLUGIN_VIDEO_DECODER | PLUGIN_MUST_PRELOAD, 18, "ffmpegvideo", XINE_VERSION_CODE, &dec_info_ffmpeg_video, init_video_plugin }, - { PLUGIN_VIDEO_DECODER, 18, "ffmpeg-wmv8", XINE_VERSION_CODE, &dec_info_ffmpeg_wmv8, init_video_plugin }, - { PLUGIN_VIDEO_DECODER, 18, "ffmpeg-wmv9", XINE_VERSION_CODE, &dec_info_ffmpeg_wmv9, init_video_plugin }, - { PLUGIN_AUDIO_DECODER, 15, "ffmpegaudio", XINE_VERSION_CODE, &dec_info_ffmpeg_audio, init_audio_plugin }, + { PLUGIN_VIDEO_DECODER | PLUGIN_MUST_PRELOAD, 19, "ffmpegvideo", XINE_VERSION_CODE, &dec_info_ffmpeg_video, init_video_plugin }, + { PLUGIN_VIDEO_DECODER, 19, "ffmpeg-wmv8", XINE_VERSION_CODE, &dec_info_ffmpeg_wmv8, init_video_plugin }, + { PLUGIN_VIDEO_DECODER, 19, "ffmpeg-wmv9", XINE_VERSION_CODE, &dec_info_ffmpeg_wmv9, init_video_plugin }, + { PLUGIN_AUDIO_DECODER, 16, "ffmpegaudio", XINE_VERSION_CODE, &dec_info_ffmpeg_audio, init_audio_plugin }, { PLUGIN_NONE, 0, "", 0, NULL, NULL } }; diff --git a/src/combined/ffmpeg/ffmpeg_decoder.h b/src/combined/ffmpeg/ffmpeg_decoder.h index 0aeb71271..f679a5ce9 100644 --- a/src/combined/ffmpeg/ffmpeg_decoder.h +++ b/src/combined/ffmpeg/ffmpeg_decoder.h @@ -27,10 +27,8 @@ #ifdef HAVE_FFMPEG_AVUTIL_H # include <avcodec.h> -#elif defined HAVE_FFMPEG -# include <libavcodec/avcodec.h> #else -# include "../../libffmpeg/libavcodec/avcodec.h" +# include <libavcodec/avcodec.h> #endif #if LIBAVCODEC_VERSION_MAJOR > 51 diff --git a/src/combined/ffmpeg/ffmpeg_encoder.c b/src/combined/ffmpeg/ffmpeg_encoder.c deleted file mode 100644 index d41023675..000000000 --- a/src/combined/ffmpeg/ffmpeg_encoder.c +++ /dev/null @@ -1,334 +0,0 @@ -/* - * Copyright (C) 2000-2004 the xine project - * - * This file is part of xine, a unix video player. - * - * xine is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * xine is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA - */ - -/* mpeg encoders for the dxr3 video out plugin. */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include <stdio.h> -#include <stdlib.h> -#include <sys/ioctl.h> -#include <fcntl.h> -#include <unistd.h> -#include <errno.h> -#include <math.h> - -#define LOG_MODULE "dxr3_mpeg_encoder" -/* #define LOG_VERBOSE */ -/* #define LOG */ - -#include "video_out_dxr3.h" - -#ifdef HAVE_FFMPEG_AVUTIL_H -# include <avcodec.h> -#elif defined HAVE_FFMPEG -# include <libavcodec/avcodec.h> -#else -# include "../../libffmpeg/libavcodec/avcodec.h" -#endif - -/* buffer size for encoded mpeg1 stream; will hold one intra frame - * at 640x480 typical sizes are <50 kB. 512 kB should be plenty */ -#define DEFAULT_BUFFER_SIZE 512*1024 - - -/*initialisation function, used by the dxr3 plugin */ -int dxr3_encoder_init(dxr3_driver_t *drv) EXPORTED; - -/* functions required by encoder api */ -static int lavc_on_update_format(dxr3_driver_t *drv, dxr3_frame_t *frame); -static int lavc_on_display_frame(dxr3_driver_t *drv, dxr3_frame_t *frame); -static int lavc_on_unneeded(dxr3_driver_t *drv); - -/*encoder structure*/ -typedef struct lavc_data_s { - encoder_data_t encoder_data; - AVCodecContext *context; /* handle for encoding */ - int width, height; /* width and height of the video frame */ - uint8_t *ffmpeg_buffer; /* lavc buffer */ - AVFrame *picture; /* picture to be encoded */ - uint8_t *out[3]; /* aligned buffer for YV12 data */ - uint8_t *buf; /* unaligned YV12 buffer */ -} lavc_data_t; - - -int dxr3_encoder_init(dxr3_driver_t *drv) -{ - lavc_data_t* this; - avcodec_init(); - - avcodec_register_all(); - lprintf("lavc init , version %x\n", avcodec_version()); - this = calloc(1, sizeof(lavc_data_t)); - if (!this) return 0; - - this->encoder_data.type = ENC_LAVC; - this->encoder_data.on_update_format = lavc_on_update_format; - this->encoder_data.on_frame_copy = NULL; - this->encoder_data.on_display_frame = lavc_on_display_frame; - this->encoder_data.on_unneeded = lavc_on_unneeded; - this->context = 0; - - drv->enc = &this->encoder_data; - return 1; -} - -/* helper function */ -static int lavc_prepare_frame(lavc_data_t *this, dxr3_driver_t *drv, dxr3_frame_t *frame); - -static int lavc_on_update_format(dxr3_driver_t *drv, dxr3_frame_t *frame) -{ - lavc_data_t *this = (lavc_data_t *)drv->enc; - AVCodec *codec; - unsigned char use_quantizer; - - if (this->context) { - avcodec_close(this->context); - free(this->context); - free(this->picture); - this->context = NULL; - this->picture = NULL; - } - - /* if YUY2 and dimensions changed, we need to re-allocate the - * internal YV12 buffer */ - if (frame->vo_frame.format == XINE_IMGFMT_YUY2) { - int image_size = frame->vo_frame.pitches[0] * frame->oheight; - - this->out[0] = xine_xmalloc_aligned(16, image_size * 3/2, - (void *)&this->buf); - this->out[1] = this->out[0] + image_size; - this->out[2] = this->out[1] + image_size/4; - - /* fill with black (yuv 16,128,128) */ - memset(this->out[0], 16, image_size); - memset(this->out[1], 128, image_size/4); - memset(this->out[2], 128, image_size/4); - lprintf("Using YUY2->YV12 conversion\n"); - } - - /* resolution must be a multiple of two */ - if ((frame->vo_frame.pitches[0] % 2 != 0) || (frame->oheight % 2 != 0)) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: lavc only handles video dimensions which are multiples of 2\n"); - return 0; - } - - /* get mpeg codec handle */ - codec = avcodec_find_encoder(CODEC_ID_MPEG1VIDEO); - if (!codec) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: lavc MPEG1 codec not found\n"); - return 0; - } - lprintf("lavc MPEG1 encoder found.\n"); - - this->width = frame->vo_frame.pitches[0]; - this->height = frame->oheight; - - this->context = avcodec_alloc_context(); - if (!this->context) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: Couldn't start the ffmpeg library\n"); - return 0; - } - this->picture = avcodec_alloc_frame(); - if (!this->picture) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: Couldn't allocate ffmpeg frame\n"); - return 0; - } - - /* mpeg1 encoder only support YUV420P */ - this->context->pix_fmt = PIX_FMT_YUVJ420P; - - /* put sample parameters */ - this->context->bit_rate = drv->class->xine->config->register_range(drv->class->xine->config, - "dxr3.encoding.lavc_bitrate", 10000, 1000, 20000, - _("libavcodec mpeg output bitrate (kbit/s)"), - _("The bitrate the libavcodec mpeg encoder should use for DXR3's encoding mode. " - "Higher values will increase quality and CPU usage.\n" - "This setting is only considered, when constant quality mode is disabled."), 10, NULL, NULL); - this->context->bit_rate *= 1000; /* config in kbit/s, libavcodec wants bit/s */ - - use_quantizer = drv->class->xine->config->register_bool(drv->class->xine->config, - "dxr3.encoding.lavc_quantizer", 1, - _("constant quality mode"), - _("When enabled, libavcodec will use a constant quality mode by dynamically " - "compressing the images based on their complexity. When disabled, libavcodec " - "will use constant bitrate mode."), 10, NULL, NULL); - - if (use_quantizer) { - this->context->qmin = drv->class->xine->config->register_range(drv->class->xine->config, - "dxr3.encoding.lavc_qmin", 1, 1, 10, - _("minimum compression"), - _("The minimum compression to apply to an image in constant quality mode."), - 10, NULL, NULL); - - this->context->qmax = drv->class->xine->config->register_range(drv->class->xine->config, - "dxr3.encoding.lavc_qmax", 2, 1, 20, - _("maximum quantizer"), - _("The maximum compression to apply to an image in constant quality mode."), - 10, NULL, NULL); - } - - lprintf("lavc -> bitrate %d \n", this->context->bit_rate); - - this->context->width = frame->vo_frame.pitches[0]; - this->context->height = frame->oheight; - - this->context->gop_size = 0; /*intra frames only */ - this->context->me_method = ME_ZERO; /*motion estimation type*/ - - this->context->time_base.den = 90000; - if (frame->vo_frame.duration > 90000 / 24) - this->context->time_base.num = 90000 / 24; - else if (frame->vo_frame.duration < 90000 / 60) - this->context->time_base.num = 90000 / 60; - else - this->context->time_base.num = frame->vo_frame.duration; - /* ffmpeg can complain about illegal framerates, but since this seems no - * problem for the DXR3, we just tell ffmpeg to be more lax with */ - this->context->strict_std_compliance = -1; - - /* open avcodec */ - if (avcodec_open(this->context, codec) < 0) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, "dxr3_mpeg_encoder: could not open codec\n"); - return 0; - } - lprintf("dxr3_mpeg_encoder: lavc MPEG1 codec opened.\n"); - - if (!this->ffmpeg_buffer) - this->ffmpeg_buffer = (unsigned char *)malloc(DEFAULT_BUFFER_SIZE); /* why allocate more than needed ?! */ - if (!this->ffmpeg_buffer) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: Couldn't allocate temp buffer for mpeg data\n"); - return 0; - } - - return 1; -} - -static int lavc_on_display_frame(dxr3_driver_t *drv, dxr3_frame_t *frame) -{ - int size; - lavc_data_t* this = (lavc_data_t *)drv->enc; - ssize_t written; - - if (frame->vo_frame.bad_frame) return 1; - /* ignore old frames */ - if ((frame->vo_frame.pitches[0] != this->context->width) || (frame->oheight != this->context->height)) { - frame->vo_frame.free(&frame->vo_frame); - lprintf("LAVC ignoring frame !!!\n"); - return 1; - } - - /* prepare frame for conversion, handles YUY2 -> YV12 conversion when necessary */ - lavc_prepare_frame(this, drv, frame); - - /* do the encoding */ - size = avcodec_encode_video(this->context, this->ffmpeg_buffer, DEFAULT_BUFFER_SIZE, this->picture); - - frame->vo_frame.free(&frame->vo_frame); - - if (size < 0) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: encoding failed\n"); - return 0; - } - - written = write(drv->fd_video, this->ffmpeg_buffer, size); - if (written < 0) { - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: video device write failed (%s)\n", strerror(errno)); - return 0; - } - if (written != size) - xprintf(drv->class->xine, XINE_VERBOSITY_LOG, - "dxr3_mpeg_encoder: Could only write %zd of %d mpeg bytes.\n", written, size); - return 1; -} - -static int lavc_on_unneeded(dxr3_driver_t *drv) -{ - lavc_data_t *this = (lavc_data_t *)drv->enc; - lprintf("flushing buffers\n"); - if (this->context) { - avcodec_close(this->context); - free(this->context); - free(this->picture); - this->context = NULL; - this->picture = NULL; - } - return 1; -} - -static int lavc_prepare_frame(lavc_data_t *this, dxr3_driver_t *drv, dxr3_frame_t *frame) -{ - int i, j, w2; - uint8_t *yuy2; - - if (frame->vo_frame.bad_frame) return 1; - - if (frame->vo_frame.format == XINE_IMGFMT_YUY2) { - /* need YUY2->YV12 conversion */ - if (!(this->out[0] && this->out[1] && this->out[2]) ) { - lprintf("Internal YV12 buffer not created.\n"); - return 0; - } - this->picture->data[0] = this->out[0] + frame->vo_frame.pitches[0] * drv->top_bar; /* y */ - this->picture->data[1] = this->out[1] + (frame->vo_frame.pitches[0] / 2) * (drv->top_bar / 2); /* u */ - this->picture->data[2] = this->out[2] + (frame->vo_frame.pitches[0] / 2) * (drv->top_bar / 2); /* v */ - yuy2 = frame->vo_frame.base[0]; - w2 = frame->vo_frame.pitches[0] / 2; - for (i = 0; i < frame->vo_frame.height; i += 2) { - for (j = 0; j < w2; j++) { - /* packed YUV 422 is: Y[i] U[i] Y[i+1] V[i] */ - *(this->picture->data[0]++) = *(yuy2++); - *(this->picture->data[1]++) = *(yuy2++); - *(this->picture->data[0]++) = *(yuy2++); - *(this->picture->data[2]++) = *(yuy2++); - } - /* down sampling */ - for (j = 0; j < w2; j++) { - /* skip every second line for U and V */ - *(this->picture->data[0]++) = *(yuy2++); - yuy2++; - *(this->picture->data[0]++) = *(yuy2++); - yuy2++; - } - } - /* reset for encoder */ - this->picture->data[0] = this->out[0]; - this->picture->data[1] = this->out[1]; - this->picture->data[2] = this->out[2]; - } - else { /* YV12 **/ - this->picture->data[0] = frame->real_base[0]; - this->picture->data[1] = frame->real_base[1]; - this->picture->data[2] = frame->real_base[2]; - } - this->picture->linesize[0] = this->context->width; - this->picture->linesize[1] = this->context->width / 2; - this->picture->linesize[2] = this->context->width / 2; - return 1; -} diff --git a/src/combined/ffmpeg/mkcodeclist.pl b/src/combined/ffmpeg/mkcodeclist.pl index b4a10921a..311d147af 100755 --- a/src/combined/ffmpeg/mkcodeclist.pl +++ b/src/combined/ffmpeg/mkcodeclist.pl @@ -38,9 +38,9 @@ while (defined ($line = <LIST>)) { $Type = $type; $Type =~ tr/a-z/A-Z/; } elsif (substr ($line, 0, 7) eq 'config=') { - # "#ifdef CONFIG_FOO_DECODER" mappings + # avcodec minimum version mappings ($a, $f, $t) = split (/=/, $line, 3); - $config{$f} = $t; + $config{$f} = $t if $t =~ /^\d+,\d+,\d+$/ } else { # codec details push @known, [split (/\s+/, $line, 3)]; @@ -63,6 +63,7 @@ my $w = ($out ne '-'); if ($w) { # Write the C source code for the codec lists open LIST, "> $out" or die $!; + print LIST "#ifndef AV_VERSION_INT\n# define AV_VERSION_INT(a,b,c) 0x7FFFFFFF\n#endif\n" or die $!; print LIST "static const ff_codec_t ff_${type}_lookup[] = {\n" or die $!; foreach $line (@known) { next if $line->[0] eq '!'; @@ -73,12 +74,12 @@ if ($w) { foreach $line (@known) { next if $line->[0] eq '!'; next unless defined $codecs{$line->[1]}; - $a = $line->[1]; + $a = ''; $a = $config{$a} if defined $config{$a}; if ($a eq '') { print LIST " BUF_${Type}_$line->[0],\n" or die $!; } else { - print LIST " #ifdef CONFIG_${a}_DECODER\n BUF_${Type}_$line->[0],\n #endif\n" or die $!; + print LIST " #if LIBAVCODEC_VERSION_INT >= AV_VERSION_INT($a)\n BUF_${Type}_$line->[0],\n #endif\n" or die $!; } } print LIST " 0,\n};\n" or die $!; diff --git a/src/combined/ffmpeg/xine_audio.list b/src/combined/ffmpeg/xine_audio.list index 0ebbfbda6..8a40c29cb 100644 --- a/src/combined/ffmpeg/xine_audio.list +++ b/src/combined/ffmpeg/xine_audio.list @@ -1,5 +1,4 @@ type=audio -config=MP3ADU= # xine-lib BUF_AUDIO_ ffmpeg CODEC_ID_ description or comment # ("!"=ignore) (quote any "s) diff --git a/src/combined/ffmpeg/xine_video.list b/src/combined/ffmpeg/xine_video.list index bd1238d6f..009f4dafd 100644 --- a/src/combined/ffmpeg/xine_video.list +++ b/src/combined/ffmpeg/xine_video.list @@ -1,7 +1,4 @@ type=video -config=VP6F=VP6 -config=FLV1=FLV -config=THEORA= # xine-lib BUF_VIDEO_ ffmpeg CODEC_ID_ description or comment # ("!"=ignore) (quote any "s) |