ext/mad/gstmad.c: Allow for mp3 rate/channels changes. However, only very conservatively. Reason that we *have* to en...

Original commit message from CVS:
* ext/mad/gstmad.c: (gst_mad_check_caps_reset),
(gst_mad_change_state):
Allow for mp3 rate/channels changes. However, only very
conservatively. Reason that we *have* to enable this is smiply
because the mad find_sync() function is not good enough, it will
regularly sync on random data as valid frames and therefore make
us provide random caps as *final* caps of the stream. The best fix
I could think of is to simply require several of the same stream
changes in a row before we change caps.
The actual testcase that works now is #
* ext/ogg/Makefile.am:
* ext/ogg/gstogg.c: (plugin_init):
* ext/ogg/gstogmparse.c:
OGM support (video only for now; I need an audio sample file).
* gst/asfdemux/gstasfdemux.c: (gst_asf_demux_base_init),
(gst_asf_demux_process_stream), (gst_asf_demux_video_caps),
(gst_asf_demux_add_video_stream):
WMV extradata.
* gst/playback/gstplaybasebin.c: (unknown_type):
Don't error out on single unknown-types after all. It's wrong.
If we found type of video and audio but not of a subtitle stream,
it will still error out (which is unwanted). Will find a better fix
later on.
* gst/typefind/gsttypefindfunctions.c: (ogmvideo_type_find),
(ogmaudio_type_find), (plugin_init):
OGM support.
This commit is contained in:
Ronald S. Bultje 2004-09-20 12:40:40 +00:00
parent 545c4c91d8
commit 1b7b0e099d
3 changed files with 70 additions and 24 deletions

View file

@ -1,3 +1,32 @@
2004-09-20 Ronald S. Bultje <rbultje@ronald.bitfreak.net>
* ext/mad/gstmad.c: (gst_mad_check_caps_reset),
(gst_mad_change_state):
Allow for mp3 rate/channels changes. However, only very
conservatively. Reason that we *have* to enable this is smiply
because the mad find_sync() function is not good enough, it will
regularly sync on random data as valid frames and therefore make
us provide random caps as *final* caps of the stream. The best fix
I could think of is to simply require several of the same stream
changes in a row before we change caps.
The actual testcase that works now is #
* ext/ogg/Makefile.am:
* ext/ogg/gstogg.c: (plugin_init):
* ext/ogg/gstogmparse.c:
OGM support (video only for now; I need an audio sample file).
* gst/asfdemux/gstasfdemux.c: (gst_asf_demux_base_init),
(gst_asf_demux_process_stream), (gst_asf_demux_video_caps),
(gst_asf_demux_add_video_stream):
WMV extradata.
* gst/playback/gstplaybasebin.c: (unknown_type):
Don't error out on single unknown-types after all. It's wrong.
If we found type of video and audio but not of a subtitle stream,
it will still error out (which is unwanted). Will find a better fix
later on.
* gst/typefind/gsttypefindfunctions.c: (ogmvideo_type_find),
(ogmaudio_type_find), (plugin_init):
OGM support.
2004-09-20 Johan Dahlin <johan@gnome.org>
* ext/jpeg/gstjpegdec.c (gst_jpegdec_chain): Allocate the buffer

View file

@ -74,8 +74,9 @@ struct _GstMad
GstTagList *tags;
/* negotiated format */
gint rate;
gint channels;
gint rate, pending_rate;
gint channels, pending_channels;
gint times_pending;
gboolean caps_set; /* used to keep track of whether to change/update caps */
GstIndex *index;
@ -1153,7 +1154,16 @@ gst_mad_check_caps_reset (GstMad * mad)
GST_DEBUG
("Header changed from %d Hz/%d ch to %d Hz/%d ch, failed sync after seek ?",
mad->rate, mad->channels, rate, nchannels);
return;
/* we're conservative on stream changes. However, our *initial* caps
* might have been wrong as well - mad ain't perfect in syncing. So,
* we count caps changes and change if we pass a limit treshold (3). */
if (nchannels != mad->pending_channels || rate != mad->pending_rate) {
mad->times_pending = 0;
mad->pending_channels = nchannels;
mad->pending_rate = rate;
}
if (++mad->times_pending < 3)
return;
}
}
gst_mad_update_info (mad);
@ -1493,6 +1503,7 @@ gst_mad_change_state (GstElement * element)
mad->rate = 0;
mad->channels = 0;
mad->caps_set = FALSE;
mad->times_pending = mad->pending_rate = mad->pending_channels = 0;
mad->vbr_average = 0;
mad->segment_start = 0;
mad->new_header = TRUE;

View file

@ -70,7 +70,7 @@ static gboolean gst_asf_demux_setup_pad (GstASFDemux * asf_demux,
static GstElementStateReturn gst_asf_demux_change_state (GstElement * element);
static GstCaps *gst_asf_demux_video_caps (guint32 codec_fcc,
asf_stream_video_format * video, char **codec_name);
asf_stream_video_format * video, guint8 * extradata, char **codec_name);
static GstCaps *gst_asf_demux_audio_caps (guint16 codec_id,
asf_stream_audio * audio, guint8 * extradata, char **codec_name);
@ -154,7 +154,7 @@ gst_asf_demux_base_init (gpointer g_class)
vidcaps = gst_caps_new_empty ();
for (i = 0; vid_list[i] != 0; i++) {
temp = gst_asf_demux_video_caps (vid_list[i], NULL, NULL);
temp = gst_asf_demux_video_caps (vid_list[i], NULL, NULL, NULL);
gst_caps_append (vidcaps, temp);
}
@ -942,8 +942,6 @@ gst_asf_demux_process_stream (GstASFDemux * asf_demux, guint64 * obj_size)
asf_stream_video video_object;
asf_stream_video_format video_format_object;
guint16 size;
GstBuffer *buf;
guint32 got_bytes;
guint16 id;
/* Get the rest of the header's header */
@ -1018,21 +1016,6 @@ gst_asf_demux_process_stream (GstASFDemux * asf_demux, guint64 * obj_size)
if (!gst_asf_demux_add_video_stream (asf_demux, &video_format_object, id))
return FALSE;
/* Read any additional information */
if (size) {
got_bytes = gst_bytestream_read (asf_demux->bs, &buf, size);
/* There is additional data */
while (got_bytes < size) {
guint32 remaining;
GstEvent *event;
gst_bytestream_get_status (asf_demux->bs, &remaining, &event);
gst_event_unref (event);
got_bytes = gst_bytestream_read (asf_demux->bs, &buf, size);
}
}
break;
default:
GST_ELEMENT_ERROR (asf_demux, STREAM, WRONG_TYPE, (NULL),
@ -1743,7 +1726,7 @@ gst_asf_demux_add_audio_stream (GstASFDemux * asf_demux,
static GstCaps *
gst_asf_demux_video_caps (guint32 codec_fcc,
asf_stream_video_format * video, char **codec_name)
asf_stream_video_format * video, guint8 * extradata, char **codec_name)
{
GstCaps *caps = NULL;
gint width = 0, height = 0;
@ -1864,6 +1847,17 @@ gst_asf_demux_video_caps (guint32 codec_fcc,
"width", G_TYPE_INT, video->width,
"height", G_TYPE_INT, video->height,
"framerate", G_TYPE_DOUBLE, (double) 25, NULL);
if (extradata) {
GstBuffer *buffer;
buffer = gst_buffer_new_and_alloc (video->size);
memcpy (GST_BUFFER_DATA (buffer), extradata, video->size);
/* gst_util_dump_mem (GST_BUFFER_DATA (buffer), video->size); */
gst_caps_set_simple (caps, "codec_data", GST_TYPE_BUFFER, buffer, NULL);
gst_data_unref (GST_DATA (buffer));
}
} else {
gst_caps_set_simple (caps,
"width", GST_TYPE_INT_RANGE, 1, G_MAXINT,
@ -1883,6 +1877,7 @@ gst_asf_demux_add_video_stream (GstASFDemux * asf_demux,
gchar *name = NULL;
char *codec_name = NULL;
GstTagList *list = gst_tag_list_new ();
gint size_left = video->size - 40;
/* Create the audio pad */
name = g_strdup_printf ("video_%02d", asf_demux->num_video_streams);
@ -1890,7 +1885,18 @@ gst_asf_demux_add_video_stream (GstASFDemux * asf_demux,
g_free (name);
/* Now try some gstreamer formatted MIME types (from gst_avi_demux_strf_vids) */
caps = gst_asf_demux_video_caps (video->tag, video, &codec_name);
if (size_left) {
guint8 *extradata;
GST_WARNING_OBJECT (asf_demux,
"asfdemux: Video header contains %d bytes of codec specific data",
size_left);
gst_bytestream_peek_bytes (asf_demux->bs, &extradata, size_left);
caps = gst_asf_demux_video_caps (video->tag, video, extradata, &codec_name);
gst_bytestream_flush (asf_demux->bs, size_left);
} else {
caps = gst_asf_demux_video_caps (video->tag, video, NULL, &codec_name);
}
gst_tag_list_add (list, GST_TAG_MERGE_APPEND, GST_TAG_VIDEO_CODEC,
codec_name, NULL);
gst_element_found_tags (GST_ELEMENT (asf_demux), list);