2 * Copyright (C) <1999> Erik Walthinsen <omega@cse.ogi.edu>
3 * <2001> Steve Baker <stevebaker_org@yahoo.co.uk>
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Library General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Library General Public License for more details.
15 * You should have received a copy of the GNU Library General Public
16 * License along with this library; if not, write to the
17 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
23 #include <gst/control/control.h>
25 #include "gstladspa.h"
26 #include <ladspa.h> /* main ladspa sdk include file */
27 #include "utils.h" /* ladspa sdk utility functions */
30 GST_PAD_TEMPLATE_FACTORY (ladspa_sink_factory,
37 "rate", GST_PROPS_INT_RANGE (4000, 96000),
38 "format", GST_PROPS_STRING ("float"),
39 "layout", GST_PROPS_STRING ("gfloat"),
40 "intercept", GST_PROPS_FLOAT(0.0),
41 "slope", GST_PROPS_FLOAT(1.0),
42 "channels", GST_PROPS_INT (1)
46 GST_PAD_TEMPLATE_FACTORY (ladspa_src_factory,
53 "rate", GST_PROPS_INT_RANGE (4000, 96000),
54 "format", GST_PROPS_STRING ("float"),
55 "layout", GST_PROPS_STRING ("gfloat"),
56 "intercept", GST_PROPS_FLOAT (0.0),
57 "slope", GST_PROPS_FLOAT (1.0),
58 "channels", GST_PROPS_INT (1)
62 static GstPadTemplate *srctempl, *sinktempl;
71 static void gst_ladspa_class_init (GstLADSPAClass *klass);
72 static void gst_ladspa_init (GstLADSPA *ladspa);
74 static void gst_ladspa_update_int(const GValue *value, gpointer data);
75 static GstPadLinkReturn gst_ladspa_connect (GstPad *pad, GstCaps *caps);
76 static GstPadLinkReturn gst_ladspa_connect_get (GstPad *pad, GstCaps *caps);
77 static void gst_ladspa_force_src_caps (GstLADSPA *ladspa, GstPad *pad);
79 static void gst_ladspa_set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec);
80 static void gst_ladspa_get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec);
82 static gboolean gst_ladspa_instantiate (GstLADSPA *ladspa);
83 static void gst_ladspa_activate (GstLADSPA *ladspa);
84 static void gst_ladspa_deactivate (GstLADSPA *ladspa);
86 static GstElementStateReturn gst_ladspa_change_state (GstElement *element);
87 static void gst_ladspa_loop (GstElement *element);
88 static void gst_ladspa_chain (GstPad *pad,GstBuffer *buf);
89 static GstBuffer * gst_ladspa_get (GstPad *pad);
91 static GstElementClass *parent_class = NULL;
92 /* static guint gst_ladspa_signals[LAST_SIGNAL] = { 0 }; */
94 static GstPlugin *ladspa_plugin;
95 static GHashTable *ladspa_descriptors;
98 gst_ladspa_get_bufferpool (GstPad *pad)
102 GstLADSPA *ladspa = (GstLADSPA *) gst_pad_get_parent (pad);
103 GstLADSPAClass *oclass = (GstLADSPAClass *) (G_OBJECT_GET_CLASS (ladspa));
105 if (oclass->numsrcpads > 0)
106 for (i=0;i<oclass->numsrcpads;i++)
107 if ((bp = gst_pad_get_bufferpool(ladspa->srcpads[i])) != NULL)
114 gst_ladspa_class_init (GstLADSPAClass *klass)
116 GObjectClass *gobject_class;
117 GstElementClass *gstelement_class;
118 LADSPA_Descriptor *desc;
119 gint i,current_portnum,sinkcount,srccount,controlcount;
121 gint argtype,argperms;
122 GParamSpec *paramspec = NULL;
123 gchar *argname, *tempstr, *paren;
125 gobject_class = (GObjectClass*)klass;
126 gstelement_class = (GstElementClass*)klass;
128 gobject_class->set_property = gst_ladspa_set_property;
129 gobject_class->get_property = gst_ladspa_get_property;
131 gstelement_class->change_state = gst_ladspa_change_state;
133 /* look up and store the ladspa descriptor */
134 klass->descriptor = g_hash_table_lookup(ladspa_descriptors,GINT_TO_POINTER(G_TYPE_FROM_CLASS(klass)));
135 desc = klass->descriptor;
137 klass->numports = desc->PortCount;
139 klass->numsinkpads = 0;
140 klass->numsrcpads = 0;
141 klass->numcontrols = 0;
143 /* walk through the ports, count the input, output and control ports */
144 for (i=0;i<desc->PortCount;i++) {
145 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[i]) &&
146 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])){
147 klass->numsinkpads++;
150 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[i]) &&
151 LADSPA_IS_PORT_OUTPUT(desc->PortDescriptors[i])){
155 if (LADSPA_IS_PORT_CONTROL(desc->PortDescriptors[i]) &&
156 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])){
157 klass->numcontrols++;
161 klass->srcpad_portnums = g_new0(gint,klass->numsrcpads);
162 klass->sinkpad_portnums = g_new0(gint,klass->numsinkpads);
163 klass->control_portnums = g_new0(gint,klass->numcontrols);
168 /* walk through the ports, note the portnums for srcpads, sinkpads and control
170 for (i=0;i<desc->PortCount;i++) {
171 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[i]) &&
172 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])){
173 GST_DEBUG ("input port %d", i);
174 klass->sinkpad_portnums[sinkcount++] = i;
177 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[i]) &&
178 LADSPA_IS_PORT_OUTPUT(desc->PortDescriptors[i])){
179 GST_DEBUG ("output port %d", i);
180 klass->srcpad_portnums[srccount++] = i;
183 if (LADSPA_IS_PORT_CONTROL(desc->PortDescriptors[i]) &&
184 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])){
185 GST_DEBUG ("control port %d", i);
186 klass->control_portnums[controlcount++] = i;
190 /* no sink pads - we'll use get mode and add params for samplerate and
192 if (klass->numsinkpads == 0 && klass->numsrcpads > 0){
193 g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_SAMPLERATE,
194 g_param_spec_int("samplerate","samplerate","samplerate",
195 0,G_MAXINT,44100,G_PARAM_READWRITE));
196 g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_BUFFERSIZE,
197 g_param_spec_int("buffersize","buffersize","buffersize",
198 0,G_MAXINT,64,G_PARAM_READWRITE));
202 /* now build the contorl info from the control ports */
203 klass->control_info = g_new0(ladspa_control_info,klass->numcontrols);
205 for (i=0;i<klass->numcontrols;i++) {
206 current_portnum = klass->control_portnums[i];
208 /* short name for hint descriptor */
209 hintdesc = desc->PortRangeHints[current_portnum].HintDescriptor;
211 /* get the various bits */
212 if (LADSPA_IS_HINT_TOGGLED(hintdesc))
213 klass->control_info[i].toggled = TRUE;
214 if (LADSPA_IS_HINT_LOGARITHMIC(hintdesc))
215 klass->control_info[i].logarithmic = TRUE;
216 if (LADSPA_IS_HINT_INTEGER(hintdesc))
217 klass->control_info[i].integer = TRUE;
219 /* figure out the argument details */
220 if (klass->control_info[i].toggled) argtype = G_TYPE_BOOLEAN;
221 else if (klass->control_info[i].integer) argtype = G_TYPE_INT;
222 else argtype = G_TYPE_FLOAT;
224 /* grab the bounds */
225 if (LADSPA_IS_HINT_BOUNDED_BELOW(hintdesc)) {
226 klass->control_info[i].lower = TRUE;
227 klass->control_info[i].lowerbound =
228 desc->PortRangeHints[current_portnum].LowerBound;
230 if (argtype==G_TYPE_INT) klass->control_info[i].lowerbound = (gfloat)G_MININT;
231 if (argtype==G_TYPE_FLOAT) klass->control_info[i].lowerbound = -G_MAXFLOAT;
234 if (LADSPA_IS_HINT_BOUNDED_ABOVE(hintdesc)) {
235 klass->control_info[i].upper = TRUE;
236 klass->control_info[i].upperbound =
237 desc->PortRangeHints[current_portnum].UpperBound;
238 if (LADSPA_IS_HINT_SAMPLE_RATE(hintdesc))
239 klass->control_info[i].samplerate = TRUE;
241 if (argtype==G_TYPE_INT) klass->control_info[i].upperbound = (gfloat)G_MAXINT;
242 if (argtype==G_TYPE_FLOAT) klass->control_info[i].upperbound = G_MAXFLOAT;
245 klass->control_info[i].def = klass->control_info[i].lowerbound;
247 #ifdef LADSPA_IS_HINT_HAS_DEFAULT
248 /* figure out the defaults */
249 if (LADSPA_IS_HINT_HAS_DEFAULT (hintdesc)) {
250 if (LADSPA_IS_HINT_DEFAULT_MINIMUM (hintdesc))
251 klass->control_info[i].def = klass->control_info[i].lowerbound;
252 else if (LADSPA_IS_HINT_DEFAULT_LOW (hintdesc))
253 if (LADSPA_IS_HINT_LOGARITHMIC (hintdesc))
254 klass->control_info[i].def = exp (0.75*log(klass->control_info[i].lowerbound) +
255 0.25*log(klass->control_info[i].upperbound));
257 klass->control_info[i].def = (0.75*klass->control_info[i].lowerbound +
258 0.25*klass->control_info[i].upperbound);
259 else if (LADSPA_IS_HINT_DEFAULT_MIDDLE (hintdesc))
260 if (LADSPA_IS_HINT_LOGARITHMIC (hintdesc))
261 klass->control_info[i].def = exp (0.5*log(klass->control_info[i].lowerbound) +
262 0.5*log(klass->control_info[i].upperbound));
264 klass->control_info[i].def = (0.5*klass->control_info[i].lowerbound +
265 0.5*klass->control_info[i].upperbound);
266 else if (LADSPA_IS_HINT_DEFAULT_HIGH (hintdesc))
267 if (LADSPA_IS_HINT_LOGARITHMIC (hintdesc))
268 klass->control_info[i].def = exp (0.25*log(klass->control_info[i].lowerbound) +
269 0.75*log(klass->control_info[i].upperbound));
271 klass->control_info[i].def = (0.25*klass->control_info[i].lowerbound +
272 0.75*klass->control_info[i].upperbound);
273 else if (LADSPA_IS_HINT_DEFAULT_MAXIMUM (hintdesc))
274 klass->control_info[i].def = klass->control_info[i].upperbound;
275 else if (LADSPA_IS_HINT_DEFAULT_0 (hintdesc))
276 klass->control_info[i].def = 0.0;
277 else if (LADSPA_IS_HINT_DEFAULT_1 (hintdesc))
278 klass->control_info[i].def = 1.0;
279 else if (LADSPA_IS_HINT_DEFAULT_100 (hintdesc))
280 klass->control_info[i].def = 100.0;
281 else if (LADSPA_IS_HINT_DEFAULT_440 (hintdesc))
282 klass->control_info[i].def = 440.0;
284 #endif /* LADSPA_IS_HINT_HAS_DEFAULT */
286 klass->control_info[i].def = CLAMP(klass->control_info[i].def,
287 klass->control_info[i].lowerbound, klass->control_info[i].upperbound);
289 if (LADSPA_IS_PORT_INPUT(desc->PortDescriptors[current_portnum])) {
290 argperms = G_PARAM_READWRITE;
291 klass->control_info[i].writable = TRUE;
293 argperms = G_PARAM_READABLE;
294 klass->control_info[i].writable = FALSE;
297 klass->control_info[i].name = g_strdup(desc->PortNames[current_portnum]);
298 argname = g_strdup(klass->control_info[i].name);
299 /* find out if there is a (unitname) at the end of the argname and get rid
301 paren = g_strrstr (argname, " (");
305 /* this is the same thing that param_spec_* will do */
306 g_strcanon (argname, G_CSET_A_2_Z G_CSET_a_2_z G_CSET_DIGITS "-", '-');
307 /* satisfy glib2 (argname[0] must be [A-Za-z]) */
308 if (!((argname[0] >= 'a' && argname[0] <= 'z') || (argname[0] >= 'A' && argname[0] <= 'Z'))) {
310 argname = g_strconcat("param-", argname, NULL);
314 /* check for duplicate property names */
315 if (g_object_class_find_property(G_OBJECT_CLASS(klass), argname) != NULL){
317 gchar *numargname = g_strdup_printf("%s_%d",argname,numarg++);
318 while (g_object_class_find_property(G_OBJECT_CLASS(klass), numargname) != NULL){
320 numargname = g_strdup_printf("%s_%d",argname,numarg++);
322 argname = numargname;
325 klass->control_info[i].param_name = argname;
327 GST_DEBUG ("adding arg %s from %s",argname, klass->control_info[i].name);
329 if (argtype==G_TYPE_BOOLEAN){
330 paramspec = g_param_spec_boolean(argname,argname,argname, FALSE, argperms);
331 } else if (argtype==G_TYPE_INT){
332 paramspec = g_param_spec_int(argname,argname,argname,
333 (gint)klass->control_info[i].lowerbound,
334 (gint)klass->control_info[i].upperbound,
335 (gint)klass->control_info[i].def, argperms);
336 } else if (klass->control_info[i].samplerate){
337 paramspec = g_param_spec_float(argname,argname,argname,
341 paramspec = g_param_spec_float(argname,argname,argname,
342 klass->control_info[i].lowerbound, klass->control_info[i].upperbound,
343 klass->control_info[i].def, argperms);
346 g_object_class_install_property(G_OBJECT_CLASS(klass), i+ARG_LAST, paramspec);
351 gst_ladspa_init (GstLADSPA *ladspa)
353 GstLADSPAClass *oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS(ladspa));
354 ladspa_control_info cinfo;
356 LADSPA_Descriptor *desc;
357 gint i,sinkcount,srccount,controlcount;
359 desc = oclass->descriptor;
360 ladspa->descriptor = oclass->descriptor;
362 /* allocate the various arrays */
363 ladspa->srcpads = g_new0(GstPad*,oclass->numsrcpads);
364 ladspa->sinkpads = g_new0(GstPad*,oclass->numsinkpads);
365 ladspa->controls = g_new(gfloat,oclass->numcontrols);
366 ladspa->dpman = gst_dpman_new ("ladspa_dpman", GST_ELEMENT(ladspa));
368 /* walk through the ports and add all the pads */
372 for (i=0;i<desc->PortCount;i++) {
374 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[i])){
375 gchar *canon_port_name = g_strdup((gchar *)desc->PortNames[i]);
376 g_strcanon (canon_port_name, G_CSET_A_2_Z G_CSET_a_2_z G_CSET_DIGITS "-", '-');
377 if (LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])) {
378 ladspa->sinkpads[sinkcount] = gst_pad_new_from_template (sinktempl, canon_port_name);
379 gst_element_add_pad(GST_ELEMENT(ladspa),ladspa->sinkpads[sinkcount]);
382 if (LADSPA_IS_PORT_OUTPUT(desc->PortDescriptors[i])) {
383 ladspa->srcpads[srccount] = gst_pad_new_from_template (srctempl, canon_port_name);
384 gst_element_add_pad(GST_ELEMENT(ladspa),ladspa->srcpads[srccount]);
388 if (LADSPA_IS_PORT_CONTROL(desc->PortDescriptors[i]) &&
389 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[i])) {
390 cinfo = oclass->control_info[controlcount];
391 /* use the lowerbound as the default value if it exists */
392 ladspa->controls[controlcount]=cinfo.def;
394 /* set up dparams for this instance */
396 gst_dpman_add_required_dparam_callback (
398 g_param_spec_int(cinfo.param_name, cinfo.name, cinfo.name,
399 0, 1, (gint)(ladspa->controls[controlcount]), G_PARAM_READWRITE),
400 "int", gst_ladspa_update_int, &(ladspa->controls[controlcount])
403 else if (cinfo.integer){
404 gst_dpman_add_required_dparam_callback (
406 g_param_spec_int(cinfo.param_name, cinfo.name, cinfo.name,
407 (gint)cinfo.lowerbound, (gint)cinfo.upperbound,
408 (gint)ladspa->controls[controlcount], G_PARAM_READWRITE),
409 "int", gst_ladspa_update_int, &(ladspa->controls[controlcount])
412 else if (cinfo.samplerate){
413 gst_dpman_add_required_dparam_direct (
415 g_param_spec_float(cinfo.param_name, cinfo.name, cinfo.name,
416 cinfo.lowerbound, cinfo.upperbound,
417 ladspa->controls[controlcount], G_PARAM_READWRITE),
418 "hertz-rate-bound", &(ladspa->controls[controlcount])
422 gst_dpman_add_required_dparam_direct (
424 g_param_spec_float(cinfo.param_name, cinfo.name, cinfo.name,
425 cinfo.lowerbound, cinfo.upperbound,
426 ladspa->controls[controlcount], G_PARAM_READWRITE),
427 "float", &(ladspa->controls[controlcount])
435 /* nonzero default needed to instantiate() some plugins */
436 ladspa->samplerate = 44100;
438 ladspa->buffersize = 64;
439 ladspa->numbuffers = 16;
440 ladspa->activated = FALSE;
441 ladspa->bufpool = NULL;
442 ladspa->inplace_broken = LADSPA_IS_INPLACE_BROKEN(ladspa->descriptor->Properties);
444 if (sinkcount==0 && srccount == 1) {
445 /* get mode (no sink pads) */
446 GST_DEBUG ("mono get mode with 1 src pad");
448 ladspa->newcaps = TRUE;
450 gst_pad_set_link_function (ladspa->srcpads[0], gst_ladspa_connect_get);
451 gst_pad_set_get_function (ladspa->srcpads[0], gst_ladspa_get);
452 } else if (sinkcount==1){
453 /* with one sink we can use the chain function */
454 GST_DEBUG ("chain mode");
456 gst_pad_set_link_function (ladspa->sinkpads[0], gst_ladspa_connect);
457 gst_pad_set_chain_function (ladspa->sinkpads[0], gst_ladspa_chain);
458 gst_pad_set_bufferpool_function (ladspa->sinkpads[0], gst_ladspa_get_bufferpool);
459 } else if (sinkcount > 1){
460 /* more than one sink pad needs loop mode */
461 GST_DEBUG ("loop mode with %d sink pads and %d src pads", sinkcount, srccount);
463 for (i=0;i<sinkcount;i++) {
464 gst_pad_set_link_function (ladspa->sinkpads[i], gst_ladspa_connect);
465 gst_pad_set_bufferpool_function (ladspa->sinkpads[i], gst_ladspa_get_bufferpool);
467 gst_element_set_loop_function (GST_ELEMENT (ladspa), gst_ladspa_loop);
469 else if (sinkcount==0 && srccount == 0){
470 /* for some reason these plugins exist - we'll just ignore them */
472 GST_DEBUG ("%d sink pads, %d src pads not yet supported", sinkcount, srccount);
475 gst_ladspa_instantiate (ladspa);
479 gst_ladspa_update_int(const GValue *value, gpointer data)
481 gfloat *target = (gfloat*) data;
482 *target = (gfloat)g_value_get_int(value);
485 static GstPadLinkReturn
486 gst_ladspa_connect (GstPad *pad, GstCaps *caps)
488 GstLADSPA *ladspa = (GstLADSPA *) GST_PAD_PARENT (pad);
489 GstLADSPAClass *oclass = (GstLADSPAClass *) (G_OBJECT_GET_CLASS (ladspa));
493 g_return_val_if_fail (caps != NULL, GST_PAD_LINK_DELAYED);
494 g_return_val_if_fail (pad != NULL, GST_PAD_LINK_DELAYED);
496 if (gst_caps_get_int (caps, "rate", &rate)){
497 /* have to instantiate ladspa plugin when samplerate changes (groan) */
498 if (ladspa->samplerate != rate){
499 ladspa->samplerate = rate;
501 if (! gst_ladspa_instantiate(ladspa))
502 return GST_PAD_LINK_REFUSED;
506 /* if the caps are fixed, we are going to try to set all srcpads using this
507 one caps object. if any of the pads barfs, we'll refuse the connection. i'm
508 not sure if this is correct. */
509 if (GST_CAPS_IS_FIXED (caps)) {
510 for (i=0;i<oclass->numsrcpads;i++) {
511 if (gst_pad_try_set_caps (ladspa->srcpads[i], caps) <= 0)
512 return GST_PAD_LINK_REFUSED;
516 return GST_PAD_LINK_OK;
519 static GstPadLinkReturn
520 gst_ladspa_connect_get (GstPad *pad, GstCaps *caps)
522 GstLADSPA *ladspa = (GstLADSPA*)GST_OBJECT_PARENT (pad);
525 g_return_val_if_fail (caps != NULL, GST_PAD_LINK_DELAYED);
526 g_return_val_if_fail (pad != NULL, GST_PAD_LINK_DELAYED);
528 if (gst_caps_get_int (caps, "rate", &rate)){
529 if (ladspa->samplerate != rate) {
530 ladspa->samplerate = rate;
531 if (! gst_ladspa_instantiate(ladspa))
532 return GST_PAD_LINK_REFUSED;
536 return GST_PAD_LINK_OK;
540 gst_ladspa_force_src_caps(GstLADSPA *ladspa, GstPad *pad)
542 GST_DEBUG ("forcing caps with rate %d", ladspa->samplerate);
543 gst_pad_try_set_caps (pad, gst_caps_new (
547 "format", GST_PROPS_STRING ("float"),
548 "layout", GST_PROPS_STRING ("gfloat"),
549 "intercept", GST_PROPS_FLOAT(0.0),
550 "slope", GST_PROPS_FLOAT(1.0),
551 "rate", GST_PROPS_INT (ladspa->samplerate),
552 "channels", GST_PROPS_INT (1),
556 ladspa->newcaps=FALSE;
560 gst_ladspa_set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec)
562 GstLADSPA *ladspa = (GstLADSPA*)object;
563 gint cid = prop_id - ARG_LAST;
564 GstLADSPAClass *oclass;
565 ladspa_control_info *control_info;
568 /* these are only registered in get mode */
571 ladspa->samplerate = g_value_get_int (value);
572 ladspa->newcaps=TRUE;
573 gst_ladspa_instantiate (ladspa);
576 ladspa->buffersize = g_value_get_int (value);
580 /* is it a ladspa plugin arg? */
583 oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS (object));
585 /* verify it exists and is a control (not a port) */
586 g_return_if_fail(cid < oclass->numcontrols);
588 control_info = &(oclass->control_info[cid]);
589 g_return_if_fail (control_info->name != NULL);
591 /* check to see if it's writable */
592 g_return_if_fail (control_info->writable);
594 /* now see what type it is */
595 if (control_info->toggled) {
596 if (g_value_get_boolean (value))
597 ladspa->controls[cid] = 1.0;
599 ladspa->controls[cid] = 0.0;
600 } else if (control_info->integer) {
601 val = (gfloat)g_value_get_int (value);
602 ladspa->controls[cid] = val;
604 val = g_value_get_float (value);
605 ladspa->controls[cid] = val;
608 GST_DEBUG ("set arg %s to %f", control_info->name, ladspa->controls[cid]);
612 gst_ladspa_get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
614 GstLADSPA *ladspa = (GstLADSPA*)object;
615 gint cid = prop_id - ARG_LAST;
616 GstLADSPAClass *oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS (object));
617 ladspa_control_info *control_info;
619 /* these are only registered in get mode */
622 g_value_set_int (value, ladspa->samplerate);
625 g_value_set_int (value, ladspa->buffersize);
631 /* verify it exists and is a control (not a port) */
632 if (cid >= oclass->numcontrols) return;
633 control_info = &(oclass->control_info[cid]);
634 if (control_info->name == NULL) return;
636 GST_DEBUG ("got arg %s as %f", control_info->name, ladspa->controls[cid]);
638 /* now see what type it is */
639 if (control_info->toggled) {
640 if (ladspa->controls[cid] == 1.0)
641 g_value_set_boolean (value, TRUE);
643 g_value_set_boolean (value, FALSE);
644 } else if (control_info->integer) {
645 g_value_set_int (value, (gint)ladspa->controls[cid]);
647 g_value_set_float (value, ladspa->controls[cid]);
652 gst_ladspa_instantiate (GstLADSPA *ladspa)
654 LADSPA_Descriptor *desc;
656 GstLADSPAClass *oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS (ladspa));
657 gboolean was_activated;
659 desc = ladspa->descriptor;
661 /* check for old handle */
662 was_activated = ladspa->activated;
663 if (ladspa->handle != NULL){
664 gst_ladspa_deactivate(ladspa);
665 desc->cleanup(ladspa->handle);
668 /* instantiate the plugin */
669 GST_DEBUG ("instantiating the plugin");
671 ladspa->handle = desc->instantiate(desc,ladspa->samplerate);
672 g_return_val_if_fail (ladspa->handle != NULL, FALSE);
674 /* walk through the ports and add all the arguments */
675 for (i=0;i<oclass->numcontrols;i++) {
676 /* connect the argument to the plugin */
677 GST_DEBUG ("added control port %d", oclass->control_portnums[i]);
678 desc->connect_port(ladspa->handle,
679 oclass->control_portnums[i],
680 &(ladspa->controls[i]));
683 /* reactivate if it was activated before the reinstantiation */
685 gst_ladspa_activate(ladspa);
690 static GstElementStateReturn
691 gst_ladspa_change_state (GstElement *element)
693 LADSPA_Descriptor *desc;
694 GstLADSPA *ladspa = (GstLADSPA*)element;
695 desc = ladspa->descriptor;
697 GST_DEBUG ("changing state");
698 switch (GST_STATE_TRANSITION (element)) {
699 case GST_STATE_NULL_TO_READY:
700 gst_ladspa_activate(ladspa);
702 case GST_STATE_READY_TO_NULL:
703 gst_ladspa_deactivate(ladspa);
709 if (GST_ELEMENT_CLASS (parent_class)->change_state)
710 return GST_ELEMENT_CLASS (parent_class)->change_state (element);
712 return GST_STATE_SUCCESS;
716 gst_ladspa_activate(GstLADSPA *ladspa)
718 LADSPA_Descriptor *desc;
719 desc = ladspa->descriptor;
721 if (ladspa->activated){
722 gst_ladspa_deactivate(ladspa);
725 GST_DEBUG ("activating");
727 /* activate the plugin (function might be null) */
728 if (desc->activate != NULL) {
729 desc->activate(ladspa->handle);
732 ladspa->activated = TRUE;
736 gst_ladspa_deactivate(GstLADSPA *ladspa)
738 LADSPA_Descriptor *desc;
739 desc = ladspa->descriptor;
741 GST_DEBUG ("deactivating");
743 /* deactivate the plugin (function might be null) */
744 if (ladspa->activated && (desc->deactivate != NULL)) {
745 desc->deactivate(ladspa->handle);
748 ladspa->activated = FALSE;
752 gst_ladspa_loop(GstElement *element)
754 guint bufferbytesize, i, numsrcpads, numsinkpads, num_empty_pads;
755 guint num_processed, num_to_process;
756 GstEvent *event = NULL;
759 LADSPA_Data **data_in, **data_out;
760 GstBuffer **buffers_in, **buffers_out;
761 GstBufferPool *bufpool;
762 GstByteStream **bytestreams;
764 GstLADSPA *ladspa = (GstLADSPA *)element;
765 GstLADSPAClass *oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS (ladspa));
766 LADSPA_Descriptor *desc = ladspa->descriptor;
768 numsinkpads = oclass->numsinkpads;
769 numsrcpads = oclass->numsrcpads;
771 data_in = g_new0(LADSPA_Data*, numsinkpads);
772 data_out = g_new0(LADSPA_Data*, numsrcpads);
773 buffers_in = g_new0(GstBuffer*, numsinkpads);
774 buffers_out = g_new0(GstBuffer*, numsrcpads);
775 bytestreams = g_new0(GstByteStream*, numsinkpads);
777 /* find a bufferpool */
778 if (numsrcpads > 0 && (bufpool = gst_pad_get_bufferpool (ladspa->srcpads[0]))) {
779 GST_DEBUG ("Got bufferpool from first source pad");
781 bufferbytesize = sizeof (LADSPA_Data) * ladspa->buffersize;
782 bufpool = gst_buffer_pool_get_default (bufferbytesize, ladspa->numbuffers);
783 GST_DEBUG ("Created default bufferpool, %d x %d bytes", ladspa->numbuffers, bufferbytesize);
786 /* get the bytestreams for each pad */
787 for (i=0 ; i<numsinkpads ; i++){
788 bytestreams[i] = gst_bytestream_new (ladspa->sinkpads[i]);
791 /* since this is a loop element, we just loop here til things fall apart. */
793 /* we need to get the buffers_out first so we can know how many bytes to process */
794 for (i=0 ; i<numsrcpads ; i++){
795 buffers_out[i] = gst_buffer_new_from_pool (bufpool, 0, 0);
796 GST_BUFFER_TIMESTAMP(buffers_out[i]) = ladspa->timestamp;
797 data_out[i] = (LADSPA_Data *) GST_BUFFER_DATA(buffers_out[i]);
800 bufferbytesize = GST_BUFFER_SIZE (buffers_out[0]);
801 ladspa->buffersize = bufferbytesize / sizeof (LADSPA_Data);
804 /* first get all the necessary data from the input ports */
805 for (i=0 ; i<numsinkpads ; i++){
806 GST_DEBUG ("pulling %u bytes through channel %d's bytestream", bufferbytesize, i);
807 got_bytes = gst_bytestream_read (bytestreams[i], buffers_in + i, bufferbytesize);
809 if (got_bytes != bufferbytesize) {
810 /* we need to check for an event. */
811 gst_bytestream_get_status (bytestreams[i], &waiting, &event);
813 if (event && GST_EVENT_TYPE(event) == GST_EVENT_EOS) {
814 /* if we get an EOS event from one of our sink pads, we assume that
815 pad's finished handling data. delete the bytestream, free up the
816 pad, and free up the memory associated with the input channel. */
817 GST_DEBUG ("got an EOS event on sinkpad %d", i);
819 /* CHECKME should maybe check for other events and try to pull more data here */
822 data_in[i] = (LADSPA_Data *) GST_BUFFER_DATA(buffers_in[i]);
823 GST_BUFFER_TIMESTAMP(buffers_in[i]) = ladspa->timestamp;
827 if (num_empty_pads > 0){
828 if (num_empty_pads < numsinkpads){
829 /* only some pads have EOS, need to create some empty buffers */
830 for (i=0 ; i<numsinkpads ; i++){
831 if (buffers_in[i] == NULL){
834 buffers_in[i] = gst_buffer_new_from_pool (ladspa->bufpool, 0, 0);
835 GST_BUFFER_TIMESTAMP(buffers_in[i]) = ladspa->timestamp;
836 data_in[i] = data = (LADSPA_Data *) GST_BUFFER_DATA(buffers_in[i]);
837 for (x=0 ; x < ladspa->buffersize ; x++)
840 data_in[i] = (LADSPA_Data *) GST_BUFFER_DATA(buffers_in[i]);
841 GST_BUFFER_TIMESTAMP(buffers_in[i]) = ladspa->timestamp;
846 /* all pads have EOS, time to quit */
847 /* CHECKME do I have to push EOS events here? */
848 GST_DEBUG ("All sink pads have EOS, finishing.");
853 GST_DPMAN_PREPROCESS(ladspa->dpman, ladspa->buffersize, ladspa->timestamp);
856 /* split up processing of the buffer into chunks so that dparams can
857 * be updated when required.
858 * In many cases the buffer will be processed in one chunk anyway.
860 while(GST_DPMAN_PROCESS(ladspa->dpman, num_processed)) {
862 num_to_process = GST_DPMAN_FRAMES_TO_PROCESS(ladspa->dpman);
863 for (i=0 ; i<numsinkpads ; i++){
864 desc->connect_port (ladspa->handle, oclass->sinkpad_portnums[i], data_in[i]);
866 for (i=0 ; i<numsrcpads ; i++){
867 desc->connect_port (ladspa->handle, oclass->srcpad_portnums[i], data_out[i]);
869 desc->run(ladspa->handle, num_to_process);
870 for (i=0 ; i<numsinkpads ; i++){
871 data_in[i] += num_to_process;
873 for (i=0 ; i<numsrcpads ; i++){
874 data_out[i] += num_to_process;
877 num_processed += num_to_process;
880 for (i=0 ; i<numsrcpads ; i++) {
881 GST_DEBUG ("pushing buffer (%p) on src pad %d", buffers_out[i], i);
882 gst_pad_push (ladspa->srcpads[i], buffers_out[i]);
885 buffers_out[i] = NULL;
887 for (i=0 ; i<numsinkpads ; i++) {
888 gst_buffer_unref(buffers_in[i]);
890 buffers_in[i] = NULL;
893 ladspa->timestamp += ladspa->buffersize * 10^9 / ladspa->samplerate;
895 gst_element_yield (element);
898 gst_buffer_pool_unref(bufpool);
900 for (i=0 ; i<numsinkpads ; i++){
901 gst_bytestream_destroy (bytestreams[i]);
904 g_free (buffers_out);
908 g_free (bytestreams);
912 gst_ladspa_chain (GstPad *pad, GstBuffer *buf)
914 LADSPA_Descriptor *desc;
915 LADSPA_Data *data_in, **data_out = NULL;
916 GstBuffer **buffers_out = NULL;
918 unsigned long num_samples;
919 guint num_to_process, num_processed, i, numsrcpads;
922 GstLADSPAClass *oclass;
924 g_return_if_fail(pad != NULL);
925 g_return_if_fail(GST_IS_PAD(pad));
926 g_return_if_fail(buf != NULL);
928 ladspa = (GstLADSPA *)gst_pad_get_parent (pad);
929 g_return_if_fail(ladspa != NULL);
931 /* this might happen if caps nego hasn't happened */
932 g_return_if_fail(ladspa->handle != NULL);
934 oclass = (GstLADSPAClass *) (G_OBJECT_GET_CLASS (ladspa));
936 if (GST_IS_EVENT (buf)) {
937 /* push the event out all the src pads */
938 for (i=0 ; i<oclass->numsrcpads ; i++){
939 gst_pad_push (ladspa->srcpads[0], buf);
944 data_in = (LADSPA_Data *) GST_BUFFER_DATA(buf);
945 num_samples = GST_BUFFER_SIZE(buf) / sizeof(gfloat);
946 numsrcpads = oclass->numsrcpads;
948 desc = ladspa->descriptor;
951 guint num_created_buffers = 0;
952 buffers_out = g_new(GstBuffer*, numsrcpads);
953 data_out = g_new(LADSPA_Data*, numsrcpads);
955 if (ladspa->inplace_broken){
956 num_created_buffers = numsrcpads;
959 /* we can share the buffer for input and output */
960 buffers_out[0] = buf;
961 data_out[0] = (LADSPA_Data *)GST_BUFFER_DATA(buf);
962 num_created_buffers = numsrcpads - 1;
965 if (num_created_buffers > 0){
966 ladspa->bufpool = gst_buffer_pool_get_default (sizeof (LADSPA_Data) * GST_BUFFER_SIZE(buf), ladspa->numbuffers);
968 for (i = numsrcpads - num_created_buffers ; i<numsrcpads ; i++){
969 buffers_out[i] = gst_buffer_new_from_pool (ladspa->bufpool, 0, 0);
970 GST_BUFFER_TIMESTAMP(buffers_out[i]) = GST_BUFFER_TIMESTAMP(buf);
971 data_out[i] = (LADSPA_Data *) GST_BUFFER_DATA(buffers_out[i]);
976 GST_DPMAN_PREPROCESS(ladspa->dpman, num_samples, GST_BUFFER_TIMESTAMP(buf));
979 /* split up processing of the buffer into chunks so that dparams can
980 * be updated when required.
981 * In many cases the buffer will be processed in one chunk anyway.
983 while(GST_DPMAN_PROCESS(ladspa->dpman, num_processed)) {
984 num_to_process = GST_DPMAN_FRAMES_TO_PROCESS(ladspa->dpman);
986 desc->connect_port(ladspa->handle,oclass->sinkpad_portnums[0],data_in);
987 for (i=0 ; i<numsrcpads ; i++){
988 desc->connect_port(ladspa->handle,oclass->srcpad_portnums[i],data_out[i]);
990 desc->run(ladspa->handle, num_to_process);
992 data_in += num_to_process;
993 for (i=0 ; i<numsrcpads ; i++){
994 data_out[i] += num_to_process;
996 num_processed += num_to_process;
1000 for (i=0 ; i<numsrcpads ; i++){
1001 gst_pad_push (ladspa->srcpads[i], buffers_out[i]);
1003 g_free(buffers_out);
1008 /* if we have reached here, there are no src pads */
1009 gst_buffer_unref(buf);
1013 gst_ladspa_get(GstPad *pad)
1016 GstLADSPAClass *oclass;
1020 LADSPA_Descriptor *desc;
1022 guint num_to_process, num_processed;
1024 g_return_val_if_fail(pad != NULL, NULL);
1025 g_return_val_if_fail(GST_IS_PAD(pad), NULL);
1027 ladspa = (GstLADSPA *)gst_pad_get_parent (pad);
1028 g_return_val_if_fail(ladspa != NULL, NULL);
1030 /* this might happen if caps nego hasn't happened */
1031 g_return_val_if_fail(ladspa->handle != NULL, NULL);
1033 oclass = (GstLADSPAClass*)(G_OBJECT_GET_CLASS(ladspa));
1035 /* force src pad to set caps */
1036 if (ladspa->newcaps) {
1037 gst_ladspa_force_src_caps(ladspa, ladspa->srcpads[0]);
1040 /* get a bufferpool */
1041 if (ladspa->bufpool == NULL) {
1042 ladspa->bufpool = gst_pad_get_bufferpool (ladspa->srcpads[0]);
1043 if (ladspa->bufpool == NULL) {
1044 ladspa->bufpool = gst_buffer_pool_get_default (sizeof (LADSPA_Data) * ladspa->buffersize, ladspa->numbuffers);
1048 buf = gst_buffer_new_from_pool (ladspa->bufpool, 0, 0);
1049 GST_BUFFER_TIMESTAMP(buf) = ladspa->timestamp;
1050 data = (LADSPA_Data *) GST_BUFFER_DATA(buf);
1052 desc = ladspa->descriptor;
1053 GST_DPMAN_PREPROCESS(ladspa->dpman, GST_BUFFER_SIZE (buf) / sizeof (gfloat), ladspa->timestamp);
1056 /* split up processing of the buffer into chunks so that dparams can
1057 * be updated when required.
1058 * In many cases the buffer will be processed in one chunk anyway.
1060 while(GST_DPMAN_PROCESS(ladspa->dpman, num_processed)) {
1061 num_to_process = GST_DPMAN_FRAMES_TO_PROCESS(ladspa->dpman);
1063 /* update timestamp */
1064 ladspa->timestamp += num_to_process * GST_SECOND / ladspa->samplerate;
1066 desc->connect_port(ladspa->handle,oclass->srcpad_portnums[0],data);
1067 desc->run(ladspa->handle, num_to_process);
1069 data += num_to_process;
1070 num_processed = num_to_process;
1077 ladspa_describe_plugin(const char *pcFullFilename,
1078 void *pvPluginHandle,
1079 LADSPA_Descriptor_Function pfDescriptorFunction)
1081 const LADSPA_Descriptor *desc;
1084 GstElementDetails *details;
1085 GTypeInfo typeinfo = {
1086 sizeof(GstLADSPAClass),
1089 (GClassInitFunc)gst_ladspa_class_init,
1094 (GInstanceInitFunc)gst_ladspa_init,
1097 GstElementFactory *factory;
1099 /* walk through all the plugins in this pluginlibrary */
1101 while ((desc = pfDescriptorFunction(i++))) {
1104 /* construct the type */
1105 type_name = g_strdup_printf("ladspa_%s",desc->Label);
1106 g_strcanon (type_name, G_CSET_A_2_Z G_CSET_a_2_z G_CSET_DIGITS "-_+", '-');
1107 /* if it's already registered, drop it */
1108 if (g_type_from_name(type_name)) {
1112 /* create the type now */
1113 type = g_type_register_static(GST_TYPE_ELEMENT, type_name, &typeinfo, 0);
1115 /* construct the element details struct */
1116 details = g_new0(GstElementDetails,1);
1117 details->longname = g_strdup(desc->Name);
1118 details->klass = "Filter/Audio/LADSPA";
1119 details->license = "LGPL";
1120 details->description = details->longname;
1121 details->version = g_strdup_printf("%ld",desc->UniqueID);
1122 details->author = g_strdup(desc->Maker);
1123 details->copyright = g_strdup(desc->Copyright);
1125 /* register the plugin with gstreamer */
1126 factory = gst_element_factory_new(type_name,type,details);
1127 g_return_if_fail(factory != NULL);
1128 gst_plugin_add_feature (ladspa_plugin, GST_PLUGIN_FEATURE (factory));
1130 /* add this plugin to the hash */
1131 g_hash_table_insert(ladspa_descriptors,
1132 GINT_TO_POINTER(type),
1136 /* only add sink padtemplate if there are sinkpads */
1137 for (j=0;j<desc->PortCount;j++) {
1138 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[j]) &&
1139 LADSPA_IS_PORT_INPUT(desc->PortDescriptors[j])) {
1140 sinktempl = ladspa_sink_factory();
1141 gst_element_factory_add_pad_template (factory, sinktempl);
1146 /* only add src padtemplate if there are srcpads */
1147 for (j=0;j<desc->PortCount;j++) {
1148 if (LADSPA_IS_PORT_AUDIO(desc->PortDescriptors[j]) &&
1149 LADSPA_IS_PORT_OUTPUT(desc->PortDescriptors[j])) {
1150 srctempl = ladspa_src_factory();
1151 gst_element_factory_add_pad_template (factory, srctempl);
1160 plugin_init (GModule *module, GstPlugin *plugin)
1162 ladspa_descriptors = g_hash_table_new(NULL,NULL);
1163 parent_class = g_type_class_ref(GST_TYPE_ELEMENT);
1165 ladspa_plugin = plugin;
1167 LADSPAPluginSearch(ladspa_describe_plugin);
1169 if (! gst_library_load ("gstbytestream"))
1172 /* initialize dparam support library */
1173 gst_control_init(NULL,NULL);
1178 GstPluginDesc plugin_desc = {