LMMS
Loading...
Searching...
No Matches
tap_utils.h
Go to the documentation of this file.
1/* -*- linux-c -*-
2 Copyright (C) 2004 Tom Szilagyi
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17*/
18#ifndef _ISOC99_SOURCE
19#define _ISOC99_SOURCE
20#endif
21
22#include <stdint.h>
23
24
25/* push a sample into a ringbuffer and return the sample falling out */
26static inline
29 unsigned long buflen, unsigned long * pos) {
30
31 LADSPA_Data outsample;
32
33 outsample = buffer[*pos];
34 buffer[(*pos)++] = insample;
35
36 if (*pos >= buflen)
37 *pos = 0;
38
39 return outsample;
40}
41
42
43/* read a value from a ringbuffer.
44 * n == 0 returns the oldest sample from the buffer.
45 * n == buflen-1 returns the sample written to the buffer
46 * at the last push_buffer call.
47 * n must not exceed buflen-1, or your computer will explode.
48 */
49static inline
51read_buffer(LADSPA_Data * buffer, unsigned long buflen,
52 unsigned long pos, unsigned long n) {
53
54 while (n + pos >= buflen)
55 n -= buflen;
56 return buffer[n + pos];
57}
58
59
60/* overwrites a value in a ringbuffer, but pos stays the same.
61 * n == 0 overwrites the oldest sample pushed in the buffer.
62 * n == buflen-1 overwrites the sample written to the buffer
63 * at the last push_buffer call.
64 * n must not exceed buflen-1, or your computer... you know.
65 */
66static inline
67void
68write_buffer(LADSPA_Data insample, LADSPA_Data * buffer, unsigned long buflen,
69 unsigned long pos, unsigned long n) {
70
71 while (n + pos >= buflen)
72 n -= buflen;
73 buffer[n + pos] = insample;
74}
75
76
77
78
79/* Please note that the majority of the definitions and helper
80functions below have been derived from the source code of Steve
81Harris's SWH plugins (particularly from the "biquad.h" file). While I
82give him credit for his excellent work, I reserve myself to be blamed
83for any bugs or malfunction. */
84
85
86#define db2lin(x) ((x) > -90.0f ? powf(10.0f, (x) * 0.05f) : 0.0f)
87
88#define ABS(x) (x)>0.0f?(x):-1.0f*(x)
89
90
91#define LN_2_2 0.34657359f
92#define LIMIT(v,l,u) ((v)<(l)?(l):((v)>(u)?(u):(v)))
93
94#define BIQUAD_TYPE float
95typedef BIQUAD_TYPE bq_t;
96
97
98/* Biquad filter (adapted from lisp code by Eli Brandt,
99 http://www.cs.cmu.edu/~eli/) */
100
101/* The prev. comment has been preserved from Steve Harris's biquad.h */
102
103typedef struct {
104 bq_t a1;
105 bq_t a2;
106 bq_t b0;
107 bq_t b1;
108 bq_t b2;
109 bq_t x1;
110 bq_t x2;
111 bq_t y1;
112 bq_t y2;
113} biquad;
114
115
116static inline void biquad_init(biquad *f) {
117
118 f->x1 = 0.0f;
119 f->x2 = 0.0f;
120 f->y1 = 0.0f;
121 f->y2 = 0.0f;
122}
123
124
125static inline
126void
127eq_set_params(biquad *f, bq_t fc, bq_t gain, bq_t bw, bq_t fs) {
128
129 bq_t w = 2.0f * M_PI * LIMIT(fc, 1.0f, fs/2.0f) / fs;
130 bq_t cw = cosf(w);
131 bq_t sw = sinf(w);
132 bq_t J = pow(10.0f, gain * 0.025f);
133 bq_t g = sw * sinhf(LN_2_2 * LIMIT(bw, 0.0001f, 4.0f) * w / sw);
134 bq_t a0r = 1.0f / (1.0f + (g / J));
135
136 f->b0 = (1.0f + (g * J)) * a0r;
137 f->b1 = (-2.0f * cw) * a0r;
138 f->b2 = (1.0f - (g * J)) * a0r;
139 f->a1 = -(f->b1);
140 f->a2 = ((g / J) - 1.0f) * a0r;
141}
142
143
144static inline void lp_set_params(biquad *f, bq_t fc, bq_t bw, bq_t fs) {
145 bq_t omega = 2.0 * M_PI * fc/fs;
146 bq_t sn = sin(omega);
147 bq_t cs = cos(omega);
148 bq_t alpha = sn * sinh(M_LN2 / 2.0 * bw * omega / sn);
149
150 const float a0r = 1.0 / (1.0 + alpha);
151#if 0
152b0 = (1 - cs) /2;
153b1 = 1 - cs;
154b2 = (1 - cs) /2;
155a0 = 1 + alpha;
156a1 = -2 * cs;
157a2 = 1 - alpha;
158#endif
159 f->b0 = a0r * (1.0 - cs) * 0.5;
160 f->b1 = a0r * (1.0 - cs);
161 f->b2 = a0r * (1.0 - cs) * 0.5;
162 f->a1 = a0r * (2.0 * cs);
163 f->a2 = a0r * (alpha - 1.0);
164}
165
166
167static inline
168void
170{
171 bq_t omega = 2.0 * M_PI * fc/fs;
172 bq_t sn = sin(omega);
173 bq_t cs = cos(omega);
174 bq_t alpha = sn * sinh(M_LN2 / 2.0 * bw * omega / sn);
175
176 const float a0r = 1.0 / (1.0 + alpha);
177
178#if 0
179b0 = (1 + cs) /2;
180b1 = -(1 + cs);
181b2 = (1 + cs) /2;
182a0 = 1 + alpha;
183a1 = -2 * cs;
184a2 = 1 - alpha;
185#endif
186 f->b0 = a0r * (1.0 + cs) * 0.5;
187 f->b1 = a0r * -(1.0 + cs);
188 f->b2 = a0r * (1.0 + cs) * 0.5;
189 f->a1 = a0r * (2.0 * cs);
190 f->a2 = a0r * (alpha - 1.0);
191}
192
193
194static inline
195void
196ls_set_params(biquad *f, bq_t fc, bq_t gain, bq_t slope, bq_t fs)
197{
198
199 bq_t w = 2.0f * M_PI * LIMIT(fc, 1.0, fs/2.0) / fs;
200 bq_t cw = cosf(w);
201 bq_t sw = sinf(w);
202 bq_t A = powf(10.0f, gain * 0.025f);
203 bq_t b = sqrt(((1.0f + A * A) / LIMIT(slope, 0.0001f, 1.0f)) - ((A -
204 1.0f) * (A - 1.0)));
205 bq_t apc = cw * (A + 1.0f);
206 bq_t amc = cw * (A - 1.0f);
207 bq_t bs = b * sw;
208 bq_t a0r = 1.0f / (A + 1.0f + amc + bs);
209
210 f->b0 = a0r * A * (A + 1.0f - amc + bs);
211 f->b1 = a0r * 2.0f * A * (A - 1.0f - apc);
212 f->b2 = a0r * A * (A + 1.0f - amc - bs);
213 f->a1 = a0r * 2.0f * (A - 1.0f + apc);
214 f->a2 = a0r * (-A - 1.0f - amc + bs);
215}
216
217
218static inline
219void
220hs_set_params(biquad *f, bq_t fc, bq_t gain, bq_t slope, bq_t fs) {
221
222 bq_t w = 2.0f * M_PI * LIMIT(fc, 1.0, fs/2.0) / fs;
223 bq_t cw = cosf(w);
224 bq_t sw = sinf(w);
225 bq_t A = powf(10.0f, gain * 0.025f);
226 bq_t b = sqrt(((1.0f + A * A) / LIMIT(slope, 0.0001f, 1.0f)) - ((A -
227 1.0f) * (A - 1.0f)));
228 bq_t apc = cw * (A + 1.0f);
229 bq_t amc = cw * (A - 1.0f);
230 bq_t bs = b * sw;
231 bq_t a0r = 1.0f / (A + 1.0f - amc + bs);
232
233 f->b0 = a0r * A * (A + 1.0f + amc + bs);
234 f->b1 = a0r * -2.0f * A * (A - 1.0f + apc);
235 f->b2 = a0r * A * (A + 1.0f + amc - bs);
236 f->a1 = a0r * -2.0f * (A - 1.0f - apc);
237 f->a2 = a0r * (-A - 1.0f + amc + bs);
238}
239
240
241static inline
242bq_t
244
245 union {
246 bq_t y;
247 uint32_t y_int;
248 } u;
249
250 u.y = f->b0 * x + f->b1 * f->x1 + f->b2 * f->x2
251 + f->a1 * f->y1 + f->a2 * f->y2;
252 if ((u.y_int & 0x7f800000) == 0)
253 u.y = 0.0f;
254 f->x2 = f->x1;
255 f->x1 = x;
256 f->y2 = f->y1;
257 f->y1 = u.y;
258
259 return u.y;
260}
#define M_LN2
Definition compat.h:146
#define M_PI
Definition compat.h:149
UINT_D64 w
Definition inflate.c:942
int y
Definition inflate.c:1588
int g
Definition inflate.c:1573
struct huft * u[BMAX]
Definition inflate.c:1583
unsigned x[BMAX+1]
Definition inflate.c:1586
unsigned f
Definition inflate.c:1572
float LADSPA_Data
Definition ladspa.h:84
#define A(x)
Definition lice_arc.cpp:13
unsigned int uint32_t
Definition mid.cpp:100
Definition biquad.h:21
#define BIQUAD_TYPE
Definition biquad.h:13
#define LN_2_2
Definition biquad.h:4
BIQUAD_TYPE bq_t
Definition biquad.h:16
static void biquad_init(biquad *f)
Definition tap_utils.h:116
static LADSPA_Data read_buffer(LADSPA_Data *buffer, unsigned long buflen, unsigned long pos, unsigned long n)
Definition tap_utils.h:51
static void hs_set_params(biquad *f, bq_t fc, bq_t gain, bq_t slope, bq_t fs)
Definition tap_utils.h:220
static void write_buffer(LADSPA_Data insample, LADSPA_Data *buffer, unsigned long buflen, unsigned long pos, unsigned long n)
Definition tap_utils.h:68
static void eq_set_params(biquad *f, bq_t fc, bq_t gain, bq_t bw, bq_t fs)
Definition tap_utils.h:127
static void lp_set_params(biquad *f, bq_t fc, bq_t bw, bq_t fs)
Definition tap_utils.h:144
static void hp_set_params(biquad *f, bq_t fc, bq_t bw, bq_t fs)
Definition tap_utils.h:169
static void ls_set_params(biquad *f, bq_t fc, bq_t gain, bq_t slope, bq_t fs)
Definition tap_utils.h:196
static bq_t biquad_run(biquad *f, bq_t x)
Definition tap_utils.h:243
#define LIMIT(v, l, u)
Definition tap_utils.h:92
static LADSPA_Data push_buffer(LADSPA_Data insample, LADSPA_Data *buffer, unsigned long buflen, unsigned long *pos)
Definition tap_utils.h:28
int n
Definition crypt.c:458
b
Definition crypt.c:628