From: <th...@ke...> - 2008-01-14 17:00:16
|
CVS Root: /cvs/gstreamer Module: gst-plugins-base Changes by: thaytan Date: Mon Jan 14 2008 17:00:17 UTC Log message: * ext/theora/gsttheoradec.h: * ext/theora/gsttheoraparse.h: * ext/theora/theoradec.c: * ext/theora/theoraparse.c: Take a 2nd stab at handling libtheora granulepos changes in the decoder and parser by inspecting the bitstream version of the incoming data. Modified files: . : ChangeLog ext/theora : gsttheoradec.h gsttheoraparse.h theoradec.c theoraparse.c Links: http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-base/ChangeLog.diff?r1=1.3694&r2=1.3695 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-base/ext/theora/gsttheoradec.h.diff?r1=1.7&r2=1.8 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-base/ext/theora/gsttheoraparse.h.diff?r1=1.4&r2=1.5 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-base/ext/theora/theoradec.c.diff?r1=1.95&r2=1.96 http://freedesktop.org/cgi-bin/viewcvs.cgi/gstreamer/gst-plugins-base/ext/theora/theoraparse.c.diff?r1=1.10&r2=1.11 ====Begin Diffs==== Index: ChangeLog =================================================================== RCS file: /cvs/gstreamer/gst-plugins-base/ChangeLog,v retrieving revision 1.3694 retrieving revision 1.3695 diff -u -d -r1.3694 -r1.3695 --- ChangeLog 14 Jan 2008 13:11:00 -0000 1.3694 +++ ChangeLog 14 Jan 2008 17:00:00 -0000 1.3695 @@ -1,3 +1,12 @@ +2008-01-14 Jan Schmidt <jan...@su...> + + * ext/theora/gsttheoradec.h: + * ext/theora/gsttheoraparse.h: + * ext/theora/theoradec.c: + * ext/theora/theoraparse.c: + Take a 2nd stab at handling libtheora granulepos changes in the decoder + and parser by inspecting the bitstream version of the incoming data. 2008-01-14 Sebastian Dröge <sl...@ci...> * configure.ac: Index: gsttheoradec.h RCS file: /cvs/gstreamer/gst-plugins-base/ext/theora/gsttheoradec.h,v retrieving revision 1.7 retrieving revision 1.8 diff -u -d -r1.7 -r1.8 --- gsttheoradec.h 7 May 2007 11:43:31 -0000 1.7 +++ gsttheoradec.h 14 Jan 2008 17:00:02 -0000 1.8 @@ -64,6 +64,7 @@ gboolean have_header; gboolean sent_newsegment; + gboolean is_old_bitstream; guint64 granulepos; guint64 granule_shift; Index: gsttheoraparse.h RCS file: /cvs/gstreamer/gst-plugins-base/ext/theora/gsttheoraparse.h,v retrieving revision 1.4 retrieving revision 1.5 diff -u -d -r1.4 -r1.5 --- gsttheoraparse.h 5 Aug 2006 17:08:05 -0000 1.4 +++ gsttheoraparse.h 14 Jan 2008 17:00:02 -0000 1.5 @@ -57,6 +57,7 @@ guint packetno; gboolean send_streamheader; gboolean streamheader_received; + gboolean is_old_bitstream; GstBuffer * streamheader[3]; GQueue * event_queue; Index: theoradec.c RCS file: /cvs/gstreamer/gst-plugins-base/ext/theora/theoradec.c,v retrieving revision 1.95 retrieving revision 1.96 diff -u -d -r1.95 -r1.96 --- theoradec.c 11 Jan 2008 15:48:11 -0000 1.95 +++ theoradec.c 14 Jan 2008 17:00:03 -0000 1.96 @@ -51,15 +51,6 @@ #define GST_CAT_DEFAULT theoradec_debug GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT); -/* With libtheora-1.0beta1 the granulepos scheme was changed: - * where earlier the granulepos refered to the index/beginning - * of a frame, it now refers to the end, which matches the use - * in vorbis/speex. There don't seem to be defines for the - * theora version we're compiling against, so we'll just use - * a run-time check for now. See theora_enc_get_ogg_packet_end_time(). - */ -static gboolean use_old_granulepos; - #define THEORA_DEF_CROP TRUE enum { @@ -150,8 +141,6 @@ gstelement_class->change_state = theora_dec_change_state; GST_DEBUG_CATEGORY_INIT (theoradec_debug, "theoradec", 0, "Theora decoder"); - use_old_granulepos = (theora_version_number () <= 0x00030200); } static void @@ -242,7 +231,7 @@ framenum += granulepos - (framenum << ilog); /* This is 1-based for current libtheora, 0 based for old. Fix up. */ - if (!use_old_granulepos) + if (!dec->is_old_bitstream) framenum -= 1; GST_DEBUG_OBJECT (dec, "framecount=%d, ilog=%u", framenum, ilog); @@ -791,6 +780,7 @@ GstFlowReturn ret = GST_FLOW_OK; gboolean eret; GstEvent *event; + guint32 bitstream_version; GST_DEBUG_OBJECT (dec, "fps %d/%d, PAR %d/%d", dec->info.fps_numerator, dec->info.fps_denominator, @@ -841,6 +831,16 @@ dec->granule_shift = _theora_ilog (dec->info.keyframe_frequency_force - 1); + /* With libtheora-1.0beta1 the granulepos scheme was changed: + * where earlier the granulepos refered to the index/beginning + * of a frame, it now refers to the end, which matches the use + * in vorbis/speex. We check the bitstream version from the header so + * we know which way to interpret the incoming granuepos + */ + bitstream_version = (dec->info.version_major << 16) | + (dec->info.version_minor << 8) | dec->info.version_subminor; + dec->is_old_bitstream = (bitstream_version <= 0x00030200); GST_DEBUG_OBJECT (dec, "after fixup frame dimension %dx%d, offset %d:%d", dec->width, dec->height, dec->offset_x, dec->offset_y); Index: theoraparse.c RCS file: /cvs/gstreamer/gst-plugins-base/ext/theora/theoraparse.c,v retrieving revision 1.10 retrieving revision 1.11 diff -u -d -r1.10 -r1.11 --- theoraparse.c 14 Sep 2006 20:09:18 -0000 1.10 +++ theoraparse.c 14 Jan 2008 17:00:03 -0000 1.11 @@ -313,6 +313,7 @@ GstCaps *caps; gint i; g_assert (!parse->streamheader_received); @@ -341,6 +342,16 @@ parse->fps_d = parse->info.fps_denominator; parse->shift = _theora_ilog (parse->info.keyframe_frequency_force - 1); + bitstream_version = (parse->info.version_major << 16) | + (parse->info.version_minor << 8) | parse->info.version_subminor; + parse->is_old_bitstream = (bitstream_version <= 0x00030200); parse->streamheader_received = TRUE; @@ -391,28 +402,36 @@ static gint64 -make_granulepos (gint64 keyframe, gint64 frame, gint shift) +make_granulepos (GstTheoraParse * parse, gint64 keyframe, gint64 frame) if (keyframe == -1) keyframe = 0; + /* If using newer theora, offset the granulepos by +1, see comment + * in theora_parse_set_streamheader */ + if (!parse->is_old_bitstream) + keyframe += 1; g_return_val_if_fail (frame >= keyframe, -1); - g_return_val_if_fail (frame - keyframe < 1 << shift, -1); + g_return_val_if_fail (frame - keyframe < 1 << parse->shift, -1); - return (keyframe << shift) + (frame - keyframe); + return (keyframe << parse->shift) + (frame - keyframe); -parse_granulepos (gint64 granulepos, gint shift, gint64 * keyframe, - gint64 * frame) +parse_granulepos (GstTheoraParse * parse, gint64 granulepos, + gint64 * keyframe, gint64 * frame) gint64 kf; - kf = granulepos >> shift; + kf = granulepos >> parse->shift; + /* If using newer theora, offset the granulepos by -1, see comment + kf -= 1; if (keyframe) *keyframe = kf; if (frame) - *frame = kf + (granulepos & ((1 << shift) - 1)); + *frame = kf + (granulepos & ((1 << parse->shift) - 1)); static gboolean @@ -474,7 +493,7 @@ next_time = gst_util_uint64_scale_int (GST_SECOND * (frame + 1), parse->fps_d, parse->fps_n); - GST_BUFFER_OFFSET_END (buf) = make_granulepos (keyframe, frame, parse->shift); + GST_BUFFER_OFFSET_END (buf) = make_granulepos (parse, keyframe, frame); GST_BUFFER_OFFSET (buf) = this_time; GST_BUFFER_TIMESTAMP (buf) = this_time; GST_BUFFER_DURATION (buf) = next_time - this_time; @@ -521,7 +540,7 @@ if (parse->prev_keyframe < 0) { if (GST_BUFFER_OFFSET_END_IS_VALID (buf)) { - parse_granulepos (GST_BUFFER_OFFSET_END (buf), parse->shift, + parse_granulepos (parse, GST_BUFFER_OFFSET_END (buf), &parse->prev_keyframe, NULL); } else { /* No previous keyframe known; can't extract one from this frame. That @@ -550,7 +569,7 @@ gint64 keyframe, prev_frame, frame; - parse_granulepos (granulepos, parse->shift, &keyframe, &frame); + parse_granulepos (parse, granulepos, &keyframe, &frame); prev_frame = frame - g_queue_get_length (parse->buffer_queue); if (prev_frame < parse->prev_frame) { @@ -606,7 +625,7 @@ if (GST_BUFFER_OFFSET_END_IS_VALID (buf)) { - parse_granulepos (GST_BUFFER_OFFSET_END (buf), parse->shift, + parse_granulepos (parse, GST_BUFFER_OFFSET_END (buf), &parse->prev_keyframe, NULL); } ret = theora_parse_drain_queue (parse, GST_BUFFER_OFFSET_END (buf)); |