annotate libaf/af_extrastereo.c @ 24992:5701e23ebcb4

Better handling of win32 GUI thread: 1. Use _beginthreadex to create the GUI thread to avoid possible memory leak when linked to MS CRT. 2. Terminate the GUI thread in an cleaner way using PostThreadMessage() rather than the unrecommended TerminateThread().
author zuxy
date Sun, 11 Nov 2007 08:14:57 +0000
parents b2402b4f0afa
children 72d0b1444141
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
1 /*=============================================================================
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
2 //
13602
14090f7300a8 The full name of the GPL is GNU General Public License.
diego
parents: 13550
diff changeset
3 // This software has been released under the terms of the GNU General Public
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
4 // license. See http://www.gnu.org/copyleft/gpl.html for details.
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
5 //
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
6 // Copyright 2004 Alex Beregszaszi & Pierre Lombard
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
7 //
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
8 //=============================================================================
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
9 */
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
10
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
11 #include <stdio.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
12 #include <stdlib.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
13 #include <string.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
14
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
15 #include <inttypes.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
16 #include <math.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
17 #include <limits.h>
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
18
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
19 #include "af.h"
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
20
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
21 // Data for specific instances of this filter
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
22 typedef struct af_extrastereo_s
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
23 {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
24 float mul;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
25 }af_extrastereo_t;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
26
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
27 static af_data_t* play_s16(struct af_instance_s* af, af_data_t* data);
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
28 static af_data_t* play_float(struct af_instance_s* af, af_data_t* data);
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
29
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
30 // Initialization and runtime control
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
31 static int control(struct af_instance_s* af, int cmd, void* arg)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
32 {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
33 af_extrastereo_t* s = (af_extrastereo_t*)af->setup;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
34
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
35 switch(cmd){
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
36 case AF_CONTROL_REINIT:{
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
37 // Sanity check
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
38 if(!arg) return AF_ERROR;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
39
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
40 af->data->rate = ((af_data_t*)arg)->rate;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
41 af->data->nch = 2;
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
42 if (((af_data_t*)arg)->format == AF_FORMAT_FLOAT_NE)
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
43 {
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
44 af->data->format = AF_FORMAT_FLOAT_NE;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
45 af->data->bps = 4;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
46 af->play = play_float;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
47 }// else
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
48 {
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
49 af->data->format = AF_FORMAT_S16_NE;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
50 af->data->bps = 2;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
51 af->play = play_s16;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
52 }
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
53
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
54 return af_test_output(af,(af_data_t*)arg);
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
55 }
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
56 case AF_CONTROL_COMMAND_LINE:{
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
57 float f;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
58 sscanf((char*)arg,"%f", &f);
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
59 s->mul = f;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
60 return AF_OK;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
61 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
62 case AF_CONTROL_ES_MUL | AF_CONTROL_SET:
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
63 s->mul = *(float*)arg;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
64 return AF_OK;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
65 case AF_CONTROL_ES_MUL | AF_CONTROL_GET:
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
66 *(float*)arg = s->mul;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
67 return AF_OK;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
68 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
69 return AF_UNKNOWN;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
70 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
71
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
72 // Deallocate memory
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
73 static void uninit(struct af_instance_s* af)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
74 {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
75 if(af->data)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
76 free(af->data);
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
77 if(af->setup)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
78 free(af->setup);
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
79 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
80
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
81 // Filter data through filter
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
82 static af_data_t* play_s16(struct af_instance_s* af, af_data_t* data)
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
83 {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
84 af_extrastereo_t *s = af->setup;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
85 register int i = 0;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
86 int16_t *a = (int16_t*)data->audio; // Audio data
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
87 int len = data->len/2; // Number of samples
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
88 int avg, l, r;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
89
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
90 for (i = 0; i < len; i+=2)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
91 {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
92 avg = (a[i] + a[i + 1]) / 2;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
93
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
94 l = avg + (int)(s->mul * (a[i] - avg));
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
95 r = avg + (int)(s->mul * (a[i + 1] - avg));
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
96
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
97 a[i] = clamp(l, SHRT_MIN, SHRT_MAX);
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
98 a[i + 1] = clamp(r, SHRT_MIN, SHRT_MAX);
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
99 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
100
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
101 return data;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
102 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
103
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
104 static af_data_t* play_float(struct af_instance_s* af, af_data_t* data)
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
105 {
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
106 af_extrastereo_t *s = af->setup;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
107 register int i = 0;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
108 float *a = (float*)data->audio; // Audio data
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
109 int len = data->len/4; // Number of samples
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
110 float avg, l, r;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
111
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
112 for (i = 0; i < len; i+=2)
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
113 {
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
114 avg = (a[i] + a[i + 1]) / 2;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
115
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
116 l = avg + (s->mul * (a[i] - avg));
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
117 r = avg + (s->mul * (a[i + 1] - avg));
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
118
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
119 a[i] = af_softclip(l);
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
120 a[i + 1] = af_softclip(r);
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
121 }
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
122
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
123 return data;
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
124 }
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
125
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
126 // Allocate memory and set function pointers
22746
fd6f824ef894 Rename open to af_open so as not to conflict with a previous header definition.
diego
parents: 14624
diff changeset
127 static int af_open(af_instance_t* af){
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
128 af->control=control;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
129 af->uninit=uninit;
14624
7b7c94b5e78a now supports float based operation aswell
alex
parents: 14245
diff changeset
130 af->play=play_s16;
24888
b2402b4f0afa libaf: change filter input/output ratio calculations
uau
parents: 22748
diff changeset
131 af->mul=1;
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
132 af->data=calloc(1,sizeof(af_data_t));
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
133 af->setup=calloc(1,sizeof(af_extrastereo_t));
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
134 if(af->data == NULL || af->setup == NULL)
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
135 return AF_ERROR;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
136
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
137 ((af_extrastereo_t*)af->setup)->mul = 2.5;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
138 return AF_OK;
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
139 }
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
140
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
141 // Description of this filter
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
142 af_info_t af_info_extrastereo = {
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
143 "Extra stereo",
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
144 "extrastereo",
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
145 "Alex Beregszaszi & Pierre Lombard",
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
146 "",
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
147 AF_FLAGS_NOT_REENTRANT,
22746
fd6f824ef894 Rename open to af_open so as not to conflict with a previous header definition.
diego
parents: 14624
diff changeset
148 af_open
13550
81e62cbe57d9 reimplementation of the pl_extrastereo and pl_volnorm plugins
alex
parents:
diff changeset
149 };