From fd97b5a8a3e96f883b3cf92560e9a4a5d5bad732 Mon Sep 17 00:00:00 2001 From: Wim Taymans Date: Sun, 3 Feb 2002 20:10:04 +0000 Subject: [PATCH] Assorted fixes. Original commit message from CVS: Assorted fixes. Use the new clocking stuff. --- configure.ac | 2 + ext/mad/Makefile.am | 1 - ext/mad/gstmad.c | 73 +++++++++++++++++++++++++++++--- ext/mad/gstmad.h | 80 ----------------------------------- gst/mpegstream/gstmpegdemux.c | 52 ++++++++++++++++++++--- 5 files changed, 113 insertions(+), 95 deletions(-) delete mode 100644 ext/mad/gstmad.h diff --git a/configure.ac b/configure.ac index 91be69f5de..1c183b1892 100644 --- a/configure.ac +++ b/configure.ac @@ -763,6 +763,7 @@ gst/chart/Makefile gst/cutter/Makefile gst/deinterlace/Makefile gst/flx/Makefile +gst/goom/Makefile gst/intfloat/Makefile gst/law/Makefile gst/level/Makefile @@ -835,6 +836,7 @@ ext/shout/Makefile ext/sidplay/Makefile ext/smoothwave/Makefile ext/vorbis/Makefile +ext/tarkin/Makefile ext/xmms/Makefile gst-libs/Makefile gst-libs/gst/Makefile diff --git a/ext/mad/Makefile.am b/ext/mad/Makefile.am index d58d721488..a0468da3b2 100644 --- a/ext/mad/Makefile.am +++ b/ext/mad/Makefile.am @@ -7,4 +7,3 @@ libgstmad_la_CFLAGS = $(GST_CFLAGS) libgstmad_la_LIBADD = $(GST_LIBS) $(MAD_LIBS) libgstmad_la_LDFLAGS = @GST_PLUGIN_LDFLAGS@ -noinst_HEADERS = gstmad.h diff --git a/ext/mad/gstmad.c b/ext/mad/gstmad.c index bba6e671a1..f5bdae1653 100644 --- a/ext/mad/gstmad.c +++ b/ext/mad/gstmad.c @@ -17,8 +17,52 @@ * Boston, MA 02111-1307, USA. */ +#include + #include -#include "gstmad.h" +#include + +#define GST_TYPE_MAD \ + (gst_mad_get_type()) +#define GST_MAD(obj) \ + (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_MAD,GstMad)) +#define GST_MAD_CLASS(klass) \ + (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_MAD,GstMad)) +#define GST_IS_MAD(obj) \ + (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_MAD)) +#define GST_IS_MAD_CLASS(obj) \ + (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_MAD)) + +typedef struct _GstMad GstMad; +typedef struct _GstMadClass GstMadClass; + +struct _GstMad { + GstElement element; + + /* pads */ + GstPad *sinkpad,*srcpad; + + /* state */ + struct mad_stream stream; + struct mad_frame frame; + struct mad_synth synth; + guchar *tempbuffer; + glong tempsize; + gboolean need_sync; + guint64 last_time; + guint64 framestamp; /* timestamp-like, but counted in frames */ + guint64 sync_point; + guint64 total_samples; /* the number of samples since the sync point */ + + /* info */ + struct mad_header header; + gboolean new_header; + gint channels; +}; + +struct _GstMadClass { + GstElementClass parent_class; +}; /* elementfactory information */ static GstElementDetails gst_mad_details = { @@ -140,6 +184,8 @@ gst_mad_init (GstMad *mad) mad->need_sync = TRUE; mad->last_time = 0; mad->framestamp = 0; + mad->total_samples = 0; + mad->sync_point = 0; mad->new_header = TRUE; } @@ -213,6 +259,11 @@ gst_mad_chain (GstPad *pad, GstBuffer *buffer) data = GST_BUFFER_DATA (buffer); size = GST_BUFFER_SIZE (buffer); + if (!GST_PAD_IS_CONNECTED (mad->srcpad)) { + gst_buffer_unref (buffer); + return; + } + while (size > 0) { gint tocopy; guchar *mad_input_buffer; @@ -259,8 +310,18 @@ gst_mad_chain (GstPad *pad, GstBuffer *buffer) outbuffer = gst_buffer_new (); outdata = (gint16 *) GST_BUFFER_DATA (outbuffer) = g_malloc (nsamples * nchannels * 2); GST_BUFFER_SIZE (outbuffer) = nsamples * nchannels * 2; - GST_BUFFER_TIMESTAMP (outbuffer) = GST_BUFFER_TIMESTAMP (buffer); - + + mad->total_samples += nsamples; + + if (GST_BUFFER_TIMESTAMP (buffer) != -1) { + if (GST_BUFFER_TIMESTAMP (buffer) > mad->sync_point) { + mad->sync_point = GST_BUFFER_TIMESTAMP (buffer); + mad->total_samples = 0; + } + } + GST_BUFFER_TIMESTAMP (outbuffer) = mad->sync_point + + mad->total_samples * 1000000LL / mad->frame.header.samplerate; + /* end of new bit */ while (nsamples--) { /* output sample(s) in 16-bit signed native-endian PCM */ @@ -291,10 +352,7 @@ gst_mad_chain (GstPad *pad, GstBuffer *buffer) NULL))); } - if (GST_PAD_IS_CONNECTED (mad->srcpad)) - gst_pad_push (mad->srcpad, outbuffer); - else - gst_buffer_unref (outbuffer); + gst_pad_push (mad->srcpad, outbuffer); next: /* figure out how many bytes mad consumed */ consumed = mad->stream.next_frame - mad_input_buffer; @@ -323,6 +381,7 @@ gst_mad_change_state (GstElement *element) mad_stream_init (&mad->stream); mad_frame_init (&mad->frame); mad_synth_init (&mad->synth); + mad->tempsize=0; break; case GST_STATE_PAUSED_TO_PLAYING: /* do something to get out of the chain function faster */ diff --git a/ext/mad/gstmad.h b/ext/mad/gstmad.h deleted file mode 100644 index 26874d6be2..0000000000 --- a/ext/mad/gstmad.h +++ /dev/null @@ -1,80 +0,0 @@ -/* Gnome-Streamer - * Copyright (C) <1999> Erik Walthinsen - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library 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 - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - */ - - -#ifndef __GST_MAD_H__ -#define __GST_MAD_H__ - - -#include - -#include - -#ifdef __cplusplus -extern "C" { -#endif /* __cplusplus */ - -#define GST_TYPE_MAD \ - (gst_mad_get_type()) -#define GST_MAD(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_MAD,GstMad)) -#define GST_MAD_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_MAD,GstMad)) -#define GST_IS_MAD(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_MAD)) -#define GST_IS_MAD_CLASS(obj) \ - (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_MAD)) - -typedef struct _GstMad GstMad; -typedef struct _GstMadClass GstMadClass; - -struct _GstMad { - GstElement element; - - /* pads */ - GstPad *sinkpad,*srcpad; - - /* state */ - struct mad_stream stream; - struct mad_frame frame; - struct mad_synth synth; - guchar *tempbuffer; - glong tempsize; - gboolean need_sync; - guint64 last_time; - guint64 framestamp; /* timestamp-like, but counted in frames */ - - /* info */ - struct mad_header header; - gboolean new_header; - gint channels; -}; - -struct _GstMadClass { - GstElementClass parent_class; -}; - -GType gst_mad_get_type(void); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - - -#endif /* __GST_MAD_H__ */ diff --git a/gst/mpegstream/gstmpegdemux.c b/gst/mpegstream/gstmpegdemux.c index 9d14aa1363..f724e7f285 100644 --- a/gst/mpegstream/gstmpegdemux.c +++ b/gst/mpegstream/gstmpegdemux.c @@ -135,6 +135,9 @@ static gboolean gst_mpeg_demux_parse_packet (GstMPEGParse *mpeg_parse, GstBuffe static gboolean gst_mpeg_demux_parse_pes (GstMPEGParse *mpeg_parse, GstBuffer *buffer); static void gst_mpeg_demux_send_data (GstMPEGParse *mpeg_parse, GstData *data); +static GstElementStateReturn + gst_mpeg_demux_change_state (GstElement *element); + static GstMPEGParseClass *parent_class = NULL; /*static guint gst_mpeg_demux_signals[LAST_SIGNAL] = { 0 };*/ @@ -164,16 +167,21 @@ static void gst_mpeg_demux_class_init (GstMPEGDemuxClass *klass) { GstMPEGParseClass *mpeg_parse_class; + GstElementClass *gstelement_class; parent_class = g_type_class_ref (GST_TYPE_MPEG_PARSE); mpeg_parse_class = (GstMPEGParseClass *) klass; + gstelement_class = (GstElementClass *) klass; + + gstelement_class->change_state = gst_mpeg_demux_change_state; mpeg_parse_class->parse_packhead = gst_mpeg_demux_parse_packhead; mpeg_parse_class->parse_syshead = gst_mpeg_demux_parse_syshead; mpeg_parse_class->parse_packet = gst_mpeg_demux_parse_packet; mpeg_parse_class->parse_pes = gst_mpeg_demux_parse_pes; mpeg_parse_class->send_data = gst_mpeg_demux_send_data; + } static void @@ -508,10 +516,6 @@ done: GST_DEBUG (0,"mpeg_demux::parse_packet: 0x%02X: we have an audio packet\n", id); outpad = &mpeg_demux->audio_pad[id & 0x1F]; outoffset = mpeg_demux->audio_offset[id & 0x1F]; - if (pts == -1) - pts = mpeg_demux->audio_PTS[id & 0x1F]; - else - mpeg_demux->audio_PTS[id & 0x1F] = pts; mpeg_demux->audio_offset[id & 0x1F] += datalen; /* video */ } else if ((id >= 0xE0) && (id <= 0xEF)) { @@ -547,10 +551,15 @@ done: outbuf = gst_buffer_create_sub (buffer, headerlen+4, datalen); GST_BUFFER_OFFSET (outbuf) = outoffset; - GST_BUFFER_TIMESTAMP (outbuf) = (pts * 100LL)/9LL; + if (pts != -1) { + GST_BUFFER_TIMESTAMP (outbuf) = (pts * 100LL)/9LL; + } + else { + GST_BUFFER_TIMESTAMP (outbuf) = -1LL; + } GST_DEBUG (0,"mpeg_demux::parse_packet: pushing buffer of len %d id %d, ts %lld\n", datalen, id, GST_BUFFER_TIMESTAMP (outbuf)); - gst_pad_push ((*outpad),outbuf); + gst_pad_push ((*outpad), outbuf); } return TRUE; @@ -816,6 +825,35 @@ _forall_pads (GstMPEGDemux *mpeg_demux, GFunc fun, gpointer user_data) } } +static GstElementStateReturn +gst_mpeg_demux_change_state (GstElement *element) +{ + GstMPEGDemux *mpeg_demux = GST_MPEG_DEMUX (element); + gint i; + + switch (GST_STATE_TRANSITION (element)) { + case GST_STATE_READY_TO_PAUSED: + break; + case GST_STATE_PAUSED_TO_READY: + for (i=0;ivideo_offset[i] = 0; + mpeg_demux->video_PTS[i] = 0; + } + for (i=0;iaudio_offset[i] = 0; + mpeg_demux->audio_PTS[i] = 0; + } + break; + case GST_STATE_READY_TO_NULL: + break; + default: + break; + } + + return GST_ELEMENT_CLASS (parent_class)->change_state (element); +} + + gboolean gst_mpeg_demux_plugin_init (GModule *module, GstPlugin *plugin) { @@ -833,12 +871,12 @@ gst_mpeg_demux_plugin_init (GModule *module, GstPlugin *plugin) g_return_val_if_fail (factory != NULL, FALSE); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (sink_factory)); - gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (audio_factory)); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (video_mpeg1_factory)); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (video_mpeg2_factory)); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (private1_factory)); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (private2_factory)); gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (subtitle_factory)); + gst_elementfactory_add_padtemplate (factory, GST_PADTEMPLATE_GET (audio_factory)); gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory));