merge from HEAD on 20011016 BRANCH-EVENTS1-200110161 EVENTS1-200110161-ROOT
authorErik Walthinsen <omega@temple-baptist.org>
Wed, 17 Oct 2001 08:51:04 +0000 (08:51 +0000)
committerErik Walthinsen <omega@temple-baptist.org>
Wed, 17 Oct 2001 08:51:04 +0000 (08:51 +0000)
Original commit message from CVS:
merge from HEAD on 20011016

69 files changed:
Makefile.am
REQUIREMENTS
configure.base
debian/README.Debian
debian/gstreamer-plugin-template.postinst
debian/gstreamer-plugin-template.postrm
debian/gstreamer-runtime.postinst
docs/gst/Makefile.am
docs/gst/gstreamer.types.in
gst/Makefile.am
gst/autoplug/gststaticautoplugrender.c
gst/cothreads.h
gst/elements/Makefile.am
gst/elements/gstelements.c
gst/gobject2gtk.c
gst/gobject2gtk.h
gst/gst.c
gst/gst.h
gst/gstautoplug.c
gst/gstbin.c
gst/gstdparam.c [deleted file]
gst/gstdparam.h [deleted file]
gst/gstdparammanager.c [deleted file]
gst/gstdparammanager.h [deleted file]
gst/gstelement.c
gst/gstelement.h
gst/gstelementfactory.c
gst/gstextratypes.c
gst/gstlog.h
gst/gstobject.c
gst/gstpad.c
gst/gstpad.h
gst/gstparse.c
gst/gstpipeline.c
gst/gstplugin.c
gst/gstpluginfeature.c
gst/gstprops.c
gst/gstqueue.c
gst/gstscheduler.c
gst/gstthread.c
gst/gsttrace.c
gst/gsttype.c
gst/gsttypefind.c
gst/gstutils.c
gst/gstutils.h
gst/gstxml.c
include/Makefile.am
include/gstaudio.h [deleted file]
libs/Makefile.am
libs/audio/gstaudio.h
libs/control/Makefile.am [new file with mode: 0644]
libs/control/gstcontrol.c [new file with mode: 0644]
libs/control/gstcontrol.h [new file with mode: 0644]
libs/control/gstdparam.c [new file with mode: 0644]
libs/control/gstdparam.h [new file with mode: 0644]
libs/control/gstdparammanager.c [new file with mode: 0644]
libs/control/gstdparammanager.h [new file with mode: 0644]
libs/control/gstdplinearinterp.c [new file with mode: 0644]
libs/control/gstdplinearinterp.h [new file with mode: 0644]
plugins/elements/Makefile.am
plugins/elements/gstelements.c
plugins/elements/gstqueue.c
test/Makefile.am
test/mpeg2parse.c [deleted file]
test/sinesliders.c
tests/autoplug.c
tools/.gitignore
tools/Makefile.am
tools/gstreamer-guilaunch.c [new file with mode: 0644]

index e319295b683cfc01f2214bcc819c5aa17cd12837..2916ddd30a2ced8303239d54ec1dc78928cdb45d 100644 (file)
@@ -15,7 +15,7 @@ SUBDIRS_DOCS =
 endif
 
 if BUILD_TESTS
-SUBDIRS_TESTS = test tests testsuite
+SUBDIRS_TESTS =
 else
 SUBDIRS_TESTS =
 endif
@@ -47,7 +47,7 @@ EXTRA_DIST = gstreamer.spec.in gstreamer-config.in gstreamer.m4 \
             gstreamer.pc.in gstreamer-uninstalled.pc.in \
             configure.base autogen.sh \
             LICENSE REQUIREMENTS ABOUT-NLS $(man_MANS) \
-            idiottest.mak ltconfig.sh
+            idiottest.mak
 
 dist-hook:
        cp gstreamer.spec $(distdir)
index 6c581ea30c8d2fc6f2162857d5d31845b8fb018c..0795d02e341dd9012eac6269b92400fb1b0a26ef 100644 (file)
@@ -79,9 +79,10 @@ CVS (using autogen.sh):
 
 Required tools:
 ===============
-autoconf
-automake v1.4 or better
-libtool v1.3.5 or better
+autoconf v2.13 or better, 2.52 prefered
+automake v1.4 or better, 1.5 prefered
+libtool v1.4 or better
+pkgconfig 0.8.0 (http://www.freedesktop.org/software/pkgconfig/)
 
 Optional tools:
 ===============
index 810d93356520d79df67357bab0672bed9bffd31b..7597efb68bdec3137beac2bd016999bcf6fb3fbb 100644 (file)
@@ -83,6 +83,9 @@ else
   HAVE_NASM="yes"
 fi
 
+dnl Check for pkgconfig
+AC_CHECK_PROG(HAVE_PKGCONFIG, pkg-config, true, false)
+
 dnl check for gtkdoc
 AC_CHECK_PROG(HAVE_GTK_DOC, gtkdoc-mkdb, true, false)
 AC_CHECK_PROG(HAVE_GTK_DOC, gtkdoc-scanobj, :, false)
@@ -803,8 +806,12 @@ AC_ARG_ENABLE(profiling,
 esac], 
 [USE_PROFILING=no]) dnl Default value
 
-dnl Default value
-GST_CONFIG_DIR=/etc/gstreamer
+dnl default to building registry in the source tree if we are enabling plugin build dir
+if test "x$PLUGINS_USE_BUILDDIR" = xyes; then
+  GST_CONFIG_DIR=$builddir
+else
+  GST_CONFIG_DIR=/etc/gstreamer
+fi
 AC_ARG_WITH(configdir,
 [  --with-configdir             specify path to use for configdir],
 [case "${withval}" in
@@ -1181,6 +1188,7 @@ libs/putbits/Makefile
 libs/idct/Makefile
 libs/audio/Makefile
 libs/bytestream/Makefile
+libs/control/Makefile
 plugins/Makefile
 plugins/a52dec/Makefile
 plugins/aasink/Makefile
@@ -1228,7 +1236,7 @@ plugins/rtp/Makefile
 plugins/rtp/rtpsend/Makefile
 plugins/mulaw/Makefile
 plugins/alaw/Makefile
-plugins/ffmpeg/Makefile
+dnl until ffmpeg is handled by configure plugins/ffmpeg/Makefile
 plugins/filters/Makefile
 plugins/filters/smooth/Makefile
 plugins/filters/median/Makefile
@@ -1281,12 +1289,14 @@ plugins/gsm/Makefile
 plugins/1394/Makefile
 plugins/sdlsink/Makefile
 plugins/dv/Makefile
+plugins/synthesis/Makefile
+plugins/synthesis/sinesrc/Makefile
 gstplay/Makefile
 dnl components/bonobo-gstmediaplay/Makefile
 test/Makefile
 test/xml/Makefile
 test/bindings/Makefile
-test/misc/Makefile
+dnl someone should fix this test/misc/Makefile
 test/memchunk/Makefile
 test/events/Makefile
 tests/Makefile
@@ -1296,7 +1306,7 @@ tests/muxing/Makefile
 testsuite/Makefile
 testsuite/capsnego/Makefile
 testsuite/refcounting/Makefile
-testsuite/plugin/Makefile
+dnl someone should fix this testsuite/plugin/Makefile
 tests/nego/Makefile
 examples/Makefile
 examples/autoplug/Makefile
index 96407182ae652dacdb6b7dc8a8b1378723eacbd1..64d1a1302e0e21ff531482529e9cfec33bd4d3bb 100644 (file)
@@ -19,6 +19,7 @@ recommended plugins:
 
 optional plugins:
 
+   gstreamer-a52dec
    gstreamer-aa
    gstreamer-alsa
    gstreamer-arts
@@ -35,10 +36,12 @@ optional plugins:
    gstreamer-jpeg
    gstreamer-lame
    gstreamer-mad
+   gstreamer-mikmod
    gstreamer-mpeg2dec
    gstreamer-mpg123
    gstreamer-oss
    gstreamer-sdl
+   gstreamer-sid
    gstreamer-vorbis
    gstreamer-x
 
index d1c4e4b60286dc66b49ddc496938307d7bb21d1a..9afaa890b39dc94a9d29812547cb344e7bc5938c 100644 (file)
@@ -3,8 +3,8 @@
 set -e
 
 if [ "$1" = "configure" ]; then
-   gstreamer-register --gst-mask=0
-   gstreamer-compprep --gst-mask=0
+   gstreamer-register --gst-mask=0 || true
+   gstreamer-compprep --gst-mask=0 || true
 fi
 
 #DEBHELPER#
index 95f4dac0cfd09a1bafbc52926d3a38d529a6654d..b8658f30e189f3518ac89096817b87836c4de0d1 100644 (file)
@@ -3,8 +3,8 @@
 set -e
 
 if [ "$1" = "remove" ]; then
-   gstreamer-register --gst-mask=0
-   gstreamer-compprep --gst-mask=0
+   gstreamer-register --gst-mask=0 || true
+   gstreamer-compprep --gst-mask=0 || true
 fi
 
 #DEBHELPER#
index d1c4e4b60286dc66b49ddc496938307d7bb21d1a..9afaa890b39dc94a9d29812547cb344e7bc5938c 100644 (file)
@@ -3,8 +3,8 @@
 set -e
 
 if [ "$1" = "configure" ]; then
-   gstreamer-register --gst-mask=0
-   gstreamer-compprep --gst-mask=0
+   gstreamer-register --gst-mask=0 || true
+   gstreamer-compprep --gst-mask=0 || true
 fi
 
 #DEBHELPER#
index 235a8040a3e465041048c06d5dba5fa84b2b1b3d..a9b1fe92995417ae61b7a813bfb27ba913d1618b 100644 (file)
@@ -9,6 +9,9 @@ DOC_MAIN_SGML_FILE=$(DOC_MODULE)-docs.sgml
 # The directory containing the source code (if it contains documentation).
 DOC_SOURCE_DIR=$(top_srcdir)/gst
 
+# thomas
+# there's something wrong with gstreamer-sections.txt not being in the dist
+# maybe it doesn't resolve
 EXTRA_DIST = gstreamer.types.in gstreamer.hierarchy $(DOC_MODULE)-sections.txt $(DOC_MAIN_SGML_FILE)
 
 HTML_DIR=$(datadir)/gstreamer/html
index 41ade6afbee10324dcda844bbe2963a5d8c05eb5..5020474c6eff87c513d5f3744b39715afffdd7b9 100644 (file)
@@ -16,7 +16,6 @@ gst_fakesink_get_type
 gst_disksrc_get_type
 @GST_HTTPSRC_GET_TYPE@
 gst_fdsrc_get_type
-gst_sinesrc_get_type
 
 gst_fdsink_get_type
 
index da6c2c49b5f68188ec95212f3b9a24e90c91c8fb..6e7583219ab214ecf580fd94efc8977762789d28 100644 (file)
@@ -67,8 +67,6 @@ libgst_la_SOURCES =           \
        gstcaps.c               \
        gstclock.c              \
        gstcpu.c                \
-       gstdparam.c             \
-       gstdparammanager.c      \
        gstelement.c            \
        gstelementfactory.c     \
        gstevent.c              \
@@ -139,12 +137,11 @@ cothreads.o: $(srcdir)/cothreads.c $(srcdir)/cothreads.h $(srcdir)/gst_private.h
 # Generate both marshal files together.  Makes dependency work easier.
 gstmarshal.h: gstmarshal.list
        glib-genmarshal --header --prefix=gst_marshal gstmarshal.list > gstmarshal.h
-       echo "#include \"glib-object.h\"" >gstmarshal.c
-       glib-genmarshal --body --prefix=gst_marshal gstmarshal.list >> gstmarshal.c
 
 gstmarshal.c: gstmarshal.list
-       glib-genmarshal --header --prefix=gst_marshal gstmarshal.list > gstmarshal.h
        echo "#include \"glib-object.h\"" >gstmarshal.c
+       echo "#include \"gstlog.h\"" >> gstmarshal.c
+       echo "#include \"gstmarshal.h\"" >> gstmarshal.c
        glib-genmarshal --body --prefix=gst_marshal gstmarshal.list >> gstmarshal.c
 
 ##### end built sources #####
@@ -172,8 +169,6 @@ libgstinclude_HEADERS =             \
        gstclock.h              \
        gstcpu.h                \
        gstdata.h               \
-       gstdparam.h             \
-       gstdparammanager.h      \
        gstelement.h            \
        gstevent.h              \
        gstextratypes.h         \
@@ -201,6 +196,18 @@ noinst_HEADERS =   \
        gstarch.h       \
        gstpropsprivate.h
 
+CFLAGS = \
+       $(LIBGST_CFLAGS) \
+       -D_GNU_SOURCE \
+       -DG_LOG_DOMAIN=g_log_domain_gstreamer \
+       -DGST_CONFIG_DIR=\""$(GST_CONFIG_DIR)"\" \
+       \
+       -W -Wpointer-arith -Wbad-function-cast \
+       -Wcast-align -Wsign-compare \
+       -Wmissing-prototypes -Wmissing-declarations \
+       -Wnested-externs \
+       -Winline -Wno-unused
+
 CFLAGS = $(LIBGST_CFLAGS) -D_GNU_SOURCE -DGST_CONFIG_DIR=\""$(GST_CONFIG_DIR)"\" -Wall
 LIBS = $(LIBGST_LIBS)
 LDFLAGS = ""
index 94b5295ffdf75e6fbc76b89dcbb36aea14c3e07a..0c71fffc0852c8407d59e59ced2717380051eb08 100644 (file)
@@ -187,7 +187,7 @@ gst_autoplug_pads_autoplug_func (GstElement *src, GstPad *pad, GstElement *sink)
       if (state == GST_STATE_PLAYING)
         gst_element_set_state (GST_ELEMENT (gst_element_get_parent (src)), GST_STATE_PAUSED);
        
-      if ((connected = gst_pad_connect (pad, sinkpad))) {
+      if ((connected = gst_pad_try_connect (pad, sinkpad))) {
         if (state == GST_STATE_PLAYING)
           gst_element_set_state (GST_ELEMENT (gst_element_get_parent (src)), GST_STATE_PLAYING);
        break;
index d33a45f7e2e55b4d6ee70f1fa1d11249c86528c1..013ecd676741fff03f08616cd144922a14a078f9 100644 (file)
@@ -66,7 +66,7 @@ struct _cothread_state {
 };
 
 
-cothread_context*              cothread_init();
+cothread_context*              cothread_init           (void);
 cothread_state*                        cothread_create         (cothread_context *ctx);
 void                           cothread_setfunc        (cothread_state *thread, cothread_func func,
                                                         int argc, char **argv);
index 3902ca30c41fcd20174a3124c6790f9dad8a5abb..f50e4f75b4ca79919c724e7cc19d7112d6aa9014 100644 (file)
@@ -25,7 +25,6 @@ libgstelements_la_SOURCES =   \
        gstpipefilter.c         \
        gsttee.c                \
        gstaggregator.c         \
-       gstsinesrc.c            \
        $(GSTHTTPSRC)
 
 noinst_HEADERS =               \
index 799c632029a3842e7bc9399126620588d9f5bbd7..bdd540d49eefd395cabacd6be3b9f855e773a730 100644 (file)
@@ -32,7 +32,6 @@
 #include "gstfdsrc.h"
 #include "gstmultidisksrc.h"
 #include "gstpipefilter.h"
-#include "gstsinesrc.h"
 #include "gsttee.h"
 #include "gstaggregator.h"
 
@@ -64,7 +63,6 @@ static struct _elements_entry _elements[] = {
   { "fdsrc",       gst_fdsrc_get_type,         &gst_fdsrc_details,             NULL },
   { "multidisksrc", gst_multidisksrc_get_type, &gst_multidisksrc_details,      NULL },
   { "pipefilter",   gst_pipefilter_get_type,   &gst_pipefilter_details,        NULL },
-  { "sinesrc",             gst_sinesrc_get_type,       &gst_sinesrc_details,           gst_sinesrc_factory_init },
   { "tee",                 gst_tee_get_type,           &gst_tee_details,               gst_tee_factory_init },
   { "aggregator",   gst_aggregator_get_type,   &gst_aggregator_details,        gst_aggregator_factory_init },
 
@@ -87,13 +85,20 @@ plugin_init (GModule *module, GstPlugin *plugin)
     factory = gst_elementfactory_new (_elements[i].name,
                                       (_elements[i].type) (),
                                       _elements[i].details);
-    if (factory != NULL) {
-      gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory));
-      if (_elements[i].factoryinit) {
-        _elements[i].factoryinit (factory);
+
+    if (!factory)
+      {
+       g_warning ("gst_elementfactory_new failed for `%s'",
+                  _elements[i].name);
+       continue;
       }
-//      g_print("added factory '%s'\n",_elements[i].name);
+
+    gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory));
+    if (_elements[i].factoryinit) {
+      _elements[i].factoryinit (factory);
     }
+//      g_print("added factory '%s'\n",_elements[i].name);
+
     i++;
   }
 
index 7d3f9be8eba748454112561416f2bf98b63e2c90..72165d39c83bb7af7efdb8b29c0a5c7275a0b609 100644 (file)
@@ -2,6 +2,7 @@
 /* Modified by Jamie Gennis 06-2001 */
 #include <string.h>
 #include <stdio.h>
+#include "gstlog.h"
 #include "gobject2gtk.h"
 
 
@@ -126,16 +127,16 @@ g2g_object_class_find_property(GObjectClass *class, const gchar *name)
 
   //fprintf(stderr,"class name is %s\n",gtk_type_name(class->type));
 
-  gtk_object_arg_get_info(class->type,name,&info);
+  // the return value NULL if no error
+  if (gtk_object_arg_get_info(class->type,name,&info) != NULL) {
+    return NULL;
+  }
+  
   spec = g_new0(GParamSpec,1);
 
-  if (info) {
-    spec->name = (gchar *) name;
-    spec->value_type = info->type;
-    spec->flags = info->arg_flags;
-  } else {
-    spec->value_type = GTK_TYPE_NONE;
-  }
+  spec->name = (gchar *) name;
+  spec->value_type = info->type;
+  spec->flags = info->arg_flags;
 
   return spec;
 }
index 87e22c1632827869e630cfaabda7da4492c00b58..6201c12a781c7ae5ad9ea11af8b410cedc66956e 100644 (file)
@@ -23,6 +23,9 @@ GSList *g_slist_delete_link (GSList *list, GSList *llink);
 typedef struct _GObject GObject;
 typedef struct _GObjectClass GObjectClass;
 
+#define g_string_printf   g_string_sprintf
+#define g_string_printfa  g_string_sprintfa
+
 #define g_object_ref(obj)                      gtk_object_ref((GtkObject *)(obj))
 #define g_object_unref(obj)                    gtk_object_unref((GtkObject *)(obj))
 
@@ -79,6 +82,7 @@ typedef struct _GObjectClass GObjectClass;
 #define gst_marshal_VOID__VOID                 gtk_marshal_NONE__NONE
 #define gst_marshal_VOID__BOOLEAN              gtk_marshal_NONE__BOOL
 #define gst_marshal_VOID__INT                  gtk_marshal_NONE__INT
+#define gst_marshal_VOID__INT_INT              gtk_marshal_NONE__INT_INT
 #define gst_marshal_VOID__STRING               gtk_marshal_NONE__STRING
 #define gst_marshal_VOID__POINTER              gtk_marshal_NONE__POINTER
 #define gst_marshal_VOID__OBJECT               gtk_marshal_NONE__POINTER
@@ -241,7 +245,7 @@ struct _GParamSpec {
 };
 
 #define g_value_init(value,t)                  ((value)->type = (t))
-#define g_value_copy                   gtk_arg_copy
+#define g_value_copy(src_val,dest_val) (dest_val = gtk_arg_copy(src_val,dest_val))
 #define g_value_unset(val)
 
 #define g_object_class_install_property                g2g_object_class_install_property
index 0eb794e0bddbebe3e9659814ce93fbec12fb697a..8ecacbacfce96f03f65e0a28ce1270813806c4db 100644 (file)
--- a/gst/gst.c
+++ b/gst/gst.c
@@ -53,6 +53,18 @@ static void          load_plugin_func        (gpointer data, gpointer user_data);
 
 static GSList *preload_plugins = NULL;
 
+const gchar *g_log_domain_gstreamer = "GStreamer";
+
+static void
+debug_log_handler (const gchar *log_domain,
+                  GLogLevelFlags log_level,
+                  const gchar *message,
+                  gpointer user_data)
+{
+  g_log_default_handler(log_domain, log_level, message, user_data);
+  g_on_error_query(NULL);
+}
+
 /**
  * gst_init:
  * @argc: pointer to application's argc
@@ -64,6 +76,7 @@ static GSList *preload_plugins = NULL;
 void 
 gst_init (int *argc, char **argv[]) 
 {
+  GLogLevelFlags llf;
 #ifndef GST_DISABLE_TRACE
   GstTrace *gst_trace;
 #endif
@@ -92,6 +105,9 @@ gst_init (int *argc, char **argv[])
     exit (0);                          // FIXME!
   }
 
+  llf = G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_ERROR | G_LOG_FLAG_FATAL;
+  g_log_set_handler(g_log_domain_gstreamer, llf, debug_log_handler, NULL);
+
   GST_INFO (GST_CAT_GST_INIT, "Initializing GStreamer Core Library");
 
   gst_object_get_type ();
index 9216029c4a31c8daabb7195478f61acb910434c6..032d5d2c57fc24d4b6d0871b265f82c3b16cf917 100644 (file)
--- a/gst/gst.h
+++ b/gst/gst.h
@@ -49,8 +49,6 @@
 #include <gst/gstxml.h>
 #include <gst/cothreads.h>
 #include <gst/gstscheduler.h>
-#include <gst/gstdparam.h>
-#include <gst/gstdparammanager.h>
 #include <gst/gsttimecache.h>
 #include <gst/gstevent.h>
 
index af7736d2683bfc6a4dec0c63c183614e56dc509c..612cd4b9ce54685417fa25cbf2ae15c3fe9e4283 100644 (file)
@@ -61,6 +61,7 @@ GType gst_autoplug_get_type(void)
       sizeof(GstAutoplug),
       4,
       (GInstanceInitFunc)gst_autoplug_init,
+      NULL
     };
     autoplug_type = g_type_register_static (GST_TYPE_OBJECT, "GstAutoplug", &autoplug_info, G_TYPE_FLAG_ABSTRACT);
   }
@@ -194,6 +195,7 @@ gst_autoplugfactory_get_type (void)
       sizeof(GstAutoplugFactory),
       0,
       (GInstanceInitFunc) gst_autoplugfactory_init,
+      NULL
     };
     autoplugfactory_type = g_type_register_static (GST_TYPE_PLUGIN_FEATURE, 
                                                  "GstAutoplugFactory", &autoplugfactory_info, 0);
index 561328e5c06c9b5aba9b92a14becdf17fd251698..4396fe3da4c7f48c8dbbaffb07805593010ab704 100644 (file)
@@ -37,7 +37,7 @@ GstElementDetails gst_bin_details = {
 };
 
 
-static void                    gst_bin_real_destroy            (GObject *object);
+static void                    gst_bin_dispose         (GObject *object);
 
 static GstElementStateReturn   gst_bin_change_state            (GstElement *element);
 static GstElementStateReturn   gst_bin_change_state_norecurse  (GstBin *bin);
@@ -87,6 +87,7 @@ gst_bin_get_type (void)
       sizeof(GstBin),
       8,
       (GInstanceInitFunc)gst_bin_init,
+      NULL
     };
     bin_type = g_type_register_static (GST_TYPE_ELEMENT, "GstBin", &bin_info, 0);
   }
@@ -122,8 +123,7 @@ gst_bin_class_init (GstBinClass *klass)
 
   gstelement_class->change_state =     GST_DEBUG_FUNCPTR (gst_bin_change_state);
 
-// FIXME
-//  gobject_class->destroy =           GST_DEBUG_FUNCPTR (gst_bin_real_destroy);
+  gobject_class->dispose =             GST_DEBUG_FUNCPTR (gst_bin_dispose);
 }
 
 static void
@@ -170,7 +170,7 @@ gst_bin_reset_element_sched (GstElement *element, GstSchedule *sched)
 //    GST_SCHEDULE_ADD_ELEMENT (sched, element);
 }
 
-void
+static void
 gst_bin_set_element_sched (GstElement *element,GstSchedule *sched)
 {
   GList *children;
@@ -211,7 +211,7 @@ gst_bin_set_element_sched (GstElement *element,GstSchedule *sched)
 }
 
 
-void
+static void
 gst_bin_unset_element_sched (GstElement *element)
 {
   GList *children;
@@ -475,13 +475,13 @@ gst_bin_set_state_type (GstBin *bin,
 }
 
 static void
-gst_bin_real_destroy (GObject *object)
+gst_bin_dispose (GObject *object)
 {
   GstBin *bin = GST_BIN (object);
   GList *children, *orig;
   GstElement *child;
 
-  GST_DEBUG (GST_CAT_REFCOUNTING,"destroy()\n");
+  GST_DEBUG (GST_CAT_REFCOUNTING,"dispose\n");
 
   if (bin->children) {
     orig = children = g_list_copy (bin->children);
@@ -500,9 +500,7 @@ gst_bin_real_destroy (GObject *object)
 
   g_cond_free (bin->eoscond);
 
-// FIXME!!!
-//  if (G_OBJECT_CLASS (parent_class)->destroy)
-//    G_OBJECT_CLASS (parent_class)->destroy (object);
+  G_OBJECT_CLASS (parent_class)->dispose (object);
 }
 
 /**
diff --git a/gst/gstdparam.c b/gst/gstdparam.c
deleted file mode 100644 (file)
index c18ec58..0000000
+++ /dev/null
@@ -1,187 +0,0 @@
-/* GStreamer
- * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
- *
- * gstdparam.c: Dynamic Parameter functionality
- *
- * 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.
- */
-
-#include "gst_private.h"
-
-#include "gstdparam.h"
-
-static void gst_dparam_class_init (GstDParamClass *klass);
-static void gst_dparam_base_class_init (GstDParamClass *klass);
-static void gst_dparam_init (GstDParam *dparam);
-
-static void gst_dparam_do_update_realtime (GstDParam *dparam, gint64 timestamp);
-static GValue** gst_dparam_get_point_realtime (GstDParam *dparam, gint64 timestamp);
-
-GType 
-gst_dparam_get_type(void) {
-       static GType dparam_type = 0;
-
-       if (!dparam_type) {
-               static const GTypeInfo dparam_info = {
-                       sizeof(GstDParamClass),
-                       (GBaseInitFunc)gst_dparam_base_class_init,
-                       NULL,
-                       (GClassInitFunc)gst_dparam_class_init,
-                       NULL,
-                       NULL,
-                       sizeof(GstDParam),
-                       0,
-                       (GInstanceInitFunc)gst_dparam_init,
-               };
-               dparam_type = g_type_register_static(GST_TYPE_OBJECT, "GstDParam", &dparam_info, 0);
-       }
-       return dparam_type;
-}
-
-static void
-gst_dparam_base_class_init (GstDParamClass *klass)
-{
-       GObjectClass *gobject_class;
-
-       gobject_class = (GObjectClass*) klass;
-
-}
-
-static void
-gst_dparam_class_init (GstDParamClass *klass)
-{
-       GObjectClass *gobject_class;
-       GstDParamClass *dparam_class;
-       GstObjectClass *gstobject_class;
-
-       gobject_class = (GObjectClass*)klass;
-       dparam_class = (GstDParamClass*)klass;
-       gstobject_class = (GstObjectClass*) klass;
-
-       //gstobject_class->save_thyself = gst_dparam_save_thyself;
-
-}
-
-static void
-gst_dparam_init (GstDParam *dparam)
-{
-       g_return_if_fail (dparam != NULL);
-       GST_DPARAM_VALUE(dparam) = NULL;
-       dparam->lock = g_mutex_new ();
-}
-
-/**
- * gst_dparam_new:
- *
- * Returns: a new instance of GstDParam
- */
-GstDParam* 
-gst_dparam_new ()
-{
-       GstDParam *dparam;
-
-       dparam = g_object_new (gst_dparam_get_type (), NULL);
-       dparam->do_update_func = gst_dparam_do_update_realtime;
-       dparam->get_point_func = gst_dparam_get_point_realtime;
-       
-       dparam->point = gst_dparam_new_value_array(G_TYPE_NONE, 0);     
-       
-       return dparam;
-}
-
-/**
- * gst_dparam_set_parent
- * @dparam: GstDParam instance
- * @parent: the GstDParamManager that this dparam belongs to
- *
- */
-void
-gst_dparam_set_parent (GstDParam *dparam, GstObject *parent)
-{
-       g_return_if_fail (dparam != NULL);
-       g_return_if_fail (GST_IS_DPARAM (dparam));
-       g_return_if_fail (GST_DPARAM_PARENT (dparam) == NULL);
-       g_return_if_fail (parent != NULL);
-       g_return_if_fail (G_IS_OBJECT (parent));
-       g_return_if_fail ((gpointer)dparam != (gpointer)parent);
-
-       gst_object_set_parent (GST_OBJECT (dparam), parent);
-}
-
-/**
- * gst_dparam_new_value_array
- * @type: the type of the first GValue in the array
- * @...: the type of other GValues in the array
- *
- * The list of types should be terminated with a 0.
- * If the type of a value is not yet known then use G_TYPE_NONE .
- *
- * Returns: an newly created array of GValues
- */
-GValue**
-gst_dparam_new_value_array(GType type, ...)
-{
-       GValue **point;
-       GValue *value;
-       guint x;
-       gint values_length = 0;
-       va_list var_args;
-
-       va_start (var_args, type);
-       while (type){
-               values_length++;
-               type = va_arg (var_args, GType);
-       }
-       va_end (var_args);
-       
-       point = g_new0(GValue*,values_length + 1);
-
-       va_start (var_args, type);
-       for (x=0 ; x < values_length ; x++){
-               value = g_new0(GValue,1);
-               if (type != G_TYPE_NONE){
-                       g_value_init(value, type);
-               }
-               point[x] = value;
-               type = va_arg (var_args, GType);
-       }
-       point[values_length] = NULL;
-       va_end (var_args);
-       
-       GST_DEBUG(GST_CAT_PARAMS, "array with %d values created\n", values_length);
-
-       return point;
-}
-
-static void
-gst_dparam_do_update_realtime (GstDParam *dparam, gint64 timestamp)
-{
-       GST_DEBUG(GST_CAT_PARAMS, "updating point for %s(%p)\n",GST_DPARAM_NAME (dparam),dparam);
-       
-       GST_DPARAM_LOCK(dparam);
-       GST_DPARAM_READY_FOR_UPDATE(dparam) = FALSE;
-       g_value_copy(dparam->point[0], GST_DPARAM_VALUE(dparam));
-       GST_DPARAM_UNLOCK(dparam);
-}
-
-static GValue** 
-gst_dparam_get_point_realtime (GstDParam *dparam, gint64 timestamp)
-{
-       GST_DEBUG(GST_CAT_PARAMS, "getting point for %s(%p)\n",GST_DPARAM_NAME (dparam),dparam);
-       return dparam->point;
-}
-
-
diff --git a/gst/gstdparam.h b/gst/gstdparam.h
deleted file mode 100644 (file)
index e7dbb4e..0000000
+++ /dev/null
@@ -1,121 +0,0 @@
-/* GStreamer
- * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
- *
- * gstdparam.h: Dynamic Parameter functionality
- *
- * 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_DPARAM_H__
-#define __GST_DPARAM_H__
-
-#include <gst/gstobject.h>
-#include <gst/gstprops.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif /* __cplusplus */
-
-#define GST_TYPE_DPARAM                        (gst_dparam_get_type ())
-#define GST_DPARAM(obj)                        (G_TYPE_CHECK_INSTANCE_CAST ((obj), GST_TYPE_DPARAM,GstDparam))
-#define GST_DPARAM_CLASS(klass)                (G_TYPE_CHECK_CLASS_CAST ((klass), GST_TYPE_DPARAM,GstDParam))
-#define GST_IS_DPARAM(obj)                     (G_TYPE_CHECK_INSTANCE_TYPE     ((obj), GST_TYPE_DPARAM))
-#define GST_IS_DPARAM_CLASS(obj)               (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_DPARAM))
-
-#define GST_DPARAM_NAME(dparam)                                 (GST_OBJECT_NAME(dparam))
-#define GST_DPARAM_PARENT(dparam)                       (GST_OBJECT_PARENT(dparam))
-#define GST_DPARAM_VALUE(dparam)                                ((dparam)->value)
-
-#define GST_DPARAM_LOCK(dparam)                (g_mutex_lock((dparam)->lock))
-#define GST_DPARAM_UNLOCK(dparam)              (g_mutex_unlock((dparam)->lock))
-
-#define GST_DPARAM_READY_FOR_UPDATE(dparam)            ((dparam)->ready_for_update)
-#define GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam)       ((dparam)->next_update_timestamp)
-
-#define GST_DPARAM_GET_POINT(dparam, timestamp) \
-       ((dparam->get_point_func)(dparam, timestamp))
-
-#define GST_DPARAM_FIND_POINT(dparam, timestamp, search_flag) \
-       ((dparam->find_point_func)(dparam, data, search_flag))
-
-#define GST_DPARAM_DO_UPDATE(dparam, timestamp) \
-       ((dparam->do_update_func)(dparam, timestamp))
-               
-#define GST_DPARAM_INSERT_POINT(dparam, timestamp) \
-       ((dparam->insert_point_func)(dparam, timestamp))
-
-#define GST_DPARAM_REMOVE_POINT(dparam, data) \
-       ((dparam->remove_point_func)(dparam, data))
-       
-typedef enum {
-  GST_DPARAM_CLOSEST,
-  GST_DPARAM_CLOSEST_AFTER,
-  GST_DPARAM_CLOSEST_BEFORE,
-  GST_DPARAM_EXACT,
-} GstDParamSearchFlag;
-
-typedef enum {
-  GST_DPARAM_NOT_FOUND = 0,
-  GST_DPARAM_FOUND_EXACT,
-  GST_DPARAM_FOUND_CLOSEST,
-} GstDParamSearchResult;
-
-typedef struct _GstDParam GstDParam;
-typedef struct _GstDParamClass GstDParamClass;
-typedef struct _GstDParamModel GstDParamModel;
-
-typedef GValue** (*GstDParamInsertPointFunction) (GstDParam *dparam, guint64 timestamp);
-typedef void (*GstDParamRemovePointFunction) (GstDParam *dparam, GValue** point);
-typedef GValue** (*GstDParamGetPointFunction) (GstDParam *dparam, gint64 timestamp);
-typedef GstDParamSearchResult (*GstDParamFindPointFunction) (GstDParam *dparam, gint64 *timestamp, GstDParamSearchFlag search_flag);
-
-typedef void (*GstDParamDoUpdateFunction) (GstDParam *dparam, gint64 timestamp);
-
-struct _GstDParam {
-       GstObject               object;
-
-       GstDParamGetPointFunction get_point_func;
-       GstDParamFindPointFunction find_point_func;
-
-       GstDParamDoUpdateFunction do_update_func;
-       
-       GstDParamInsertPointFunction insert_point_func;
-       GstDParamRemovePointFunction remove_point_func; 
-       
-       GMutex *lock;
-       GValue *value;
-       GValue **point;
-       gint64 next_update_timestamp;
-       gboolean ready_for_update;
-       
-};
-
-struct _GstDParamClass {
-       GstObjectClass parent_class;
-
-       /* signal callbacks */
-};
-
-GType gst_dparam_get_type (void);
-GstDParam* gst_dparam_new ();
-void gst_dparam_set_parent (GstDParam *dparam, GstObject *parent);
-GValue** gst_dparam_new_value_array(GType type, ...);
-
-#ifdef __cplusplus
-}
-#endif /* __cplusplus */
-
-#endif /* __GST_DPARAM_H__ */
diff --git a/gst/gstdparammanager.c b/gst/gstdparammanager.c
deleted file mode 100644 (file)
index a05bfe6..0000000
+++ /dev/null
@@ -1,459 +0,0 @@
-/* GStreamer
- * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
- *
- * gstdparammanager.c: Dynamic Parameter group functionality
- *
- * 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.
- */
-
-#include "gst_private.h"
-
-#include "gstdparammanager.h"
-#include <gst/gstelement.h>
-
-
-static void gst_dpman_base_class_init (GstDParamManagerClass *klass);
-static void gst_dpman_class_init (GstDParamManagerClass *klass);
-static void gst_dpman_init (GstDParamManager *dpman);
-static void gst_dpman_state_change (GstElement *element, gint state, GstDParamManager *dpman);
-static void gst_dpman_caps_changed (GstPad *pad, GstCaps *caps, GstDParamManager *dpman);
-static guint gst_dpman_first_countdown_synchronous(GstDParamManager *dpman, guint frames, gint64 timestamp);
-static guint gst_dpman_first_countdown_noop(GstDParamManager *dpman, guint frames, gint64 timestamp);
-static guint gst_dpman_countdown_noop(GstDParamManager *dpman, guint frame_count);
-
-GType
-gst_dpman_get_type (void)
-{
-       static GType dpman_type = 0;
-
-       if (!dpman_type) {
-               static const GTypeInfo dpman_info = {
-                       sizeof(GstDParamManagerClass),
-                       (GBaseInitFunc)gst_dpman_base_class_init,
-                       NULL,
-                       (GClassInitFunc)gst_dpman_class_init,
-                       NULL,
-                       NULL,
-                       sizeof(GstDParamManager),
-                       0,
-                       (GInstanceInitFunc)gst_dpman_init,
-               };
-               dpman_type = g_type_register_static(GST_TYPE_OBJECT, "GstDParamManager", &dpman_info, 0);
-       }
-       return dpman_type;
-}
-
-static void
-gst_dpman_base_class_init (GstDParamManagerClass *klass)
-{
-       GObjectClass *gobject_class;
-
-       gobject_class = (GObjectClass*) klass;
-
-}
-
-static void
-gst_dpman_class_init (GstDParamManagerClass *klass)
-{
-       GstObjectClass *gstobject_class;
-       GObjectClass *gobject_class;
-
-       gstobject_class = (GstObjectClass*) klass;
-       gobject_class = (GObjectClass*) klass;
-
-       klass->modes = g_hash_table_new(g_str_hash,g_str_equal);
-
-       gst_dpman_register_mode (klass, "synchronous", 
-                              gst_dpman_first_countdown_synchronous, gst_dpman_countdown_noop, NULL, NULL);
-       gst_dpman_register_mode (klass, "asynchronous", 
-                              gst_dpman_first_countdown_noop, gst_dpman_countdown_noop, NULL, NULL);
-       gst_dpman_register_mode (klass, "disabled", 
-                              gst_dpman_first_countdown_noop, gst_dpman_countdown_noop, NULL, NULL);
-
-}
-
-static void
-gst_dpman_init (GstDParamManager *dpman)
-{
-       GST_DPMAN_DPARAMS(dpman) = g_hash_table_new(g_str_hash,g_str_equal);
-       GST_DPMAN_DPARAMS_LIST(dpman) = NULL;
-       GST_DPMAN_NAME(dpman) = NULL;
-       GST_DPMAN_PARENT(dpman) = NULL;
-       GST_DPMAN_MODE_NAME(dpman) = NULL;
-       GST_DPMAN_MODE(dpman) = NULL;
-       GST_DPMAN_MODE_DATA(dpman) = NULL;
-       GST_DPMAN_RATE(dpman) = 0;
-}
-
-/**
- * gst_dpman_new:
- * @name: name of the GstDParamManager instance
- * @parent: element which created this instance
- *
- * Returns: a new instance of GstDParamManager
- */
-GstDParamManager* 
-gst_dpman_new (gchar *name, GstElement *parent)
-{
-       GstDParamManager *dpman;
-       
-       g_return_val_if_fail (name != NULL, NULL);
-
-       dpman = g_object_new (gst_dpman_get_type (), NULL);
-       gst_object_set_name (GST_OBJECT (dpman), name);
-       gst_dpman_set_parent(dpman, parent);
-
-       gst_dpman_set_mode(dpman, "disabled");
-
-       return dpman;
-}
-
-/**
- * gst_dpman_add_required_dparam:
- * @dpman: GstDParamManager instance
- * @dparam_name: a parameter name unique to this GstDParamManager
- * @type: the GValue type that this parameter will store
- * @update_func: callback to update the element with the new value
- * @update_data: will be included in the call to update_func
- *
- * Returns: true if it was successfully added
- */
-gboolean 
-gst_dpman_add_required_dparam (GstDParamManager *dpman, 
-                                gchar *dparam_name, 
-                                GType type, 
-                                GstDpmUpdateFunction update_func, 
-                                gpointer update_data)
-{
-       GstDParamWrapper* dpwrap;
-
-       g_return_val_if_fail (dpman != NULL, FALSE);
-       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
-       g_return_val_if_fail (dparam_name != NULL, FALSE);
-       g_return_val_if_fail (update_func != NULL, FALSE);
-
-       g_return_val_if_fail(g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), dparam_name) == NULL, FALSE);
-
-       GST_DEBUG(GST_CAT_PARAMS,"adding required dparam: %s\n", dparam_name);
-       
-       dpwrap = g_new0(GstDParamWrapper,1);
-       dpwrap->dparam_name = dparam_name;
-       dpwrap->update_func = update_func;
-       dpwrap->update_data = update_data;
-       dpwrap->value = g_new0(GValue,1);
-       g_value_init(dpwrap->value, type);
-
-       g_hash_table_insert(GST_DPMAN_DPARAMS(dpman), dparam_name, dpwrap);
-       GST_DPMAN_DPARAMS_LIST(dpman) = g_slist_append(GST_DPMAN_DPARAMS_LIST(dpman), dpwrap);
-       
-       return TRUE;    
-}
-
-/**
- * gst_dpman_remove_required_dparam:
- * @dpman: GstDParamManager instance
- * @dparam_name: the name of an existing parameter
- *
- */
-void 
-gst_dpman_remove_required_dparam (GstDParamManager *dpman, gchar *dparam_name)
-{
-       GstDParamWrapper* dpwrap;
-
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-       g_return_if_fail (dparam_name != NULL);
-
-       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), dparam_name);
-
-       g_return_if_fail(dpwrap != NULL);
-       g_return_if_fail(dpwrap->dparam == NULL);
-
-       GST_DEBUG(GST_CAT_PARAMS, "removing required dparam: %s\n", dparam_name);
-       
-       g_hash_table_remove(GST_DPMAN_DPARAMS(dpman), dparam_name);
-       GST_DPMAN_DPARAMS_LIST(dpman) = g_slist_remove(GST_DPMAN_DPARAMS_LIST(dpman), dpwrap);
-
-       g_free(dpwrap->value);
-       g_free(dpwrap);
-}
-
-/**
- * gst_dpman_attach_dparam:
- * @dpman: GstDParamManager instance
- * @dparam_name: a name previously added with gst_dpman_add_required_dparam
- * @dparam: GstDParam instance to attach
- *
- * Returns: true if it was successfully attached
- */
-gboolean 
-gst_dpman_attach_dparam (GstDParamManager *dpman, gchar *dparam_name, GstDParam *dparam)
-{
-       GstDParamWrapper* dpwrap;
-
-       g_return_val_if_fail (dpman != NULL, FALSE);
-       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
-       g_return_val_if_fail (dparam_name != NULL, FALSE);
-       g_return_val_if_fail (dparam != NULL, FALSE);
-       g_return_val_if_fail (GST_IS_DPARAM (dparam), FALSE);
-       g_return_val_if_fail (dparam != NULL, FALSE);
-
-       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), dparam_name);
-
-       g_return_val_if_fail(dpwrap != NULL, FALSE);
-       g_return_val_if_fail(dpwrap->value != NULL, FALSE);
-
-       GST_DPARAM_VALUE(dparam) = dpwrap->value;
-       dpwrap->dparam = dparam;
-       gst_dparam_set_parent (dparam, GST_OBJECT(dpman));
-       GST_DPARAM_NAME(dparam) = dparam_name;
-
-       return TRUE;
-}
-
-/**
- * gst_dpman_dettach_dparam:
- * @dpman: GstDParamManager instance
- * @dparam_name: the name of a parameter with a previously attached GstDParam
- *
- */
-void 
-gst_dpman_dettach_dparam (GstDParamManager *dpman, gchar *dparam_name)
-{
-       GstDParamWrapper* dpwrap;
-
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-       g_return_if_fail (dparam_name != NULL);
-       
-       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), dparam_name);
-
-       g_return_if_fail(dpwrap);
-       
-       GST_DPARAM_VALUE(dpwrap->dparam) = NULL;
-       GST_DPARAM_NAME(dpwrap->dparam) = NULL;
-       gst_object_unparent (GST_OBJECT(dpwrap->dparam));
-
-       dpwrap->dparam = NULL;
-       
-}
-
-/**
- * gst_dpman_get_dparam:
- * @dpman: GstDParamManager instance
- * @name: the name of an existing dparam instance
- *
- * Returns: the dparam with the given name - or NULL otherwise
- */
-GstDParam *
-gst_dpman_get_dparam (GstDParamManager *dpman, gchar *name)
-{
-       GstDParamWrapper* dpwrap;
-
-       g_return_val_if_fail (dpman != NULL, NULL);
-       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
-       g_return_val_if_fail (name != NULL, NULL);
-       
-       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), name);
-       g_return_val_if_fail (dpwrap != NULL, NULL);
-       
-       return dpwrap->dparam;
-}
-
-/**
- * gst_dpman_register_mode
- * @klass: GstDParamManagerClass class instance
- * @modename: the unique name of the new mode
- * @firstcountdownfunc: the function which will be called before each buffer is processed
- * @countdownfunc: the function which may be called throughout the processing of a buffer
- * @setupfunc: the function which initialises the mode when activated
- * @teardownfunc: the function which frees any resources the mode uses
- *
- */
-void
-gst_dpman_register_mode (GstDParamManagerClass *klass,
-                         gchar *modename, 
-                         GstDpmModeFirstCountdownFunction firstcountdownfunc,
-                         GstDpmModeCountdownFunction countdownfunc,
-                         GstDpmModeSetupFunction setupfunc,
-                         GstDpmModeTeardownFunction teardownfunc)
-{
-       GstDpmMode *mode;
-
-       g_return_if_fail (klass != NULL);
-       g_return_if_fail (modename != NULL);
-       g_return_if_fail (GST_IS_DPMAN_CLASS (klass));
-       
-       mode = g_new0(GstDpmMode,1);
-
-       mode->firstcountdownfunc = firstcountdownfunc;
-       mode->countdownfunc = countdownfunc;
-       mode->setupfunc = setupfunc;
-       mode->teardownfunc = teardownfunc;
-       
-       g_hash_table_insert(klass->modes, modename, mode);
-       GST_DEBUG(GST_CAT_PARAMS, "mode '%s' registered\n", modename);
-}
-
-/**
- * gst_dpman_set_mode
- * @dpman: GstDParamManager instance
- * @modename: the name of the mode to use
- *
- * Returns: TRUE if the mode was set, FALSE otherwise
- */
-gboolean
-gst_dpman_set_mode(GstDParamManager *dpman, gchar *modename)
-{
-       GstDpmMode *mode=NULL;
-       GstDParamManagerClass *oclass;
-       
-       g_return_val_if_fail (dpman != NULL, FALSE);
-       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
-       g_return_val_if_fail (modename != NULL, FALSE);
-
-       oclass = (GstDParamManagerClass*)(G_OBJECT_GET_CLASS(dpman));
-       
-       mode = g_hash_table_lookup(oclass->modes, modename);
-       g_return_val_if_fail (mode != NULL, FALSE);
-       GST_DEBUG(GST_CAT_PARAMS, "setting mode to %s\n", modename);
-       if (GST_DPMAN_MODE(dpman) && GST_DPMAN_TEARDOWNFUNC(dpman)){
-               GST_DPMAN_TEARDOWNFUNC(dpman)(dpman);
-       }
-       
-       GST_DPMAN_MODE(dpman) = mode;
-
-       if (GST_DPMAN_SETUPFUNC(dpman)){
-               GST_DPMAN_SETUPFUNC(dpman)(dpman);
-       }
-       
-       return TRUE;
-}
-
-/**
- * gst_dpman_set_parent
- * @dpman: GstDParamManager instance
- * @parent: the element that this GstDParamManager belongs to
- *
- */
-void
-gst_dpman_set_parent (GstDParamManager *dpman, GstElement *parent)
-{
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-       g_return_if_fail (parent != NULL);
-       g_return_if_fail (GST_IS_ELEMENT (parent));
-
-       gst_object_set_parent (GST_OBJECT (dpman), GST_OBJECT(parent));
-       g_signal_connect(G_OBJECT(parent), "state_change", 
-                        G_CALLBACK (gst_dpman_state_change), dpman);
-}
-
-/**
- * gst_dpman_set_rate_change_pad
- * @dpman: GstDParamManager instance
- * @pad: the pad which may have a "rate" caps property
- *
- */
-void
-gst_dpman_set_rate_change_pad(GstDParamManager *dpman, GstPad *pad)
-{
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-       g_return_if_fail (pad != NULL);
-       g_return_if_fail (GST_IS_PAD (pad));
-
-       g_signal_connect(G_OBJECT(pad), "caps_changed", 
-                        G_CALLBACK (gst_dpman_caps_changed), dpman);
-}
-
-static void 
-gst_dpman_state_change (GstElement *element, gint state, GstDParamManager *dpman)
-{
-       GSList *dwraps;
-       GstDParam *dparam;
-       GstDParamWrapper *dpwrap;
-       
-       if (state == GST_STATE_PLAYING) return;
-       GST_DEBUG(GST_CAT_PARAMS, "initialising params\n");
-       
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-
-       // force all params to be updated
-       dwraps = GST_DPMAN_DPARAMS_LIST(dpman);
-       while (dwraps){
-               dpwrap = (GstDParamWrapper*)dwraps->data;
-               dparam = dpwrap->dparam;
-               
-               if (dparam){
-                       GST_DPARAM_READY_FOR_UPDATE(dparam) = TRUE;
-               }
-               dwraps = g_slist_next(dwraps);
-       }
-}
-
-static void
-gst_dpman_caps_changed (GstPad *pad, GstCaps *caps, GstDParamManager *dpman)
-{
-       g_return_if_fail (caps != NULL);
-       g_return_if_fail (dpman != NULL);
-       g_return_if_fail (GST_IS_DPMAN (dpman));
-       
-       GST_DPMAN_RATE(dpman) = gst_caps_get_int (caps, "rate");
-       
-       GST_DEBUG(GST_CAT_PARAMS, "got caps change %d\n", GST_DPMAN_RATE(dpman));
-}
-
-static guint 
-gst_dpman_first_countdown_synchronous(GstDParamManager *dpman, guint frames, gint64 timestamp)
-{
-       GSList *dwraps;
-       GstDParam *dparam;
-       GstDParamWrapper *dpwrap;
-
-       g_return_val_if_fail (dpman != NULL, frames);
-       g_return_val_if_fail (GST_IS_DPMAN (dpman), frames);
-
-       // now check whether any passive dparams are ready for an update
-       dwraps = GST_DPMAN_DPARAMS_LIST(dpman);
-       while (dwraps){
-               dpwrap = (GstDParamWrapper*)dwraps->data;
-               dparam = dpwrap->dparam;
-               
-               if (dparam && (GST_DPARAM_READY_FOR_UPDATE(dparam) || 
-                             (GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam) < timestamp))){
-                       GST_DPARAM_DO_UPDATE(dparam, timestamp);
-                       GST_DPMAN_DO_UPDATE(dpwrap);
-               }
-               dwraps = g_slist_next(dwraps);
-       }
-       
-       return frames;
-}
-
-static guint 
-gst_dpman_first_countdown_noop(GstDParamManager *dpman, guint frames, gint64 timestamp)
-{
-       return frames;
-}
-
-static guint 
-gst_dpman_countdown_noop(GstDParamManager *dpman, guint frame_count)
-{
-       return 0;
-}
-
diff --git a/gst/gstdparammanager.h b/gst/gstdparammanager.h
deleted file mode 100644 (file)
index 06fa76c..0000000
+++ /dev/null
@@ -1,138 +0,0 @@
-/* GStreamer
- * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
- *
- * gstdparammanager.h: Dynamic Parameter group functionality
- *
- * 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_DPMAN_H__
-#define __GST_DPMAN_H__
-
-#include <gst/gstobject.h>
-#include <gst/gstdparam.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif /* __cplusplus */
-
-#define GST_TYPE_DPMAN                 (gst_dpman_get_type ())
-#define GST_DPMAN(obj)                 (G_TYPE_CHECK_INSTANCE_CAST     ((obj), GST_TYPE_DPMAN,GstDParamManager))
-#define GST_DPMAN_CLASS(klass)         (G_TYPE_CHECK_CLASS_CAST        ((klass), GST_TYPE_DPMAN,GstDParamManager))
-#define GST_IS_DPMAN(obj)                      (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GST_TYPE_DPMAN))
-#define GST_IS_DPMAN_CLASS(obj)                (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_DPMAN))
-
-#define GST_DPMAN_NAME(dpman)                  (GST_OBJECT_NAME(dpman))
-#define GST_DPMAN_PARENT(dpman)                (GST_OBJECT_PARENT(dpman))
-#define GST_DPMAN_DPARAMS(dpman)               ((dpman)->dparams)
-#define GST_DPMAN_DPARAMS_LIST(dpman)          ((dpman)->dparams_list)
-
-#define GST_DPMAN_MODE_NAME(dpman)                              ((dpman)->mode_name)
-#define GST_DPMAN_MODE(dpman)                           ((dpman)->mode)
-#define GST_DPMAN_MODE_DATA(dpman)                              ((dpman)->mode_data)
-#define GST_DPMAN_RATE(dpman)                           ((dpman)->rate)
-
-typedef struct _GstDParamManager GstDParamManager;
-typedef struct _GstDParamManagerClass GstDParamManagerClass;
-typedef struct _GstDpmMode GstDpmMode;
-typedef struct _GstDParamWrapper GstDParamWrapper;
-
-typedef guint (*GstDpmModeFirstCountdownFunction) (GstDParamManager *dpman, guint frames, gint64 timestamp);
-typedef guint (*GstDpmModeCountdownFunction) (GstDParamManager *dpman, guint frame_count);
-typedef void (*GstDpmModeSetupFunction) (GstDParamManager *dpman);
-typedef void (*GstDpmModeTeardownFunction) (GstDParamManager *dpman);
-
-typedef void (*GstDpmUpdateFunction) (GValue *value, gpointer data);
-
-struct _GstDParamManager {
-       GstObject               object;
-
-       GHashTable *dparams;
-       GSList *dparams_list;
-       
-       gchar *mode_name;
-       GstDpmMode* mode;
-       gpointer mode_data;
-       
-       gint64 timestamp;
-       guint rate;
-};
-
-struct _GstDParamManagerClass {
-       GstObjectClass parent_class;
-       
-       GHashTable *modes;
-       /* signal callbacks */
-};
-
-struct _GstDpmMode {
-       GstDpmModeFirstCountdownFunction firstcountdownfunc;
-       GstDpmModeCountdownFunction countdownfunc;
-       GstDpmModeSetupFunction setupfunc;
-       GstDpmModeTeardownFunction teardownfunc;
-};
-
-struct _GstDParamWrapper {
-       gchar *dparam_name;
-       GValue *value;
-       GstDParam *dparam;
-       GstDpmUpdateFunction update_func;
-       gpointer update_data;
-};
-
-#define GST_DPMAN_FIRST_COUNTDOWNFUNC(dpman)           (((dpman)->mode)->firstcountdownfunc)
-#define GST_DPMAN_COUNTDOWNFUNC(dpman)         (((dpman)->mode)->countdownfunc)
-#define GST_DPMAN_SETUPFUNC(dpman)             (((dpman)->mode)->setupfunc)
-#define GST_DPMAN_TEARDOWNFUNC(dpman)          (((dpman)->mode)->teardownfunc)
-
-#define GST_DPMAN_FIRST_COUNTDOWN(dpman, buffer_size, timestamp) \
-                               (GST_DPMAN_FIRST_COUNTDOWNFUNC(dpman)(dpman, buffer_size, timestamp))
-
-#define GST_DPMAN_COUNTDOWN(dpman, frame_countdown, frame_count) \
-                               (frame_countdown-- || \
-                               (frame_countdown = GST_DPMAN_COUNTDOWNFUNC(dpman)(dpman, frame_count)))
-
-#define GST_DPMAN_DO_UPDATE(dpwrap) ((dpwrap->update_func)(dpwrap->value, dpwrap->update_data))
-
-GType gst_dpman_get_type (void);
-GstDParamManager* gst_dpman_new (gchar *name, GstElement *parent);
-void gst_dpman_set_parent (GstDParamManager *dpman, GstElement *parent);
-
-gboolean gst_dpman_add_required_dparam (GstDParamManager *dpman, 
-                                        gchar *dparam_name, 
-                                        GType type, 
-                                        GstDpmUpdateFunction update_func, 
-                                        gpointer update_data);
-void gst_dpman_remove_required_dparam (GstDParamManager *dpman, gchar *dparam_name);
-gboolean gst_dpman_attach_dparam (GstDParamManager *dpman, gchar *dparam_name, GstDParam *dparam);
-void gst_dpman_dettach_dparam (GstDParamManager *dpman, gchar *dparam_name);                         
-GstDParam* gst_dpman_get_dparam(GstDParamManager *dpman, gchar *name);
-
-void gst_dpman_set_rate_change_pad(GstDParamManager *dpman, GstPad *pad);
-
-gboolean gst_dpman_set_mode(GstDParamManager *dpman, gchar *modename);
-void gst_dpman_register_mode (GstDParamManagerClass *klass,
-                           gchar *modename, 
-                           GstDpmModeFirstCountdownFunction firstcountdownfunc,
-                           GstDpmModeCountdownFunction countdownfunc,
-                           GstDpmModeSetupFunction setupfunc,
-                           GstDpmModeTeardownFunction teardownfunc);
-
-#ifdef __cplusplus
-}
-#endif /* __cplusplus */
-
-#endif /* __GST_DPMAN_H__ */
index 874bf8ef2ee26749fc15033066b08550d282d108..332c91be6e683e30997bf950f37b9188ae213455 100644 (file)
@@ -56,8 +56,7 @@ static void                   gst_element_set_property        (GObject *object, guint prop_id,
 static void                    gst_element_get_property        (GObject *object, guint prop_id, GValue *value, 
                                                                 GParamSpec *pspec);
 
-static void                    gst_element_shutdown            (GObject *object);
-static void                    gst_element_real_destroy        (GObject *object);
+static void                    gst_element_dispose             (GObject *object);
 
 static GstElementStateReturn   gst_element_change_state        (GstElement *element);
 
@@ -84,6 +83,7 @@ GType gst_element_get_type (void)
       sizeof(GstElement),
       0,
       (GInstanceInitFunc)gst_element_init,
+      NULL
     };
     _gst_element_type = g_type_register_static(GST_TYPE_OBJECT, "GstElement", &element_info, G_TYPE_FLAG_ABSTRACT);
   }
@@ -140,9 +140,7 @@ gst_element_class_init (GstElementClass *klass)
 
   gobject_class->set_property =                GST_DEBUG_FUNCPTR(gst_element_set_property);
   gobject_class->get_property =                GST_DEBUG_FUNCPTR(gst_element_get_property);
-//  gobject_class->shutdown =          GST_DEBUG_FUNCPTR(gst_element_shutdown);
-// FIXME!
-//  gobject_class->destroy =           GST_DEBUG_FUNCPTR(gst_element_real_destroy);
+  gobject_class->dispose =             GST_DEBUG_FUNCPTR(gst_element_dispose);
 
 #ifndef GST_DISABLE_LOADSAVE
   gstobject_class->save_thyself =      GST_DEBUG_FUNCPTR(gst_element_save_thyself);
@@ -940,36 +938,23 @@ GST_ELEMENT_NAME(element),GST_ELEMENT_NAME(GST_ELEMENT_PARENT(element)),GST_ELEM
 }
 
 static void
-gst_element_shutdown (GObject *object)
+gst_element_dispose (GObject *object)
 {
   GstElement *element = GST_ELEMENT (object);
-
-  GST_DEBUG_ELEMENT (GST_CAT_REFCOUNTING, element, "shutdown\n");
+  GList *pads;
+  GstPad *pad;
+  
+  GST_DEBUG_ELEMENT (GST_CAT_REFCOUNTING, element, "dispose\n");
 
   if (GST_IS_BIN (GST_OBJECT_PARENT (element)))
     gst_bin_remove (GST_BIN (GST_OBJECT_PARENT (element)), element);
 
-//  if (G_OBJECT_CLASS (parent_class)->shutdown)
-//    G_OBJECT_CLASS (parent_class)->shutdown (G_OBJECT (object));
-}
-
-static void
-gst_element_real_destroy (GObject *object)
-{
-  GstElement *element = GST_ELEMENT (object);
-  GList *pads;
-  GstPad *pad;
-
-  GST_DEBUG_ELEMENT (GST_CAT_REFCOUNTING, element, "destroy\n");
 
   if (element->pads) {
     GList *orig;
     orig = pads = g_list_copy (element->pads);
     while (pads) {
       pad = GST_PAD (pads->data);
-      //gst_object_destroy (GST_OBJECT (pad));
-      gst_object_ref (GST_OBJECT (pad));
-      gst_element_remove_pad (element, pad);
       gst_object_unref (GST_OBJECT (pad));
       pads = g_list_next (pads);
     }
@@ -981,9 +966,7 @@ gst_element_real_destroy (GObject *object)
   element->numsrcpads = 0;
   element->numsinkpads = 0;
 
-// FIXME!
-//  if (G_OBJECT_CLASS (parent_class)->destroy)
-//    G_OBJECT_CLASS (parent_class)->destroy (object);
+  G_OBJECT_CLASS (parent_class)->dispose (object);
 }
 
 /*
@@ -1142,9 +1125,9 @@ gst_element_restore_thyself (xmlNodePtr self, GstObject *parent)
   // first get the needed tags to construct the element
   while (children) {
     if (!strcmp (children->name, "name")) {
-      name = g_strdup (xmlNodeGetContent (children));
+      name = xmlNodeGetContent (children);
     } else if (!strcmp (children->name, "type")) {
-      type = g_strdup (xmlNodeGetContent (children));
+      type = xmlNodeGetContent (children);
     }
     children = children->next;
   }
@@ -1171,10 +1154,10 @@ gst_element_restore_thyself (xmlNodePtr self, GstObject *parent)
 
       while (child) {
         if (!strcmp (child->name, "name")) {
-          name = g_strdup (xmlNodeGetContent (child));
+          name = xmlNodeGetContent (child);
        }
        else if (!strcmp (child->name, "value")) {
-          value = g_strdup (xmlNodeGetContent (child));
+          value = xmlNodeGetContent (child);
        }
         child = child->next;
       }
index d7ceb7a914833ee217957c9ae5904b7343fd8934..1d05451878e8efd99e3431e8c1eab77c7e2ea61d 100644 (file)
@@ -30,7 +30,6 @@
 #include <gst/gstpad.h>
 #include <gst/cothreads.h>
 #include <gst/gstpluginfeature.h>
-#include <gst/gstdparammanager.h>
 
 #ifdef __cplusplus
 extern "C" {
@@ -123,7 +122,6 @@ typedef enum {
 #define GST_ELEMENT_MANAGER(obj)               (((GstElement*)(obj))->manager)
 #define GST_ELEMENT_SCHED(obj)                 (((GstElement*)(obj))->sched)
 #define GST_ELEMENT_PADS(obj)                  ((obj)->pads)
-#define GST_ELEMENT_DPARAM_MANAGER(obj)                ((obj)->dpman)
 
 //typedef struct _GstElement GstElement;
 //typedef struct _GstElementClass GstElementClass;
@@ -149,8 +147,6 @@ struct _GstElement {
   guint16              numsinkpads;
   GList                *pads;
   GstPad               *select_pad;
-
-  GstDParamManager     *dpman;
 };
 
 struct _GstElementClass {
@@ -262,6 +258,8 @@ struct _GstElementFactory {
 
   GType type;                  /* unique GType of element */
 
+  guint details_dynamic : 1;
+
   GstElementDetails *details;  /* pointer to details struct */
 
   GList *padtemplates;
index 43a5d18c9fd5ea07889202121cd30768d36defce..0f4dde38c0aee60957b22f0cf87685daa3553b21 100644 (file)
@@ -57,6 +57,7 @@ gst_elementfactory_get_type (void)
       sizeof(GstElementFactory),
       0,
       (GInstanceInitFunc) gst_elementfactory_init,
+      NULL
     };
     elementfactory_type = g_type_register_static (GST_TYPE_PLUGIN_FEATURE, 
                                                  "GstElementFactory", &elementfactory_info, 0);
@@ -138,6 +139,25 @@ gst_elementfactory_get_list (void)
   return _gst_elementfactories;
 }
 
+static void
+gst_element_details_free (GstElementDetails *dp)
+{
+  g_return_if_fail (dp);
+
+  if (dp->longname)
+    g_free (dp->longname);
+  if (dp->klass)
+    g_free (dp->klass);
+  if (dp->description)
+    g_free (dp->description);
+  if (dp->version)
+    g_free (dp->version);
+  if (dp->author)
+    g_free (dp->author);
+  if (dp->copyright)
+    g_free (dp->copyright);
+  g_free (dp);
+}
 
 /**
  * gst_elementfactory_new:
@@ -157,19 +177,31 @@ gst_elementfactory_new (const gchar *name, GType type,
   GstElementFactory *factory;
 
   g_return_val_if_fail(name != NULL, NULL);
-  g_return_val_if_fail(type != 0, NULL);
+  g_return_val_if_fail (type, NULL);
+  g_return_val_if_fail (details, NULL);
 
   factory = gst_elementfactory_find (name);
-  if (!factory) {
+
+  if (!factory)
     factory = GST_ELEMENTFACTORY (g_object_new (GST_TYPE_ELEMENTFACTORY, NULL));
-  }
 
-  gst_object_set_name (GST_OBJECT (factory), name);
-  factory->type = type;
-  if (factory->details)
-    g_free (factory->details);
+  if (factory->details_dynamic)
+    {
+      gst_element_details_free (factory->details);
+      factory->details_dynamic = FALSE;
+    }
+
   factory->details = details;
 
+  if (!factory->type)
+    factory->type = type;
+  else if (factory->type != type)
+/* FIXME: g_critical is glib-2.0, not glib-1.2
+    g_critical ("`%s' requested type change (!)", name);
+*/
+    g_warning ("`%s' requested type change (!)", name);
+  gst_object_set_name (GST_OBJECT (factory), name);
+
   return factory;
 }
 
@@ -194,12 +226,20 @@ gst_elementfactory_create (GstElementFactory *factory,
   g_return_val_if_fail(factory != NULL, NULL);
   g_return_val_if_fail(name != NULL, NULL);
 
-  GST_DEBUG (GST_CAT_ELEMENTFACTORY,"creating element from factory \"%s\" with name \"%s\"\n", 
-             GST_OBJECT_NAME (factory), name);
+  GST_DEBUG (GST_CAT_ELEMENTFACTORY,"creating element from factory \"%s\" with name \"%s\" and type %d\n", 
+             GST_OBJECT_NAME (factory), name, factory->type);
 
   gst_plugin_feature_ensure_loaded (GST_PLUGIN_FEATURE (factory));
 
-  g_return_val_if_fail(factory->type != 0, NULL);
+  if (factory->type == 0)
+    {
+/* FIXME: g_critical is glib-2.0, not glib-1.2
+      g_critical ("Factory for `%s' has no type",
+*/
+      g_warning ("Factory for `%s' has no type",
+                 gst_object_get_name (GST_OBJECT (factory)));
+      return NULL;
+    }
 
   // create an instance of the element
   element = GST_ELEMENT(g_object_new(factory->type,NULL));
@@ -275,7 +315,9 @@ gst_elementfactory_add_padtemplate (GstElementFactory *factory,
   g_return_if_fail(templ != NULL);
 
   padtemplates = factory->padtemplates;
-  
+
+  gst_object_ref (GST_OBJECT (templ));
+
   while (padtemplates) {
     GstPadTemplate *oldtempl = GST_PADTEMPLATE (padtemplates->data);
     
@@ -383,12 +425,18 @@ gst_elementfactory_save_thyself (GstObject *object,
 
   g_return_val_if_fail(factory != NULL, NULL);
 
-  xmlNewChild(parent,NULL,"longname", factory->details->longname);
-  xmlNewChild(parent,NULL,"class", factory->details->klass);
-  xmlNewChild(parent,NULL,"description", factory->details->description);
-  xmlNewChild(parent,NULL,"version", factory->details->version);
-  xmlNewChild(parent,NULL,"author", factory->details->author);
-  xmlNewChild(parent,NULL,"copyright", factory->details->copyright);
+  if (factory->details)
+    {
+      xmlNewChild(parent,NULL,"longname", factory->details->longname);
+      xmlNewChild(parent,NULL,"class", factory->details->klass);
+      xmlNewChild(parent,NULL,"description", factory->details->description);
+      xmlNewChild(parent,NULL,"version", factory->details->version);
+      xmlNewChild(parent,NULL,"author", factory->details->author);
+      xmlNewChild(parent,NULL,"copyright", factory->details->copyright);
+    }
+  else
+    g_warning ("elementfactory `%s' is missing details",
+              object->name);
 
   pads = factory->padtemplates;
   if (pads) {
@@ -410,6 +458,8 @@ gst_elementfactory_restore_thyself (GstObject *object, xmlNodePtr parent)
 {
   GstElementFactory *factory = GST_ELEMENTFACTORY (object);
   xmlNodePtr children = parent->xmlChildrenNode;
+  
+  factory->details_dynamic = TRUE;
   factory->details = g_new0(GstElementDetails, 1);
   factory->padtemplates = NULL;
 
index 162bdb50a13a4bc7fa2ed586d50dfbce5576a0a6..032f9efb9e2a339626e7890fe351aa1f1088b25c 100644 (file)
@@ -41,6 +41,7 @@ gst_extra_get_filename_type (void)
       0, //sizeof(GstElement),
       0,
       NULL,
+      NULL
     };
     filename_type = g_type_register_static (G_TYPE_STRING, "GstFilename", &filename_info, 0);
   }
index cba96eb9245e78c88a9fcfd1580bccc9ff7b1ae1..0e9817445e0e5b59b3ef5196edf06562987f415f 100644 (file)
@@ -23,6 +23,8 @@
 #ifndef __GST_LOG_H__
 #define __GST_LOG_H__
 
+extern const char             *g_log_domain_gstreamer;
+
 /* information messages */
 #define GST_SHOW_INFO
 #ifdef GST_SHOW_INFO
index 4ca9a0358766dc6814f096186129e06f24e27ac2..70d81227c3bbf8cd55401eaf2a507e49f3d70871 100644 (file)
@@ -57,8 +57,7 @@ static guint gst_signal_object_signals[SO_LAST_SIGNAL] = { 0 };
 static void            gst_object_class_init           (GstObjectClass *klass);
 static void            gst_object_init                 (GstObject *object);
 
-static void            gst_object_real_destroy         (GObject *object);
-static void            gst_object_shutdown             (GObject *object);
+static void            gst_object_dispose              (GObject *object);
 static void            gst_object_finalize             (GObject *object);
 
 static GObjectClass *parent_class = NULL;
@@ -78,6 +77,7 @@ gst_object_get_type (void)
       sizeof (GstObject),
       32,
       (GInstanceInitFunc) gst_object_init,
+      NULL
     };
     _gst_object_type = g_type_register_static (G_TYPE_OBJECT, "GstObject", &object_info, G_TYPE_FLAG_ABSTRACT);
   }
@@ -110,8 +110,7 @@ gst_object_class_init (GstObjectClass *klass)
 // FIXME!!!
 //  klass->signal_object = g_object_new(gst_signal_object_get_type (,NULL));
 
-//  gobject_class->shutdown = gst_object_shutdown;
-//  gobject_class->destroy = gst_object_real_destroy;
+  gobject_class->dispose = gst_object_dispose;
   gobject_class->finalize = gst_object_finalize;
 }
 
@@ -142,7 +141,6 @@ gst_object_ref (GstObject *object)
              G_OBJECT(object)->ref_count,G_OBJECT(object)->ref_count+1);
 
   g_object_ref (G_OBJECT (object));
-
   return object;
 }
 #define gst_object_ref gst_object_ref
@@ -201,29 +199,19 @@ gst_object_destroy (GstObject *object)
      * invocations.
      */
     gst_object_ref (object);
-//    G_OBJECT_GET_CLASS (object)->shutdown (G_OBJECT (object));
+    G_OBJECT_GET_CLASS (object)->dispose (G_OBJECT (object));
     gst_object_unref (object);
   }
 }
 
 static void
-gst_object_shutdown (GObject *object)
+gst_object_dispose (GObject *object)
 {
-  GST_DEBUG (GST_CAT_REFCOUNTING, "shutdown '%s'\n",GST_OBJECT_NAME(object));
+  GST_DEBUG (GST_CAT_REFCOUNTING, "dispose '%s'\n",GST_OBJECT_NAME(object));
   GST_FLAG_SET (GST_OBJECT (object), GST_DESTROYED);
-//  parent_class->shutdown (object);
-}
-
-/* finilize is called when the object has to free its resources */
-static void
-gst_object_real_destroy (GObject *g_object)
-{
-  GST_DEBUG (GST_CAT_REFCOUNTING, "destroy '%s'\n",GST_OBJECT_NAME(g_object));
-
-  GST_OBJECT_PARENT (g_object) = NULL;
+  GST_OBJECT_PARENT (object) = NULL;
 
-// FIXME!!
-//  parent_class->destroy (g_object);
+  parent_class->dispose (object);
 }
 
 /* finilize is called when the object has to free its resources */
@@ -342,6 +330,8 @@ gst_object_unparent (GstObject *object)
   if (object->parent == NULL)
     return;
 
+  GST_DEBUG (GST_CAT_REFCOUNTING, "unparent '%s'\n",GST_OBJECT_NAME(object));
+  
   object->parent = NULL;
   gst_object_unref (object);
 }
@@ -608,6 +598,7 @@ gst_signal_object_get_type (void)
       sizeof(GstSignalObject),
       16,
       (GInstanceInitFunc)gst_signal_object_init,
+      NULL
     };
     signal_object_type = g_type_register_static(G_TYPE_OBJECT, "GstSignalObject", &signal_object_info, 0);
   }
index b5c9d4d011fe75a31322b758954c912cb312ca3e..c5c985d025e9c5441d8c72fd4b90ad7e7ed3a9b1 100644 (file)
@@ -24,6 +24,7 @@
 #include "gst_private.h"
 
 #include "gstpad.h"
+#include "gstutils.h"
 #include "gstelement.h"
 #include "gsttype.h"
 #include "gstbin.h"
@@ -55,6 +56,7 @@ gst_pad_get_type(void)
       sizeof(GstPad),
       32,
       (GInstanceInitFunc)gst_pad_init,
+      NULL
     };
     _gst_pad_type = g_type_register_static(GST_TYPE_OBJECT, "GstPad", &pad_info, 0);
   }
@@ -101,7 +103,7 @@ static void gst_real_pad_init               (GstRealPad *pad);
 static void    gst_real_pad_set_property       (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec);
 static void    gst_real_pad_get_property       (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec);
 
-static void    gst_real_pad_destroy            (GObject *object);
+static void    gst_real_pad_dispose            (GObject *object);
 
 static void    gst_pad_push_func               (GstPad *pad, GstBuffer *buf);
 
@@ -123,6 +125,7 @@ gst_real_pad_get_type(void) {
       sizeof(GstRealPad),
       32,
       (GInstanceInitFunc)gst_real_pad_init,
+      NULL
     };
     _gst_real_pad_type = g_type_register_static(GST_TYPE_PAD, "GstRealPad", &pad_info, 0);
   }
@@ -140,8 +143,7 @@ gst_real_pad_class_init (GstRealPadClass *klass)
 
   real_pad_parent_class = g_type_class_ref(GST_TYPE_PAD);
 
-// FIXME!
-//  gobject_class->destroy  = GST_DEBUG_FUNCPTR(gst_real_pad_destroy);
+  gobject_class->dispose  = GST_DEBUG_FUNCPTR(gst_real_pad_dispose);
   gobject_class->set_property  = GST_DEBUG_FUNCPTR(gst_real_pad_set_property);
   gobject_class->get_property  = GST_DEBUG_FUNCPTR(gst_real_pad_get_property);
 
@@ -284,10 +286,10 @@ gst_pad_new_from_template (GstPadTemplate *templ,
   g_return_val_if_fail (templ != NULL, NULL);
 
   pad = gst_pad_new (name, templ->direction);
+  
   gst_object_ref (GST_OBJECT (templ));
-  gst_object_sink (GST_OBJECT (templ));
   GST_PAD_PADTEMPLATE(pad) = templ;
-
+  
   return pad;
 }
 
@@ -552,11 +554,36 @@ gst_pad_disconnect (GstPad *srcpad,
  *
  * Connects the source pad to the sink pad.
  *
- * Returns: TRUE if the pad could be connected
+ * You shouldn't use this API in a real application because the
+ * failure mode dumps diagnostics to stderr.  A professional
+ * application should never fail, or use gst_pad_try_connect and
+ * check the return code.
  */
-gboolean
+void
 gst_pad_connect (GstPad *srcpad,
                 GstPad *sinkpad)
+{
+  if (!gst_pad_try_connect (srcpad, sinkpad))
+/* FIXME: g_critical is glib-2.0, not glib-1.2
+    g_critical ("couldn't connect %s:%s and %s:%s",
+*/
+    g_warning ("couldn't connect %s:%s and %s:%s",
+               GST_DEBUG_PAD_NAME (srcpad),
+               GST_DEBUG_PAD_NAME (sinkpad));
+}
+
+/**
+ * gst_pad_try_connect:
+ * @srcpad: the source pad to connect
+ * @sinkpad: the sink pad to connect
+ *
+ * Connects the source pad to the sink pad.
+ *
+ * Returns: TRUE if the pad could be connected
+ */
+gboolean
+gst_pad_try_connect (GstPad *srcpad,
+                    GstPad *sinkpad)
 {
   GstRealPad *realsrc, *realsink;
   gboolean negotiated = FALSE;
@@ -994,21 +1021,27 @@ gst_pad_get_bufferpool (GstPad *pad)
 }
 
 static void
-gst_real_pad_destroy (GObject *object)
+gst_real_pad_dispose (GObject *object)
 {
   GstPad *pad = GST_PAD (object);
+  
+  GST_DEBUG (GST_CAT_REFCOUNTING, "dispose %s:%s\n", GST_DEBUG_PAD_NAME(pad));
 
-  GST_DEBUG (GST_CAT_REFCOUNTING, "destroy %s:%s\n", GST_DEBUG_PAD_NAME(pad));
-
-  if (GST_PAD (pad)->padtemplate)
+  if (GST_PAD (pad)->padtemplate){
+    GST_DEBUG (GST_CAT_REFCOUNTING, "unreffing padtemplate'%s'\n",GST_OBJECT_NAME(GST_OBJECT (GST_PAD (pad)->padtemplate)));
     gst_object_unref (GST_OBJECT (GST_PAD (pad)->padtemplate));
-
-  if (GST_PAD_PEER (pad))
+  }
+  
+  if (GST_PAD_PEER (pad)){
+    GST_DEBUG (GST_CAT_REFCOUNTING, "disconnecting pad '%s'\n",GST_OBJECT_NAME(GST_OBJECT (GST_PAD (GST_PAD_PEER (pad)))));
     gst_pad_disconnect (pad, GST_PAD (GST_PAD_PEER (pad)));
-
-  if (GST_IS_ELEMENT (GST_OBJECT_PARENT (pad)))
+  }
+  
+  if (GST_IS_ELEMENT (GST_OBJECT_PARENT (pad))){
+    GST_DEBUG (GST_CAT_REFCOUNTING, "removing pad from element '%s'\n",GST_OBJECT_NAME(GST_OBJECT (GST_ELEMENT (GST_OBJECT_PARENT (pad)))));
     gst_element_remove_pad (GST_ELEMENT (GST_OBJECT_PARENT (pad)), pad);
-
+  }
+  
   // FIXME we should destroy the ghostpads, because they are nothing without the real pad
   if (GST_REAL_PAD (pad)->ghostpads) {
     GList *orig, *ghostpads;
@@ -1018,18 +1051,17 @@ gst_real_pad_destroy (GObject *object)
     while (ghostpads) {
       GstPad *ghostpad = GST_PAD (ghostpads->data);
 
-      if (GST_IS_ELEMENT (GST_OBJECT_PARENT (ghostpad)))
+      if (GST_IS_ELEMENT (GST_OBJECT_PARENT (ghostpad))){
+        GST_DEBUG (GST_CAT_REFCOUNTING, "removing ghost pad from element '%s'\n", GST_OBJECT_NAME(GST_OBJECT_PARENT (ghostpad)));
         gst_element_remove_pad (GST_ELEMENT (GST_OBJECT_PARENT (ghostpad)), ghostpad);
-
+      }
       ghostpads = g_list_next (ghostpads);
     }
     g_list_free (orig);
     g_list_free (GST_REAL_PAD(pad)->ghostpads);
   }
 
-// FIXME !!
-//  if (G_OBJECT_CLASS (real_pad_parent_class)->destroy)
-//    G_OBJECT_CLASS (real_pad_parent_class)->destroy (object);
+  G_OBJECT_CLASS (real_pad_parent_class)->dispose (object);
 }
 
 
@@ -1058,7 +1090,7 @@ gst_pad_load_and_connect (xmlNodePtr self,
       pad = gst_element_get_pad (GST_ELEMENT (parent), xmlNodeGetContent (field));
     }
     else if (!strcmp(field->name, "peer")) {
-      peer = g_strdup (xmlNodeGetContent (field));
+      peer = xmlNodeGetContent (field);
     }
     field = field->next;
   }
@@ -1424,7 +1456,9 @@ gst_pad_push (GstPad *pad, GstBuffer *buf)
           GST_DEBUG_FUNCPTR_NAME (peer->chainhandler), GST_DEBUG_PAD_NAME (((GstPad*)peer)));
     (peer->chainhandler) (((GstPad*)peer), buf);
   } else
-    GST_DEBUG (GST_CAT_DATAFLOW, "no chainhandler\n");
+    {
+      GST_DEBUG (GST_CAT_DATAFLOW, "no chainhandler\n");
+    }
 }
 #endif
 
@@ -1445,7 +1479,15 @@ gst_pad_pull (GstPad *pad)
   GST_DEBUG_ENTER("(%s:%s)",GST_DEBUG_PAD_NAME(pad));
 
   g_return_val_if_fail (GST_PAD_DIRECTION (pad) == GST_PAD_SINK, NULL);
-  g_return_val_if_fail (peer != NULL, NULL);
+
+  if (!peer)
+    {
+/* FIXME: g_critical is glib-2.0, not glib-1.2
+      g_critical ("gst_pad_pull but %s:%s is unconnected", GST_DEBUG_PAD_NAME(pad));
+*/
+      g_warning ("gst_pad_pull but %s:%s is unconnected", GST_DEBUG_PAD_NAME(pad));
+      return NULL;
+    }
 
   if (peer->gethandler) {
     GST_DEBUG (GST_CAT_DATAFLOW,"calling gethandler %s of peer pad %s:%s\n",
@@ -1610,6 +1652,7 @@ gst_padtemplate_get_type (void)
       sizeof(GstPadTemplate),
       32,
       (GInstanceInitFunc)gst_padtemplate_init,
+      NULL
     };
     padtemplate_type = g_type_register_static(GST_TYPE_OBJECT, "GstPadTemplate", &padtemplate_info, 0);
   }
@@ -1858,6 +1901,7 @@ gst_ghost_pad_get_type(void) {
       sizeof(GstGhostPad),
       8,
       (GInstanceInitFunc)gst_ghost_pad_init,
+      NULL
     };
     _gst_ghost_pad_type = g_type_register_static(GST_TYPE_PAD, "GstGhostPad", &pad_info, 0);
   }
index c1d63b043be223012118f82321dc2186a00a81da..70f0a396478e9cd95472206d23d95eefa9ccf0cb 100644 (file)
@@ -374,7 +374,8 @@ GstPad*                     gst_pad_get_peer                (GstPad *pad);
 
 GstBufferPool*         gst_pad_get_bufferpool          (GstPad *pad);
 
-gboolean               gst_pad_connect                 (GstPad *srcpad, GstPad *sinkpad);
+gboolean                gst_pad_try_connect             (GstPad *srcpad, GstPad *sinkpad);
+void                    gst_pad_connect                        (GstPad *srcpad, GstPad *sinkpad);
 void                   gst_pad_disconnect              (GstPad *srcpad, GstPad *sinkpad);
 
 gboolean               gst_pad_renegotiate             (GstPad *pad);
@@ -442,6 +443,9 @@ xmlNodePtr          gst_padtemplate_save_thyself    (GstPadTemplate *templ, xmlNodePtr pare
 GstPadTemplate*                gst_padtemplate_load_thyself    (xmlNodePtr parent);
 #endif
 
+xmlNodePtr              gst_pad_ghost_save_thyself   (GstPad *pad,
+                                                     GstElement *bin,
+                                                     xmlNodePtr parent);
 
 #ifdef __cplusplus
 }
index a0f3fe12f5000cbd9c8ad95fe3f5f3e468aa8a55..b7e519175a510b28d7bde3e28d20cdb190e78f52 100644 (file)
@@ -88,9 +88,11 @@ dynamic_connect (GstElement *element, GstPad *newpad, gpointer data)
 static gchar *
 gst_parse_unique_name(gchar *type,gst_parse_priv *priv)
 {
+  gpointer tmp;
   gint count;
 
-  count = GPOINTER_TO_INT(g_hash_table_lookup(priv->elementcounts,type));
+  tmp = g_hash_table_lookup (priv->elementcounts,type);
+  count = GPOINTER_TO_INT (tmp);
   count++;
   g_hash_table_insert(priv->elementcounts,type,GINT_TO_POINTER(count));
 
@@ -233,6 +235,7 @@ gst_parse_launch_cmdline(int argc,char *argv[],GstBin *parent,gst_parse_priv *pr
       argname = arg;
       pos[0] = '\0';
       argval = pos+1;
+      
       GST_DEBUG(0,"attempting to set argument '%s' to '%s' on element '%s'\n",
             argname,argval,GST_ELEMENT_NAME(previous));
       gst_util_set_object_arg (G_OBJECT(previous), argname, argval);
@@ -361,7 +364,7 @@ gst_parse_launch_cmdline(int argc,char *argv[],GstBin *parent,gst_parse_priv *pr
         }
       }
 
-      if (!sinkpads) GST_DEBUG(0,"can't find a sink pad for %s\n", gst_element_get_name (previous));
+      if (!sinkpads) GST_DEBUG(0,"can't find a sink pad for element\n");
       else GST_DEBUG(0,"have sink pad %s:%s\n",GST_DEBUG_PAD_NAME(GST_PARSE_LISTPAD(sinkpads)));
 
       if (!srcpads && sinkpads && previous) {
@@ -375,8 +378,10 @@ gst_parse_launch_cmdline(int argc,char *argv[],GstBin *parent,gst_parse_priv *pr
           srcpadname,
           GST_DEBUG_PAD_NAME(GST_PARSE_LISTPAD(sinkpads)));
 
-        g_signal_connect (G_OBJECT (previous), "new_pad", dynamic_connect, connect);
-        g_signal_connect (G_OBJECT (previous), "new_ghost_pad", dynamic_connect, connect);
+        g_signal_connect (G_OBJECT (previous), "new_pad",
+                         G_CALLBACK (dynamic_connect), connect);
+        g_signal_connect (G_OBJECT (previous), "new_ghost_pad",
+                         G_CALLBACK (dynamic_connect), connect);
       }
       else {
         for (j=0; (j<numsrcpads) && (j<numsinkpads); j++){
@@ -448,9 +453,10 @@ GST_DEBUG_PAD_NAME(temppad),GST_ELEMENT_NAME (parent),GST_PAD_NAME(temppad));
 
   if (retval) return retval;
 
-  if (closingchar != '\0')
-    DEBUG("returning IN THE WRONG PLACE\n");
-  else DEBUG("ending pipeline\n");
+  DEBUG (closingchar != '\0'?
+        "returning IN THE WRONG PLACE\n" : 
+        "ending pipeline\n");
+
   return i+1;
 }
 
index 85a67dadeaf68e7923f9ffc9d027a16a784b5f5a..18c73fcffafe29a10d83e4582beab3bf3cdf2e01 100644 (file)
@@ -75,6 +75,7 @@ gst_pipeline_get_type (void) {
       sizeof(GstPipeline),
       0,
       (GInstanceInitFunc)gst_pipeline_init,
+      NULL
     };
     pipeline_type = g_type_register_static (GST_TYPE_BIN, "GstPipeline", &pipeline_info, 0);
   }
index 528f4210b682343c383c7a9ba868b830a4404316..9f1f1408b2e73e4a6962fb6e406ee2afee21d55d 100644 (file)
@@ -674,7 +674,7 @@ gst_plugin_find_feature_func (GstPlugin *plugin, const gchar *name, GType type)
   return NULL;
 }
 
-GstPluginFeature*
+static GstPluginFeature*
 gst_plugin_find_feature (const gchar *name, GType type)
 {
   GList *plugins;
index 7e814440794acd127db9ec00828c7ecbfd36580a..11021ef2c7dd23348452b4aedfb9e7b298af8723 100644 (file)
@@ -51,6 +51,7 @@ gst_plugin_feature_get_type (void)
       sizeof (GstObject),
       32,
       (GInstanceInitFunc) gst_plugin_feature_init,
+      NULL
     };
     plugin_feature_type = g_type_register_static (GST_TYPE_OBJECT, "GstPluginFeature", 
                                                  &plugin_feature_info, G_TYPE_FLAG_ABSTRACT);
index 1269e7fb03e4ef54a962cc3a14a510c19a82c5a9..670498d2831475a3450b49ce426454a7c5d5926f 100644 (file)
@@ -23,6 +23,7 @@
 //#define GST_DEBUG_ENABLED
 #include "gst_private.h"
 
+#include "gstlog.h"
 #include "gstprops.h"
 #include "gstpropsprivate.h"
 
index fdf8bfec54f7a596b746b35925a5fadd57bc424b..08cc5f8a60320b95f6f65142431251a281ce1fb8 100644 (file)
@@ -121,6 +121,7 @@ gst_queue_get_type(void)
       sizeof(GstQueue),
       4,
       (GInstanceInitFunc)gst_queue_init,
+      NULL
     };
     queue_type = g_type_register_static (GST_TYPE_ELEMENT, "GstQueue", &queue_info, 0);
   }
index afa948a29fcbacb9b114ea6adf06e1d7da9ca291..fc4abe0a72d6a6f665aee3d8dd9815bde9d85c5c 100644 (file)
@@ -842,6 +842,7 @@ GType gst_schedule_get_type(void) {
       sizeof(GstSchedule),
       0,
       (GInstanceInitFunc)gst_schedule_init,
+      NULL
     };
     schedule_type = g_type_register_static(GST_TYPE_OBJECT, "GstSchedule", &schedule_info, 0);
   }
@@ -910,7 +911,7 @@ GstElement *gst_schedule_check_pad (GstSchedule *sched, GstPad *pad) {
 }
 */
 
-GstScheduleChain *
+static GstScheduleChain *
 gst_schedule_chain_new (GstSchedule *sched)
 {
   GstScheduleChain *chain = g_new (GstScheduleChain, 1);
@@ -934,7 +935,7 @@ gst_schedule_chain_new (GstSchedule *sched)
   return chain;
 }
 
-void
+static void
 gst_schedule_chain_destroy (GstScheduleChain *chain)
 {
   GstSchedule *sched = chain->sched;
@@ -951,7 +952,7 @@ gst_schedule_chain_destroy (GstScheduleChain *chain)
   GST_INFO (GST_CAT_SCHEDULING, "destroyed chain %p, now are %d chains in sched %p",chain,sched->num_chains,sched);
 }
 
-void
+static void
 gst_schedule_chain_add_element (GstScheduleChain *chain, GstElement *element)
 {
   GST_INFO (GST_CAT_SCHEDULING, "adding element \"%s\" to chain %p", GST_ELEMENT_NAME (element),chain);
@@ -964,7 +965,7 @@ gst_schedule_chain_add_element (GstScheduleChain *chain, GstElement *element)
   chain->num_elements++;
 }
 
-void
+static void
 gst_schedule_chain_enable_element (GstScheduleChain *chain, GstElement *element)
 {
   GST_INFO (GST_CAT_SCHEDULING, "enabling element \"%s\" in chain %p", GST_ELEMENT_NAME (element),chain);
@@ -979,7 +980,7 @@ gst_schedule_chain_enable_element (GstScheduleChain *chain, GstElement *element)
   gst_schedule_cothreaded_chain(GST_BIN(chain->sched->parent),chain);
 }
 
-void
+static void
 gst_schedule_chain_disable_element (GstScheduleChain *chain, GstElement *element)
 {
   GST_INFO (GST_CAT_SCHEDULING, "disabling element \"%s\" in chain %p", GST_ELEMENT_NAME (element),chain);
@@ -995,7 +996,7 @@ gst_schedule_chain_disable_element (GstScheduleChain *chain, GstElement *element
 //  gst_schedule_cothreaded_chain(GST_BIN(chain->sched->parent),chain);
 }
 
-void
+static void
 gst_schedule_chain_remove_element (GstScheduleChain *chain, GstElement *element)
 {
   GST_INFO (GST_CAT_SCHEDULING, "removing element \"%s\" from chain %p", GST_ELEMENT_NAME (element),chain);
@@ -1017,7 +1018,7 @@ gst_schedule_chain_remove_element (GstScheduleChain *chain, GstElement *element)
   element->sched = NULL;
 }
 
-void
+static void
 gst_schedule_chain_elements (GstSchedule *sched, GstElement *element1, GstElement *element2)
 {
   GList *chains;
@@ -1103,7 +1104,7 @@ GST_ELEMENT_SCHED(srcelement),GST_ELEMENT_SCHED(sinkelement));
 }
 
 // find the chain within the schedule that holds the element, if any
-GstScheduleChain *
+static GstScheduleChain *
 gst_schedule_find_chain (GstSchedule *sched, GstElement *element)
 {
   GList *chains;
@@ -1125,7 +1126,7 @@ gst_schedule_find_chain (GstSchedule *sched, GstElement *element)
   return NULL;
 }
 
-void
+static void
 gst_schedule_chain_recursive_add (GstScheduleChain *chain, GstElement *element)
 {
   GList *pads;
index a1cdc2bba5785c927b6ceca4d9e8872f4765cb6b..27ae96c6d71297953baebf05dfb89b99239efce5 100644 (file)
@@ -61,7 +61,7 @@ enum {
 static void                    gst_thread_class_init           (GstThreadClass *klass);
 static void                    gst_thread_init                 (GstThread *thread);
 
-static void                    gst_thread_real_destroy         (GObject *object);
+static void                    gst_thread_dispose      (GObject *object);
 
 static void                    gst_thread_set_property         (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec);
 static void                    gst_thread_get_property         (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec);
@@ -95,6 +95,7 @@ gst_thread_get_type(void) {
       sizeof(GstThread),
       4,
       (GInstanceInitFunc)gst_thread_init,
+      NULL
     };
     thread_type = g_type_register_static(GST_TYPE_BIN, "GstThread", &thread_info, 0);
   }
@@ -120,8 +121,7 @@ gst_thread_class_init (GstThreadClass *klass)
     g_param_spec_boolean("create_thread", "Create Thread", "Whether to create a thread.",
                          TRUE,G_PARAM_READWRITE));
 
-// FIXME!
-//  gobject_class->destroy =           gst_thread_real_destroy;
+  gobject_class->dispose =             gst_thread_dispose;
 
 #ifndef GST_DISABLE_LOADSAVE
   gstobject_class->save_thyself =      GST_DEBUG_FUNCPTR (gst_thread_save_thyself);
@@ -161,21 +161,20 @@ gst_thread_init (GstThread *thread)
 }
 
 static void
-gst_thread_real_destroy (GObject *object)
+gst_thread_dispose (GObject *object)
 {
   GstThread *thread = GST_THREAD (object);
 
-  GST_DEBUG (GST_CAT_REFCOUNTING,"destroy()\n");
+  GST_DEBUG (GST_CAT_REFCOUNTING,"dispose\n");
 
   g_mutex_free (thread->lock);
   g_cond_free (thread->cond);
 
-// FIXME!
-//  if (G_OBJECT_CLASS (parent_class)->destroy)
-//    G_OBJECT_CLASS (parent_class)->destroy (object);
+  G_OBJECT_CLASS (parent_class)->dispose (object);
 
   gst_object_destroy (GST_OBJECT (GST_ELEMENT_SCHED (thread)));
   gst_object_unref (GST_OBJECT (GST_ELEMENT_SCHED (thread)));
+
 }
 
 static void
@@ -256,7 +255,6 @@ gst_thread_change_state (GstElement *element)
   gboolean stateset = GST_STATE_SUCCESS;
   gint transition;
   pthread_t self = pthread_self();
-  GstElement *peerelement;
 
   g_return_val_if_fail (GST_IS_THREAD(element), FALSE);
 //  GST_DEBUG_ENTER("(\"%s\")",GST_ELEMENT_NAME(element));
@@ -394,10 +392,15 @@ gst_thread_change_state (GstElement *element)
             GList *pads = GST_ELEMENT_PADS(e);
             while (pads)
             {
+             GstRealPad *peer;
+             GstElement *peerelement;
               GstPad *p = GST_PAD(pads->data);
               pads = g_list_next(pads);
 
-              peerelement = GST_PAD_PARENT(GST_PAD_PEER(p));
+             peer = GST_PAD_PEER(p);
+             if (!peer) continue;
+
+              peerelement = GST_PAD_PARENT(peer);
               if (!peerelement) continue;              // deal with case where there's no peer
 
               if (!GST_FLAG_IS_SET(peerelement,GST_ELEMENT_DECOUPLED)) {
index fb0c7b1a239339a5cac0615901fc0d514c052303..6aad09125366cf3acbe5963d9bb480b2e52849c1 100644 (file)
@@ -30,6 +30,7 @@
 
 #include "gst_private.h"
 
+#include "gstlog.h"
 #include "gsttrace.h"
 
 
index 99bee4c2d879489c906f143b3013c04dafe79dea..feeac265065df08a7c10f304e2ccb0fba5ab295f 100644 (file)
@@ -69,6 +69,7 @@ gst_typefactory_get_type (void)
       sizeof(GstTypeFactory),
       0,
       (GInstanceInitFunc) gst_typefactory_init,
+      NULL
     };
     typefactory_type = g_type_register_static (GST_TYPE_PLUGIN_FEATURE,
                                                "GstTypeFactory", &typefactory_info, 0);
index 09894e0de17495bd486facf9dea125a175bfd4bb..44a557ee3d78002d2a756242c1e7ca1fbcccb15a 100644 (file)
@@ -81,6 +81,7 @@ gst_typefind_get_type (void)
       sizeof(GstTypeFind),
       0,
       (GInstanceInitFunc)gst_typefind_init,
+      NULL
     };
     typefind_type = g_type_register_static (GST_TYPE_ELEMENT, "GstTypeFind", &typefind_info, 0);
   }
index 7681ad3e118caf7021b1ceb71a1eb36a020be541..f38f39caa96389cc475a6fc9d813447252a4bca1 100644 (file)
@@ -28,6 +28,8 @@
 
 #include "gstextratypes.h"
 
+#define ZERO(mem) memset(&mem, 0, sizeof(mem))
+
 /**
  * gst_util_get_int_arg:
  * @object: the object to query
@@ -40,8 +42,9 @@
 gint
 gst_util_get_int_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_INT);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -60,8 +63,9 @@ gst_util_get_int_arg (GObject *object, const gchar *argname)
 gint
 gst_util_get_bool_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_BOOLEAN);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -80,8 +84,9 @@ gst_util_get_bool_arg (GObject *object, const gchar *argname)
 glong
 gst_util_get_long_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_LONG);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -100,8 +105,9 @@ gst_util_get_long_arg (GObject *object, const gchar *argname)
 gfloat
 gst_util_get_float_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_FLOAT);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -120,8 +126,9 @@ gst_util_get_float_arg (GObject *object, const gchar *argname)
 gdouble 
 gst_util_get_double_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_DOUBLE);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -140,12 +147,13 @@ gst_util_get_double_arg (GObject *object, const gchar *argname)
  const gchar*
 gst_util_get_string_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_STRING);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
-  return g_value_get_string(&value);
+  return g_value_get_string(&value);  // memleak?
 }
 
 /**
@@ -160,8 +168,9 @@ gst_util_get_string_arg (GObject *object, const gchar *argname)
 gpointer
 gst_util_get_pointer_arg (GObject *object, const gchar *argname) 
 {
-  GValue value = {0, };
+  GValue value;
 
+  ZERO (value);
   g_value_init (&value, G_TYPE_POINTER);
   g_object_get_property(G_OBJECT(object),argname,&value);
 
@@ -315,3 +324,217 @@ gst_util_set_object_arg (GObject *object,  const gchar *name,  const gchar *valu
     }
   }
 }
+
+// -----------------------------------------------------
+//
+// The following code will be moved out of the main
+// gstreamer library someday.
+//
+
+#include "gstpad.h"
+#include "gsttype.h"
+#include "gstprops.h"
+#include "gstpropsprivate.h"
+
+static void string_append_indent (GString *str, gint count)
+{
+  gint xx;
+  for (xx=0; xx < count; xx++)
+    g_string_append_c (str, ' ');
+}
+
+static void 
+gst_print_props (GString *buf, gint indent,
+                GList *props, gboolean showname)
+{
+  GList *elem;
+  guint width = 0;
+           
+  if (showname)
+    for (elem = props; elem; elem = g_list_next (elem))
+      {
+       GstPropsEntry *prop = elem->data;
+       const gchar *name = g_quark_to_string (prop->propid);
+
+       if (width < strlen (name))
+         width = strlen (name);
+      }
+
+  for (elem = props; elem; elem = g_list_next (elem))
+    {
+      GstPropsEntry *prop = elem->data;
+
+      string_append_indent (buf, indent);
+      if (showname)
+       {
+         const gchar *name = g_quark_to_string (prop->propid);
+         
+         g_string_append (buf, name);
+         string_append_indent (buf, 2 + width - strlen (name));
+       }
+
+      switch (prop->propstype) {
+      case GST_PROPS_INT_ID:
+       g_string_printfa (buf, "%d (int)\n", prop->data.int_data);
+       break;
+      case GST_PROPS_INT_RANGE_ID:
+       g_string_printfa (buf, "%d - %d (int)\n",
+                         prop->data.int_range_data.min,
+                         prop->data.int_range_data.max);
+       break;
+      case GST_PROPS_FLOAT_ID:
+       g_string_printfa (buf, "%f (float)\n", prop->data.float_data);
+      break;
+      case GST_PROPS_FLOAT_RANGE_ID:
+       g_string_printfa (buf, "%f - %f (float)\n",
+                         prop->data.float_range_data.min,
+                         prop->data.float_range_data.max);
+       break;
+      case GST_PROPS_BOOL_ID:
+       g_string_printfa (buf, "%s\n",
+                         prop->data.bool_data ? "TRUE" : "FALSE");
+       break;
+      case GST_PROPS_STRING_ID:
+       g_string_printfa (buf, "\"%s\"\n", prop->data.string_data.string);
+       break;
+      case GST_PROPS_FOURCC_ID:
+       g_string_printfa (buf, "'%c%c%c%c' (fourcc)\n",
+                         prop->data.fourcc_data & 0xff,
+                         prop->data.fourcc_data>>8 & 0xff,
+                         prop->data.fourcc_data>>16 & 0xff,
+                         prop->data.fourcc_data>>24 & 0xff);
+       break;
+      case GST_PROPS_LIST_ID:
+       gst_print_props (buf, indent+2, prop->data.list_data.entries, FALSE);
+       break;
+      default:
+       g_string_printfa (buf, "unknown proptype %d\n", prop->propstype);
+       break;
+      }
+  }
+}
+
+void gst_print_pad_caps (GString *buf, gint indent, GstPad *pad)
+{
+  GstRealPad *realpad;
+  GstCaps *caps;
+
+  realpad = GST_PAD_REALIZE(pad);
+  caps = realpad->caps;
+
+  if (!caps)
+    {
+      string_append_indent (buf, indent);
+      g_string_printf (buf, "%s:%s has no capabilities",
+                      GST_DEBUG_PAD_NAME (pad));
+    }
+  else
+    {
+      gint capx = 0;
+
+      while (caps) {
+       GstType *type;
+
+       string_append_indent (buf, indent);
+       g_string_printfa (buf, "Cap[%d]: %s\n", capx++, caps->name);
+
+       type = gst_type_find_by_id (caps->id);
+       string_append_indent (buf, indent+2);
+       g_string_printfa (buf, "MIME type: %s\n",
+                         type->mime? type->mime : "unknown/unknown");
+
+       if (caps->properties)
+         gst_print_props (buf, indent + 4,
+                          caps->properties->properties, TRUE);
+
+       caps = caps->next;
+      }
+    }
+}
+
+void gst_print_element_args (GString *buf, gint indent, GstElement *element)
+{
+  gint num_properties;
+  gint px;
+  guint width;
+
+  GParamSpec **property_specs =
+    g_object_class_list_properties (G_OBJECT_GET_CLASS (element),
+                                   &num_properties);
+  
+  width=0;
+  for (px=0; px < num_properties; px++) {
+    GParamSpec *param = property_specs[px];
+    if (width < strlen (param->name))
+      width = strlen (param->name);
+  }
+
+  for (px=0; px < num_properties; px++) {
+    GParamSpec *param = property_specs[px];
+    GValue value;
+
+    ZERO (value);
+
+    g_value_init (&value, param->value_type);
+    g_object_get_property (G_OBJECT (element), param->name, &value);
+
+    string_append_indent (buf, indent);
+    g_string_append (buf, param->name);
+    string_append_indent (buf, 2 + width - strlen (param->name));
+
+    if (G_IS_PARAM_SPEC_ENUM (param)) {
+      GEnumValue *values;
+
+#ifdef USE_GLIB2
+      values = G_ENUM_CLASS (g_type_class_ref (param->value_type))->values;
+#else
+      values = gtk_type_enum_get_values (param->value_type);
+#endif
+
+      g_string_printfa (buf, "%s (%s)",
+                       values [g_value_get_enum (&value)].value_nick,
+                       g_type_name (G_VALUE_TYPE (&value)));
+    }
+    else
+      switch (G_VALUE_TYPE (&value)) {
+      case G_TYPE_STRING:
+       g_string_printfa (buf, "\"%s\"", g_value_get_string (&value));
+       break;
+      case G_TYPE_BOOLEAN:
+       g_string_append (buf, g_value_get_boolean (&value)? "TRUE":"FALSE");
+       break;
+      case G_TYPE_ULONG:{
+       gulong val = g_value_get_ulong (&value);
+       g_string_printfa (buf, "%lu (0x%lx)", val, val);
+       break;}
+      case G_TYPE_LONG:{
+       glong val = g_value_get_long (&value);
+       g_string_printfa (buf, "%ld (0x%lx)", val, val);
+       break;}
+      case G_TYPE_UINT:{
+       guint val = g_value_get_uint (&value);
+       g_string_printfa (buf, "%u (0x%x)", val, val);
+       break;}
+      case G_TYPE_INT:{
+       gint val = g_value_get_int (&value);
+       g_string_printfa (buf, "%d (0x%x)", val, val);
+       break;}
+      case G_TYPE_FLOAT:
+       g_string_printfa (buf, "%f", g_value_get_float (&value));
+       break;
+      case G_TYPE_DOUBLE:
+       g_string_printfa (buf, "%f", g_value_get_double (&value));
+       break;
+      default:
+       g_string_printfa (buf, "unknown value_type %d", G_VALUE_TYPE (&value));
+       break;
+      }
+
+    g_string_append_c (buf, '\n');
+
+    if (G_VALUE_TYPE (&value))
+      g_value_unset (&value);
+  }
+
+  g_free (property_specs);
+}
index daf2b2aa5397e07dfca4e2deb4af0f73957b254f..e7e1fa5f988e4e729dbfa62582f50c4fecd87a27 100644 (file)
@@ -44,6 +44,10 @@ void                 gst_util_set_object_arg         (GObject *object, const gchar *name, const gchar
        
 void           gst_util_dump_mem               (guchar *mem, guint size);
 
+
+void gst_print_pad_caps (GString *buf, gint indent, GstPad *pad);
+void gst_print_element_args (GString *buf, gint indent, GstElement *element);
+
 #ifdef __cplusplus
 }
 #endif /* __cplusplus */
index 54d311c2a7c5fb12d53b2c0ed539b6df4ceec991..5d29e212b7dce4a5004220283a2ccc1b574ed8ee 100644 (file)
@@ -54,6 +54,7 @@ gst_xml_get_type(void)
       sizeof(GstXML),
       0,
       (GInstanceInitFunc)gst_xml_init,
+      NULL
     };
     xml_type = g_type_register_static (GST_TYPE_OBJECT, "GstXml", &xml_info, 0);
   }
index 8253f453fbe212c84c4400082e5178d27ae3fd20..8e8427c28819fc35e6e23b6a60e3589ba43298a4 100644 (file)
@@ -1,7 +1,6 @@
 noinst_HEADERS = \
        mmx.h \
-       sse.h \
-       gstaudio.h
+       sse.h
 
 # This test needs to go here because this is the first makefile which the
 # install target gets run in.
diff --git a/include/gstaudio.h b/include/gstaudio.h
deleted file mode 100644 (file)
index a661159..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-/* GStreamer
- * Copyright (C) 1999,2000 Erik Walthinsen <omega@cse.ogi.edu>
- *                    2000 Wim Taymans <wtay@chello.be>
- *
- * gstaudio.h: convenience macros for pad capabilities
- *
- * 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.
- */
-
-/* for people that are looking at this source: the purpose of these defines is
- * to make GstCaps a bit easier, in that you don't have to know all of the
- * properties that need to be defined. you can just use these macros. currently
- * (8/01) the only plugins that use these are the passthrough, speed, volume,
- * and [de]interleave plugins. so. these are for convenience only, and do not
- * specify the 'limits' of gstreamer. you might also use these definitions as a
- * base for making your own caps, if need be.
- *
- * for example, to make a source pad that can output mono streams of either
- * float or int:
-
-    template = gst_padtemplate_new 
-      ("sink", GST_PAD_SINK, GST_PAD_ALWAYS,
-      gst_caps_append(gst_caps_new ("sink_int",  "audio/raw",
-                                    GST_AUDIO_INT_PAD_TEMPLATE_PROPS),
-                      gst_caps_new ("sink_float", "audio/raw",
-                                    GST_AUDIO_FLOAT_MONO_PAD_TEMPLATE_PROPS)),
-      NULL);
-
-    srcpad = gst_pad_new_from_template(template,"src");
-
- * Andy Wingo, 18 August 2001 */
-
-#define GST_AUDIO_INT_PAD_TEMPLATE_PROPS \
-        gst_props_new (\
-          "format",             GST_PROPS_STRING ("int"),\
-            "law",              GST_PROPS_INT (0),\
-            "endianness",       GST_PROPS_INT (G_BYTE_ORDER),\
-            "signed",           GST_PROPS_LIST (\
-                                                 GST_PROPS_BOOLEAN (TRUE),\
-                                                 GST_PROPS_BOOLEAN(FALSE)\
-                                               ),\
-            "width",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
-            "depth",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
-            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
-            "channels",         GST_PROPS_INT_RANGE (1, G_MAXINT),\
-          NULL)
-
-#define GST_AUDIO_INT_MONO_PAD_TEMPLATE_PROPS \
-        gst_props_new (\
-          "format",             GST_PROPS_STRING ("int"),\
-            "law",              GST_PROPS_INT (0),\
-            "endianness",       GST_PROPS_INT (G_BYTE_ORDER),\
-            "signed",           GST_PROPS_LIST (\
-                                                 GST_PROPS_BOOLEAN (TRUE),\
-                                                 GST_PROPS_BOOLEAN(FALSE)\
-                                               ),\
-            "width",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
-            "depth",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
-            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
-            "channels",         GST_PROPS_INT (1),\
-          NULL)
-
-#define GST_AUDIO_FLOAT_MONO_PAD_TEMPLATE_PROPS \
-        gst_props_new (\
-          "format",             GST_PROPS_STRING ("float"),\
-            "layout",           GST_PROPS_STRING ("gfloat"),\
-            "intercept",        GST_PROPS_FLOAT (0.0),\
-            "slope",            GST_PROPS_FLOAT (1.0),\
-            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
-            "channels",         GST_PROPS_INT (1),\
-            NULL)
index a7f69c30b98771002bdc9cfd3f812ca5283a4f7c..581277f9d2621500d3c2aae067891929455b0c69 100644 (file)
@@ -1,4 +1,3 @@
+SUBDIRS = riff getbits putbits idct audio bytestream control
 
-SUBDIRS = riff getbits putbits idct audio bytestream
-
-DIST_SUBDIRS = riff getbits putbits audio idct bytestream
+DIST_SUBDIRS = riff getbits putbits audio idct bytestream control
index 7cced9acf277f617e85e3070e2bbf27561ba2e39..09ef3ec796b9c734e05019c22f8edc28cac70963 100644 (file)
  * Boston, MA 02111-1307, USA.
  */
 
+#include <gst/gst.h>
+
+/* for people that are looking at this source: the purpose of these defines is
+ * to make GstCaps a bit easier, in that you don't have to know all of the
+ * properties that need to be defined. you can just use these macros. currently
+ * (8/01) the only plugins that use these are the passthrough, speed, volume,
+ * and [de]interleave plugins. so. these are for convenience only, and do not
+ * specify the 'limits' of gstreamer. you might also use these definitions as a
+ * base for making your own caps, if need be.
+ *
+ * for example, to make a source pad that can output mono streams of either
+ * float or int:
+
+    template = gst_padtemplate_new 
+      ("sink", GST_PAD_SINK, GST_PAD_ALWAYS,
+      gst_caps_append(gst_caps_new ("sink_int",  "audio/raw",
+                                    GST_AUDIO_INT_PAD_TEMPLATE_PROPS),
+                      gst_caps_new ("sink_float", "audio/raw",
+                                    GST_AUDIO_FLOAT_MONO_PAD_TEMPLATE_PROPS)),
+      NULL);
+
+    srcpad = gst_pad_new_from_template(template,"src");
+
+ * Andy Wingo, 18 August 2001 */
+
+#define GST_AUDIO_INT_PAD_TEMPLATE_PROPS \
+        gst_props_new (\
+          "format",             GST_PROPS_STRING ("int"),\
+            "law",              GST_PROPS_INT (0),\
+            "endianness",       GST_PROPS_INT (G_BYTE_ORDER),\
+            "signed",           GST_PROPS_LIST (\
+                                                 GST_PROPS_BOOLEAN (TRUE),\
+                                                 GST_PROPS_BOOLEAN(FALSE)\
+                                               ),\
+            "width",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
+            "depth",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
+            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
+            "channels",         GST_PROPS_INT_RANGE (1, G_MAXINT),\
+          NULL)
+
+#define GST_AUDIO_INT_MONO_PAD_TEMPLATE_PROPS \
+        gst_props_new (\
+          "format",             GST_PROPS_STRING ("int"),\
+            "law",              GST_PROPS_INT (0),\
+            "endianness",       GST_PROPS_INT (G_BYTE_ORDER),\
+            "signed",           GST_PROPS_LIST (\
+                                                 GST_PROPS_BOOLEAN (TRUE),\
+                                                 GST_PROPS_BOOLEAN(FALSE)\
+                                               ),\
+            "width",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
+            "depth",            GST_PROPS_LIST (GST_PROPS_INT(8), GST_PROPS_INT(16)),\
+            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
+            "channels",         GST_PROPS_INT (1),\
+          NULL)
+
+#define GST_AUDIO_FLOAT_MONO_PAD_TEMPLATE_PROPS \
+        gst_props_new (\
+          "format",             GST_PROPS_STRING ("float"),\
+            "layout",           GST_PROPS_STRING ("gfloat"),\
+            "intercept",        GST_PROPS_FLOAT (0.0),\
+            "slope",            GST_PROPS_FLOAT (1.0),\
+            "rate",             GST_PROPS_INT_RANGE (4000, 96000),\
+            "channels",         GST_PROPS_INT (1),\
+            NULL)
+
 /*
  * this library defines and implements some helper functions for audio
  * handling
  */
 
-#include <gst/gst.h>
-
 /* get byte size of audio frame (based on caps of pad */
 int            gst_audio_frame_byte_size       (GstPad* pad);
 
@@ -43,3 +106,4 @@ long                 gst_audio_highest_sample_value  (GstPad* pad);
 /* check if the buffer size is a whole multiple of the frame size */
 gboolean       gst_audio_is_buffer_framed      (GstPad* pad, GstBuffer* buf);
 
+
diff --git a/libs/control/Makefile.am b/libs/control/Makefile.am
new file mode 100644 (file)
index 0000000..bb72125
--- /dev/null
@@ -0,0 +1,21 @@
+filterdir = $(libdir)/gst
+
+filter_LTLIBRARIES = libgstcontrol.la
+
+libgstcontrol_la_SOURCES = \
+    gstcontrol.c \
+    gstdparammanager.c \
+    gstdparam.c \
+    gstdplinearinterp.c
+    
+
+libgstcontrolincludedir = $(includedir)/gst/libs/control
+libgstcontrolinclude_HEADERS = \
+    gstcontrol.h \
+    gstdparammanager.h \
+    gstdparam.h \
+    gstdplinearinterp.h
+
+libgstcontrol_la_LIBADD = -lm
+
+CFLAGS += -O2 $(FOMIT_FRAME_POINTER) -finline-functions -ffast-math
diff --git a/libs/control/gstcontrol.c b/libs/control/gstcontrol.c
new file mode 100644 (file)
index 0000000..9be5095
--- /dev/null
@@ -0,0 +1,22 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstcontrol.c: GStreamer control utility library
+ *
+ * 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.
+ */
+#include "gstcontrol.h"
diff --git a/libs/control/gstcontrol.h b/libs/control/gstcontrol.h
new file mode 100644 (file)
index 0000000..764f37b
--- /dev/null
@@ -0,0 +1,41 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstcontrol.h: GStreamer control utility library
+ *
+ * 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_CONTROL_H__
+#define __GST_CONTROL_H__
+
+#include <gst/gstobject.h>
+#include <gst/gstprops.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif /* __cplusplus */
+
+#include <libs/control/gstdparammanager.h>
+#include <libs/control/gstdparam.h>
+
+#include <libs/control/gstdplinearinterp.h>
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+
+#endif /* __GST_CONTROL_H__ */
diff --git a/libs/control/gstdparam.c b/libs/control/gstdparam.c
new file mode 100644 (file)
index 0000000..665b66d
--- /dev/null
@@ -0,0 +1,368 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdparam.c: Dynamic Parameter functionality
+ *
+ * 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.
+ */
+
+#include <math.h>
+#include <string.h>
+#include <gst/gstinfo.h>
+
+#include "gstdparam.h"
+#include "gstdparammanager.h"
+
+static void gst_dparam_class_init (GstDParamClass *klass);
+static void gst_dparam_init (GstDParam *dparam);
+
+static void gst_dparam_do_update_realtime (GstDParam *dparam, gint64 timestamp);
+static GValue** gst_dparam_get_point_realtime (GstDParam *dparam, gint64 timestamp);
+
+GType 
+gst_dparam_get_type(void) {
+       static GType dparam_type = 0;
+
+       if (!dparam_type) {
+               static const GTypeInfo dparam_info = {
+                       sizeof(GstDParamClass),
+                       NULL,
+                       NULL,
+                       (GClassInitFunc)gst_dparam_class_init,
+                       NULL,
+                       NULL,
+                       sizeof(GstDParam),
+                       0,
+                       (GInstanceInitFunc)gst_dparam_init,
+               };
+               dparam_type = g_type_register_static(GST_TYPE_OBJECT, "GstDParam", &dparam_info, 0);
+       }
+       return dparam_type;
+}
+
+static void
+gst_dparam_class_init (GstDParamClass *klass)
+{
+       GObjectClass *gobject_class;
+       GstDParamClass *dparam_class;
+       GstObjectClass *gstobject_class;
+
+       gobject_class = (GObjectClass*)klass;
+       dparam_class = (GstDParamClass*)klass;
+       gstobject_class = (GstObjectClass*) klass;
+
+       //gstobject_class->save_thyself = gst_dparam_save_thyself;
+
+}
+
+static void
+gst_dparam_init (GstDParam *dparam)
+{
+       g_return_if_fail (dparam != NULL);
+       GST_DPARAM_VALUE(dparam) = NULL;
+       GST_DPARAM_TYPE(dparam) = 0;
+       GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam)=0LL;
+       GST_DPARAM_LAST_UPDATE_TIMESTAMP(dparam)=0LL;
+       GST_DPARAM_READY_FOR_UPDATE(dparam)=FALSE;
+       dparam->lock = g_mutex_new ();
+}
+
+/**
+ * gst_dparam_new:
+ * @type: the type that this dparam will store
+ *
+ * Returns: a new instance of GstDParam
+ */
+GstDParam* 
+gst_dparam_new (GType type)
+{
+       GstDParam *dparam;
+
+       dparam = g_object_new (gst_dparam_get_type (), NULL);
+       dparam->do_update_func = gst_dparam_do_update_realtime;
+       dparam->get_point_func = gst_dparam_get_point_realtime;
+       
+       dparam->point = gst_dparam_new_value_array(type, 0);    
+       GST_DPARAM_TYPE(dparam) = type;
+       
+       return dparam;
+}
+
+/**
+ * gst_dparam_attach
+ * @dparam: GstDParam instance
+ * @parent: the GstDParamManager that this dparam belongs to
+ *
+ */
+void
+gst_dparam_attach (GstDParam *dparam, GstObject *parent, GValue *value, GstDParamSpec *spec)
+{
+       
+       g_return_if_fail (dparam != NULL);
+       g_return_if_fail (GST_IS_DPARAM (dparam));
+       g_return_if_fail (GST_DPARAM_PARENT (dparam) == NULL);
+       g_return_if_fail (parent != NULL);
+       g_return_if_fail (G_IS_OBJECT (parent));
+       g_return_if_fail (GST_IS_DPMAN (parent));
+       g_return_if_fail ((gpointer)dparam != (gpointer)parent);
+       g_return_if_fail (value != NULL);
+       g_return_if_fail (spec != NULL);
+       g_return_if_fail (GST_DPARAM_TYPE(dparam) == G_VALUE_TYPE(value));
+       
+       GST_DPARAM_NAME(dparam) = spec->dparam_name;
+       GST_DPARAM_VALUE(dparam) = value;
+       GST_DPARAM_SPEC(dparam) = spec;
+       gst_object_set_parent (GST_OBJECT (dparam), parent);
+}
+
+/**
+ * gst_dparam_new_value_array
+ * @type: the type of the first GValue in the array
+ * @...: the type of other GValues in the array
+ *
+ * The list of types should be terminated with a 0.
+ * If the type of a value is not yet known then use G_TYPE_NONE .
+ *
+ * Returns: an newly created array of GValues
+ */
+GValue**
+gst_dparam_new_value_array(GType type, ...)
+{
+       GValue **point;
+       GValue *value;
+       guint x;
+       guint values_length = 0;
+       va_list var_args;
+       GType each_type;
+
+       va_start (var_args, type);
+       each_type = type;
+       while (each_type){
+               values_length++;
+               each_type = va_arg (var_args, GType);
+       }
+       va_end (var_args);
+       
+       point = g_new0(GValue*,values_length + 1);
+
+       va_start (var_args, type);
+       each_type = type;
+       for (x=0 ; x < values_length ; x++){
+               value = g_new0(GValue,1);
+               if (each_type != G_TYPE_NONE){
+                       g_value_init(value, each_type);
+               }
+               point[x] = value;
+               each_type = va_arg (var_args, GType);
+       }
+       point[values_length] = NULL;
+       va_end (var_args);
+       
+       GST_DEBUG(GST_CAT_PARAMS, "array with %d values created\n", values_length);
+
+       return point;
+}
+
+void
+gst_dparam_set_value_from_string(GValue *value, const gchar *value_str)
+{
+
+       g_return_if_fail(value != NULL);
+       g_return_if_fail(value_str != NULL);
+       
+       GST_DEBUG(GST_CAT_PARAMS, "parsing '%s' to type %s\n", value_str, g_type_name(G_VALUE_TYPE(value)));
+
+       switch (G_VALUE_TYPE(value)) {
+               case G_TYPE_STRING:
+                       g_value_set_string(value, g_strdup(value_str));
+                       break;
+               case G_TYPE_ENUM: 
+               case G_TYPE_INT: {
+                       gint i;
+                       sscanf (value_str, "%d", &i);
+                       g_value_set_int(value, i);
+                       break;
+               }
+               case G_TYPE_UINT: {
+                       guint i;
+                       sscanf (value_str, "%u", &i);
+                       g_value_set_uint(value, i);
+                       break;
+               }
+               case G_TYPE_LONG: {
+                       glong i;
+                       sscanf (value_str, "%ld", &i);
+                       g_value_set_long(value, i);
+                       break;
+               }
+               case G_TYPE_ULONG: {
+                       gulong i;
+                       sscanf (value_str, "%lu", &i);
+                       g_value_set_ulong(value, i);
+                       break;
+               }
+               case G_TYPE_BOOLEAN: {
+                       gboolean i = FALSE;
+                       if (!strncmp ("true", value_str, 4)) i = TRUE;
+                       g_value_set_boolean(value, i);
+                       break;
+               }
+               case G_TYPE_CHAR: {
+                       gchar i;
+                       sscanf (value_str, "%c", &i);
+                       g_value_set_char(value, i);
+                       break;
+               }
+               case G_TYPE_UCHAR: {
+                       guchar i;
+                       sscanf (value_str, "%c", &i);
+                       g_value_set_uchar(value, i);
+                       break;
+               }
+               case G_TYPE_FLOAT: {
+                       gfloat i;
+                       sscanf (value_str, "%f", &i);
+                       g_value_set_float(value, i);
+                       break;
+               }
+               case G_TYPE_DOUBLE: {
+                       gfloat i;
+                       sscanf (value_str, "%g", &i);
+                       g_value_set_double(value, (gdouble)i);
+                       break;
+               }
+               default:
+                       break;
+       }
+}
+
+static void
+gst_dparam_do_update_realtime (GstDParam *dparam, gint64 timestamp)
+{
+       GST_DPARAM_LOCK(dparam);
+       GST_DPARAM_READY_FOR_UPDATE(dparam) = FALSE;
+       GST_DEBUG(GST_CAT_PARAMS, "updating value for %s(%p)\n",GST_DPARAM_NAME (dparam),dparam);
+       g_value_copy(dparam->point[0], GST_DPARAM_VALUE(dparam));
+       GST_DPARAM_UNLOCK(dparam);
+}
+
+static GValue** 
+gst_dparam_get_point_realtime (GstDParam *dparam, gint64 timestamp)
+{
+       GST_DEBUG(GST_CAT_PARAMS, "getting point for %s(%p)\n",GST_DPARAM_NAME (dparam),dparam);
+       return dparam->point;
+}
+
+/**********************
+ * GstDParamSmooth
+ **********************/
+
+static void gst_dparam_do_update_smooth (GstDParam *dparam, gint64 timestamp);
+static GValue** gst_dparam_get_point_smooth (GstDParam *dparam, gint64 timestamp);
+
+/**
+ * gst_dparam_smooth_new:
+ * @type: the type that this dparam will store
+ *
+ * Returns: a new instance of GstDParamSmooth
+ */
+GstDParam* 
+gst_dparam_smooth_new (GType type)
+{
+       GstDParam *dparam;
+
+       dparam = g_object_new (gst_dparam_get_type (), NULL);
+       
+       dparam->do_update_func = gst_dparam_do_update_smooth;
+       dparam->get_point_func = gst_dparam_get_point_smooth;
+       
+       dparam->point = gst_dparam_new_value_array(type, type, G_TYPE_FLOAT, 0);        
+       GST_DPARAM_TYPE(dparam) = type;
+       
+       return dparam;
+}
+
+static void
+gst_dparam_do_update_smooth (GstDParam *dparam, gint64 timestamp)
+{
+       gint64 time_diff;
+       gfloat time_ratio;
+       
+       time_diff = MIN(GST_DPARAM_DEFAULT_UPDATE_PERIOD(dparam), 
+                       timestamp - GST_DPARAM_LAST_UPDATE_TIMESTAMP(dparam));
+                       
+       time_ratio = (gfloat)time_diff / g_value_get_float(dparam->point[2]);
+
+       GST_DPARAM_LOCK(dparam);
+
+       GST_DPARAM_LAST_UPDATE_TIMESTAMP(dparam) = GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam);  
+       while(GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam) <= timestamp){
+               GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam) += GST_DPARAM_DEFAULT_UPDATE_PERIOD(dparam);
+       }
+       GST_DEBUG(GST_CAT_PARAMS, "last:%lld current:%lld next:%lld\n",
+                                  GST_DPARAM_LAST_UPDATE_TIMESTAMP(dparam), timestamp, GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam));
+
+       
+       switch (G_VALUE_TYPE(GST_DPARAM_VALUE(dparam))){
+               case G_TYPE_FLOAT: {
+                       gfloat current, target, max_change, current_diff, final_val;
+                       
+                       target = g_value_get_float(dparam->point[0]);
+                       current = g_value_get_float(GST_DPARAM_VALUE(dparam));
+                       max_change = time_ratio * g_value_get_float(dparam->point[1]);
+
+                       GST_DEBUG(GST_CAT_PARAMS, "target:%f current:%f max_change:%f \n", 
+                                                  target, current, max_change);
+                                                  
+                       if (dparam->spec->is_log){
+                               gfloat current_log;
+                               current_log = log(current);
+                               current_diff = ABS(current_log - log(target));
+                               if (current_diff > max_change)
+                                       final_val = (target < current) ? exp(current_log-max_change) : exp(current_log+max_change);
+                               else
+                                       final_val = target;
+                       } 
+                       else {
+                               current_diff = ABS (current - target);
+                               if (current_diff > max_change)
+                                       final_val = (target < current) ? current-max_change : current+max_change;
+                               else
+                                       final_val = target;                                                                     
+                       }
+
+                       GST_DPARAM_READY_FOR_UPDATE(dparam) = (current_diff > max_change);
+                       g_value_set_float(GST_DPARAM_VALUE(dparam), final_val);
+                       
+                       break;
+               }
+               default:
+                       break;
+       }
+
+                                          
+       //GST_DEBUG(GST_CAT_PARAMS, "smooth update for %s(%p): %f\n",
+       //                           GST_DPARAM_NAME (dparam),dparam, g_value_get_float(GST_DPARAM_VALUE(dparam)));
+
+       GST_DPARAM_UNLOCK(dparam);
+}
+
+static GValue** 
+gst_dparam_get_point_smooth (GstDParam *dparam, gint64 timestamp)
+{
+       GST_DEBUG(GST_CAT_PARAMS, "getting point for %s(%p)\n",GST_DPARAM_NAME (dparam),dparam);
+       return dparam->point;
+}
diff --git a/libs/control/gstdparam.h b/libs/control/gstdparam.h
new file mode 100644 (file)
index 0000000..72d5fad
--- /dev/null
@@ -0,0 +1,146 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdparam.h: Dynamic Parameter functionality
+ *
+ * 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_DPARAM_H__
+#define __GST_DPARAM_H__
+
+#include <gst/gstobject.h>
+#include <gst/gstprops.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif /* __cplusplus */
+
+
+#define GST_TYPE_DPARAM                        (gst_dparam_get_type ())
+#define GST_DPARAM(obj)                        (G_TYPE_CHECK_INSTANCE_CAST ((obj), GST_TYPE_DPARAM,GstDParam))
+#define GST_DPARAM_CLASS(klass)                (G_TYPE_CHECK_CLASS_CAST ((klass), GST_TYPE_DPARAM,GstDParam))
+#define GST_IS_DPARAM(obj)                     (G_TYPE_CHECK_INSTANCE_TYPE     ((obj), GST_TYPE_DPARAM))
+#define GST_IS_DPARAM_CLASS(obj)               (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_DPARAM))
+
+#define GST_DPARAM_NAME(dparam)                                 (GST_OBJECT_NAME(dparam))
+#define GST_DPARAM_PARENT(dparam)                       (GST_OBJECT_PARENT(dparam))
+#define GST_DPARAM_VALUE(dparam)                                ((dparam)->value)
+#define GST_DPARAM_SPEC(dparam)                                 ((dparam)->spec)
+#define GST_DPARAM_TYPE(dparam)                                 ((dparam)->type)
+
+#define GST_DPARAM_LOCK(dparam)                (g_mutex_lock((dparam)->lock))
+#define GST_DPARAM_UNLOCK(dparam)              (g_mutex_unlock((dparam)->lock))
+
+#define GST_DPARAM_READY_FOR_UPDATE(dparam)            ((dparam)->ready_for_update)
+#define GST_DPARAM_DEFAULT_UPDATE_PERIOD(dparam)       ((dparam)->default_update_period)
+#define GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam)       ((dparam)->next_update_timestamp)
+#define GST_DPARAM_LAST_UPDATE_TIMESTAMP(dparam)       ((dparam)->last_update_timestamp)
+
+#define GST_DPARAM_GET_POINT(dparam, timestamp) \
+       ((dparam->get_point_func)(dparam, timestamp))
+
+#define GST_DPARAM_FIND_POINT(dparam, timestamp, search_flag) \
+       ((dparam->find_point_func)(dparam, data, search_flag))
+
+#define GST_DPARAM_DO_UPDATE(dparam, timestamp) \
+       ((dparam->do_update_func)(dparam, timestamp))
+               
+#define GST_DPARAM_INSERT_POINT(dparam, timestamp) \
+       ((dparam->insert_point_func)(dparam, timestamp))
+
+#define GST_DPARAM_REMOVE_POINT(dparam, data) \
+       ((dparam->remove_point_func)(dparam, data))
+       
+typedef enum {
+  GST_DPARAM_CLOSEST,
+  GST_DPARAM_CLOSEST_AFTER,
+  GST_DPARAM_CLOSEST_BEFORE,
+  GST_DPARAM_EXACT,
+} GstDParamSearchFlag;
+
+typedef enum {
+  GST_DPARAM_NOT_FOUND = 0,
+  GST_DPARAM_FOUND_EXACT,
+  GST_DPARAM_FOUND_CLOSEST,
+} GstDParamSearchResult;
+
+typedef struct _GstDParam GstDParam;
+typedef struct _GstDParamClass GstDParamClass;
+typedef struct _GstDParamSpec GstDParamSpec;
+
+typedef GValue** (*GstDParamInsertPointFunction) (GstDParam *dparam, guint64 timestamp);
+typedef void (*GstDParamRemovePointFunction) (GstDParam *dparam, GValue** point);
+typedef GValue** (*GstDParamGetPointFunction) (GstDParam *dparam, gint64 timestamp);
+typedef GstDParamSearchResult (*GstDParamFindPointFunction) (GstDParam *dparam, gint64 *timestamp, GstDParamSearchFlag search_flag);
+
+typedef void (*GstDParamDoUpdateFunction) (GstDParam *dparam, gint64 timestamp);
+
+struct _GstDParam {
+       GstObject               object;
+
+       GstDParamGetPointFunction get_point_func;
+       GstDParamFindPointFunction find_point_func;
+
+       GstDParamDoUpdateFunction do_update_func;
+       
+       GstDParamInsertPointFunction insert_point_func;
+       GstDParamRemovePointFunction remove_point_func; 
+       
+       GMutex *lock;
+       GValue *value;
+       GstDParamSpec *spec;
+       GValue **point;
+       GType type;
+       gint64 last_update_timestamp;
+       gint64 next_update_timestamp;
+       gint64 default_update_period;
+       gboolean ready_for_update;
+};
+
+struct _GstDParamClass {
+       GstObjectClass parent_class;
+
+       /* signal callbacks */
+};
+
+struct _GstDParamSpec {
+       gchar *dparam_name;
+       gchar *unit_name;
+       GValue *min_val;
+       GValue *max_val;
+       GValue *default_val;
+       gboolean is_log;
+       gboolean is_rate;
+};
+
+GType gst_dparam_get_type (void);
+GstDParam* gst_dparam_new (GType type);
+void gst_dparam_attach (GstDParam *dparam, GstObject *parent, GValue *value, GstDParamSpec *spec);
+GValue** gst_dparam_new_value_array(GType type, ...);
+void gst_dparam_set_value_from_string(GValue *value, const gchar *value_str);
+
+/**********************
+ * GstDParamSmooth
+ **********************/
+
+GstDParam* gst_dparam_smooth_new (GType type);
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+
+#endif /* __GST_DPARAM_H__ */
diff --git a/libs/control/gstdparammanager.c b/libs/control/gstdparammanager.c
new file mode 100644 (file)
index 0000000..efba373
--- /dev/null
@@ -0,0 +1,760 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdparammanager.c: Dynamic Parameter group functionality
+ *
+ * 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.
+ */
+
+#include "gstdparammanager.h"
+#include <gst/gstelement.h>
+#include <gst/gstinfo.h>
+
+static GHashTable *_element_registry;
+
+static void gst_dpman_class_init (GstDParamManagerClass *klass);
+static void gst_dpman_init (GstDParamManager *dpman);
+static GstDParamWrapper* gst_dpman_new_wrapper(GstDParamManager *dpman, gchar *dparam_name, GType type, GstDPMUpdateMethod update_method);
+static GstDParamWrapper* gst_dpman_get_wrapper(GstDParamManager *dpman, gchar *dparam_name);
+static void gst_dpman_state_change (GstElement *element, gint state, GstDParamManager *dpman);
+static void gst_dpman_caps_changed (GstPad *pad, GstCaps *caps, GstDParamManager *dpman);
+static guint gst_dpman_preprocess_synchronous(GstDParamManager *dpman, guint frames, gint64 timestamp);
+static guint gst_dpman_preprocess_noop(GstDParamManager *dpman, guint frames, gint64 timestamp);
+static guint gst_dpman_process_noop(GstDParamManager *dpman, guint frame_count);
+
+GType
+gst_dpman_get_type (void)
+{
+       static GType dpman_type = 0;
+
+       if (!dpman_type) {
+               static const GTypeInfo dpman_info = {
+                       sizeof(GstDParamManagerClass),
+                       NULL,
+                       NULL,
+                       (GClassInitFunc)gst_dpman_class_init,
+                       NULL,
+                       NULL,
+                       sizeof(GstDParamManager),
+                       0,
+                       (GInstanceInitFunc)gst_dpman_init,
+               };
+               dpman_type = g_type_register_static(GST_TYPE_OBJECT, "GstDParamManager", &dpman_info, 0);
+       }
+       return dpman_type;
+}
+
+static void
+gst_dpman_class_init (GstDParamManagerClass *klass)
+{
+       GstObjectClass *gstobject_class;
+       GObjectClass *gobject_class;
+
+       gstobject_class = (GstObjectClass*) klass;
+       gobject_class = (GObjectClass*) klass;
+
+       klass->modes = g_hash_table_new(g_str_hash,g_str_equal);
+       _element_registry = g_hash_table_new(NULL,NULL);
+
+       gst_dpman_register_mode (klass, "synchronous", 
+                              gst_dpman_preprocess_synchronous, gst_dpman_process_noop, NULL, NULL);
+       gst_dpman_register_mode (klass, "asynchronous", 
+                              gst_dpman_preprocess_noop, gst_dpman_process_noop, NULL, NULL);
+       gst_dpman_register_mode (klass, "disabled", 
+                              gst_dpman_preprocess_noop, gst_dpman_process_noop, NULL, NULL);
+
+}
+
+static void
+gst_dpman_init (GstDParamManager *dpman)
+{
+       GST_DPMAN_DPARAMS(dpman) = g_hash_table_new(g_str_hash,g_str_equal);
+       GST_DPMAN_DPARAMS_LIST(dpman) = NULL;
+       GST_DPMAN_NAME(dpman) = NULL;
+       GST_DPMAN_PARENT(dpman) = NULL;
+       GST_DPMAN_MODE_NAME(dpman) = NULL;
+       GST_DPMAN_MODE(dpman) = NULL;
+       GST_DPMAN_MODE_DATA(dpman) = NULL;
+       GST_DPMAN_RATE(dpman) = 0;
+}
+
+/**
+ * gst_dpman_new:
+ * @name: name of the GstDParamManager instance
+ * @parent: element which created this instance
+ *
+ * Returns: a new instance of GstDParamManager
+ */
+GstDParamManager* 
+gst_dpman_new (gchar *name, GstElement *parent)
+{
+       GstDParamManager *dpman;
+       
+       g_return_val_if_fail (name != NULL, NULL);
+
+       dpman = g_object_new (gst_dpman_get_type (), NULL);
+       gst_object_set_name (GST_OBJECT (dpman), name);
+       gst_dpman_set_parent(dpman, parent);
+
+       gst_dpman_set_mode(dpman, "disabled");
+
+       return dpman;
+}
+
+/**
+ * gst_dpman_add_required_dparam_callback:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: a parameter name unique to this GstDParamManager
+ * @type: the GValue type that this parameter will store
+ * @update_func: callback to update the element with the new value
+ * @update_data: will be included in the call to update_func
+ *
+ * Returns: true if it was successfully added
+ */
+gboolean 
+gst_dpman_add_required_dparam_callback (GstDParamManager *dpman, 
+                                        gchar *dparam_name, 
+                                        GType type, 
+                                        GstDPMUpdateFunction update_func, 
+                                        gpointer update_data)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
+       g_return_val_if_fail (update_func != NULL, FALSE);
+
+       dpwrap = gst_dpman_new_wrapper(dpman, dparam_name, type, GST_DPMAN_CALLBACK);
+
+       g_return_val_if_fail (dpwrap != NULL, FALSE);
+
+       GST_DEBUG(GST_CAT_PARAMS,"adding required callback dparam '%s' of type %s\n", dparam_name, g_type_name(type));
+
+       dpwrap->update_func = update_func;
+       dpwrap->update_data = update_data;
+
+       return TRUE;    
+}
+
+/**
+ * gst_dpman_add_required_dparam_direct:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: a parameter name unique to this GstDParamManager
+ * @type: the GValue type that this parameter will store
+ * @update_data: pointer to the member to be updated
+ *
+ * Returns: true if it was successfully added
+ */
+gboolean 
+gst_dpman_add_required_dparam_direct (GstDParamManager *dpman, 
+                                        gchar *dparam_name, 
+                                        GType type, 
+                                        gpointer update_data)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
+       g_return_val_if_fail (update_data != NULL, FALSE);
+
+       dpwrap = gst_dpman_new_wrapper(dpman, dparam_name, type, GST_DPMAN_DIRECT);
+
+       g_return_val_if_fail (dpwrap != NULL, FALSE);
+
+       GST_DEBUG(GST_CAT_PARAMS,"adding required direct dparam '%s' of type %s\n", dparam_name, g_type_name(type));
+
+       dpwrap->update_data = update_data;
+
+       return TRUE;    
+}
+
+/**
+ * gst_dpman_add_required_dparam_array:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: a parameter name unique to this GstDParamManager
+ * @type: the GValue type that this parameter will store
+ * @update_data: pointer to where the array will be stored
+ *
+ * Returns: true if it was successfully added
+ */
+gboolean 
+gst_dpman_add_required_dparam_array (GstDParamManager *dpman, 
+                                        gchar *dparam_name, 
+                                        GType type, 
+                                        gpointer update_data)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
+       g_return_val_if_fail (update_data != NULL, FALSE);
+
+       dpwrap = gst_dpman_new_wrapper(dpman, dparam_name, type, GST_DPMAN_ARRAY);
+
+       g_return_val_if_fail (dpwrap != NULL, FALSE);
+
+       GST_DEBUG(GST_CAT_PARAMS,"adding required array dparam '%s' of type %s\n", dparam_name, g_type_name(type));
+
+       dpwrap->update_data = update_data;
+
+       return TRUE;    
+}
+
+/**
+ * gst_dpman_remove_required_dparam:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: the name of an existing parameter
+ *
+ */
+void 
+gst_dpman_remove_required_dparam (GstDParamManager *dpman, gchar *dparam_name)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       g_return_if_fail (dparam_name != NULL);
+
+       dpwrap = gst_dpman_get_wrapper(dpman, dparam_name);
+       
+       g_return_if_fail(dpwrap != NULL);
+       g_return_if_fail(dpwrap->dparam == NULL);
+
+       GST_DEBUG(GST_CAT_PARAMS, "removing required dparam: %s\n", dparam_name);
+       
+       g_hash_table_remove(GST_DPMAN_DPARAMS(dpman), dparam_name);
+       GST_DPMAN_DPARAMS_LIST(dpman) = g_slist_remove(GST_DPMAN_DPARAMS_LIST(dpman), dpwrap);
+
+       g_free(dpwrap->value);
+       g_free(dpwrap);
+}
+
+/**
+ * gst_dpman_attach_dparam:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: a name previously added with gst_dpman_add_required_dparam
+ * @dparam: GstDParam instance to attach
+ *
+ * Returns: true if it was successfully attached
+ */
+gboolean 
+gst_dpman_attach_dparam (GstDParamManager *dpman, gchar *dparam_name, GstDParam *dparam)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
+       g_return_val_if_fail (dparam_name != NULL, FALSE);
+       g_return_val_if_fail (dparam != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPARAM (dparam), FALSE);
+       g_return_val_if_fail (dparam != NULL, FALSE);
+
+       dpwrap = gst_dpman_get_wrapper(dpman, dparam_name);
+
+       g_return_val_if_fail(dpwrap != NULL, FALSE);
+       g_return_val_if_fail(dpwrap->value != NULL, FALSE);
+
+       dpwrap->dparam = dparam;
+       gst_dparam_attach(dparam, GST_OBJECT(dpman), dpwrap->value, dpwrap->spec);
+
+       return TRUE;
+}
+
+/**
+ * gst_dpman_dettach_dparam:
+ * @dpman: GstDParamManager instance
+ * @dparam_name: the name of a parameter with a previously attached GstDParam
+ *
+ */
+void 
+gst_dpman_dettach_dparam (GstDParamManager *dpman, gchar *dparam_name)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       g_return_if_fail (dparam_name != NULL);
+       
+       dpwrap = gst_dpman_get_wrapper(dpman, dparam_name);
+
+       g_return_if_fail(dpwrap);
+       
+       GST_DPARAM_VALUE(dpwrap->dparam) = NULL;
+       GST_DPARAM_NAME(dpwrap->dparam) = NULL;
+       gst_object_unparent (GST_OBJECT(dpwrap->dparam));
+
+       dpwrap->dparam = NULL;
+       
+}
+
+/**
+ * gst_dpman_get_dparam:
+ * @dpman: GstDParamManager instance
+ * @name: the name of an existing dparam instance
+ *
+ * Returns: the dparam with the given name - or NULL otherwise
+ */
+GstDParam *
+gst_dpman_get_dparam (GstDParamManager *dpman, gchar *name)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, NULL);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
+       g_return_val_if_fail (name != NULL, NULL);
+       
+       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), name);
+       g_return_val_if_fail (dpwrap != NULL, NULL);
+       
+       return dpwrap->dparam;
+}
+
+/**
+ * gst_dpman_get_dparam_type:
+ * @dpman: GstDParamManager instance
+ * @name: the name of dparam
+ *
+ * Returns: the type that this dparam requires/uses
+ */
+GType
+gst_dpman_get_dparam_type (GstDParamManager *dpman, gchar *name)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, 0);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), 0);
+       g_return_val_if_fail (name != NULL, 0);
+       
+       dpwrap = g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), name);
+       g_return_val_if_fail (dpwrap != NULL, 0);
+       
+       return G_VALUE_TYPE(dpwrap->value);
+}
+
+GstDParamSpec**
+gst_dpman_list_dparam_specs(GstDParamManager *dpman)
+{
+       GstDParamWrapper* dpwrap;
+       GSList *dpwraps;
+       GstDParamSpec** dparam_specs;
+       guint x = 0;
+
+       g_return_val_if_fail (dpman != NULL, NULL);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
+       
+       dpwraps = GST_DPMAN_DPARAMS_LIST(dpman);
+
+       dparam_specs = g_new0(GstDParamSpec*, g_slist_length(dpwraps) + 1);
+       
+       while (dpwraps){
+               dpwrap = (GstDParamWrapper*)dpwraps->data;
+               dparam_specs[x++] = dpwrap->spec;
+               dpwraps = g_slist_next(dpwraps);
+       }
+       return dparam_specs;
+}
+
+GstDParamSpec*
+gst_dpman_get_dparam_spec (GstDParamManager *dpman, gchar *dparam_name)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, NULL);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
+       g_return_val_if_fail (dparam_name != NULL, NULL);
+
+       dpwrap = gst_dpman_get_wrapper(dpman, dparam_name);
+       return dpwrap->spec;
+}
+
+void
+gst_dpman_dparam_spec_has_changed (GstDParamManager *dpman, gchar *dparam_name)
+{
+       
+}
+
+/**
+ * gst_dpman_register_mode
+ * @klass: GstDParamManagerClass class instance
+ * @modename: the unique name of the new mode
+ * @preprocessfunc: the function which will be called before each buffer is processed
+ * @processfunc: the function which may be called throughout the processing of a buffer
+ * @setupfunc: the function which initialises the mode when activated
+ * @teardownfunc: the function which frees any resources the mode uses
+ *
+ */
+void
+gst_dpman_register_mode (GstDParamManagerClass *klass,
+                         gchar *modename, 
+                         GstDPMModePreProcessFunction preprocessfunc,
+                         GstDPMModeProcessFunction processfunc,
+                         GstDPMModeSetupFunction setupfunc,
+                         GstDPMModeTeardownFunction teardownfunc)
+{
+       GstDPMMode *mode;
+
+       g_return_if_fail (klass != NULL);
+       g_return_if_fail (modename != NULL);
+       g_return_if_fail (GST_IS_DPMAN_CLASS (klass));
+       
+       mode = g_new0(GstDPMMode,1);
+
+       mode->preprocessfunc = preprocessfunc;
+       mode->processfunc = processfunc;
+       mode->setupfunc = setupfunc;
+       mode->teardownfunc = teardownfunc;
+       
+       g_hash_table_insert(klass->modes, modename, mode);
+       GST_DEBUG(GST_CAT_PARAMS, "mode '%s' registered\n", modename);
+}
+
+/**
+ * gst_dpman_set_mode
+ * @dpman: GstDParamManager instance
+ * @modename: the name of the mode to use
+ *
+ * Returns: TRUE if the mode was set, FALSE otherwise
+ */
+gboolean
+gst_dpman_set_mode(GstDParamManager *dpman, gchar *modename)
+{
+       GstDPMMode *mode=NULL;
+       GstDParamManagerClass *oclass;
+       
+       g_return_val_if_fail (dpman != NULL, FALSE);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), FALSE);
+       g_return_val_if_fail (modename != NULL, FALSE);
+
+       oclass = (GstDParamManagerClass*)(G_OBJECT_GET_CLASS(dpman));
+       
+       mode = g_hash_table_lookup(oclass->modes, modename);
+       g_return_val_if_fail (mode != NULL, FALSE);
+       GST_DEBUG(GST_CAT_PARAMS, "setting mode to %s\n", modename);
+       if (GST_DPMAN_MODE(dpman) && GST_DPMAN_TEARDOWNFUNC(dpman)){
+               GST_DPMAN_TEARDOWNFUNC(dpman)(dpman);
+       }
+       
+       GST_DPMAN_MODE(dpman) = mode;
+
+       if (GST_DPMAN_SETUPFUNC(dpman)){
+               GST_DPMAN_SETUPFUNC(dpman)(dpman);
+       }
+       
+       return TRUE;
+}
+
+/**
+ * gst_dpman_set_parent
+ * @dpman: GstDParamManager instance
+ * @parent: the element that this GstDParamManager belongs to
+ *
+ */
+void
+gst_dpman_set_parent (GstDParamManager *dpman, GstElement *parent)
+{
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       g_return_if_fail (parent != NULL);
+       g_return_if_fail (GST_IS_ELEMENT (parent));
+
+       g_hash_table_insert(_element_registry, parent, dpman);
+       gst_object_set_parent (GST_OBJECT (dpman), GST_OBJECT(parent));
+       g_signal_connect(G_OBJECT(parent), "state_change", 
+                        G_CALLBACK (gst_dpman_state_change), dpman);
+}
+
+/**
+ * gst_dpman_get_manager
+ * @parent: the element that the desired GstDParamManager belongs to
+ *
+ * Returns: the GstDParamManager which belongs to this element or NULL
+ * if it doesn't exist
+ */
+GstDParamManager *
+gst_dpman_get_manager (GstElement *parent)
+{
+       GstDParamManager *dpman;
+       g_return_val_if_fail (parent != NULL, NULL);
+       g_return_val_if_fail (GST_IS_ELEMENT (parent), NULL);
+       
+       dpman = (GstDParamManager*)g_hash_table_lookup(_element_registry, parent);
+       g_return_val_if_fail (dpman != NULL, NULL);
+       return dpman;
+}
+
+/**
+ * gst_dpman_set_rate_change_pad
+ * @dpman: GstDParamManager instance
+ * @pad: the pad which may have a "rate" caps property
+ *
+ */
+void
+gst_dpman_set_rate_change_pad(GstDParamManager *dpman, GstPad *pad)
+{
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       g_return_if_fail (pad != NULL);
+       g_return_if_fail (GST_IS_PAD (pad));
+
+       g_signal_connect(G_OBJECT(pad), "caps_changed", 
+                        G_CALLBACK (gst_dpman_caps_changed), dpman);
+}
+
+static GstDParamWrapper* 
+gst_dpman_get_wrapper(GstDParamManager *dpman, gchar *dparam_name)
+{
+       g_return_val_if_fail (dpman != NULL, NULL);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
+       g_return_val_if_fail (dparam_name != NULL, NULL);
+       
+       return g_hash_table_lookup(GST_DPMAN_DPARAMS(dpman), dparam_name);
+}
+
+static GstDParamWrapper* 
+gst_dpman_new_wrapper(GstDParamManager *dpman, gchar *dparam_name, GType type, GstDPMUpdateMethod update_method)
+{
+       GstDParamWrapper* dpwrap;
+
+       g_return_val_if_fail (dpman != NULL, NULL);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), NULL);
+       g_return_val_if_fail (dparam_name != NULL, NULL);
+
+       g_return_val_if_fail(gst_dpman_get_wrapper(dpman, dparam_name) == NULL, NULL);
+
+       dpwrap = g_new0(GstDParamWrapper,1);
+       dpwrap->update_method = update_method;
+       dpwrap->value = g_new0(GValue,1);
+       g_value_init(dpwrap->value, type);
+       
+       dpwrap->spec = g_new0(GstDParamSpec,1);
+       dpwrap->spec->dparam_name = dparam_name;
+       dpwrap->spec->min_val = g_new0(GValue,1);
+       dpwrap->spec->max_val = g_new0(GValue,1);
+       dpwrap->spec->default_val = g_new0(GValue,1);
+       g_value_init(dpwrap->spec->min_val, type);
+       g_value_init(dpwrap->spec->max_val, type);
+       g_value_init(dpwrap->spec->default_val, type);
+
+       g_hash_table_insert(GST_DPMAN_DPARAMS(dpman), dparam_name, dpwrap);
+       GST_DPMAN_DPARAMS_LIST(dpman) = g_slist_append(GST_DPMAN_DPARAMS_LIST(dpman), dpwrap);
+       
+       return dpwrap;  
+}
+
+
+static void 
+gst_dpman_state_change (GstElement *element, gint state, GstDParamManager *dpman)
+{
+       GSList *dwraps;
+       GstDParam *dparam;
+       GstDParamWrapper *dpwrap;
+
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       
+       if (state == GST_STATE_PLAYING){
+               GST_DEBUG(GST_CAT_PARAMS, "initialising params\n");
+                       
+               // force all params to be updated
+               dwraps = GST_DPMAN_DPARAMS_LIST(dpman);
+               while (dwraps){
+                       dpwrap = (GstDParamWrapper*)dwraps->data;
+                       dparam = dpwrap->dparam;
+                       
+                       if (dparam){
+                               GST_DPARAM_READY_FOR_UPDATE(dparam) = TRUE;
+                               if (dparam->spec){
+                                       g_value_copy(dparam->spec->default_val, GST_DPARAM_VALUE(dparam));
+                               }
+                       }
+                       dwraps = g_slist_next(dwraps);
+               }
+       }
+}
+
+static void
+gst_dpman_caps_changed (GstPad *pad, GstCaps *caps, GstDParamManager *dpman)
+{
+       g_return_if_fail (caps != NULL);
+       g_return_if_fail (dpman != NULL);
+       g_return_if_fail (GST_IS_DPMAN (dpman));
+       
+       GST_DPMAN_RATE(dpman) = gst_caps_get_int (caps, "rate");
+       
+       GST_DEBUG(GST_CAT_PARAMS, "got caps change %d\n", GST_DPMAN_RATE(dpman));
+}
+
+static guint 
+gst_dpman_preprocess_synchronous(GstDParamManager *dpman, guint frames, gint64 timestamp)
+{
+       GSList *dwraps;
+       GstDParam *dparam;
+       GstDParamWrapper *dpwrap;
+       guint x;
+
+       g_return_val_if_fail (dpman != NULL, frames);
+       g_return_val_if_fail (GST_IS_DPMAN (dpman), frames);
+
+       // now check whether any passive dparams are ready for an update
+       dwraps = GST_DPMAN_DPARAMS_LIST(dpman);
+       while (dwraps){
+               dpwrap = (GstDParamWrapper*)dwraps->data;
+               dparam = dpwrap->dparam;
+
+               if (dparam && (GST_DPARAM_READY_FOR_UPDATE(dparam) && 
+                             (GST_DPARAM_NEXT_UPDATE_TIMESTAMP(dparam) <= timestamp))){
+                               
+                   // this will make dpwrap->value contain the latest value.
+                   // now we just need to get it to the element
+                       GST_DPARAM_DO_UPDATE(dparam, timestamp);
+                       
+                       switch (dpwrap->update_method) {
+                               
+                               // direct method - set the value directly in the struct of the element
+                               case GST_DPMAN_DIRECT:
+                                       GST_DEBUG(GST_CAT_PARAMS, "doing direct update\n");
+                                       switch (G_VALUE_TYPE(dpwrap->value)){
+                                               case G_TYPE_CHAR:
+                                                       *(gchar*)dpwrap->update_data = g_value_get_char(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_UCHAR:
+                                                       *(guchar*)dpwrap->update_data = g_value_get_uchar(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_BOOLEAN:
+                                                       *(gboolean*)dpwrap->update_data = g_value_get_boolean(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_INT:
+                                                       *(gint*)dpwrap->update_data = g_value_get_int(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_UINT:
+                                                       *(guint*)dpwrap->update_data = g_value_get_uint(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_LONG:
+                                                       *(glong*)dpwrap->update_data = g_value_get_long(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_ULONG:
+                                                       *(gulong*)dpwrap->update_data = g_value_get_ulong(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_FLOAT:
+                                                       *(gfloat*)dpwrap->update_data = g_value_get_float(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_DOUBLE:
+                                                       *(gdouble*)dpwrap->update_data = g_value_get_double(dpwrap->value);
+                                                       break;
+                                               case G_TYPE_POINTER:
+                                                       *(gpointer*)dpwrap->update_data = g_value_get_pointer(dpwrap->value);
+                                                       break;
+                                               default:
+                                                       break;
+                                       }
+                                       break;
+
+                               // callback method - call the element's callback so it can do what it likes
+                               case GST_DPMAN_CALLBACK:
+                                       GST_DEBUG(GST_CAT_PARAMS, "doing callback update\n");
+                                       GST_DPMAN_DO_UPDATE(dpwrap);
+                                       break;
+                                       
+                               // array method - generate an array of the right size 
+                               // with each value being the same (in synchronous update mode)
+                               case GST_DPMAN_ARRAY:
+                                       GST_DEBUG(GST_CAT_PARAMS, "doing array update\n");
+                                       switch (G_VALUE_TYPE(dpwrap->value)){
+                                               case G_TYPE_CHAR:
+                                                       (gchar*)dpwrap->update_data = g_new(gchar, frames);
+                                                       *(gchar*)dpwrap->update_data = g_value_get_char(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gchar*)dpwrap->update_data)[x] = *(gchar*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_UCHAR:
+                                                       (guchar*)dpwrap->update_data = g_new(guchar, frames);
+                                                       *(guchar*)dpwrap->update_data = g_value_get_uchar(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((guchar*)dpwrap->update_data)[x] = *(guchar*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_BOOLEAN:
+                                                       (gboolean*)dpwrap->update_data = g_new(gboolean, frames);
+                                                       *(gboolean*)dpwrap->update_data = g_value_get_boolean(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gboolean*)dpwrap->update_data)[x] = *(gboolean*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_INT:
+                                                       (gint*)dpwrap->update_data = g_new(gint, frames);
+                                                       *(gint*)dpwrap->update_data = g_value_get_int(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gint*)dpwrap->update_data)[x] = *(gint*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_UINT:
+                                                       (guint*)dpwrap->update_data = g_new(guint, frames);
+                                                       *(guint*)dpwrap->update_data = g_value_get_uint(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((guint*)dpwrap->update_data)[x] = *(guint*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_LONG:
+                                                       (glong*)dpwrap->update_data = g_new(glong, frames);
+                                                       *(glong*)dpwrap->update_data = g_value_get_long(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((glong*)dpwrap->update_data)[x] = *(glong*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_ULONG:
+                                                       (gulong*)dpwrap->update_data = g_new(gulong, frames);
+                                                       *(gulong*)dpwrap->update_data = g_value_get_ulong(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gulong*)dpwrap->update_data)[x] = *(gulong*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_FLOAT:
+                                                       (gfloat*)dpwrap->update_data = g_new(gfloat, frames);
+                                                       *(gfloat*)dpwrap->update_data = g_value_get_float(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gfloat*)dpwrap->update_data)[x] = *(gfloat*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_DOUBLE:
+                                                       (gdouble*)dpwrap->update_data = g_new(gdouble, frames);
+                                                       *(gdouble*)dpwrap->update_data = g_value_get_double(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gdouble*)dpwrap->update_data)[x] = *(gdouble*)dpwrap->update_data;
+                                                       break;
+                                               case G_TYPE_POINTER:
+                                                       (gpointer*)dpwrap->update_data = g_new(gpointer, frames);
+                                                       *(gpointer*)dpwrap->update_data = g_value_get_pointer(dpwrap->value);
+                                                       for (x = 1 ; x < frames ; x++)
+                                                               ((gpointer*)dpwrap->update_data)[x] = *(gpointer*)dpwrap->update_data;
+                                                       break;
+                                               default:
+                                                       break;
+                                       }
+                                       break;
+                               default:
+                                       break;
+                       }
+               }
+               dwraps = g_slist_next(dwraps);
+       }
+       return frames;
+}
+
+static guint 
+gst_dpman_preprocess_noop(GstDParamManager *dpman, guint frames, gint64 timestamp)
+{
+       return frames;
+}
+
+static guint 
+gst_dpman_process_noop(GstDParamManager *dpman, guint frame_count)
+{
+       return 0;
+}
+
diff --git a/libs/control/gstdparammanager.h b/libs/control/gstdparammanager.h
new file mode 100644 (file)
index 0000000..e8799e6
--- /dev/null
@@ -0,0 +1,163 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdparammanager.h: Dynamic Parameter group functionality
+ *
+ * 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_DPMAN_H__
+#define __GST_DPMAN_H__
+
+#include <gst/gstobject.h>
+#include <gst/gstprops.h>
+#include <libs/control/gstdparam.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif /* __cplusplus */
+
+#define GST_TYPE_DPMAN                 (gst_dpman_get_type ())
+#define GST_DPMAN(obj)                 (G_TYPE_CHECK_INSTANCE_CAST     ((obj), GST_TYPE_DPMAN,GstDParamManager))
+#define GST_DPMAN_CLASS(klass)         (G_TYPE_CHECK_CLASS_CAST        ((klass), GST_TYPE_DPMAN,GstDParamManager))
+#define GST_IS_DPMAN(obj)                      (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GST_TYPE_DPMAN))
+#define GST_IS_DPMAN_CLASS(obj)                (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_DPMAN))
+
+#define GST_DPMAN_NAME(dpman)                  (GST_OBJECT_NAME(dpman))
+#define GST_DPMAN_PARENT(dpman)                (GST_OBJECT_PARENT(dpman))
+#define GST_DPMAN_DPARAMS(dpman)               ((dpman)->dparams)
+#define GST_DPMAN_DPARAMS_LIST(dpman)          ((dpman)->dparams_list)
+
+#define GST_DPMAN_MODE_NAME(dpman)                              ((dpman)->mode_name)
+#define GST_DPMAN_MODE(dpman)                           ((dpman)->mode)
+#define GST_DPMAN_MODE_DATA(dpman)                              ((dpman)->mode_data)
+#define GST_DPMAN_RATE(dpman)                           ((dpman)->rate)
+
+typedef enum {
+  GST_DPMAN_CALLBACK,
+  GST_DPMAN_DIRECT,
+  GST_DPMAN_ARRAY,
+} GstDPMUpdateMethod;
+
+typedef struct _GstDParamManager GstDParamManager;
+typedef struct _GstDParamManagerClass GstDParamManagerClass;
+typedef struct _GstDPMMode GstDPMMode;
+typedef struct _GstDParamWrapper GstDParamWrapper;
+
+typedef guint (*GstDPMModePreProcessFunction) (GstDParamManager *dpman, guint frames, gint64 timestamp);
+typedef guint (*GstDPMModeProcessFunction) (GstDParamManager *dpman, guint frame_count);
+typedef void (*GstDPMModeSetupFunction) (GstDParamManager *dpman);
+typedef void (*GstDPMModeTeardownFunction) (GstDParamManager *dpman);
+
+typedef void (*GstDPMUpdateFunction) (GValue *value, gpointer data);
+
+struct _GstDParamManager {
+       GstObject               object;
+
+       GHashTable *dparams;
+       GSList *dparams_list;
+       
+       gchar *mode_name;
+       GstDPMMode* mode;
+       gpointer mode_data;
+       
+       gint64 timestamp;
+       guint rate;
+};
+
+struct _GstDParamManagerClass {
+       GstObjectClass parent_class;
+       
+       GHashTable *modes;
+       /* signal callbacks */
+};
+
+struct _GstDPMMode {
+       GstDPMModePreProcessFunction preprocessfunc;
+       GstDPMModeProcessFunction processfunc;
+       GstDPMModeSetupFunction setupfunc;
+       GstDPMModeTeardownFunction teardownfunc;
+};
+
+struct _GstDParamWrapper {
+       GstDParamSpec* spec;
+       GValue *value;
+       GstDParam *dparam;
+       GstDPMUpdateMethod update_method;
+       gpointer update_data;
+       GstDPMUpdateFunction update_func;
+};
+
+#define GST_DPMAN_PREPROCESSFUNC(dpman)                (((dpman)->mode)->preprocessfunc)
+#define GST_DPMAN_PROCESSFUNC(dpman)           (((dpman)->mode)->processfunc)
+#define GST_DPMAN_SETUPFUNC(dpman)             (((dpman)->mode)->setupfunc)
+#define GST_DPMAN_TEARDOWNFUNC(dpman)          (((dpman)->mode)->teardownfunc)
+
+#define GST_DPMAN_PREPROCESS(dpman, buffer_size, timestamp) \
+                               (GST_DPMAN_PREPROCESSFUNC(dpman)(dpman, buffer_size, timestamp))
+
+#define GST_DPMAN_PROCESS(dpman, frame_count) \
+                               (GST_DPMAN_PROCESSFUNC(dpman)(dpman, frame_count))
+
+#define GST_DPMAN_PROCESS_COUNTDOWN(dpman, frame_countdown, frame_count) \
+                               (frame_countdown-- || \
+                               (frame_countdown = GST_DPMAN_PROCESS(dpman, frame_count)))
+                               
+#define GST_DPMAN_DO_UPDATE(dpwrap) ((dpwrap->update_func)(dpwrap->value, dpwrap->update_data))
+
+GType gst_dpman_get_type (void);
+GstDParamManager* gst_dpman_new (gchar *name, GstElement *parent);
+void gst_dpman_set_parent (GstDParamManager *dpman, GstElement *parent);
+GstDParamManager* gst_dpman_get_manager (GstElement *parent);
+
+gboolean gst_dpman_add_required_dparam_callback (GstDParamManager *dpman, 
+                                                gchar *dparam_name, 
+                                                GType type, 
+                                                GstDPMUpdateFunction update_func, 
+                                                gpointer update_data);
+gboolean gst_dpman_add_required_dparam_direct (GstDParamManager *dpman, 
+                                               gchar *dparam_name, 
+                                               GType type, 
+                                               gpointer update_data);
+gboolean gst_dpman_add_required_dparam_array (GstDParamManager *dpman, 
+                                              gchar *dparam_name, 
+                                              GType type, 
+                                              gpointer update_data);
+void gst_dpman_remove_required_dparam (GstDParamManager *dpman, gchar *dparam_name);
+gboolean gst_dpman_attach_dparam (GstDParamManager *dpman, gchar *dparam_name, GstDParam *dparam);
+void gst_dpman_dettach_dparam (GstDParamManager *dpman, gchar *dparam_name);                         
+GstDParam* gst_dpman_get_dparam(GstDParamManager *dpman, gchar *name);
+GType gst_dpman_get_dparam_type (GstDParamManager *dpman, gchar *name);
+
+GstDParamSpec** gst_dpman_list_dparam_specs(GstDParamManager *dpman);
+GstDParamSpec* gst_dpman_get_dparam_spec (GstDParamManager *dpman, gchar *dparam_name);
+void gst_dpman_dparam_spec_has_changed (GstDParamManager *dpman, gchar *dparam_name);
+
+void gst_dpman_set_rate_change_pad(GstDParamManager *dpman, GstPad *pad);
+
+gboolean gst_dpman_set_mode(GstDParamManager *dpman, gchar *modename);
+void gst_dpman_register_mode (GstDParamManagerClass *klass,
+                           gchar *modename, 
+                           GstDPMModePreProcessFunction preprocessfunc,
+                           GstDPMModeProcessFunction processfunc,
+                           GstDPMModeSetupFunction setupfunc,
+                           GstDPMModeTeardownFunction teardownfunc);
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+
+#endif /* __GST_DPMAN_H__ */
diff --git a/libs/control/gstdplinearinterp.c b/libs/control/gstdplinearinterp.c
new file mode 100644 (file)
index 0000000..2444165
--- /dev/null
@@ -0,0 +1,83 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdplinearinterp.c: linear interpolation dynamic parameter
+ *
+ * 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.
+ */
+
+#include "gstdplinearinterp.h"
+
+static void gst_dp_linint_class_init (GstDParamClass *klass);
+static void gst_dp_linint_base_class_init (GstDParamClass *klass);
+static void gst_dp_linint_init (GstDParam *dp_linint);
+
+GType 
+gst_dp_linint_get_type(void) {
+       static GType dp_linint_type = 0;
+
+       if (!dp_linint_type) {
+               static const GTypeInfo dp_linint_info = {
+                       sizeof(GstDParamClass),
+                       (GBaseInitFunc)gst_dp_linint_base_class_init,
+                       NULL,
+                       (GClassInitFunc)gst_dp_linint_class_init,
+                       NULL,
+                       NULL,
+                       sizeof(GstDParam),
+                       0,
+                       (GInstanceInitFunc)gst_dp_linint_init,
+               };
+               dp_linint_type = g_type_register_static(GST_TYPE_DPARAM, "GstDParamLinInterp", &dp_linint_info, 0);
+       }
+       return dp_linint_type;
+}
+
+static void
+gst_dp_linint_base_class_init (GstDParamClass *klass)
+{
+
+}
+
+static void
+gst_dp_linint_class_init (GstDParamClass *klass)
+{
+
+}
+
+static void
+gst_dp_linint_init (GstDParam *dp_linint)
+{
+       g_return_if_fail (dp_linint != NULL);
+}
+
+/**
+ * gst_dp_linint_new:
+ * @type: the type that this dp_linint will store
+ *
+ * Returns: a new instance of GstDParam
+ */
+GstDParam* 
+gst_dp_linint_new (GType type)
+{
+       GstDParam *dparam;
+       GstDParamLinInterp *dp_linint;
+
+       dp_linint = g_object_new (gst_dp_linint_get_type (), NULL);
+       dparam = GST_DPARAM(dp_linint);
+       
+       return dparam;
+}
diff --git a/libs/control/gstdplinearinterp.h b/libs/control/gstdplinearinterp.h
new file mode 100644 (file)
index 0000000..fa1a7dc
--- /dev/null
@@ -0,0 +1,61 @@
+/* GStreamer
+ * Copyright (C) 2001 Steve Baker <stevebaker_org@yahoo.co.uk>
+ *
+ * gstdplinearinterp.h: linear interpolation dynamic parameter
+ *
+ * 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_DP_LININT_H__
+#define __GST_DP_LININT_H__
+
+#include <gst/gstobject.h>
+#include "gstdparam.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif /* __cplusplus */
+
+
+#define GST_TYPE_DP_LININT                     (gst_dp_linint_get_type ())
+#define GST_DP_LININT(obj)                     (G_TYPE_CHECK_INSTANCE_CAST ((obj), GST_TYPE_DP_LININT,GstDParamLinInterp))
+#define GST_DP_LININT_CLASS(klass)             (G_TYPE_CHECK_CLASS_CAST ((klass), GST_TYPE_DP_LININT,GstDParamLinInterp))
+#define GST_IS_DP_LININT(obj)                  (G_TYPE_CHECK_INSTANCE_TYPE     ((obj), GST_TYPE_DP_LININT))
+#define GST_IS_DP_LININT_CLASS(obj)            (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_DP_LININT))
+
+typedef struct _GstDParamLinInterp GstDParamLinInterp;
+typedef struct _GstDParamLinInterpClass GstDParamLinInterpClass;
+
+struct _GstDParamLinInterp {
+       GstDParam               dparam;
+
+};
+
+struct _GstDParamLinInterpClass {
+       GstDParamClass parent_class;
+
+       /* signal callbacks */
+};
+
+GType gst_dp_linint_get_type (void);
+GstDParam* gst_dp_linint_new (GType type);
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+
+#endif /* __GST_DP_LININT_H__ */
index 3902ca30c41fcd20174a3124c6790f9dad8a5abb..f50e4f75b4ca79919c724e7cc19d7112d6aa9014 100644 (file)
@@ -25,7 +25,6 @@ libgstelements_la_SOURCES =   \
        gstpipefilter.c         \
        gsttee.c                \
        gstaggregator.c         \
-       gstsinesrc.c            \
        $(GSTHTTPSRC)
 
 noinst_HEADERS =               \
index 799c632029a3842e7bc9399126620588d9f5bbd7..bdd540d49eefd395cabacd6be3b9f855e773a730 100644 (file)
@@ -32,7 +32,6 @@
 #include "gstfdsrc.h"
 #include "gstmultidisksrc.h"
 #include "gstpipefilter.h"
-#include "gstsinesrc.h"
 #include "gsttee.h"
 #include "gstaggregator.h"
 
@@ -64,7 +63,6 @@ static struct _elements_entry _elements[] = {
   { "fdsrc",       gst_fdsrc_get_type,         &gst_fdsrc_details,             NULL },
   { "multidisksrc", gst_multidisksrc_get_type, &gst_multidisksrc_details,      NULL },
   { "pipefilter",   gst_pipefilter_get_type,   &gst_pipefilter_details,        NULL },
-  { "sinesrc",             gst_sinesrc_get_type,       &gst_sinesrc_details,           gst_sinesrc_factory_init },
   { "tee",                 gst_tee_get_type,           &gst_tee_details,               gst_tee_factory_init },
   { "aggregator",   gst_aggregator_get_type,   &gst_aggregator_details,        gst_aggregator_factory_init },
 
@@ -87,13 +85,20 @@ plugin_init (GModule *module, GstPlugin *plugin)
     factory = gst_elementfactory_new (_elements[i].name,
                                       (_elements[i].type) (),
                                       _elements[i].details);
-    if (factory != NULL) {
-      gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory));
-      if (_elements[i].factoryinit) {
-        _elements[i].factoryinit (factory);
+
+    if (!factory)
+      {
+       g_warning ("gst_elementfactory_new failed for `%s'",
+                  _elements[i].name);
+       continue;
       }
-//      g_print("added factory '%s'\n",_elements[i].name);
+
+    gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory));
+    if (_elements[i].factoryinit) {
+      _elements[i].factoryinit (factory);
     }
+//      g_print("added factory '%s'\n",_elements[i].name);
+
     i++;
   }
 
index fdf8bfec54f7a596b746b35925a5fadd57bc424b..08cc5f8a60320b95f6f65142431251a281ce1fb8 100644 (file)
@@ -121,6 +121,7 @@ gst_queue_get_type(void)
       sizeof(GstQueue),
       4,
       (GInstanceInitFunc)gst_queue_init,
+      NULL
     };
     queue_type = g_type_register_static (GST_TYPE_ELEMENT, "GstQueue", &queue_info, 0);
   }
index c4b5afa1df83c0fdcc687ca62cc8397782e221be..2613c070e0c347c7df2e39226ac35074f7148fc9 100644 (file)
@@ -3,8 +3,9 @@
 if HAVE_GNOME
 GNOME_PROGS = spectrum wave mp1parse videotest aviparse \
                videotest2 video2mp1 dvshow dv2mp1 \
-               mpeg2parse mpeg2parse2 mpeg2parse3 \
+               mpeg2parse2 mpeg2parse3 \
                mp2tomp1v2 main sinesliders testspeed
+sinesliders_LDADD = ../libs/control/libgstcontrol.la
 else
 GNOME_PROGS =
 endif
diff --git a/test/mpeg2parse.c b/test/mpeg2parse.c
deleted file mode 100644 (file)
index e010e73..0000000
+++ /dev/null
@@ -1,229 +0,0 @@
-
-#include <gnome.h>
-#include <gst/gst.h>
-
-void eof(GstElement *src) {
-  g_print("have eos, quitting\n");
-  exit(0);
-}
-
-gboolean idle_func(gpointer data) {
-  gst_bin_iterate(GST_BIN(data));
-  return TRUE;
-}
-
-GstElement *merge_subtitles;
-
-void mpeg2parse_newpad(GstElement *parser,GstPad *pad, GstElement *pipeline) {
-  GstElement *parse_audio, *parse_video, *decode, *decode_video, *play, *show;
-  GstElement *audio_queue, *video_queue;
-  GstElement *audio_thread, *video_thread;
-
-  GtkWidget *appwindow;
-
-  g_print("***** a new pad %s was created\n", gst_pad_get_name(pad));
-  gst_element_set_state(GST_ELEMENT(pipeline),GST_STATE_PAUSED);
-
-  // connect to audio pad
-  //if (0) {
-  if (strncmp(gst_pad_get_name(pad), "private_stream_1.0", 18) == 0) {
-    gst_plugin_load("ac3parse");
-    gst_plugin_load("ac3dec");
-    // construct internal pipeline elements
-    parse_audio = gst_elementfactory_make("ac3parse","parse_audio");
-    g_return_if_fail(parse_audio != NULL);
-    decode = gst_elementfactory_make("ac3dec","decode_audio");
-    g_return_if_fail(decode != NULL);
-    play = gst_elementfactory_make("osssink","play_audio");
-    g_return_if_fail(play != NULL);
-
-    // create the thread and pack stuff into it
-    audio_thread = gst_thread_new("audio_thread");
-    g_return_if_fail(audio_thread != NULL);
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(parse_audio));
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(decode));
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(play));
-
-    // set up pad connections
-    gst_element_add_ghost_pad(GST_ELEMENT(audio_thread),
-                              gst_element_get_pad(parse_audio,"sink"),"sink");
-    gst_pad_connect(gst_element_get_pad(parse_audio,"src"),
-                    gst_element_get_pad(decode,"sink"));
-    gst_pad_connect(gst_element_get_pad(decode,"src"),
-                    gst_element_get_pad(play,"sink"));
-
-    // construct queue and connect everything in the main pipelie
-    audio_queue = gst_elementfactory_make("queue","audio_queue");
-    gtk_object_set(GTK_OBJECT(audio_queue),"max_level",30,NULL);
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(audio_queue));
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(audio_thread));
-    gst_pad_connect(pad,
-                    gst_element_get_pad(audio_queue,"sink"));
-    gst_pad_connect(gst_element_get_pad(audio_queue,"src"),
-                    gst_element_get_pad(audio_thread,"sink"));
-
-    // set up thread state and kick things off
-    gtk_object_set(GTK_OBJECT(audio_thread),"create_thread",TRUE,NULL);
-    g_print("setting to READY state\n");
-    gst_element_set_state(GST_ELEMENT(audio_thread),GST_STATE_READY);
-  } else if (strncmp(gst_pad_get_name(pad), "subtitle_stream_4", 17) == 0) {
-    gst_pad_connect(pad,
-                    gst_element_get_pad(merge_subtitles,"subtitle"));
-    
-  } else if (strncmp(gst_pad_get_name(pad), "audio_", 6) == 0) {
-    gst_plugin_load("mp3parse");
-    gst_plugin_load("mpg123");
-    // construct internal pipeline elements
-    parse_audio = gst_elementfactory_make("mp3parse","parse_audio");
-    g_return_if_fail(parse_audio != NULL);
-    decode = gst_elementfactory_make("mpg123","decode_audio");
-    g_return_if_fail(decode != NULL);
-    play = gst_elementfactory_make("osssink","play_audio");
-    g_return_if_fail(play != NULL);
-
-    // create the thread and pack stuff into it
-    audio_thread = gst_thread_new("audio_thread");
-    g_return_if_fail(audio_thread != NULL);
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(parse_audio));
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(decode));
-    gst_bin_add(GST_BIN(audio_thread),GST_ELEMENT(play));
-
-    // set up pad connections
-    gst_element_add_ghost_pad(GST_ELEMENT(audio_thread),
-                              gst_element_get_pad(parse_audio,"sink"),"sink");
-    gst_pad_connect(gst_element_get_pad(parse_audio,"src"),
-                    gst_element_get_pad(decode,"sink"));
-    gst_pad_connect(gst_element_get_pad(decode,"src"),
-                    gst_element_get_pad(play,"sink"));
-
-    // construct queue and connect everything in the main pipelie
-    audio_queue = gst_elementfactory_make("queue","audio_queue");
-    gtk_object_set(GTK_OBJECT(audio_queue),"max_level",30,NULL);
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(audio_queue));
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(audio_thread));
-    gst_pad_connect(pad,
-                    gst_element_get_pad(audio_queue,"sink"));
-    gst_pad_connect(gst_element_get_pad(audio_queue,"src"),
-                    gst_element_get_pad(audio_thread,"sink"));
-
-    // set up thread state and kick things off
-    gtk_object_set(GTK_OBJECT(audio_thread),"create_thread",TRUE,NULL);
-    g_print("setting to READY state\n");
-    gst_element_set_state(GST_ELEMENT(audio_thread),GST_STATE_READY);
-  } else if (strncmp(gst_pad_get_name(pad), "video_", 6) == 0) {
-  //} else if (0) {
-
-    gst_plugin_load("mp1videoparse");
-    gst_plugin_load("mpeg2play");
-    gst_plugin_load("mpeg2subt");
-    gst_plugin_load("videosink");
-    // construct internal pipeline elements
-    parse_video = gst_elementfactory_make("mp1videoparse","parse_video");
-    g_return_if_fail(parse_video != NULL);
-    decode_video = gst_elementfactory_make("mpeg2play","decode_video");
-    g_return_if_fail(decode_video != NULL);
-    merge_subtitles = gst_elementfactory_make("mpeg2subt","merge_subtitles");
-    g_return_if_fail(merge_subtitles != NULL);
-    show = gst_elementfactory_make("videosink","show");
-    //gtk_object_set(GTK_OBJECT(show),"xv_enabled",FALSE,NULL);
-    g_return_if_fail(show != NULL);
-    //gtk_object_set(GTK_OBJECT(show),"width",640, "height", 480,NULL);
-
-    appwindow = gnome_app_new("MPEG player","MPEG player");
-    gnome_app_set_contents(GNOME_APP(appwindow),
-               gst_util_get_pointer_arg(GTK_OBJECT(show),"widget"));
-               gtk_widget_show_all(appwindow);
-
-    // create the thread and pack stuff into it
-    video_thread = gst_thread_new("video_thread");
-    g_return_if_fail(video_thread != NULL);
-    gst_bin_add(GST_BIN(video_thread),GST_ELEMENT(parse_video));
-    gst_bin_add(GST_BIN(video_thread),GST_ELEMENT(decode_video));
-    gst_bin_add(GST_BIN(video_thread),GST_ELEMENT(merge_subtitles));
-    gst_bin_add(GST_BIN(video_thread),GST_ELEMENT(show));
-
-    // set up pad connections
-    gst_element_add_ghost_pad(GST_ELEMENT(video_thread),
-                              gst_element_get_pad(parse_video,"sink"),"sink");
-    gst_pad_connect(gst_element_get_pad(parse_video,"src"),
-                    gst_element_get_pad(decode_video,"sink"));
-    gst_pad_connect(gst_element_get_pad(decode_video,"src"),
-                    gst_element_get_pad(merge_subtitles,"video"));
-    gst_pad_connect(gst_element_get_pad(merge_subtitles,"src"),
-                    gst_element_get_pad(show,"sink"));
-
-    // construct queue and connect everything in the main pipeline
-    video_queue = gst_elementfactory_make("queue","video_queue");
-    gtk_object_set(GTK_OBJECT(video_queue),"max_level",30,NULL);
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(video_queue));
-    gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(video_thread));
-    gst_pad_connect(pad,
-                    gst_element_get_pad(video_queue,"sink"));
-    gst_pad_connect(gst_element_get_pad(video_queue,"src"),
-                    gst_element_get_pad(video_thread,"sink"));
-
-    // set up thread state and kick things off
-    gtk_object_set(GTK_OBJECT(video_thread),"create_thread",TRUE,NULL);
-    g_print("setting to READY state\n");
-    gst_element_set_state(GST_ELEMENT(video_thread),GST_STATE_READY);
-  }
-  g_print("\n");
-  gst_element_set_state(GST_ELEMENT(pipeline),GST_STATE_PLAYING);
-}
-
-int main(int argc,char *argv[]) {
-  GstPipeline *pipeline;
-  GstElement *src, *parse;
-
-  g_print("have %d args\n",argc);
-
-  g_thread_init(NULL);
-  gtk_init(&argc,&argv);
-  gst_init(&argc,&argv);
-  gnome_init("MPEG2 Video player","0.0.1",argc,argv);
-  gst_plugin_load("mpeg2parse");
-  //gst_plugin_load("mpeg1parse");
-
-  pipeline = GST_PIPELINE(gst_pipeline_new("pipeline"));
-  g_return_val_if_fail(pipeline != NULL, -1);
-
-  if (strstr(argv[1],"video_ts")) {
-    src = gst_elementfactory_make("dvdsrc","src");
-    g_print("using DVD source\n");
-  } else
-    src = gst_elementfactory_make("disksrc","src");
-
-  g_return_val_if_fail(src != NULL, -1);
-  gtk_object_set(GTK_OBJECT(src),"location",argv[1],NULL);
-  if (argc >= 3) {
-    gtk_object_set(GTK_OBJECT(src),"bytesperread",atoi(argv[2]),NULL);
-    g_print("block size is %d\n",atoi(argv[2]));
-  }
-  g_print("should be using file '%s'\n",argv[1]);
-
-  parse = gst_elementfactory_make("mpeg2parse","parse");
-  //parse = gst_elementfactory_make("mpeg1parse","parse");
-  g_return_val_if_fail(parse != NULL, -1);
-
-  gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(src));
-  gst_bin_add(GST_BIN(pipeline),GST_ELEMENT(parse));
-
-  gtk_signal_connect(GTK_OBJECT(parse),"new_pad",mpeg2parse_newpad, pipeline);
-
-  gtk_signal_connect(GTK_OBJECT(src),"eos",GTK_SIGNAL_FUNC(eof),NULL);
-
-  gst_pad_connect(gst_element_get_pad(src,"src"),
-                  gst_element_get_pad(parse,"sink"));
-
-  g_print("setting to READY state\n");
-  gst_element_set_state(GST_ELEMENT(pipeline),GST_STATE_READY);
-  gst_element_set_state(GST_ELEMENT(pipeline),GST_STATE_PLAYING);
-
-  gtk_idle_add(idle_func,pipeline);
-
-  gdk_threads_enter();
-  gtk_main();
-  gdk_threads_leave();
-
-  return 0;
-}
index 71402bb41ca7c7f14e320da7cdcc50cfe2d3bcd5..aaab8bbb60381847ed52e3b23169aa715b95802c 100644 (file)
@@ -1,7 +1,8 @@
 #include <stdio.h>
+#include <math.h>
 #include <gtk/gtk.h>
 #include <gst/gst.h>
-#include <sys/soundcard.h>
+#include <libs/control/gstcontrol.h>
 
 static gint quit_live(GtkWidget *window, GdkEventAny *e, gpointer data) {
   gtk_main_quit();
@@ -13,6 +14,20 @@ static gint quit_live(GtkWidget *window, GdkEventAny *e, gpointer data) {
 //  gtk_object_set(GTK_OBJECT(element),"volume",adj->value,NULL);
 //}
 
+static void dynparm_log_value_changed(GtkAdjustment *adj,GstDParam *dparam) {
+  GValue **point;
+  g_return_if_fail(dparam != NULL);
+  g_return_if_fail(GST_IS_DPARAM (dparam));
+
+  point = GST_DPARAM_GET_POINT(dparam, 0LL);
+  
+  GST_DPARAM_LOCK(dparam);
+  g_print("setting value from %f to %f\n", g_value_get_float(point[0]), (gfloat)exp(adj->value));  
+  g_value_set_float(point[0], (gfloat)exp(adj->value));
+  GST_DPARAM_READY_FOR_UPDATE(dparam) = TRUE;
+  GST_DPARAM_UNLOCK(dparam);
+}
+
 static void dynparm_value_changed(GtkAdjustment *adj,GstDParam *dparam) {
   GValue **point;
   g_return_if_fail(dparam != NULL);
@@ -38,25 +53,15 @@ int main(int argc,char *argv[]) {
 
   GstElement *thread, *sinesrc, *osssink;
   GstDParamManager *dpman;
-  GstDParam *volume, *freq;
+  GstDParam *volume;
+  GstDParam *freq;
+  GstDParamSpec *spec;
+  
+  GValue **vals;
 
   gtk_init(&argc,&argv);
   gst_init(&argc,&argv);
 
-  /***** set up the GUI *****/
-  window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
-  g_signal_connect(window,"delete_event",GTK_SIGNAL_FUNC(quit_live),NULL);
-  hbox = gtk_hbox_new(TRUE,0);
-  gtk_container_add(GTK_CONTAINER(window),hbox);
-
-  volume_adj = (GtkAdjustment*)gtk_adjustment_new(1.0, 0.0, 1.0, 0.01, 0.01, 0.01);
-  volume_slider = gtk_vscale_new(volume_adj);
-  gtk_box_pack_start(GTK_BOX(hbox),volume_slider,TRUE,TRUE,0);
-
-  freq_adj = (GtkAdjustment*)gtk_adjustment_new(440.0, 0.0, 2000.0, 1.0, 5.0, 5.0);
-  freq_slider = gtk_vscale_new(freq_adj);
-  gtk_box_pack_start(GTK_BOX(hbox),freq_slider,TRUE,TRUE,0);
-
   /***** construct the pipeline *****/
   
   g_print("creating elements\n");
@@ -66,17 +71,67 @@ int main(int argc,char *argv[]) {
   gst_bin_add(GST_BIN(thread),sinesrc);
   gst_bin_add(GST_BIN(thread),osssink);
   gst_element_connect(sinesrc,"src",osssink,"sink");
-  gtk_object_set(GTK_OBJECT(sinesrc),"GstSineSrc::buffersize",64,NULL);
+  g_object_set(G_OBJECT(osssink),"fragment",0x00180008,NULL);
+  g_object_set(G_OBJECT(sinesrc),"buffersize",64,NULL);
  
-  dpman = GST_ELEMENT_DPARAM_MANAGER(sinesrc);
-  volume = gst_dparam_new();
-  freq = gst_dparam_new();
+  dpman = gst_dpman_get_manager (sinesrc);
 
+  freq = gst_dparam_smooth_new(G_TYPE_FLOAT);
+  vals = GST_DPARAM_GET_POINT(freq, 0LL);
+  
+  g_value_set_float(vals[0], 10.0);
+
+  // this defines the maximum slope that this
+  // param can change.  This says that in 50ms
+  // the value can change by a maximum of one semitone
+  // (the log of one semitone is 0.693)
+  g_value_set_float(vals[1], 0.693);
+  g_value_set_float(vals[2], 50000000.0);
+  
+  // set the default update period to 0.5ms, or 2000Hz
+  GST_DPARAM_DEFAULT_UPDATE_PERIOD(freq) = 2000000LL;
+  
+  volume = gst_dparam_smooth_new(G_TYPE_FLOAT);
+  vals = GST_DPARAM_GET_POINT(volume, 0LL);
+  
+  // this defines the maximum slope that this
+  // param can change.  This says that in 10ms
+  // the value can change by a maximum of 0.2
+  g_value_set_float(vals[1], 0.2);
+  g_value_set_float(vals[2], 10000000.0);
+  
+  // set the default update period to 0.5ms, or 2000Hz
+  GST_DPARAM_DEFAULT_UPDATE_PERIOD(volume) = 2000000LL;
+  
   g_assert(gst_dpman_attach_dparam (dpman, "volume", volume));
   g_assert(gst_dpman_attach_dparam (dpman, "freq", freq));
   
   gst_dpman_set_mode(dpman, "synchronous");
 
+  /***** set up the GUI *****/
+  window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
+  gtk_window_set_default_size(GTK_WINDOW(window), 80, 400);
+  g_signal_connect(window,"delete_event",GTK_SIGNAL_FUNC(quit_live),NULL);
+  hbox = gtk_hbox_new(TRUE,0);
+  gtk_container_add(GTK_CONTAINER(window),hbox);
+
+  spec = gst_dpman_get_dparam_spec (dpman, "volume");
+  volume_adj = (GtkAdjustment*)gtk_adjustment_new(g_value_get_float(spec->default_val), 
+                                                  g_value_get_float(spec->min_val),
+                                                  g_value_get_float(spec->max_val), 0.1, 0.01, 0.01);
+  volume_slider = gtk_vscale_new(volume_adj);
+  gtk_scale_set_digits(GTK_SCALE(volume_slider), 2);
+  gtk_box_pack_start(GTK_BOX(hbox),volume_slider,TRUE,TRUE,0);
+
+  spec = gst_dpman_get_dparam_spec (dpman, "freq");
+  freq_adj = (GtkAdjustment*)gtk_adjustment_new((gfloat)log(g_value_get_float(spec->default_val)), 
+                                                (gfloat)log(g_value_get_float(spec->min_val)),
+                                                (gfloat)log(g_value_get_float(spec->max_val)), 0.1, 0.01, 0.01);
+  freq_slider = gtk_vscale_new(freq_adj);
+  gtk_scale_set_digits(GTK_SCALE(freq_slider), 2);
+  gtk_box_pack_start(GTK_BOX(hbox),freq_slider,TRUE,TRUE,0);
+  
+  
   /***** set up the handlers and such *****/
   //gtk_signal_connect(volume_adj,"value-changed",GTK_SIGNAL_FUNC(volume_changed),sinesrc);
   g_signal_connect(volume_adj,"value-changed",
@@ -84,7 +139,7 @@ int main(int argc,char *argv[]) {
                                         volume);
 
   g_signal_connect(freq_adj,"value-changed",
-                                        GTK_SIGNAL_FUNC(dynparm_value_changed),
+                                        GTK_SIGNAL_FUNC(dynparm_log_value_changed),
                                         freq);
   gtk_adjustment_value_changed(volume_adj);
   gtk_adjustment_value_changed(freq_adj);
index 1d9e8d117640f80b5287e02bef0a098c72f16639..df720b55296e3d9f92646a0ee4e3befdce288ce4 100644 (file)
@@ -18,7 +18,7 @@ main (int argc, char *argv[])
 
   osssink = gst_elementfactory_make ("osssink", "osssink");
   g_assert (osssink != NULL);
-  videosink = gst_elementfactory_make ("videosink", "videosink");
+  videosink = gst_elementfactory_make ("xvideosink", "videosink");
   g_assert (videosink != NULL);
 
   testcaps = gst_caps_new ("test_caps",
index beeec25e2ac4715a7b9415e3c209067c7e4234fe..7cc47e8a669deda07706c117b529340d5e567334 100644 (file)
@@ -11,4 +11,5 @@ gstreamer-register
 gstreamer-inspect
 gstreamer-compprep
 gstreamer-complete
+gstreamer-guilaunch
 *.xml
index 3488808a82fab84d8a39b48076091546896e1ed6..bef06f9476b18439a57ec03cb31cdafe24cea8be 100644 (file)
@@ -11,7 +11,14 @@ else
 GST_LOADSAVE_SRC = gstreamer-compprep
 endif
 
+if USE_GLIB2
+GST_GUI_LAUNCH = 
+else
+GST_GUI_LAUNCH = gstreamer-guilaunch
+endif
+
 bin_PROGRAMS =         gstreamer-launch        \
+               $(GST_GUI_LAUNCH)       \
                $(GST_REGISTRY_SRC)     \
                gstreamer-inspect       \
                $(GST_LOADSAVE_SRC)     \
diff --git a/tools/gstreamer-guilaunch.c b/tools/gstreamer-guilaunch.c
new file mode 100644 (file)
index 0000000..ef87453
--- /dev/null
@@ -0,0 +1,350 @@
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/mman.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <fcntl.h>
+
+#include <glib.h>
+#include <gtk/gtk.h>
+#include <gst/gst.h>
+
+GtkWidget *start_but, *pause_but, *parse_but, *status;
+GtkWidget *window;
+GstElement *pipeline;
+typedef void (*found_handler) (GstElement *element, gint xid, void *priv);
+
+static gint quit_live(GtkWidget *window, GdkEventAny *e, gpointer data) {
+       gtk_main_quit();
+       return FALSE;
+}
+
+gboolean
+idle_func (gpointer data)
+{
+       return gst_bin_iterate (GST_BIN (pipeline));
+}
+
+void
+load_history(GtkWidget *pipe_combo)
+{
+
+       int history_fd;
+       struct stat statbuf;
+       gchar *map, *current, *next, *entry;
+       gchar *history_filename;
+       gint num_entries = 0, entries_limit = 50;
+       GList *history = NULL;
+       FILE *history_file;
+
+       history_filename = g_strdup_printf("%s/.gstreamer-guilaunch.history", g_get_home_dir());
+
+       
+       if ((history_fd = open(history_filename, O_RDONLY)) > -1){
+               fstat(history_fd, &statbuf);
+               map = mmap(0, statbuf.st_size, PROT_READ, MAP_SHARED, history_fd, 0);
+
+               // scan it once to find out how many entries there are
+               current = map;
+               while (current){
+                       if ((next = strstr(current, "\n"))){
+                               num_entries++;
+                               current = next + 1;
+                       }
+                       else {
+                               current = NULL;
+                       }
+               }
+               
+               current = map;
+               while (current){
+                       if ((next = strstr(current, "\n"))){
+                               
+                               // show entries_limit of the newest entries
+                               if (num_entries-- < entries_limit){
+                                       entry = g_strndup(current, next - current);
+                                       history = g_list_prepend(history, entry);
+                               }
+                               current = next + 1;
+                       }
+                       else {
+                               current = NULL;
+                       }
+               }
+               close(history_fd);
+               munmap(map, statbuf.st_size);
+       }
+       gtk_combo_set_popdown_strings(GTK_COMBO(pipe_combo), history);
+
+       history_file = fopen(history_filename, "a");
+       if (history_file == NULL){
+               perror("couldn't open history file");
+       }
+       gtk_object_set_data(GTK_OBJECT(pipe_combo), "history", history);
+       gtk_object_set_data(GTK_OBJECT(pipe_combo), "history_file", history_file);
+}
+
+void
+debug_toggle_callback(GtkWidget *widget, gpointer mode_ptr){
+       guint32 debug_mode = GPOINTER_TO_INT(mode_ptr);
+       if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))){
+               gst_info_enable_category(debug_mode);
+               gst_debug_enable_category(debug_mode);
+       }
+       else {
+               gst_info_disable_category(debug_mode);
+               gst_debug_disable_category(debug_mode);
+       }
+}
+
+void
+debug_select_callback(GtkWidget *widget, GSList *debug_list)
+{
+       gchar *name = gtk_object_get_data(GTK_OBJECT(widget), "name");
+       gboolean select = (strstr(name, "deselect all") == NULL);
+       while (debug_list){
+               gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON(debug_list->data), select);
+               debug_list = g_slist_next(debug_list);
+       }
+}
+
+void
+build_debug_page(GtkWidget *notebook)
+{
+       guint32 debug_mode;
+       GtkWidget *debug_box, *debug_buts, *debug_but, *scrolled;
+       GSList *debug_list = NULL;
+       
+       scrolled = gtk_scrolled_window_new(NULL,NULL);
+       
+       debug_box = gtk_vbox_new(TRUE, 0);
+       debug_buts = gtk_hbox_new(TRUE, 0);
+       gtk_box_pack_start(GTK_BOX(debug_box),debug_buts,TRUE,TRUE,0);
+       
+       gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(scrolled), debug_box);
+       gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrolled), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC);
+       gtk_notebook_append_page(GTK_NOTEBOOK(notebook), scrolled, gtk_label_new("Debug"));
+       
+       for (debug_mode = 0 ; (debug_mode < GST_CAT_MAX_CATEGORY) && 
+                             (gst_get_category_name(debug_mode) != NULL); debug_mode++){
+               GtkWidget *debug_enable = gtk_check_button_new_with_label (gst_get_category_name(debug_mode));
+               
+               debug_list = g_slist_append(debug_list, debug_enable);
+
+               gtk_box_pack_start(GTK_BOX(debug_box),debug_enable,TRUE,TRUE,0);
+               gtk_signal_connect (GTK_OBJECT (debug_enable), "toggled",
+                                   GTK_SIGNAL_FUNC (debug_toggle_callback), GINT_TO_POINTER(debug_mode));
+       }
+
+       debug_but = gtk_button_new_with_label("select all");
+       gtk_box_pack_start(GTK_BOX(debug_buts),debug_but,TRUE,TRUE,0);
+       gtk_object_set_data(GTK_OBJECT(debug_but), "name", "select all");
+       gtk_signal_connect (GTK_OBJECT (debug_but), "clicked",
+                           GTK_SIGNAL_FUNC (debug_select_callback), debug_list);
+
+       debug_but = gtk_button_new_with_label("deselect all");
+       gtk_box_pack_start(GTK_BOX(debug_buts),debug_but,TRUE,TRUE,0);
+       gtk_object_set_data(GTK_OBJECT(debug_but), "name", "deselect all");
+       gtk_signal_connect (GTK_OBJECT (debug_but), "clicked",
+                           GTK_SIGNAL_FUNC (debug_select_callback), debug_list);
+
+
+}
+
+void
+arg_search (GstBin *bin, gchar *argname, found_handler handler, void *priv)
+{
+       GList *children;
+       GValue *value;
+       GParamSpec **property_specs;
+       
+       value = g_new0(GValue,1);
+       g_value_init (value, G_TYPE_INT);
+       children = gst_bin_get_list(bin);
+
+       while (children) {
+               GstElement *child;
+     
+               child = GST_ELEMENT (children->data);
+               children = g_list_next (children);
+
+               if (GST_IS_BIN (child)) arg_search (GST_BIN (child), argname, handler, priv);
+               else {
+                       gint num_properties,i;
+                       
+                       property_specs = g_object_class_list_properties(G_OBJECT_GET_CLASS (child), &num_properties);
+                       
+                       for (i=0;i<num_properties;i++) {
+                               if (strstr(property_specs[i]->name,argname)) {
+                                       g_object_get_property(G_OBJECT(child),argname,value);
+
+                                       (handler)(child, g_value_get_int(value) ,priv);
+                               }
+                       }
+               }
+       }
+       g_free(value);
+}
+
+void 
+handle_have_size (GstElement *element,int width,int height) 
+{
+       g_print("setting window size\n");
+       gtk_widget_set_usize(GTK_WIDGET(gtk_object_get_data(GTK_OBJECT(element), "gtk_socket")),width,height);
+       gtk_widget_show_all(GTK_WIDGET(gtk_object_get_data(GTK_OBJECT(element), "vid_window")));
+}
+
+void 
+xid_handler (GstElement *element, gint xid, void *priv) 
+{
+       GtkWidget *gtk_socket, *vid_window;
+       
+       g_print("handling xid %d\n", xid);
+       vid_window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
+
+       gtk_socket = gtk_socket_new ();
+       gtk_widget_show(gtk_socket);
+
+       gtk_container_add(GTK_CONTAINER(vid_window),gtk_socket);
+
+       gtk_widget_realize(gtk_socket);
+       gtk_socket_steal (GTK_SOCKET (gtk_socket), xid);
+
+       gtk_object_set(GTK_OBJECT(vid_window),"allow_grow",TRUE,NULL);
+       gtk_object_set(GTK_OBJECT(vid_window),"allow_shrink",TRUE,NULL);
+
+       gtk_signal_connect (GTK_OBJECT (element), "have_size",
+                           GTK_SIGNAL_FUNC (handle_have_size), element);
+       gtk_object_set_data(GTK_OBJECT(element), "vid_window", vid_window);
+       gtk_object_set_data(GTK_OBJECT(element), "gtk_socket", gtk_socket);
+}
+
+void
+parse_callback( GtkWidget *widget,
+                GtkWidget *pipe_combo)
+{
+       GList *history = (GList*)gtk_object_get_data(GTK_OBJECT(pipe_combo), "history");
+       FILE *history_file = (FILE*)gtk_object_get_data(GTK_OBJECT(pipe_combo), "history_file");
+       
+       gchar *try_pipe = gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(pipe_combo)->entry));
+       gchar *write_pipe = g_strdup_printf("%s\n", try_pipe);
+
+       fwrite(write_pipe, sizeof(gchar), strlen(write_pipe), history_file);
+       fflush(history_file);
+
+       if (pipeline){
+               g_print("unreffing\n");
+               gst_object_unref (GST_OBJECT (pipeline));
+       }
+       g_print ("trying pipeline: %s\n", try_pipe);
+       
+       pipeline = gst_pipeline_new ("launch");
+       gst_parse_launch (try_pipe, GST_BIN (pipeline));
+       gtk_widget_set_sensitive(GTK_WIDGET(start_but), TRUE);
+
+       history = g_list_prepend(history, try_pipe);
+       gtk_combo_set_popdown_strings(GTK_COMBO(pipe_combo), history);  
+       g_free(write_pipe);
+}
+
+void
+start_callback( GtkWidget *widget,
+                gpointer   data )
+{
+       GtkWidget *pipe_combo = gtk_object_get_data(GTK_OBJECT(widget), "pipe_combo");
+       gchar *try_pipe = gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(pipe_combo)->entry));
+       
+       if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))){
+               gtk_widget_set_sensitive(GTK_WIDGET(pause_but), TRUE);
+               gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(pause_but), FALSE);
+               gtk_widget_set_sensitive(GTK_WIDGET(parse_but), FALSE);
+               gtk_widget_set_sensitive(GTK_WIDGET(pipe_combo), FALSE);
+               gtk_label_set_text(GTK_LABEL(status), "playing");
+               
+               arg_search(GST_BIN(pipeline),"xid",xid_handler,NULL);
+               gst_element_set_state (pipeline, GST_STATE_PLAYING);
+               g_idle_add(idle_func,pipeline);
+       }
+       else {
+               gtk_widget_set_sensitive(GTK_WIDGET(pause_but), FALSE);
+               gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(pause_but), FALSE);
+               gtk_widget_set_sensitive(GTK_WIDGET(parse_but), TRUE);
+               gtk_widget_set_sensitive(GTK_WIDGET(pipe_combo), TRUE);
+               gst_element_set_state (pipeline, GST_STATE_NULL);
+               gtk_label_set_text(GTK_LABEL(status), "stopped");
+               
+               g_idle_remove_by_data(pipeline);
+       }
+}
+
+void
+pause_callback( GtkWidget *widget,
+                gpointer   data )
+{
+       if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))){
+               gst_element_set_state (pipeline, GST_STATE_PAUSED);
+               gtk_label_set_text(GTK_LABEL(status), "paused");
+       }
+       else {
+               gst_element_set_state (pipeline, GST_STATE_PLAYING);
+               gtk_label_set_text(GTK_LABEL(status), "playing");
+       }
+}
+
+int main(int argc,char *argv[]) {
+       GtkWidget *window;
+       GtkWidget *vbox;
+       GtkWidget *parse_line, *pipe_combo, *notebook;
+
+       gst_init(&argc,&argv);
+       
+       /***** set up the GUI *****/
+       window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
+       g_signal_connect(window,"delete_event",GTK_SIGNAL_FUNC(quit_live),NULL);
+       vbox = gtk_vbox_new(FALSE,0);
+       gtk_container_add(GTK_CONTAINER(window),vbox);
+
+       parse_line = gtk_hbox_new(FALSE, 3);
+       gtk_box_pack_start(GTK_BOX(vbox),parse_line,FALSE,FALSE,0);
+
+       pipe_combo = gtk_combo_new();
+       gtk_combo_set_value_in_list(GTK_COMBO(pipe_combo), FALSE, FALSE);
+       load_history(pipe_combo);
+       
+       parse_but = gtk_button_new_with_label("Parse");
+       gtk_box_pack_start(GTK_BOX(parse_line),pipe_combo,TRUE,TRUE,0);
+       gtk_box_pack_start(GTK_BOX(parse_line),parse_but,FALSE,FALSE,0);
+
+       start_but = gtk_toggle_button_new_with_label("Play");
+       pause_but = gtk_toggle_button_new_with_label("Pause");
+
+       gtk_box_pack_start(GTK_BOX(parse_line),start_but,FALSE,FALSE,0);
+       gtk_box_pack_start(GTK_BOX(parse_line),pause_but,FALSE,FALSE,0);
+       
+       gtk_widget_set_sensitive(GTK_WIDGET(start_but), FALSE);
+       gtk_widget_set_sensitive(GTK_WIDGET(pause_but), FALSE);
+
+       gtk_signal_connect (GTK_OBJECT (start_but), "clicked",
+                           GTK_SIGNAL_FUNC (start_callback), NULL);
+       gtk_signal_connect (GTK_OBJECT (pause_but), "clicked",
+                           GTK_SIGNAL_FUNC (pause_callback), NULL);
+       gtk_signal_connect (GTK_OBJECT (parse_but), "clicked",
+                           GTK_SIGNAL_FUNC (parse_callback), pipe_combo);
+       
+       gtk_object_set_data(GTK_OBJECT(start_but), "pipe_combo", pipe_combo);
+       
+       notebook = gtk_notebook_new();
+       gtk_box_pack_start(GTK_BOX(vbox),notebook,TRUE,TRUE,0);
+       
+       build_debug_page(notebook);
+       
+       status = gtk_label_new("stopped");
+       gtk_box_pack_start(GTK_BOX(vbox),status,FALSE,FALSE,0);
+       
+       gtk_widget_show_all(window);
+       gtk_main();
+
+       return 0;
+}