Deluge Firmware 1.3.0
Build date: 2025.04.16
Loading...
Searching...
No Matches
filter.h
1/*
2 * Copyright © 2015-2023 Synthstrom Audible Limited
3 *
4 * This file is part of The Synthstrom Audible Deluge Firmware.
5 *
6 * The Synthstrom Audible Deluge Firmware is free software: you can redistribute it and/or modify it under the
7 * terms of the GNU General Public License as published by the Free Software Foundation,
8 * either version 3 of the License, or (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
11 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 * See the GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License along with this program.
15 * If not, see <https://www.gnu.org/licenses/>.
16 */
17
18#pragma once
19
20#include "model/mod_controllable/filters/filter_config.h"
21#include "util/fixedpoint.h"
22#include "util/functions.h"
23#include <cstdint>
24
25namespace deluge::dsp::filter {
26constexpr int32_t ONE_Q16 = 134217728;
27
28extern q31_t blendBuffer[SSI_TX_BUFFER_NUM_SAMPLES * 2];
42template <typename T>
43class [[gnu::hot]] Filter {
44public:
45 Filter() = default;
46 // returns a gain compensation value
47 q31_t configure(q31_t frequency, q31_t resonance, FilterMode lpfMode, q31_t lpfMorph, q31_t filterGain) {
48
49 // lpfmorph comes in q28 but we want q31
50 return static_cast<T*>(this)->setConfig(frequency, resonance, lpfMode, lshiftAndSaturate<2>(lpfMorph),
51 filterGain);
52 }
60 [[gnu::hot]] void filterMono(q31_t* startSample, q31_t* endSample, int32_t sampleIncrememt = 1) {
61 if (dryFade < 0.001) {
62 static_cast<T*>(this)->doFilter(startSample, endSample, sampleIncrememt);
63 }
64 else {
65 memcpy(blendBuffer, startSample, (endSample - startSample) * sizeof(q31_t));
66 static_cast<T*>(this)->doFilter(startSample, endSample, sampleIncrememt);
67
68 q31_t* currentSample = startSample;
69 q31_t* currentDrySample = blendBuffer;
70 do {
71 q31_t wet = multiply_32x32_rshift32(*currentSample, wetLevel);
72 *currentSample = multiply_accumulate_32x32_rshift32_rounded(wet, *currentDrySample, ONE_Q31 - wetLevel)
73 << 1;
74 currentSample += 1;
75 currentDrySample += 1;
76 updateBlend(); // will go to one over 512 samples
77 } while (currentSample < endSample);
78 }
79 }
80
86 [[gnu::hot]] void filterStereo(q31_t* startSample, q31_t* endSample) {
87 if (dryFade < 0.001) {
88 static_cast<T*>(this)->doFilterStereo(startSample, endSample);
89 }
90 else {
91 memcpy(blendBuffer, startSample, (endSample - startSample) * sizeof(q31_t));
92 static_cast<T*>(this)->doFilterStereo(startSample, endSample);
93
94 q31_t* currentSample = startSample;
95 q31_t* currentDrySample = blendBuffer;
96 do {
97 q31_t wet = multiply_32x32_rshift32(*currentSample, wetLevel);
98 *currentSample = multiply_accumulate_32x32_rshift32_rounded(wet, *currentDrySample, ONE_Q31 - wetLevel)
99 << 1;
100 currentSample += 1;
101 currentDrySample += 1;
102 updateBlend();
103 } while (currentSample < endSample);
104 }
105 }
106
110 void reset(bool fade = false) {
111 static_cast<T*>(this)->resetFilter();
112 if (fade) {
113 dryFade = 1;
114 wetLevel = 0;
115 }
116 }
117
118 inline void updateBlend() {
119 // fades over around 500 samples
120 dryFade = dryFade * 0.99;
121 wetLevel = (q31_t)(ONE_Q31 * (1 - dryFade));
122 }
123
128 void curveFrequency(q31_t frequency) {
129 // Between 0 and 8, by my making. 1 represented by 268435456
130 tannedFrequency = instantTan(lshiftAndSaturate<5>(frequency));
131
132 // this is 1q31*1q16/(1q16+tan(f)/2)
133 // tan(f) is q17
134 divideBy1PlusTannedFrequency = (q31_t)(288230376151711744.0 / (double)(ONE_Q16 + (tannedFrequency >> 1)));
135 fc = multiply_32x32_rshift32_rounded(tannedFrequency, divideBy1PlusTannedFrequency) << 4;
136 }
137 q31_t fc;
138 float dryFade = 1;
139 q31_t wetLevel = ONE_Q31;
140 q31_t tannedFrequency;
141 q31_t divideBy1PlusTannedFrequency;
142};
143
144} // namespace deluge::dsp::filter
void reset(bool fade=false)
Definition filter.h:110
void filterMono(q31_t *startSample, q31_t *endSample, int32_t sampleIncrememt=1)
Definition filter.h:60
void filterStereo(q31_t *startSample, q31_t *endSample)
Definition filter.h:86
void curveFrequency(q31_t frequency)
Definition filter.h:128