[xiph-commits] r9185 - in experimental/derf/theora-exp:
include/theora lib
tterribe at motherfish-iii.xiph.org
tterribe at motherfish-iii.xiph.org
Mon Apr 25 18:55:55 PDT 2005
Author: tterribe
Date: 2005-04-25 18:55:52 -0700 (Mon, 25 Apr 2005)
New Revision: 9185
Modified:
experimental/derf/theora-exp/include/theora/theoraenc.h
experimental/derf/theora-exp/lib/encint.h
experimental/derf/theora-exp/lib/encode.c
Log:
Add VP3-compatibility mode to the encoder to produce video that can be
losslessly transcoded back to VP3.
Modified: experimental/derf/theora-exp/include/theora/theoraenc.h
===================================================================
--- experimental/derf/theora-exp/include/theora/theoraenc.h 2005-04-25 21:33:07 UTC (rev 9184)
+++ experimental/derf/theora-exp/include/theora/theoraenc.h 2005-04-26 01:55:52 UTC (rev 9185)
@@ -82,6 +82,34 @@
* \retval OC_EINVAL \a _buf_sz is not <tt>sizeof(ogg_uint32_t)</tt>.
* \retval OC_IMPL Not supported by this implementation.*/
#define OC_ENCCTL_SET_KEYFRAME_FREQUENCY_FORCE (4)
+/**Disables any encoder features that would prevent lossless transcoding back
+ * to VP3.
+ * This primarily means disabling block-level QI values and not using 4MV mode
+ * when any of the luma blocks in a macro block are not coded.
+ * It also includes using the VP3 quantization tables and Huffman codes; if you
+ * set them explicitly after calling this function, the resulting stream will
+ * not by VP3-compatible.
+ * If you enable VP3-compatibility when encoding 4:2:2 or 4:4:4 source
+ * material, or when using a picture region smaller than the full frame (e.g.
+ * a non-multiple-of-16 width or height), then non-VP3 bitstream features will
+ * still be disabled, but the stream will still not be VP3-compatible, as VP3
+ * was not capable of encoding such formats.
+ * If you call this after encoding has already begun, then the quantization
+ * tables and codebooks cannot be changed, but the frame-level features will
+ * be enabled or disabled as requested.
+ *
+ * \param[in] _buf <tt>int</tt>: a non-zero value to enable VP3 compatibility,
+ * or 0 to disable it (the default).
+ * \param[out] _buf <tt>int</tt>: 1 if all bitstream features required for
+ * VP3-compatibility could be set, and 0 otherwise.
+ * The latter will be returned if with pixel format is not
+ * 4:2:0, the picture region is smaller than the full frame,
+ * or if encoding has begun, preventing the quantization
+ * tables and codebooks from being set.
+ * \retval OC_FAULT \a _enc_ctx or \a _buf is <tt>NULL</tt>.
+ * \retval OC_EINVAL \a _buf_sz is not <tt>sizeof(int)</tt>.
+ * \retval OC_IMPL Not supported by this implementation.*/
+#define OC_ENCCTL_SET_VP3_COMPATIBLE (10)
/*@}*/
Modified: experimental/derf/theora-exp/lib/encint.h
===================================================================
--- experimental/derf/theora-exp/lib/encint.h 2005-04-25 21:33:07 UTC (rev 9184)
+++ experimental/derf/theora-exp/lib/encint.h 2005-04-26 01:55:52 UTC (rev 9185)
@@ -151,6 +151,8 @@
theora_huff_code huff_codes[OC_NHUFFMAN_TABLES][OC_NDCT_TOKENS];
/*The scale factor for the current quality setting.*/
float qscale;
+ /*Whether or not VP3-compatibility is enabled.*/
+ int vp3_compatible;
/*The quantization parameters in use.*/
theora_quant_info qinfo;
/*Pointers to the quantization tables in use.*/
Modified: experimental/derf/theora-exp/lib/encode.c
===================================================================
--- experimental/derf/theora-exp/lib/encode.c 2005-04-25 21:33:07 UTC (rev 9184)
+++ experimental/derf/theora-exp/lib/encode.c 2005-04-26 01:55:52 UTC (rev 9185)
@@ -660,6 +660,8 @@
_enc->qis[fti][0]=qi0;
_enc->nqis[fti]=1;
}
+ /*If we're in VP3 compatibility mode, just use the first quantizer.*/
+ if(_enc->vp3_compatible)_enc->nqis[fti]=1;
}
}
@@ -2154,6 +2156,11 @@
/*Finally, pick the mode with the cheapest estimated bit cost.*/
mb->mode=0;
for(modei=1;modei<OC_NMODES;modei++)if(bits[modei]<bits[mb->mode]){
+ /*Do not select 4MV mode when not all the luma blocks are coded when
+ we're in VP3 compatibility mode.*/
+ if(_enc->vp3_compatible&&modei==OC_MODE_INTER_MV_FOUR&&ncoded_luma<4){
+ continue;
+ }
mb->mode=modei;
}
#if defined(OC_BITRATE_STATS)
@@ -2201,8 +2208,6 @@
last_mv[0][1]=mbmv[1];
}break;
case OC_MODE_INTER_MV_FOUR:{
- /*TODO: Handle the case when less than 4 luma blocks are being
- coded.*/
mvbitsa+=mb4mvbitsa;
mvbitsb+=mb4mvbitsb;
if(ncoded_luma>0){
@@ -2492,6 +2497,8 @@
_enc->psych=oc_psych_alloc(_enc);
/*Reset the packet-out state machine.*/
_enc->packet_state=OC_PACKET_INFO_HDR;
+ /*Mark us as not VP3-compatible.*/
+ _enc->vp3_compatible=0;
/*Set the Huffman codes and quantization parameters to the defaults.*/
memcpy(_enc->huff_codes,OC_VP31_HUFF_CODES,sizeof(_enc->huff_codes));
oc_enc_set_quant_params(_enc,NULL);
@@ -2545,28 +2552,55 @@
return oc_enc_set_huffman_codes(_enc,(theora_huff_table *)_buf);
}break;
case OC_ENCCTL_SET_QUANT_PARAMS:{
- if(_buf==NULL&&_buf_sz!=0||
- _buf!=NULL&&_buf_sz!=sizeof(theora_quant_info)){
- return OC_EINVAL;
- }
- return oc_enc_set_quant_params(_enc,(theora_quant_info *)_buf);
+ if(_buf==NULL&&_buf_sz!=0||
+ _buf!=NULL&&_buf_sz!=sizeof(theora_quant_info)){
+ return OC_EINVAL;
+ }
+ return oc_enc_set_quant_params(_enc,(theora_quant_info *)_buf);
}break;
case OC_ENCCTL_SET_KEYFRAME_FREQUENCY_FORCE:{
- ogg_uint32_t keyframe_frequency_force;
- if(_enc==NULL||_buf==NULL)return OC_FAULT;
- if(_buf_sz!=sizeof(ogg_uint32_t))return OC_EINVAL;
- keyframe_frequency_force=*(ogg_uint32_t *)_buf;
- if(_enc->packet_state==OC_PACKET_INFO_HDR){
- /*It's still early enough to enlarge keyframe_granule_shift.*/
- _enc->state.info.keyframe_granule_shift=
- OC_MAXI(_enc->state.info.keyframe_granule_shift,
- OC_MINI(31,oc_ilog(keyframe_frequency_force-1)));
- }
- _enc->keyframe_frequency_force=OC_MINI(keyframe_frequency_force,
- 1U<<_enc->state.info.keyframe_granule_shift);
- (*(ogg_uint32_t *)_buf)=_enc->keyframe_frequency_force;
- return 0;
+ ogg_uint32_t keyframe_frequency_force;
+ if(_enc==NULL||_buf==NULL)return OC_FAULT;
+ if(_buf_sz!=sizeof(ogg_uint32_t))return OC_EINVAL;
+ keyframe_frequency_force=*(ogg_uint32_t *)_buf;
+ if(_enc->packet_state==OC_PACKET_INFO_HDR){
+ /*It's still early enough to enlarge keyframe_granule_shift.*/
+ _enc->state.info.keyframe_granule_shift=
+ OC_MAXI(_enc->state.info.keyframe_granule_shift,
+ OC_MINI(31,oc_ilog(keyframe_frequency_force-1)));
+ }
+ _enc->keyframe_frequency_force=OC_MINI(keyframe_frequency_force,
+ 1U<<_enc->state.info.keyframe_granule_shift);
+ (*(ogg_uint32_t *)_buf)=_enc->keyframe_frequency_force;
+ return 0;
}break;
+ case OC_ENCCTL_SET_VP3_COMPATIBLE:{
+ int vp3_compatible;
+ int ret;
+ if(_enc==NULL||_buf==NULL)return OC_FAULT;
+ if(_buf_sz!=sizeof(int))return OC_EINVAL;
+ vp3_compatible=*(int *)_buf;
+ _enc->vp3_compatible=vp3_compatible;
+ ret=oc_enc_set_huffman_codes(_enc,OC_VP31_HUFF_CODES);
+ if(ret<0)vp3_compatible=0;
+ ret=oc_enc_set_quant_params(_enc,&OC_VP31_QUANT_INFO);
+ if(ret<0)vp3_compatible=0;
+ if(_enc->state.info.pixel_fmt!=OC_PF_420||
+ _enc->state.info.pic_width<_enc->state.info.frame_width||
+ _enc->state.info.pic_height<_enc->state.info.frame_height||
+ /*If we have more than 4095 super blocks, VP3's RLE coding might
+ overflow.
+ We could overcome this by ensuring we flip the coded/not-coded flags on
+ at lease one super block in the frame, but we pick the simple solution
+ of just marking the stream incompatible instead.
+ It's unlikely the old VP3 codec would be able to decode streams at this
+ resolution in real time in the first place.*/
+ _enc->state.nsbs>4095){
+ vp3_compatible=0;
+ }
+ *((int *)_buf)=vp3_compatible;
+ return 0;
+ }break;
default:return OC_IMPL;
}
}
More information about the commits
mailing list