1 /* GSequencer - Advanced GTK Sequencer
2  * Copyright (C) 2005-2021 Joël Krähemann
3  *
4  * This file is part of GSequencer.
5  *
6  * GSequencer is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * GSequencer is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with GSequencer.  If not, see <http://www.gnu.org/licenses/>.
18  */
19 
20 #include <ags/audio/fx/ags_fx_two_pass_aliase_channel.h>
21 
22 #include <ags/plugin/ags_plugin_port.h>
23 
24 #include <ags/audio/ags_audio_signal.h>
25 
26 #include <ags/i18n.h>
27 
28 void ags_fx_two_pass_aliase_channel_class_init(AgsFxTwoPassAliaseChannelClass *fx_two_pass_aliase_channel);
29 void ags_fx_two_pass_aliase_channel_init(AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel);
30 void ags_fx_two_pass_aliase_channel_set_property(GObject *gobject,
31 						 guint prop_id,
32 						 const GValue *value,
33 						 GParamSpec *param_spec);
34 void ags_fx_two_pass_aliase_channel_get_property(GObject *gobject,
35 						 guint prop_id,
36 						 GValue *value,
37 						 GParamSpec *param_spec);
38 void ags_fx_two_pass_aliase_channel_dispose(GObject *gobject);
39 void ags_fx_two_pass_aliase_channel_finalize(GObject *gobject);
40 
41 void ags_fx_two_pass_aliase_channel_notify_buffer_size_callback(GObject *gobject,
42 								GParamSpec *pspec,
43 								gpointer user_data);
44 
45 static AgsPluginPort* ags_fx_two_pass_aliase_channel_get_enabled_plugin_port();
46 static AgsPluginPort* ags_fx_two_pass_aliase_channel_get_a_amount_plugin_port();
47 static AgsPluginPort* ags_fx_two_pass_aliase_channel_get_a_phase_plugin_port();
48 static AgsPluginPort* ags_fx_two_pass_aliase_channel_get_b_amount_plugin_port();
49 static AgsPluginPort* ags_fx_two_pass_aliase_channel_get_b_phase_plugin_port();
50 
51 /**
52  * SECTION:ags_fx_two_pass_aliase_channel
53  * @short_description: fx two pass aliase channel
54  * @title: AgsFxTwoPassAliaseChannel
55  * @section_id:
56  * @include: ags/audio/fx/ags_fx_two_pass_aliase_channel.h
57  *
58  * The #AgsFxTwoPassAliaseChannel class provides ports to the effect processor.
59  */
60 
61 static gpointer ags_fx_two_pass_aliase_channel_parent_class = NULL;
62 
63 const gchar *ags_fx_two_pass_aliase_channel_plugin_name = "ags-fx-two-pass-aliase";
64 
65 const gchar* ags_fx_two_pass_aliase_channel_specifier[] = {
66   "./enabled[0]",
67   "./a-amount[0]",
68   "./a-phase[0]",
69   "./b-amount[0]",
70   "./b-phase[0]",
71   NULL,
72 };
73 
74 const gchar* ags_fx_two_pass_aliase_channel_control_port[] = {
75   "1/5",
76   "2/5",
77   "3/5",
78   "4/5",
79   "5/5",
80   NULL,
81 };
82 
83 enum{
84   PROP_0,
85   PROP_ENABLED,
86   PROP_A_AMOUNT,
87   PROP_A_PHASE,
88   PROP_B_AMOUNT,
89   PROP_B_PHASE,
90 };
91 
92 GType
ags_fx_two_pass_aliase_channel_get_type()93 ags_fx_two_pass_aliase_channel_get_type()
94 {
95   static volatile gsize g_define_type_id__volatile = 0;
96 
97   if(g_once_init_enter (&g_define_type_id__volatile)){
98     GType ags_type_fx_two_pass_aliase_channel = 0;
99 
100     static const GTypeInfo ags_fx_two_pass_aliase_channel_info = {
101       sizeof (AgsFxTwoPassAliaseChannelClass),
102       NULL, /* base_init */
103       NULL, /* base_finalize */
104       (GClassInitFunc) ags_fx_two_pass_aliase_channel_class_init,
105       NULL, /* class_finalize */
106       NULL, /* class_channel */
107       sizeof (AgsFxTwoPassAliaseChannel),
108       0,    /* n_preallocs */
109       (GInstanceInitFunc) ags_fx_two_pass_aliase_channel_init,
110     };
111 
112     ags_type_fx_two_pass_aliase_channel = g_type_register_static(AGS_TYPE_RECALL_CHANNEL,
113 								 "AgsFxTwoPassAliaseChannel",
114 								 &ags_fx_two_pass_aliase_channel_info,
115 								 0);
116 
117     g_once_init_leave(&g_define_type_id__volatile, ags_type_fx_two_pass_aliase_channel);
118   }
119 
120   return g_define_type_id__volatile;
121 }
122 
123 void
ags_fx_two_pass_aliase_channel_class_init(AgsFxTwoPassAliaseChannelClass * fx_two_pass_aliase_channel)124 ags_fx_two_pass_aliase_channel_class_init(AgsFxTwoPassAliaseChannelClass *fx_two_pass_aliase_channel)
125 {
126   GObjectClass *gobject;
127 
128   GParamSpec *param_spec;
129 
130   ags_fx_two_pass_aliase_channel_parent_class = g_type_class_peek_parent(fx_two_pass_aliase_channel);
131 
132   /* GObjectClass */
133   gobject = (GObjectClass *) fx_two_pass_aliase_channel;
134 
135   gobject->set_property = ags_fx_two_pass_aliase_channel_set_property;
136   gobject->get_property = ags_fx_two_pass_aliase_channel_get_property;
137 
138   gobject->dispose = ags_fx_two_pass_aliase_channel_dispose;
139   gobject->finalize = ags_fx_two_pass_aliase_channel_finalize;
140 
141   /* properties */
142   /**
143    * AgsFxTwoPassAliaseChannel:enabled:
144    *
145    * The enable control of two pass aliase.
146    *
147    * Since: 3.8.0
148    */
149   param_spec = g_param_spec_object("enabled",
150 				   i18n_pspec("two pass aliase enabled"),
151 				   i18n_pspec("The enabled port to control two pass aliase"),
152 				   AGS_TYPE_PORT,
153 				   G_PARAM_READABLE | G_PARAM_WRITABLE);
154   g_object_class_install_property(gobject,
155 				  PROP_ENABLED,
156 				  param_spec);
157 
158   /**
159    * AgsFxTwoPassAliaseChannel:a-amount:
160    *
161    * The first pass amount.
162    *
163    * Since: 3.8.0
164    */
165   param_spec = g_param_spec_object("a-amount",
166 				   i18n_pspec("a's amount"),
167 				   i18n_pspec("The amount of a"),
168 				   AGS_TYPE_PORT,
169 				   G_PARAM_READABLE | G_PARAM_WRITABLE);
170   g_object_class_install_property(gobject,
171 				  PROP_A_AMOUNT,
172 				  param_spec);
173 
174   /**
175    * AgsFxTwoPassAliaseChannel:a-phase:
176    *
177    * The first pass phase.
178    *
179    * Since: 3.8.0
180    */
181   param_spec = g_param_spec_object("a-phase",
182 				   i18n_pspec("a's phase"),
183 				   i18n_pspec("The phase of a"),
184 				   AGS_TYPE_PORT,
185 				   G_PARAM_READABLE | G_PARAM_WRITABLE);
186   g_object_class_install_property(gobject,
187 				  PROP_A_PHASE,
188 				  param_spec);
189 
190   /**
191    * AgsFxTwoPassAliaseChannel:b-amount:
192    *
193    * The second pass amount.
194    *
195    * Since: 3.8.0
196    */
197   param_spec = g_param_spec_object("b-amount",
198 				   i18n_pspec("b's amount"),
199 				   i18n_pspec("The amount of b"),
200 				   AGS_TYPE_PORT,
201 				   G_PARAM_READABLE | G_PARAM_WRITABLE);
202   g_object_class_install_property(gobject,
203 				  PROP_B_AMOUNT,
204 				  param_spec);
205 
206   /**
207    * AgsFxTwoPassAliaseChannel:b-phase:
208    *
209    * The second pass phase.
210    *
211    * Since: 3.8.0
212    */
213   param_spec = g_param_spec_object("b-phase",
214 				   i18n_pspec("b's phase"),
215 				   i18n_pspec("The phase of b"),
216 				   AGS_TYPE_PORT,
217 				   G_PARAM_READABLE | G_PARAM_WRITABLE);
218   g_object_class_install_property(gobject,
219 				  PROP_B_PHASE,
220 				  param_spec);
221 }
222 
223 void
ags_fx_two_pass_aliase_channel_init(AgsFxTwoPassAliaseChannel * fx_two_pass_aliase_channel)224 ags_fx_two_pass_aliase_channel_init(AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel)
225 {
226   guint buffer_size;
227   guint i;
228 
229   g_signal_connect(fx_two_pass_aliase_channel, "notify::buffer-size",
230 		   G_CALLBACK(ags_fx_two_pass_aliase_channel_notify_buffer_size_callback), NULL);
231 
232   AGS_RECALL(fx_two_pass_aliase_channel)->name = "ags-fx-two-pass-aliase";
233   AGS_RECALL(fx_two_pass_aliase_channel)->version = AGS_RECALL_DEFAULT_VERSION;
234   AGS_RECALL(fx_two_pass_aliase_channel)->build_id = AGS_RECALL_DEFAULT_BUILD_ID;
235   AGS_RECALL(fx_two_pass_aliase_channel)->xml_type = "ags-fx-two-pass-aliase-channel";
236 
237   buffer_size = AGS_SOUNDCARD_DEFAULT_BUFFER_SIZE;
238 
239   g_object_get(fx_two_pass_aliase_channel,
240 	       "buffer-size", &buffer_size,
241 	       NULL);
242 
243   /* enabled */
244   fx_two_pass_aliase_channel->enabled = g_object_new(AGS_TYPE_PORT,
245 						     "plugin-name", ags_fx_two_pass_aliase_channel_plugin_name,
246 						     "specifier", ags_fx_two_pass_aliase_channel_specifier[0],
247 						     "control-port", ags_fx_two_pass_aliase_channel_control_port[0],
248 						     "port-value-is-pointer", FALSE,
249 						     "port-value-type", G_TYPE_FLOAT,
250 						     "port-value-size", sizeof(gfloat),
251 						     "port-value-length", 1,
252 						     NULL);
253 
254   fx_two_pass_aliase_channel->enabled->port_value.ags_port_float = (gfloat) FALSE;
255 
256   g_object_set(fx_two_pass_aliase_channel->enabled,
257 	       "plugin-port", ags_fx_two_pass_aliase_channel_get_enabled_plugin_port(),
258 	       NULL);
259 
260   ags_recall_add_port((AgsRecall *) fx_two_pass_aliase_channel,
261 		      fx_two_pass_aliase_channel->enabled);
262 
263   /* a amount */
264   fx_two_pass_aliase_channel->a_amount = g_object_new(AGS_TYPE_PORT,
265 						      "plugin-name", ags_fx_two_pass_aliase_channel_plugin_name,
266 						      "specifier", ags_fx_two_pass_aliase_channel_specifier[0],
267 						      "control-port", ags_fx_two_pass_aliase_channel_control_port[0],
268 						      "port-value-is-pointer", FALSE,
269 						      "port-value-type", G_TYPE_FLOAT,
270 						      "port-value-size", sizeof(gfloat),
271 						      "port-value-length", 1,
272 						      NULL);
273 
274   fx_two_pass_aliase_channel->a_amount->port_value.ags_port_float = 0.0;
275 
276   g_object_set(fx_two_pass_aliase_channel->a_amount,
277 	       "plugin-port", ags_fx_two_pass_aliase_channel_get_a_amount_plugin_port(),
278 	       NULL);
279 
280   ags_recall_add_port((AgsRecall *) fx_two_pass_aliase_channel,
281 		      fx_two_pass_aliase_channel->a_amount);
282 
283   /* a phase */
284   fx_two_pass_aliase_channel->a_phase = g_object_new(AGS_TYPE_PORT,
285 						     "plugin-name", ags_fx_two_pass_aliase_channel_plugin_name,
286 						     "specifier", ags_fx_two_pass_aliase_channel_specifier[0],
287 						     "control-port", ags_fx_two_pass_aliase_channel_control_port[0],
288 						     "port-value-is-pointer", FALSE,
289 						     "port-value-type", G_TYPE_FLOAT,
290 						     "port-value-size", sizeof(gfloat),
291 						     "port-value-length", 1,
292 						     NULL);
293 
294   fx_two_pass_aliase_channel->a_phase->port_value.ags_port_float = 0.0;
295 
296   g_object_set(fx_two_pass_aliase_channel->a_phase,
297 	       "plugin-port", ags_fx_two_pass_aliase_channel_get_a_phase_plugin_port(),
298 	       NULL);
299 
300   ags_recall_add_port((AgsRecall *) fx_two_pass_aliase_channel,
301 		      fx_two_pass_aliase_channel->a_phase);
302 
303 
304   /* b amount */
305   fx_two_pass_aliase_channel->b_amount = g_object_new(AGS_TYPE_PORT,
306 						      "plugin-name", ags_fx_two_pass_aliase_channel_plugin_name,
307 						      "specifier", ags_fx_two_pass_aliase_channel_specifier[0],
308 						      "control-port", ags_fx_two_pass_aliase_channel_control_port[0],
309 						      "port-value-is-pointer", FALSE,
310 						      "port-value-type", G_TYPE_FLOAT,
311 						      "port-value-size", sizeof(gfloat),
312 						      "port-value-length", 1,
313 						      NULL);
314 
315   fx_two_pass_aliase_channel->b_amount->port_value.ags_port_float = 0.0;
316 
317   g_object_set(fx_two_pass_aliase_channel->b_amount,
318 	       "plugin-port", ags_fx_two_pass_aliase_channel_get_b_amount_plugin_port(),
319 	       NULL);
320 
321   ags_recall_add_port((AgsRecall *) fx_two_pass_aliase_channel,
322 		      fx_two_pass_aliase_channel->b_amount);
323 
324   /* b phase */
325   fx_two_pass_aliase_channel->b_phase = g_object_new(AGS_TYPE_PORT,
326 						     "plugin-name", ags_fx_two_pass_aliase_channel_plugin_name,
327 						     "specifier", ags_fx_two_pass_aliase_channel_specifier[0],
328 						     "control-port", ags_fx_two_pass_aliase_channel_control_port[0],
329 						     "port-value-is-pointer", FALSE,
330 						     "port-value-type", G_TYPE_FLOAT,
331 						     "port-value-size", sizeof(gfloat),
332 						     "port-value-length", 1,
333 						     NULL);
334 
335   fx_two_pass_aliase_channel->b_phase->port_value.ags_port_float = 0.0;
336 
337   g_object_set(fx_two_pass_aliase_channel->b_phase,
338 	       "plugin-port", ags_fx_two_pass_aliase_channel_get_b_phase_plugin_port(),
339 	       NULL);
340 
341   ags_recall_add_port((AgsRecall *) fx_two_pass_aliase_channel,
342 		      fx_two_pass_aliase_channel->b_phase);
343 
344 
345   /* input data */
346   for(i = 0; i < AGS_SOUND_SCOPE_LAST; i++){
347     fx_two_pass_aliase_channel->input_data[i] = ags_fx_two_pass_aliase_channel_input_data_alloc();
348 
349     fx_two_pass_aliase_channel->input_data[i]->parent = fx_two_pass_aliase_channel;
350 
351     fx_two_pass_aliase_channel->input_data[i]->orig_buffer = (gdouble *) ags_stream_alloc(buffer_size,
352 											  AGS_SOUNDCARD_DOUBLE);
353 
354     fx_two_pass_aliase_channel->input_data[i]->a_buffer = (gdouble *) ags_stream_alloc(buffer_size,
355 										       AGS_SOUNDCARD_DOUBLE);
356     fx_two_pass_aliase_channel->input_data[i]->b_buffer = (gdouble *) ags_stream_alloc(buffer_size,
357 										       AGS_SOUNDCARD_DOUBLE);
358 
359     fx_two_pass_aliase_channel->input_data[i]->a_mix = (gdouble *) ags_stream_alloc(buffer_size,
360 										    AGS_SOUNDCARD_DOUBLE);
361     fx_two_pass_aliase_channel->input_data[i]->b_mix = (gdouble *) ags_stream_alloc(buffer_size,
362 										    AGS_SOUNDCARD_DOUBLE);
363 
364     fx_two_pass_aliase_channel->input_data[i]->final_mix = (gdouble *) ags_stream_alloc(buffer_size,
365 											AGS_SOUNDCARD_DOUBLE);
366   }
367 }
368 
369 void
ags_fx_two_pass_aliase_channel_set_property(GObject * gobject,guint prop_id,const GValue * value,GParamSpec * param_spec)370 ags_fx_two_pass_aliase_channel_set_property(GObject *gobject,
371 					    guint prop_id,
372 					    const GValue *value,
373 					    GParamSpec *param_spec)
374 {
375   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
376 
377   GRecMutex *recall_mutex;
378 
379   fx_two_pass_aliase_channel = AGS_FX_TWO_PASS_ALIASE_CHANNEL(gobject);
380 
381   /* get recall mutex */
382   recall_mutex = AGS_RECALL_GET_OBJ_MUTEX(fx_two_pass_aliase_channel);
383 
384   switch(prop_id){
385   case PROP_ENABLED:
386   {
387     AgsPort *port;
388 
389     port = (AgsPort *) g_value_get_object(value);
390 
391     g_rec_mutex_lock(recall_mutex);
392 
393     if(port == fx_two_pass_aliase_channel->enabled){
394       g_rec_mutex_unlock(recall_mutex);
395 
396       return;
397     }
398 
399     if(fx_two_pass_aliase_channel->enabled != NULL){
400       g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->enabled));
401     }
402 
403     if(port != NULL){
404       g_object_ref(G_OBJECT(port));
405     }
406 
407     fx_two_pass_aliase_channel->enabled = port;
408 
409     g_rec_mutex_unlock(recall_mutex);
410   }
411   break;
412   case PROP_A_AMOUNT:
413   {
414     AgsPort *port;
415 
416     port = (AgsPort *) g_value_get_object(value);
417 
418     g_rec_mutex_lock(recall_mutex);
419 
420     if(port == fx_two_pass_aliase_channel->a_amount){
421       g_rec_mutex_unlock(recall_mutex);
422 
423       return;
424     }
425 
426     if(fx_two_pass_aliase_channel->a_amount != NULL){
427       g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_amount));
428     }
429 
430     if(port != NULL){
431       g_object_ref(G_OBJECT(port));
432     }
433 
434     fx_two_pass_aliase_channel->a_amount = port;
435 
436     g_rec_mutex_unlock(recall_mutex);
437   }
438   break;
439   case PROP_A_PHASE:
440   {
441     AgsPort *port;
442 
443     port = (AgsPort *) g_value_get_object(value);
444 
445     g_rec_mutex_lock(recall_mutex);
446 
447     if(port == fx_two_pass_aliase_channel->a_phase){
448       g_rec_mutex_unlock(recall_mutex);
449 
450       return;
451     }
452 
453     if(fx_two_pass_aliase_channel->a_phase != NULL){
454       g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_phase));
455     }
456 
457     if(port != NULL){
458       g_object_ref(G_OBJECT(port));
459     }
460 
461     fx_two_pass_aliase_channel->a_phase = port;
462 
463     g_rec_mutex_unlock(recall_mutex);
464   }
465   break;
466   case PROP_B_AMOUNT:
467   {
468     AgsPort *port;
469 
470     port = (AgsPort *) g_value_get_object(value);
471 
472     g_rec_mutex_lock(recall_mutex);
473 
474     if(port == fx_two_pass_aliase_channel->b_amount){
475       g_rec_mutex_unlock(recall_mutex);
476 
477       return;
478     }
479 
480     if(fx_two_pass_aliase_channel->b_amount != NULL){
481       g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_amount));
482     }
483 
484     if(port != NULL){
485       g_object_ref(G_OBJECT(port));
486     }
487 
488     fx_two_pass_aliase_channel->b_amount = port;
489 
490     g_rec_mutex_unlock(recall_mutex);
491   }
492   break;
493   case PROP_B_PHASE:
494   {
495     AgsPort *port;
496 
497     port = (AgsPort *) g_value_get_object(value);
498 
499     g_rec_mutex_lock(recall_mutex);
500 
501     if(port == fx_two_pass_aliase_channel->b_phase){
502       g_rec_mutex_unlock(recall_mutex);
503 
504       return;
505     }
506 
507     if(fx_two_pass_aliase_channel->b_phase != NULL){
508       g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_phase));
509     }
510 
511     if(port != NULL){
512       g_object_ref(G_OBJECT(port));
513     }
514 
515     fx_two_pass_aliase_channel->b_phase = port;
516 
517     g_rec_mutex_unlock(recall_mutex);
518   }
519   break;
520   default:
521     G_OBJECT_WARN_INVALID_PROPERTY_ID(gobject, prop_id, param_spec);
522     break;
523   }
524 }
525 
526 void
ags_fx_two_pass_aliase_channel_get_property(GObject * gobject,guint prop_id,GValue * value,GParamSpec * param_spec)527 ags_fx_two_pass_aliase_channel_get_property(GObject *gobject,
528 					    guint prop_id,
529 					    GValue *value,
530 					    GParamSpec *param_spec)
531 {
532   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
533 
534   GRecMutex *recall_mutex;
535 
536   fx_two_pass_aliase_channel = AGS_FX_TWO_PASS_ALIASE_CHANNEL(gobject);
537 
538   /* get recall mutex */
539   recall_mutex = AGS_RECALL_GET_OBJ_MUTEX(fx_two_pass_aliase_channel);
540 
541   switch(prop_id){
542   case PROP_ENABLED:
543   {
544     g_rec_mutex_lock(recall_mutex);
545 
546     g_value_set_object(value, fx_two_pass_aliase_channel->enabled);
547 
548     g_rec_mutex_unlock(recall_mutex);
549   }
550   break;
551   case PROP_A_AMOUNT:
552   {
553     g_rec_mutex_lock(recall_mutex);
554 
555     g_value_set_object(value, fx_two_pass_aliase_channel->a_amount);
556 
557     g_rec_mutex_unlock(recall_mutex);
558   }
559   break;
560   case PROP_A_PHASE:
561   {
562     g_rec_mutex_lock(recall_mutex);
563 
564     g_value_set_object(value, fx_two_pass_aliase_channel->a_phase);
565 
566     g_rec_mutex_unlock(recall_mutex);
567   }
568   break;
569   case PROP_B_AMOUNT:
570   {
571     g_rec_mutex_lock(recall_mutex);
572 
573     g_value_set_object(value, fx_two_pass_aliase_channel->b_amount);
574 
575     g_rec_mutex_unlock(recall_mutex);
576   }
577   break;
578   case PROP_B_PHASE:
579   {
580     g_rec_mutex_lock(recall_mutex);
581 
582     g_value_set_object(value, fx_two_pass_aliase_channel->b_phase);
583 
584     g_rec_mutex_unlock(recall_mutex);
585   }
586   break;
587   default:
588     G_OBJECT_WARN_INVALID_PROPERTY_ID(gobject, prop_id, param_spec);
589     break;
590   }
591 }
592 
593 void
ags_fx_two_pass_aliase_channel_dispose(GObject * gobject)594 ags_fx_two_pass_aliase_channel_dispose(GObject *gobject)
595 {
596   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
597 
598   fx_two_pass_aliase_channel = AGS_FX_TWO_PASS_ALIASE_CHANNEL(gobject);
599 
600   /* enabled */
601   if(fx_two_pass_aliase_channel->enabled != NULL){
602     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->enabled));
603 
604     fx_two_pass_aliase_channel->enabled = NULL;
605   }
606 
607   /* a amount */
608   if(fx_two_pass_aliase_channel->a_amount != NULL){
609     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_amount));
610 
611     fx_two_pass_aliase_channel->a_amount = NULL;
612   }
613 
614   /* a phase */
615   if(fx_two_pass_aliase_channel->a_phase != NULL){
616     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_phase));
617 
618     fx_two_pass_aliase_channel->a_phase = NULL;
619   }
620 
621   /* b amount */
622   if(fx_two_pass_aliase_channel->b_amount != NULL){
623     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_amount));
624 
625     fx_two_pass_aliase_channel->b_amount = NULL;
626   }
627 
628   /* b phase */
629   if(fx_two_pass_aliase_channel->b_phase != NULL){
630     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_phase));
631 
632     fx_two_pass_aliase_channel->b_phase = NULL;
633   }
634 
635   /* call parent */
636   G_OBJECT_CLASS(ags_fx_two_pass_aliase_channel_parent_class)->dispose(gobject);
637 }
638 
639 void
ags_fx_two_pass_aliase_channel_finalize(GObject * gobject)640 ags_fx_two_pass_aliase_channel_finalize(GObject *gobject)
641 {
642   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
643 
644   guint i;
645 
646   fx_two_pass_aliase_channel = AGS_FX_TWO_PASS_ALIASE_CHANNEL(gobject);
647 
648   /* enabled */
649   if(fx_two_pass_aliase_channel->enabled != NULL){
650     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->enabled));
651   }
652 
653   /* a amount */
654   if(fx_two_pass_aliase_channel->a_amount != NULL){
655     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_amount));
656   }
657 
658   /* a phase */
659   if(fx_two_pass_aliase_channel->a_phase != NULL){
660     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->a_phase));
661   }
662 
663   /* b amount */
664   if(fx_two_pass_aliase_channel->b_amount != NULL){
665     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_amount));
666   }
667 
668   /* b phase */
669   if(fx_two_pass_aliase_channel->b_phase != NULL){
670     g_object_unref(G_OBJECT(fx_two_pass_aliase_channel->b_phase));
671   }
672 
673   /* input data */
674   for(i = 0; i < AGS_SOUND_SCOPE_LAST; i++){
675     ags_fx_two_pass_aliase_channel_input_data_free(fx_two_pass_aliase_channel->input_data[i]);
676   }
677 
678   /* call parent */
679   G_OBJECT_CLASS(ags_fx_two_pass_aliase_channel_parent_class)->finalize(gobject);
680 }
681 
682 static AgsPluginPort*
ags_fx_two_pass_aliase_channel_get_enabled_plugin_port()683 ags_fx_two_pass_aliase_channel_get_enabled_plugin_port()
684 {
685   static AgsPluginPort *plugin_port = NULL;
686 
687   static GMutex mutex;
688 
689   g_mutex_lock(&mutex);
690 
691   if(plugin_port == NULL){
692     plugin_port = ags_plugin_port_new();
693     g_object_ref(plugin_port);
694 
695     plugin_port->flags |= (AGS_PLUGIN_PORT_INPUT |
696 			   AGS_PLUGIN_PORT_CONTROL |
697 			   AGS_PLUGIN_PORT_TOGGLED);
698 
699     plugin_port->port_index = 0;
700 
701     /* range */
702     g_value_init(plugin_port->default_value,
703 		 G_TYPE_FLOAT);
704     g_value_init(plugin_port->lower_value,
705 		 G_TYPE_FLOAT);
706     g_value_init(plugin_port->upper_value,
707 		 G_TYPE_FLOAT);
708 
709     g_value_set_float(plugin_port->default_value,
710 		      0.0);
711     g_value_set_float(plugin_port->lower_value,
712 		      0.0);
713     g_value_set_float(plugin_port->upper_value,
714 		      1.0);
715   }
716 
717   g_mutex_unlock(&mutex);
718 
719   return(plugin_port);
720 }
721 
722 static AgsPluginPort*
ags_fx_two_pass_aliase_channel_get_a_amount_plugin_port()723 ags_fx_two_pass_aliase_channel_get_a_amount_plugin_port()
724 {
725   static AgsPluginPort *plugin_port = NULL;
726 
727   static GMutex mutex;
728 
729   g_mutex_lock(&mutex);
730 
731   if(plugin_port == NULL){
732     plugin_port = ags_plugin_port_new();
733     g_object_ref(plugin_port);
734 
735     plugin_port->flags |= (AGS_PLUGIN_PORT_INPUT |
736 			   AGS_PLUGIN_PORT_CONTROL);
737 
738     plugin_port->port_index = 0;
739 
740     /* range */
741     g_value_init(plugin_port->default_value,
742 		 G_TYPE_FLOAT);
743     g_value_init(plugin_port->lower_value,
744 		 G_TYPE_FLOAT);
745     g_value_init(plugin_port->upper_value,
746 		 G_TYPE_FLOAT);
747 
748     g_value_set_float(plugin_port->default_value,
749 		      0.0);
750     g_value_set_float(plugin_port->lower_value,
751 		      0.0);
752     g_value_set_float(plugin_port->upper_value,
753 		      2.0 * M_PI);
754   }
755 
756   g_mutex_unlock(&mutex);
757 
758   return(plugin_port);
759 }
760 
761 static AgsPluginPort*
ags_fx_two_pass_aliase_channel_get_a_phase_plugin_port()762 ags_fx_two_pass_aliase_channel_get_a_phase_plugin_port()
763 {
764   static AgsPluginPort *plugin_port = NULL;
765 
766   static GMutex mutex;
767 
768   g_mutex_lock(&mutex);
769 
770   if(plugin_port == NULL){
771     plugin_port = ags_plugin_port_new();
772     g_object_ref(plugin_port);
773 
774     plugin_port->flags |= (AGS_PLUGIN_PORT_INPUT |
775 			   AGS_PLUGIN_PORT_CONTROL);
776 
777     plugin_port->port_index = 0;
778 
779     /* range */
780     g_value_init(plugin_port->default_value,
781 		 G_TYPE_FLOAT);
782     g_value_init(plugin_port->lower_value,
783 		 G_TYPE_FLOAT);
784     g_value_init(plugin_port->upper_value,
785 		 G_TYPE_FLOAT);
786 
787     g_value_set_float(plugin_port->default_value,
788 		      0.0);
789     g_value_set_float(plugin_port->lower_value,
790 		      0.0);
791     g_value_set_float(plugin_port->upper_value,
792 		      2.0 * M_PI);
793   }
794 
795   g_mutex_unlock(&mutex);
796 
797   return(plugin_port);
798 }
799 
800 static AgsPluginPort*
ags_fx_two_pass_aliase_channel_get_b_amount_plugin_port()801 ags_fx_two_pass_aliase_channel_get_b_amount_plugin_port()
802 {
803   static AgsPluginPort *plugin_port = NULL;
804 
805   static GMutex mutex;
806 
807   g_mutex_lock(&mutex);
808 
809   if(plugin_port == NULL){
810     plugin_port = ags_plugin_port_new();
811     g_object_ref(plugin_port);
812 
813     plugin_port->flags |= (AGS_PLUGIN_PORT_INPUT |
814 			   AGS_PLUGIN_PORT_CONTROL);
815 
816     plugin_port->port_index = 0;
817 
818     /* range */
819     g_value_init(plugin_port->default_value,
820 		 G_TYPE_FLOAT);
821     g_value_init(plugin_port->lower_value,
822 		 G_TYPE_FLOAT);
823     g_value_init(plugin_port->upper_value,
824 		 G_TYPE_FLOAT);
825 
826     g_value_set_float(plugin_port->default_value,
827 		      0.0);
828     g_value_set_float(plugin_port->lower_value,
829 		      0.0);
830     g_value_set_float(plugin_port->upper_value,
831 		      2.0 * M_PI);
832   }
833 
834   g_mutex_unlock(&mutex);
835 
836   return(plugin_port);
837 }
838 
839 static AgsPluginPort*
ags_fx_two_pass_aliase_channel_get_b_phase_plugin_port()840 ags_fx_two_pass_aliase_channel_get_b_phase_plugin_port()
841 {
842   static AgsPluginPort *plugin_port = NULL;
843 
844   static GMutex mutex;
845 
846   g_mutex_lock(&mutex);
847 
848   if(plugin_port == NULL){
849     plugin_port = ags_plugin_port_new();
850     g_object_ref(plugin_port);
851 
852     plugin_port->flags |= (AGS_PLUGIN_PORT_INPUT |
853 			   AGS_PLUGIN_PORT_CONTROL);
854 
855     plugin_port->port_index = 0;
856 
857     /* range */
858     g_value_init(plugin_port->default_value,
859 		 G_TYPE_FLOAT);
860     g_value_init(plugin_port->lower_value,
861 		 G_TYPE_FLOAT);
862     g_value_init(plugin_port->upper_value,
863 		 G_TYPE_FLOAT);
864 
865     g_value_set_float(plugin_port->default_value,
866 		      0.0);
867     g_value_set_float(plugin_port->lower_value,
868 		      0.0);
869     g_value_set_float(plugin_port->upper_value,
870 		      2.0 * M_PI);
871   }
872 
873   g_mutex_unlock(&mutex);
874 
875   return(plugin_port);
876 }
877 
878 void
ags_fx_two_pass_aliase_channel_notify_buffer_size_callback(GObject * gobject,GParamSpec * pspec,gpointer user_data)879 ags_fx_two_pass_aliase_channel_notify_buffer_size_callback(GObject *gobject,
880 							   GParamSpec *pspec,
881 							   gpointer user_data)
882 {
883   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
884 
885   guint buffer_size;
886   guint i;
887 
888   GRecMutex *recall_mutex;
889 
890   fx_two_pass_aliase_channel = AGS_FX_TWO_PASS_ALIASE_CHANNEL(gobject);
891 
892   /* get recall mutex */
893   recall_mutex = AGS_RECALL_GET_OBJ_MUTEX(fx_two_pass_aliase_channel);
894 
895   /* get buffer size */
896   buffer_size = AGS_SOUNDCARD_DEFAULT_BUFFER_SIZE;
897 
898   g_object_get(fx_two_pass_aliase_channel,
899 	       "buffer-size", &buffer_size,
900 	       NULL);
901 
902   /* reallocate buffer - apply buffer size */
903   g_rec_mutex_lock(recall_mutex);
904 
905   for(i = 0; i < AGS_SOUND_SCOPE_LAST; i++){
906     AgsFxTwoPassAliaseChannelInputData *input_data;
907 
908     input_data = fx_two_pass_aliase_channel->input_data[i];
909 
910     /* buffer */
911     ags_stream_free(input_data->orig_buffer);
912 
913     ags_stream_free(input_data->a_buffer);
914     ags_stream_free(input_data->b_buffer);
915 
916     if(buffer_size > 0){
917       input_data->orig_buffer = (gdouble *) ags_stream_alloc(buffer_size,
918 							     AGS_SOUNDCARD_DOUBLE);
919 
920       input_data->a_buffer = (gdouble *) ags_stream_alloc(buffer_size,
921 							  AGS_SOUNDCARD_DOUBLE);
922       input_data->b_buffer = (gdouble *) ags_stream_alloc(buffer_size,
923 							  AGS_SOUNDCARD_DOUBLE);
924 
925       input_data->a_mix = (gdouble *) ags_stream_alloc(buffer_size,
926 						       AGS_SOUNDCARD_DOUBLE);
927       input_data->b_mix = (gdouble *) ags_stream_alloc(buffer_size,
928 						       AGS_SOUNDCARD_DOUBLE);
929 
930       input_data->final_mix = (gdouble *) ags_stream_alloc(buffer_size,
931 							   AGS_SOUNDCARD_DOUBLE);
932     }else{
933       input_data->orig_buffer = NULL;
934 
935       input_data->a_buffer = NULL;
936       input_data->b_buffer = NULL;
937 
938       input_data->a_mix = NULL;
939       input_data->b_mix = NULL;
940 
941       input_data->final_mix = NULL;
942     }
943   }
944 
945   g_rec_mutex_unlock(recall_mutex);
946 }
947 
948 /**
949  * ags_fx_two_pass_aliase_channel_input_data_alloc:
950  *
951  * Allocate #AgsFxTwoPassAliaseChannelInputData-struct
952  *
953  * Returns: (type gpointer) (transfer full): the new #AgsFxTwoPassAliaseChannelInputData-struct
954  *
955  * Since: 3.8.0
956  */
957 AgsFxTwoPassAliaseChannelInputData*
ags_fx_two_pass_aliase_channel_input_data_alloc()958 ags_fx_two_pass_aliase_channel_input_data_alloc()
959 {
960   AgsFxTwoPassAliaseChannelInputData *input_data;
961 
962   input_data = (AgsFxTwoPassAliaseChannelInputData *) g_malloc(sizeof(AgsFxTwoPassAliaseChannelInputData));
963 
964   g_rec_mutex_init(&(input_data->strct_mutex));
965 
966   input_data->parent = NULL;
967 
968   input_data->orig_buffer = NULL;
969 
970   input_data->a_buffer = NULL;
971   input_data->b_buffer = NULL;
972 
973   input_data->a_mix = NULL;
974   input_data->b_mix = NULL;
975 
976   input_data->final_mix = NULL;
977 
978   return(input_data);
979 }
980 
981 /**
982  * ags_fx_two_pass_aliase_channel_input_data_free:
983  * @input_data: (type gpointer) (transfer full): the #AgsFxTwoPassAliaseChannelInputData-struct
984  *
985  * Free @input_data.
986  *
987  * Since: 3.8.0
988  */
989 void
ags_fx_two_pass_aliase_channel_input_data_free(AgsFxTwoPassAliaseChannelInputData * input_data)990 ags_fx_two_pass_aliase_channel_input_data_free(AgsFxTwoPassAliaseChannelInputData *input_data)
991 {
992   if(input_data == NULL){
993     return;
994   }
995 
996   ags_stream_free(input_data->orig_buffer);
997 
998   ags_stream_free(input_data->a_buffer);
999   ags_stream_free(input_data->b_buffer);
1000 
1001   ags_stream_free(input_data->a_mix);
1002   ags_stream_free(input_data->b_mix);
1003 
1004   ags_stream_free(input_data->final_mix);
1005 
1006   g_free(input_data);
1007 }
1008 
1009 /**
1010  * ags_fx_two_pass_aliase_channel_input_data_get_strct_mutex:
1011  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData
1012  *
1013  * Get structure mutex.
1014  *
1015  * Returns: (type gpointer) (transfer none): the #GRecMutex to lock @input_data
1016  *
1017  * Since: 3.8.0
1018  */
1019 GRecMutex*
ags_fx_two_pass_aliase_channel_input_data_get_strct_mutex(AgsFxTwoPassAliaseChannelInputData * input_data)1020 ags_fx_two_pass_aliase_channel_input_data_get_strct_mutex(AgsFxTwoPassAliaseChannelInputData *input_data)
1021 {
1022   if(input_data == NULL){
1023     return(NULL);
1024   }
1025 
1026   return(AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data));
1027 }
1028 
1029 /**
1030  * ags_fx_two_pass_aliase_channel_input_get_parent:
1031  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1032  *
1033  * Get parent of @input_data.
1034  *
1035  * Returns: (type gpointer) (transfer none): the parent
1036  *
1037  * Since: 3.8.0
1038  */
1039 gpointer
ags_fx_two_pass_aliase_channel_input_get_parent(AgsFxTwoPassAliaseChannelInputData * input_data)1040 ags_fx_two_pass_aliase_channel_input_get_parent(AgsFxTwoPassAliaseChannelInputData *input_data)
1041 {
1042   gpointer parent;
1043 
1044   GRecMutex *input_data_mutex;
1045 
1046   if(input_data == NULL){
1047     return(NULL);
1048   }
1049 
1050   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1051 
1052   /* parent */
1053   g_rec_mutex_lock(input_data_mutex);
1054 
1055   parent = input_data->parent;
1056 
1057   g_rec_mutex_unlock(input_data_mutex);
1058 
1059   return(parent);
1060 }
1061 
1062 /**
1063  * ags_fx_two_pass_aliase_channel_input_get_orig_buffer:
1064  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1065  *
1066  * Get orig buffer of @input_data.
1067  *
1068  * Returns: (type gpointer) (transfer none): the orig buffer
1069  *
1070  * Since: 3.8.0
1071  */
1072 gpointer
ags_fx_two_pass_aliase_channel_input_get_orig_buffer(AgsFxTwoPassAliaseChannelInputData * input_data)1073 ags_fx_two_pass_aliase_channel_input_get_orig_buffer(AgsFxTwoPassAliaseChannelInputData *input_data)
1074 {
1075   gpointer orig_buffer;
1076 
1077   GRecMutex *input_data_mutex;
1078 
1079   if(input_data == NULL){
1080     return(NULL);
1081   }
1082 
1083   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1084 
1085   /* orig buffer */
1086   g_rec_mutex_lock(input_data_mutex);
1087 
1088   orig_buffer = input_data->orig_buffer;
1089 
1090   g_rec_mutex_unlock(input_data_mutex);
1091 
1092   return(orig_buffer);
1093 }
1094 
1095 /**
1096  * ags_fx_two_pass_aliase_channel_input_get_a_buffer:
1097  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1098  *
1099  * Get a buffer of @input_data.
1100  *
1101  * Returns: (type gpointer) (transfer none): the a buffer
1102  *
1103  * Since: 3.8.0
1104  */
1105 gpointer
ags_fx_two_pass_aliase_channel_input_get_a_buffer(AgsFxTwoPassAliaseChannelInputData * input_data)1106 ags_fx_two_pass_aliase_channel_input_get_a_buffer(AgsFxTwoPassAliaseChannelInputData *input_data)
1107 {
1108   gpointer a_buffer;
1109 
1110   GRecMutex *input_data_mutex;
1111 
1112   if(input_data == NULL){
1113     return(NULL);
1114   }
1115 
1116   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1117 
1118   /* a buffer */
1119   g_rec_mutex_lock(input_data_mutex);
1120 
1121   a_buffer = input_data->a_buffer;
1122 
1123   g_rec_mutex_unlock(input_data_mutex);
1124 
1125   return(a_buffer);
1126 }
1127 
1128 /**
1129  * ags_fx_two_pass_aliase_channel_input_get_b_buffer:
1130  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1131  *
1132  * Get b buffer of @input_data.
1133  *
1134  * Returns: (type gpointer) (transfer none): the b buffer
1135  *
1136  * Since: 3.8.0
1137  */
1138 gpointer
ags_fx_two_pass_aliase_channel_input_get_b_buffer(AgsFxTwoPassAliaseChannelInputData * input_data)1139 ags_fx_two_pass_aliase_channel_input_get_b_buffer(AgsFxTwoPassAliaseChannelInputData *input_data)
1140 {
1141   gpointer b_buffer;
1142 
1143   GRecMutex *input_data_mutex;
1144 
1145   if(input_data == NULL){
1146     return(NULL);
1147   }
1148 
1149   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1150 
1151   /* b buffer */
1152   g_rec_mutex_lock(input_data_mutex);
1153 
1154   b_buffer = input_data->b_buffer;
1155 
1156   g_rec_mutex_unlock(input_data_mutex);
1157 
1158   return(b_buffer);
1159 }
1160 
1161 /**
1162  * ags_fx_two_pass_aliase_channel_input_get_a_mix:
1163  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1164  *
1165  * Get a mix of @input_data.
1166  *
1167  * Returns: (type gpointer) (transfer none): the a mix
1168  *
1169  * Since: 3.8.0
1170  */
1171 gpointer
ags_fx_two_pass_aliase_channel_input_get_a_mix(AgsFxTwoPassAliaseChannelInputData * input_data)1172 ags_fx_two_pass_aliase_channel_input_get_a_mix(AgsFxTwoPassAliaseChannelInputData *input_data)
1173 {
1174   gpointer a_mix;
1175 
1176   GRecMutex *input_data_mutex;
1177 
1178   if(input_data == NULL){
1179     return(NULL);
1180   }
1181 
1182   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1183 
1184   /* a mix */
1185   g_rec_mutex_lock(input_data_mutex);
1186 
1187   a_mix = input_data->a_mix;
1188 
1189   g_rec_mutex_unlock(input_data_mutex);
1190 
1191   return(a_mix);
1192 }
1193 
1194 /**
1195  * ags_fx_two_pass_aliase_channel_input_get_b_mix:
1196  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1197  *
1198  * Get b mix of @input_data.
1199  *
1200  * Returns: (type gpointer) (transfer none): the b mix
1201  *
1202  * Since: 3.8.0
1203  */
1204 gpointer
ags_fx_two_pass_aliase_channel_input_get_b_mix(AgsFxTwoPassAliaseChannelInputData * input_data)1205 ags_fx_two_pass_aliase_channel_input_get_b_mix(AgsFxTwoPassAliaseChannelInputData *input_data)
1206 {
1207   gpointer b_mix;
1208 
1209   GRecMutex *input_data_mutex;
1210 
1211   if(input_data == NULL){
1212     return(NULL);
1213   }
1214 
1215   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1216 
1217   /* b mix */
1218   g_rec_mutex_lock(input_data_mutex);
1219 
1220   b_mix = input_data->b_mix;
1221 
1222   g_rec_mutex_unlock(input_data_mutex);
1223 
1224   return(b_mix);
1225 }
1226 
1227 /**
1228  * ags_fx_two_pass_aliase_channel_input_get_final_mix:
1229  * @input_data: (type gpointer) (transfer none): the #AgsFxTwoPassAliaseChannelInputData-struct
1230  *
1231  * Get final mix of @input_data.
1232  *
1233  * Returns: (type gpointer) (transfer none): the final mix
1234  *
1235  * Since: 3.8.0
1236  */
1237 gpointer
ags_fx_two_pass_aliase_channel_input_get_final_mix(AgsFxTwoPassAliaseChannelInputData * input_data)1238 ags_fx_two_pass_aliase_channel_input_get_final_mix(AgsFxTwoPassAliaseChannelInputData *input_data)
1239 {
1240   gpointer final_mix;
1241 
1242   GRecMutex *input_data_mutex;
1243 
1244   if(input_data == NULL){
1245     return(NULL);
1246   }
1247 
1248   input_data_mutex = AGS_FX_TWO_PASS_ALIASE_CHANNEL_INPUT_DATA_GET_STRCT_MUTEX(input_data);
1249 
1250   /* final mix */
1251   g_rec_mutex_lock(input_data_mutex);
1252 
1253   final_mix = input_data->final_mix;
1254 
1255   g_rec_mutex_unlock(input_data_mutex);
1256 
1257   return(final_mix);
1258 }
1259 
1260 /**
1261  * ags_fx_two_pass_aliase_channel_new:
1262  * @channel: the #AgsChannel
1263  *
1264  * Create a new instance of #AgsFxTwoPassAliaseChannel
1265  *
1266  * Returns: the new #AgsFxTwoPassAliaseChannel
1267  *
1268  * Since: 3.8.0
1269  */
1270 AgsFxTwoPassAliaseChannel*
ags_fx_two_pass_aliase_channel_new(AgsChannel * channel)1271 ags_fx_two_pass_aliase_channel_new(AgsChannel *channel)
1272 {
1273   AgsFxTwoPassAliaseChannel *fx_two_pass_aliase_channel;
1274 
1275   fx_two_pass_aliase_channel = (AgsFxTwoPassAliaseChannel *) g_object_new(AGS_TYPE_FX_TWO_PASS_ALIASE_CHANNEL,
1276 									  "source", channel,
1277 									  NULL);
1278 
1279   return(fx_two_pass_aliase_channel);
1280 }
1281