[MPlayer-dev-eng] [PATCH] DivX6 support

Dominik 'Rathann' Mierzejewski dominik at rangers.eu.org
Wed Jun 21 17:48:36 CEST 2006


On Monday, 19 June 2006 at 09:26, Ivan Kalvachev wrote:
> 2006/6/19, Dominik 'Rathann' Mierzejewski <dominik at rangers.eu.org>:
> >Here's a preliminary but already working interface to DivX6 .so decoder
> >based on vd_divx4.c.
> >
> >The decoder binary and headers can be downloaded from
> >http://download.divx.com/labs/divx611-20060201-gcc4.0.1.tar.gz
> >
> >TODO:
> >- implement control()
> >- fix YV12 csp
> >
> >Feedback welcome.
> 
> I think it would be better to use EXPORT mpi type.

EXPORT crashes. STATIC works.

> >From the code I see that divx6 takes only one pointer (and one 
> >stride/width).

Yes, but the docs say it ignores width.

> The problem is that MPlayer may position the UV planes in compleatly
> unexpected way. (alignement etc...).
> I dare to remind you that yv12 is actually YVU (aka reverse UV). It
> doesn't matter for MPlayer that uses pointers to them, but it would
> matter to divx6 that will place them sequentially into the single
> buffer.

Fixed and new version attached.

Regards,
R.

-- 
MPlayer developer and RPMs maintainer: http://rpm.greysector.net/mplayer/
There should be a science of discontent. People need hard times and
oppression to develop psychic muscles.
	-- from "Collected Sayings of Muad'Dib" by the Princess Irulan
-------------- next part --------------
--- MPlayer-18764/Makefile.divx6	2006-06-20 16:44:58.000000000 +0200
+++ MPlayer-18764/Makefile	2006-06-20 16:44:58.000000000 +0200
@@ -101,6 +101,7 @@
              $(FAAD_LIB) \
              $(LIBLZO_LIB) \
              $(DECORE_LIB) \
+             $(DIVX6_LIB) \
              $(XVID_LIB) \
              $(DTS_LIB) \
              $(PNG_LIB) \
--- MPlayer-18764/etc/codecs.conf.divx6	2006-06-08 12:47:20.000000000 +0200
+++ MPlayer-18764/etc/codecs.conf	2006-06-21 14:05:07.000000000 +0200
@@ -651,6 +651,26 @@
   out UYVY
   out BGR32,BGR24,BGR16,BGR15
 
+videocodec divx6
+  info "DivX6"
+  comment "with postprocessing"
+  status working
+  fourcc mp4v
+  fourcc DIVX,divx
+  fourcc DIV1,div1 divx
+;  fourcc MP4S,mp4s     ; ISO MPEG-4 Video V1
+  fourcc MP43,mp43,DIV3,div3 DIV3  ; for DivX4Linux only!
+  fourcc DIV4,div4
+  fourcc div5,DIV5
+  fourcc AP41 DIV3        ; AngelPotion stuff
+  fourcc xvid,XVID,XviD
+  fourcc DX50,BLZ0 DX50
+  format 0x4
+  driver divx6
+  dll libdivx
+  out YV12,I420,IYUV
+  out BGR32,BGR24,BGR16 flip
+
 ; is divx4vfw stable enough, working everywhere and faster than divxds?
 
 videocodec divx4vfw
--- MPlayer-18764/libmpcodecs/vd.c.divx6	2006-06-07 15:16:07.000000000 +0200
+++ MPlayer-18764/libmpcodecs/vd.c	2006-06-20 16:44:58.000000000 +0200
@@ -36,6 +36,7 @@
 extern vd_functions_t mpcodecs_vd_vfwex;
 extern vd_functions_t mpcodecs_vd_odivx;
 extern vd_functions_t mpcodecs_vd_divx4;
+extern vd_functions_t mpcodecs_vd_divx6;
 extern vd_functions_t mpcodecs_vd_raw;
 extern vd_functions_t mpcodecs_vd_hmblck;
 extern vd_functions_t mpcodecs_vd_xanim;
@@ -75,6 +76,9 @@
         &mpcodecs_vd_divx4,
 #endif
 #endif
+#ifdef HAVE_DIVX6
+        &mpcodecs_vd_divx6,
+#endif
         &mpcodecs_vd_lzo,
         &mpcodecs_vd_raw,
         &mpcodecs_vd_hmblck,
--- MPlayer-18764/libmpcodecs/Makefile.divx6	2006-06-20 16:44:58.000000000 +0200
+++ MPlayer-18764/libmpcodecs/Makefile	2006-06-21 17:38:50.000000000 +0200
@@ -78,6 +78,10 @@
 ifeq ($(CONFIG_LIBAVCODEC_SO),yes)
 VIDEO_SRCS_OPT+=vd_ffmpeg.c
 endif
+ifeq ($(DIVX6),yes)
+VIDEO_SRCS_OPT+=vd_divx6.c
+CFLAGS+=$(DIVX6_INC)
+endif
 
 VIDEO_SRCS=dec_video.c \
            vd.c \
--- /dev/null	2006-06-17 18:24:06.451637250 +0200
+++ MPlayer-18764/libmpcodecs/vd_divx6.c	2006-06-21 17:32:41.000000000 +0200
@@ -0,0 +1,194 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdarg.h>
+#include <assert.h>
+
+#include "config.h"
+#include "mp_msg.h"
+#include "help_mp.h"
+
+#include "vd_internal.h"
+
+static vd_info_t info = {
+	"DivX 6 lib",
+	"divx6",
+	"Dominik Mierzejewski, based on code by A'rpi",
+	"http://www.divx.com",
+	"native binary codec"
+};
+
+LIBVD_EXTERN(divx6)
+
+#include <decoder/LibQDec.h>
+
+static void* pHandle = NULL;
+static LibQDecoreFunction* pDecore;
+
+// to set/get/query special features/parameters
+static int control(sh_video_t *sh,int cmd,void* arg,...){
+	int ret;
+	switch(cmd){
+		case VDCTRL_QUERY_MAX_PP_LEVEL:
+			return 6; // FIXME what is the max level?
+		case VDCTRL_SET_PP_LEVEL: {
+			int quality=*((int*)arg);
+			int32_t iOperation, iPostproc;
+			if(quality<0 || quality>6) quality=6;
+			iOperation = DEC_PAR_POSTPROCESSING;
+			iPostproc = quality*10;
+			ret = pDecore(pHandle, DEC_OPT_SET, &iOperation, &iPostproc);
+			return (ret==DEC_OK)?CONTROL_OK:CONTROL_ERROR;
+		}
+		case VDCTRL_SET_EQUALIZER: {
+			va_list ap;
+			int value;
+		        int option;
+			va_start(ap, arg);
+			value=va_arg(ap, int);
+			va_end(ap);
+
+		        if(!strcasecmp(arg,"Brightness"))
+				option=DEC_PAR_BRIGHTNESS;
+			else if(!strcasecmp(arg, "Contrast"))
+				option=DEC_PAR_CONTRAST;
+			else if(!strcasecmp(arg,"Saturation"))
+				option=DEC_PAR_SATURATION;
+			else if(!strcasecmp(arg,"Warmth"))
+				option=DEC_PAR_WARMTHLEVEL;
+			else return CONTROL_FALSE;
+
+			value = (value * 128) / 100;
+			ret = pDecore(pHandle, DEC_OPT_SET, &option, &value);
+			return (ret==DEC_OK)?CONTROL_OK:CONTROL_ERROR;
+		}
+	}
+	return CONTROL_UNKNOWN;
+}
+
+// init driver
+static int init(sh_video_t *sh){
+	DecInit decInit;
+	int iOperation;
+	int err;
+
+	if(!mpcodecs_config_vo(sh,sh->disp_w,sh->disp_h,IMGFMT_YV12)) return 0;
+
+	memset(&decInit, 0, sizeof(DecInit));
+
+	switch(sh->format) {
+		case mmioFOURCC('d','i','v','3'):
+		case mmioFOURCC('d','i','v','4'):
+		case mmioFOURCC('d','i','v','5'):
+		case mmioFOURCC('d','i','v','x'):
+		case mmioFOURCC('D','I','V','X'):
+		case mmioFOURCC('d','x','5','0'):
+		case mmioFOURCC('D','X','5','0'):
+			decInit.formatIn.fourCC=sh->format;
+			break;
+		case mmioFOURCC('D','I','V','3'):
+		case mmioFOURCC('D','I','V','4'):
+		case mmioFOURCC('D','I','V','5'):
+			decInit.formatIn.fourCC=FourCC_lowerCase(sh->format);
+			break;
+		default:
+			decInit.formatIn.fourCC=mmioFOURCC('D','X','5','0');
+	}
+
+	pDecore=getDecore(decInit.formatIn.fourCC);
+	if(!pDecore){
+		mp_msg(MSGT_DECVIDEO,MSGL_ERR,"DivX6: getDecore() failed for FourCC: 0x%X\n",decInit.formatIn.fourCC);
+		return 0;
+	}
+
+	decInit.formatIn.width=sh->bih->biWidth;
+	decInit.formatIn.height=sh->bih->biHeight;
+	decInit.formatIn.framePeriodIsConstant = 1;
+
+	switch(sh->codec->outfmt[sh->outfmtidx]){
+		case IMGFMT_YV12: {
+			decInit.formatOut.fourCC=mmioFOURCC('Y','V','1','2');
+			break;
+		}
+		case IMGFMT_I420:
+		case IMGFMT_IYUV: {
+			decInit.formatOut.fourCC=mmioFOURCC('I','Y','U','V');
+			break;
+		}
+		case IMGFMT_BGR16: {
+			decInit.formatOut.bpp=16;
+			decInit.formatOut.inverted=1; // doesn't seem to have any effect?!
+			break;
+		}
+		case IMGFMT_BGR24: {
+			decInit.formatOut.bpp=24;
+			decInit.formatOut.inverted=1; // doesn't seem to have any effect?!
+			break;
+		}
+		case IMGFMT_BGR32: {
+			decInit.formatOut.bpp=32;
+			decInit.formatOut.inverted=1; // doesn't seem to have any effect?!
+			break;
+		}
+		default:
+			mp_msg(MSGT_DECVIDEO,MSGL_ERR,"DivX6: Unsupported out_fmt: 0x%X\n",sh->codec->outfmt[sh->outfmtidx]);
+			return 0;
+	}
+
+	decInit.formatOut.width = sh->disp_w;
+	decInit.formatOut.height = sh->disp_h;
+	decInit.formatOut.framePeriodIsConstant = 1;
+
+	if(pDecore(NULL, DEC_OPT_INIT, (void*) &pHandle, &decInit)!=DEC_OK){
+		mp_msg(MSGT_DECVIDEO,MSGL_ERR,"DivX6: video codec init FAILED!\n");
+		return 0;
+	}
+	if (!pHandle){
+		mp_msg(MSGT_DECVIDEO,MSGL_ERR,"DivX6: video codec init FAILED!\n");
+		return 0;
+	}
+
+	iOperation = DEC_PAR_POSTPROCESSING;
+	if(!divx_quality) divx_quality=-1; // for some reason it doesn't work with ==0
+	if((err=pDecore(pHandle, DEC_OPT_SET, &iOperation, &divx_quality))!=DEC_OK){
+		mp_msg(MSGT_DECVIDEO,MSGL_WARN,"DivX6: video codec pp level setting failed: %d\n",err);
+	}
+	mp_msg(MSGT_DECVIDEO,MSGL_V,"DivX6: video codec init OK!\n");
+
+	return 1;
+}
+
+// uninit driver
+static void uninit(sh_video_t *sh){
+	int ret = pDecore(pHandle, DEC_OPT_RELEASE, 0, 0);
+	if (ret!=DEC_OK)
+		mp_msg(MSGT_DECVIDEO,MSGL_WARN,"DivX6: video codec uninit failed: %d\n",ret);
+}
+
+// decode a frame
+static mp_image_t* decode(sh_video_t *sh,void* data,int len,int flags){
+	mp_image_t* mpi;
+	DecFrame decFrame;
+	int ret;
+
+	if(len<=0) return NULL; // skipped frame
+
+	memset(&decFrame, 0, sizeof(DecFrame));
+	decFrame.bitstream.iLength = len;
+	decFrame.bitstream.pBuff = data;
+	decFrame.shallowDecode = (flags&VDFLAGS_DROPFRAME)?1:0;
+
+	mpi=mpcodecs_get_image(sh, MP_IMGTYPE_STATIC, MP_IMGFLAG_PRESERVE | MP_IMGFLAG_ACCEPT_WIDTH,
+		sh->disp_w, sh->disp_h);
+	if(!mpi) return NULL;
+
+	decFrame.pBmp = mpi->planes[0];
+	decFrame.bmpStride = mpi->width; // FIXME ignored by decoder
+
+	ret = pDecore(pHandle,DEC_OPT_FRAME,&decFrame,0);
+	if (ret!=DEC_OK)
+		mp_msg(MSGT_DECVIDEO,MSGL_WARN,"DivX6: frame decode failed: %d\n",ret);
+	if (!decFrame.frameWasDecoded)
+		mp_msg(MSGT_DECVIDEO,MSGL_WARN,"DivX6: frame not decoded\n");
+
+	return mpi;
+}
--- MPlayer-18764/ChangeLog.divx6	2006-06-20 15:53:14.000000000 +0200
+++ MPlayer-18764/ChangeLog	2006-06-21 17:40:16.000000000 +0200
@@ -9,0 +10 @@
+    * DivX6 binary decoder support
--- MPlayer-18764/configure.divx6	2006-06-20 16:44:58.000000000 +0200
+++ MPlayer-18764/configure	2006-06-21 11:51:23.000000000 +0200
@@ -263,6 +263,7 @@
   --disable-xvid         disable XviD codec [autodetect]
   --disable-x264         disable H.264 encoder [autodetect]
   --disable-divx4linux   disable DivX4linux/Divx5linux codec [autodetect]
+  --disable-divx6        disable DivX 6.x codec [autodetect]
   --enable-opendivx      enable _old_ OpenDivx codec [disable]
   --disable-libavutil    disable libavutil [autodetect]
   --disable-libavcodec   disable libavcodec [autodetect]
@@ -413,6 +414,8 @@
   --with-xvidincdir=DIR    XviD header in DIR (*)
   --with-x264libdir=DIR    libx264 in DIR
   --with-x264incdir=DIR    x264 header in DIR
+  --with-divx6libdir=DIR   libdivx (DivX6) in DIR  (*)
+  --with-divx6incdir=DIR   DivX6 header in DIR (*)
   --with-libdtslibdir=DIR  libdts library in DIR  (*)
   --with-libdtsincdir=DIR  libdts header in DIR (*)
   --with-livelibdir=DIR    LIVE555 Streaming Media libraries in DIR
@@ -1652,6 +1655,7 @@
 _x264=auto
 _divx4linux=auto
 _opendivx=no
+_divx6=auto
 _lirc=auto
 _lircc=auto
 _gui=no
@@ -1899,6 +1903,8 @@
   --disable-divx4linux)	_divx4linux=no	;;
   --enable-opendivx)	_opendivx=yes	;;
   --disable-opendivx)	_opendivx=no	;;
+  --enable-divx6)	_divx6=yes	;;
+  --disable-divx6)	_divx6=no	;;
   --enable-libavutil)	_libavutil=yes	;;
   --disable-libavutil)	_libavutil=no	;;
   --enable-libavutil_so)	_libavutil_so=yes	;;
@@ -2126,6 +2132,12 @@
   --with-x264incdir=*)
     _inc_x264=-I`echo $ac_option | cut -d '=' -f 2 |sed 's,:, -I,g'`
     ;;
+  --with-divx6libdir=*)
+    _ld_divx6=-L`echo $ac_option | cut -d '=' -f 2 | sed 's,:, -L,g'`
+    ;;
+  --with-divx6incdir=*)
+    _inc_divx6=-I`echo $ac_option | cut -d '=' -f 2 | sed 's,:, -I,g'`
+    ;;
   --with-sdl-config=*)
     _sdlconfig=`echo $ac_option | cut -d '=' -f 2`
     ;;
@@ -6602,6 +6614,34 @@
 fi
 echores "$_x264"
 
+echocheck "DivX 6.x decore"
+cat > $TMPC << EOF
+#include <decoder/LibQDec.h>
+int main(void) {
+ LibQDecoreFunction* pDecore=getDecore(FourCC_create("DX50"));
+ return pDecore(0, DEC_OPT_INIT, 0, 0);
+}
+EOF
+_ld_divx6="$_ld_divx6 -ldivx"
+if test "$_divx6" != no ; then 
+  for _inc_divx6 in "$_inc_divx6" \
+		    "-I/usr/local/include/divx" \
+		    "-I/usr/include/divx"; do
+    cc_check $_inc_divx6 $_ld_divx6 && _divx6=yes && break
+  done
+fi
+if test "$_divx6" = yes ; then
+  _divx6=yes
+  _def_divx6='#define HAVE_DIVX6 1'
+  _codecmodules="divx6 $_codecmodules"
+else
+  _divx6=no
+  _ld_divx6=''
+  _def_divx6='#undef HAVE_DIVX6'
+  _nocodecmodules="divx6 $_nocodecmodules"
+fi
+echores "$_divx6"
+
 echocheck "DivX4linux/DivX5linux/OpenDivX decore"
 # DivX5: DEC_OPT_MEMORY_REQS - DivX4: DEC_OPT_FRAME_311
 cat > $TMPC << EOF
@@ -7559,6 +7599,9 @@
 X264 = $_x264
 X264_INC = $_inc_x264
 X264_LIB = $_ld_x264
+DIVX6 = $_divx6
+DIVX6_INC = $_inc_divx6
+DIVX6_LIB = $_ld_divx6
 CONFIG_DTS = $_libdts
 DTS_INC = $_inc_libdts
 DTS_LIB = $_ld_libdts
@@ -7738,6 +7781,9 @@
 /* Define if you are using DivX5Linux Decore library */
 $_def_divx5
 
+/* Define if you are using DivX6 Codec library */
+$_def_divx6
+
 /* Define if you are using XviD library */
 $_def_xvid3
 $_def_xvid4


More information about the MPlayer-dev-eng mailing list