/*****************************************************************************
*
* - XviD 1.x export module for mplayer/mencoder -
*
* Copyright(C) 2003 Marco Belli <elcabesa@inwind.it>
* 2003-2004 Edouard Gomez <ed.gomez@free.fr>
*
* This program 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.
*
* This program 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-1301 USA
*
****************************************************************************/
/*****************************************************************************
* Includes
****************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <math.h>
#include <limits.h>
#include <time.h>
#include "config.h"
#include "mp_msg.h"
#include "codec-cfg.h"
#include "stream/stream.h"
#include "libmpdemux/demuxer.h"
#include "libmpdemux/stheader.h"
#include "stream/stream.h"
#include "libmpdemux/muxer.h"
#include "img_format.h"
#include "mp_image.h"
#include "vf.h"
#include <xvid.h>
#include <stdio.h>
#include <stdarg.h>
#include <limits.h>
#include <assert.h>
#include "m_option.h"
#ifdef USE_LIBAVUTIL_SO
#include <ffmpeg/avutil.h>
#else
#include "avutil.h"
#endif
#define FINE (!0)
#define BAD (!FINE)
#define MAX_ZONES 64
// Profile flag definitions
#define PROFILE_ADAPTQUANT 0x00000001
#define PROFILE_BVOP 0x00000002
#define PROFILE_MPEGQUANT 0x00000004
#define PROFILE_INTERLACE 0x00000008
#define PROFILE_QPEL 0x00000010
#define PROFILE_GMC 0x00000020
#define PROFILE_4MV 0x00000040
#define PROFILE_DXN 0x00000080
// Reduce code duplication in profiles[] array
#define PROFILE_S (PROFILE_4MV)
#define PROFILE_AS (PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_MPEGQUANT|PROFILE_INTERLACE|PROFILE_QPEL|PROFILE_GMC)
typedef const struct
{
char *name; ///< profile name
int id; ///< mpeg-4 profile id; iso/iec 14496-2:2001 table G-1
int width; ///< profile width restriction
int height; ///< profile height restriction
int fps; ///< profile frame rate restriction
int max_objects; ///< ??????
int total_vmv_buffer_sz; ///< macroblock memory; when BVOPS=false, vmv = 2*vcv; when BVOPS=true, vmv = 3*vcv
int max_vmv_buffer_sz; ///< max macroblocks per vop
int vcv_decoder_rate; ///< macroblocks decoded per second
int max_acpred_mbs; ///< percentage
int max_vbv_size; ///< max vbv size (bits) 16368 bits
int max_video_packet_length; ///< bits
int max_bitrate; ///< bits per second
int vbv_peakrate; ///< max bits over anyone second period; 0=don't care
int dxn_max_bframes; ///< dxn: max consecutive bframes
unsigned int flags; ///< flags for allowed options/dxn note the definitions for PROFILE_S and PROFILE_AS
} profile_t;
// Code taken from XviD VfW source for profile support
/* default vbv_occupancy is (64/170)*vbv_buffer_size */
static profile_t profiles[] =
{
/* name p@l w h fps obj Tvmv vmv vcv ac% vbv pkt bps vbv_peak dbf flags */
/* unrestricted profile (default) */
{ "unrestricted", 0x00, 0, 0, 0, 0, 0, 0, 0, 100, 0*16368, -1, 0, 0, -1, 0xffffffff & ~PROFILE_DXN },
{ "sp0", 0x08, 176, 144, 15, 1, 198, 99, 1485, 100, 10*16368, 2048, 64000, 0, -1, PROFILE_S },
/* simple@l0: max f_code=1, intra_dc_vlc_threshold=0 */
/* if ac preidition is used, adaptive quantization must not be used */
/* <=qcif must be used */
{ "sp1", 0x01, 176, 144, 15, 4, 198, 99, 1485, 100, 10*16368, 2048, 64000, 0, -1, PROFILE_S|PROFILE_ADAPTQUANT },
{ "sp2", 0x02, 352, 288, 15, 4, 792, 396, 5940, 100, 40*16368, 4096, 128000, 0, -1, PROFILE_S|PROFILE_ADAPTQUANT },
{ "sp3", 0x03, 352, 288, 15, 4, 792, 396, 11880, 100, 40*16368, 8192, 384000, 0, -1, PROFILE_S|PROFILE_ADAPTQUANT },
{ "asp0", 0xf0, 176, 144, 30, 1, 297, 99, 2970, 100, 10*16368, 2048, 128000, 0, -1, PROFILE_AS },
{ "asp1", 0xf1, 176, 144, 30, 4, 297, 99, 2970, 100, 10*16368, 2048, 128000, 0, -1, PROFILE_AS },
{ "asp2", 0xf2, 352, 288, 15, 4, 1188, 396, 5940, 100, 40*16368, 4096, 384000, 0, -1, PROFILE_AS },
{ "asp3", 0xf3, 352, 288, 30, 4, 1188, 396, 11880, 100, 40*16368, 4096, 768000, 0, -1, PROFILE_AS },
/* ISMA Profile 1, (ASP) @ L3b (CIF, 1.5 Mb/s) CIF(352x288), 30fps, 1.5Mbps max ??? */
{ "asp4", 0xf4, 352, 576, 30, 4, 2376, 792, 23760, 50, 80*16368, 8192, 3000000, 0, -1, PROFILE_AS },
{ "asp5", 0xf5, 720, 576, 30, 4, 4860, 1620, 48600, 25, 112*16368, 16384, 8000000, 0, -1, PROFILE_AS },
// information provided by DivXNetworks, USA.
// "DivX Certified Profile Compatibility v1.1", February 2005
{ "dxnhandheld", 0x00, 176, 144, 15, 1, 198, 99, 1485, 100, 32*8192, -1, 537600, 800000, 0, PROFILE_ADAPTQUANT|PROFILE_DXN },
{ "dxnportntsc", 0x00, 352, 240, 30, 1, 990, 330, 36000, 100, 384*8192, -1, 4854000, 8000000, 1, PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_DXN },
{ "dxnportpal", 0x00, 352, 288, 25, 1, 1188, 396, 36000, 100, 384*8192, -1, 4854000, 8000000, 1, PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_DXN },
{ "dxnhtntsc", 0x00, 720, 480, 30, 1, 4050, 1350, 40500, 100, 384*8192, -1, 4854000, 8000000, 1, PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_INTERLACE|PROFILE_DXN },
{ "dxnhtpal", 0x00, 720, 576, 25, 1, 4860, 1620, 40500, 100, 384*8192, -1, 4854000, 8000000, 1, PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_INTERLACE|PROFILE_DXN },
{ "dxnhdtv", 0x00, 1280, 720, 30, 1,10800, 3600, 108000, 100, 768*8192, -1, 9708400, 16000000, 2, PROFILE_4MV|PROFILE_ADAPTQUANT|PROFILE_BVOP|PROFILE_INTERLACE|PROFILE_DXN },
{ NULL, 0x00, 0, 0, 0, 0, 0
|