Add Lua binding to un/assign VCAs
[ardour.git] / libs / plugins / a-eq.lv2 / a-eq.c
index deac7a641ee0e62043da6192d18b0aedd18121ee..b0851f2120f73bc3d47829414c19973f3f310ab4 100644 (file)
 #include <stdbool.h>
 #include <stdio.h>
 
+#ifdef COMPILER_MSVC
+#include <float.h>
+#define isfinite_local(val) (bool)_finite((double)val)
+#else
+#define isfinite_local isfinite
+#endif
+
 #include "lv2/lv2plug.in/ns/lv2core/lv2.h"
 
 #ifdef LV2_EXTENDED
@@ -92,6 +99,13 @@ static void linear_svf_reset(struct linear_svf *self)
        self->s[0] = self->s[1] = 0.0;
 }
 
+static void linear_svf_protect(struct linear_svf *self)
+{
+       if (!isfinite_local (self->s[0]) || !isfinite_local (self->s[1])) {
+               linear_svf_reset (self);
+       }
+}
+
 typedef struct {
        float* f0[BANDS];
        float* g[BANDS];
@@ -256,7 +270,7 @@ activate(LV2_Handle instance)
 static void linear_svf_set_peq(struct linear_svf *self, float gdb, float sample_rate, float cutoff, float bandwidth)
 {
        double f0 = (double)cutoff;
-       double q = (double)pow(2.0, 1.0 / bandwidth) / (pow(2.0, bandwidth) - 1.0);
+       double q = (double)pow(2.0, 0.5 * bandwidth) / (pow(2.0, bandwidth) - 1.0);
        double sr = (double)sample_rate;
        double A = pow(10.0, gdb/40.0);
 
@@ -379,23 +393,17 @@ run(LV2_Handle instance, uint32_t n_samples)
                        if (!is_eq(aeq->v_f0[i], *aeq->f0[i], 0.1)) {
                                aeq->v_f0[i] += tau * (*aeq->f0[i] - aeq->v_f0[i]);
                                changed = true;
-                       } else {
-                               aeq->v_f0[i] = *aeq->f0[i];
                        }
 
                        if (*aeq->filtog[i] <= 0 || *aeq->enable <= 0) {
                                if (!is_eq(aeq->v_g[i], 0.f, 0.05)) {
                                        aeq->v_g[i] += tau * (0.0 - aeq->v_g[i]);
                                        changed = true;
-                               } else {
-                                       aeq->v_g[i] = 0.0;
                                }
                        } else {
                                if (!is_eq(aeq->v_g[i], *aeq->g[i], 0.05)) {
                                        aeq->v_g[i] += tau * (*aeq->g[i] - aeq->v_g[i]);
                                        changed = true;
-                               } else {
-                                       aeq->v_g[i] = *aeq->g[i];
                                }
                        }
 
@@ -403,8 +411,6 @@ run(LV2_Handle instance, uint32_t n_samples)
                                if (!is_eq(aeq->v_bw[i], *aeq->bw[i], 0.001)) {
                                        aeq->v_bw[i] += tau * (*aeq->bw[i] - aeq->v_bw[i]);
                                        changed = true;
-                               } else {
-                                       aeq->v_bw[i] = *aeq->bw[i];
                                }
                        }
 
@@ -432,6 +438,10 @@ run(LV2_Handle instance, uint32_t n_samples)
                offset += block;
        }
 
+       for (uint32_t j = 0; j < BANDS; j++) {
+               linear_svf_protect(&aeq->v_filter[j]);
+       }
+
 #ifdef LV2_EXTENDED
        if (aeq->need_expose && aeq->queue_draw) {
                aeq->need_expose = false;