diff options
author | kcgen <1557255+kcgen@users.noreply.github.com> | 2022-05-31 01:56:23 +0300 |
---|---|---|
committer | kcgen <1557255+kcgen@users.noreply.github.com> | 2022-05-31 03:18:50 +0300 |
commit | 92902147c3f7a1e7b657c08bd48a5316470597a8 (patch) | |
tree | 27def8de0e4b16cb7a8f1460bc1588ec5fac8993 | |
parent | c5f2bfe233edf71be0874f113c796bf01d1bf3c7 (diff) |
Use iir1 from the Meson wrapkc/iir-wrap-1
39 files changed, 34 insertions, 5995 deletions
diff --git a/.github/workflows/dormant/windows-2019.yml b/.github/workflows/dormant/windows-2019.yml index aec4e8f96..356a17a4a 100644 --- a/.github/workflows/dormant/windows-2019.yml +++ b/.github/workflows/dormant/windows-2019.yml @@ -46,7 +46,7 @@ jobs: run: | rm -R c:\vcpkg mv c:\vcpkg-bak c:\vcpkg - vcpkg install --triplet ${{ matrix.conf.arch }}-windows libpng sdl2 sdl2-net libmt32emu opusfile fluidsynth pdcurses gtest speexdsp + vcpkg install --triplet ${{ matrix.conf.arch }}-windows libpng sdl2 sdl2-net libmt32emu opusfile fluidsynth iir1 pdcurses gtest speexdsp if (-not $?) { throw "vcpkg failed to install library dependencies" } rm -R c:\vcpkg\buildtrees rm -R c:\vcpkg\packages diff --git a/.github/workflows/macos.yml b/.github/workflows/macos.yml index e4430be3d..c45856844 100644 --- a/.github/workflows/macos.yml +++ b/.github/workflows/macos.yml @@ -243,7 +243,7 @@ jobs: -Db_lto=true -Db_asneeded=true -Ddefault_library=static - -Dtry_static_libs=opusfile,sdl2,sdl2_net,speexdsp,zlib + -Dtry_static_libs=iir,opusfile,sdl2,sdl2_net,speexdsp,zlib -Dfluidsynth:try-static-deps=true build diff --git a/.github/workflows/windows-meson-msys2.yml b/.github/workflows/windows-meson-msys2.yml index 249f6ee2d..4f44a9b14 100644 --- a/.github/workflows/windows-meson-msys2.yml +++ b/.github/workflows/windows-meson-msys2.yml @@ -10,7 +10,7 @@ env: CCACHE_DIR: "/c/ccache" CCACHE_MAXSIZE: "64M" CCACHE_COMPRESS: "true" - BUILD_FLAGS: "-Dbuildtype=release -Db_asneeded=true --force-fallback-for=fluidsynth,mt32emu -Dtry_static_libs=fluidsynth,mt32emu,opusfile,png,slirp,zlib,speexdsp -Dfluidsynth:try-static-deps=true" + BUILD_FLAGS: "-Dbuildtype=release -Db_asneeded=true --force-fallback-for=fluidsynth,mt32emu -Dtry_static_libs=fluidsynth,iir,mt32emu,opusfile,png,slirp,zlib,speexdsp -Dfluidsynth:try-static-deps=true" BUILD_RELEASE_DIR: build/release BUILD_DEBUGGER_DIR: build/debugger diff --git a/.github/workflows/windows.yml b/.github/workflows/windows.yml index a1ed1f86d..b549f6f0d 100644 --- a/.github/workflows/windows.yml +++ b/.github/workflows/windows.yml @@ -56,7 +56,7 @@ jobs: git clone --depth 1 https://github.com/Microsoft/vcpkg.git cd vcpkg .\bootstrap-vcpkg.bat - vcpkg install --triplet ${{ matrix.conf.arch }}-windows libpng sdl2 sdl2-net libmt32emu opusfile fluidsynth gtest speexdsp + vcpkg install --triplet ${{ matrix.conf.arch }}-windows iir1 libpng sdl2 sdl2-net libmt32emu opusfile fluidsynth gtest speexdsp if (-not $?) { throw "vcpkg failed to install library dependencies" } rm -R c:\vcpkg\buildtrees rm -R c:\vcpkg\packages @@ -238,7 +238,7 @@ is bootstrapped, open PowerShell and run: ``` powershell PS:\> .\vcpkg integrate install -PS:\> .\vcpkg install --triplet x64-windows libpng sdl2 sdl2-net libmt32emu opusfile fluidsynth gtest speexdsp +PS:\> .\vcpkg install --triplet x64-windows libpng sdl2 sdl2-net iir1 libmt32emu opusfile fluidsynth gtest speexdsp ``` These two steps will ensure that MSVC finds and links all dependencies. diff --git a/contrib/resources/translations/update-sources.sh b/contrib/resources/translations/update-sources.sh index 6c2c11a71..dd137af7b 100755 --- a/contrib/resources/translations/update-sources.sh +++ b/contrib/resources/translations/update-sources.sh @@ -27,7 +27,7 @@ check_package() { echo " 1. cd $(git rev-parse --show-toplevel)" echo "" echo " 2. meson setup --wrap-mode=forcefallback -Db_asneeded=true \\" - echo " -Ddefault_library=static -Dtry_static_libs=fluidsynth,mt32emu,png \\" + echo " -Ddefault_library=static -Dtry_static_libs=fluidsynth,iir,mt32emu,png \\" echo " -Dfluidsynth:enable-floats=true -Dfluidsynth:try-static-deps=true \\" echo " -Db_asneeded=true -Dunit_tests=disabled -Dstrip=true \\" echo " -Dwarning_level=0 -Dc_args=-w -Dcpp_args=-w build/full-static" diff --git a/docs/build-windows.md b/docs/build-windows.md index df53bed30..a35f895c0 100644 --- a/docs/build-windows.md +++ b/docs/build-windows.md @@ -74,8 +74,8 @@ you build a binary optimized for gaming. ``` shell meson setup build/release-gcc -Dbuildtype=release -Db_asneeded=true \ - --force-fallback-for=fluidsynth,mt32emu,slirp \ - -Dtry_static_libs=fluidsynth,mt32emu,opusfile,png,slirp,speexdsp \ + --force-fallback-for=fluidsynth,iir,mt32emu,slirp \ + -Dtry_static_libs=fluidsynth,iir,mt32emu,opusfile,png,slirp,speexdsp \ -Dfluidsynth:try-static-deps=true ``` @@ -84,8 +84,8 @@ you build a binary optimized for gaming. ``` shell meson setup build/release-clang --native-file=.github/meson/native-clang.ini \ -Dbuildtype=release -Db_asneeded=true \ - --force-fallback-for=fluidsynth,mt32emu,slirp \ - -Dtry_static_libs=fluidsynth,mt32emu,opusfile,png,slirp,speexdsp \ + --force-fallback-for=fluidsynth,iir,mt32emu,slirp \ + -Dtry_static_libs=fluidsynth,iir,mt32emu,opusfile,png,slirp,speexdsp \ -Dfluidsynth:try-static-deps=true ``` diff --git a/include/mixer.h b/include/mixer.h index f1768d8ce..3648dfe64 100644 --- a/include/mixer.h +++ b/include/mixer.h @@ -31,7 +31,7 @@ #include "envelope.h" -#include "../src/libs/iir1/Iir.h" +#include <Iir.h> typedef void (*MIXER_MixHandler)(uint8_t *sampdate, uint32_t len); diff --git a/meson.build b/meson.build index ce4d100fc..a930bdde7 100644 --- a/meson.build +++ b/meson.build @@ -12,6 +12,7 @@ project('dosbox-staging', 'c', 'cpp', 'fluidsynth:enable-threads=false', 'fluidsynth:try-static-deps=false', 'fluidsynth:warning_level=0', + 'iir:exceptions=false', 'glib:glib_assert=false', 'glib:glib_checks=false', 'glib:glib_debug=disabled', @@ -240,6 +241,8 @@ sdl2_dep = dependency('sdl2', version : '>= 2.0.5', static : ('sdl2' in static_libs_list)) zlib_dep = dependency('zlib', version : '>= 1.2.11', static : ('zlib' in static_libs_list)) +libiir_dep = dependency('iir', version : '>= 1.9.2', + static : ('iir' in static_libs_list)) speexdsp_dep = dependency('speexdsp', version : '> 1.1.9', static : ('speexdsp' in static_libs_list)) sdl2_net_dep = optional_dep @@ -413,7 +416,6 @@ subdir('src/libs/residfp') subdir('src/libs/sdlcd') subdir('src/libs/whereami') subdir('src/libs/PDCurses') -subdir('src/libs/iir1') # internal libs # @@ -453,7 +455,7 @@ executable('dosbox', dosbox_sources, stdcppfs_dep, sdl2_dep, threads_dep, - libiir1_dep, + libiir_dep, libghc_dep, libloguru_dep, libpdcurses_dep, @@ -468,7 +470,7 @@ libdosbox = static_library('dosbox', ['src/dosbox.cpp', version_file], dependencies : [atomic_dep, threads_dep, sdl2_dep, - libiir1_dep, + libiir_dep, libghc_dep, libloguru_dep, libsdlcd_dep] diff --git a/meson_options.txt b/meson_options.txt index 29fd8bd09..aba9b6dcb 100644 --- a/meson_options.txt +++ b/meson_options.txt @@ -46,6 +46,7 @@ option('try_static_libs', type : 'array', choices : [ 'fluidsynth', + 'iir', 'mt32emu', 'opusfile', 'png', diff --git a/src/hardware/meson.build b/src/hardware/meson.build index ca03ebe40..04f1359ec 100644 --- a/src/hardware/meson.build +++ b/src/hardware/meson.build @@ -59,7 +59,7 @@ libhardware_sources = files([ libhardware = static_library('hardware', libhardware_sources, include_directories : incdir, dependencies : [ - libiir1_dep, + libiir_dep, libghc_dep, libloguru_dep, libnuked_dep, diff --git a/src/libs/iir1/COPYING b/src/libs/iir1/COPYING deleted file mode 100644 index b2d25b284..000000000 --- a/src/libs/iir1/COPYING +++ /dev/null @@ -1,22 +0,0 @@ -MIT License - -Copyright (c) 2009 Vinnie Falco -Copyright (c) 2012 Bernd Porr - -Permission is hereby granted, free of charge, to any person obtaining a copy -of this software and associated documentation files (the "Software"), to deal -in the Software without restriction, including without limitation the rights -to use, copy, modify, merge, publish, distribute, sublicense, and/or sell -copies of the Software, and to permit persons to whom the Software is -furnished to do so, subject to the following conditions: - -The above copyright notice and this permission notice shall be included in -all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN -THE SOFTWARE. diff --git a/src/libs/iir1/Iir.h b/src/libs/iir1/Iir.h deleted file mode 100644 index 0e849c435..000000000 --- a/src/libs/iir1/Iir.h +++ /dev/null @@ -1,55 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * -------------------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - * - **/ - -#ifndef IIR_H -#define IIR_H - -// -// Include this file in your application to get everything -// - -#include "iir/Common.h" - -#include "iir/Biquad.h" -#include "iir/Cascade.h" -#include "iir/PoleFilter.h" -#include "iir/State.h" - -#include "iir/Butterworth.h" -#include "iir/ChebyshevI.h" -#include "iir/ChebyshevII.h" -#include "iir/Custom.h" -#include "iir/RBJ.h" - -#endif diff --git a/src/libs/iir1/README.md b/src/libs/iir1/README.md deleted file mode 100644 index 2459ddc74..000000000 --- a/src/libs/iir1/README.md +++ /dev/null @@ -1,329 +0,0 @@ -# DSP IIR Realtime C++ filter library - -![alt tag](title.png) - - - High performance - - Realtime sample in - sample out processing - - Butterworth, RBJ, Chebychev filters - - Lowpass, highpass, bandpass and bandstop filters - - Template based header-only filter functions - - Cross platform: Linux, Windows and Mac - -An infinite impulse response (IIR) filter library for -Linux, Mac OSX and Windows -which implements Butterworth, RBJ, Chebychev filters -and can easily import coefficients generated by Python (scipy). - -The filter processes the data sample by sample for realtime -processing. - -It uses templates to allocate the required memory so that -it can run without any malloc / new commands. -Memory is allocated at compile time -so that there is never the risk of memory leaks. - -All realtime filter code is in the header files which guarantees -efficient integration into the main program and the compiler -can optimise both filter code and main program at the same time. - -## C++ code -Add the following include statement to your code: -``` -#include "Iir.h" -``` - -The general coding approach is that first the filter is -instantiated specifying its order, then the -parameters are set with the function `setup` and -then it's ready to be used for sample by sample realtime filtering. - -### Instantiating the filter -The idea is to allocate the memory of the -filter at compile time with a template argument to avoid any new -commands. This prevents memory leaks and can be optimised at compile -time. The `order` provided to the template (for example here for a -lowpass filter): -``` -Iir::Butterworth::LowPass<order> f; -``` -is used as the default order by the `setup` command below -but can be overridden by a lower order if required. - -### Setting the filter parameters: `setup` -All filters are available as lowpass, highpass, bandpass and bandstop/notch -filters. Butterworth / Chebyshev offer also low/high/band-shelves with -specified passband gain and 0dB gain in the stopband. - -The frequencies can either be analogue ones against the sampling rate -or normalised ones between 0..1/2 where 1/2 is the Nyquist frequency. Note -that normalised frequencies are simply f = F/Fs and are in units of 1/samples. -Internally the library uses normalised frequencies and the setup commands -simply divide by the sampling rate if given. Choose between: - 1. `setup`: sampling rate and the analogue cutoff frequencies - 2. `setupN`: normalised frequencies in 1/samples between f = 0..1/2 where 1/2 = Nyquist. - -By default `setup` uses the order supplied by the template argument but -can be overridden by lower filter orders. - -See the header files in `\iir` or the documentation for the arguments -of the `setup` commands. - -The examples below are for lowpass filters: - -1. Butterworth -- `Butterworth.h` -Standard filter suitable for most applications. Monotonic response. -``` -const int order = 4; // 4th order (=2 biquads) -Iir::Butterworth::LowPass<order> f; -const float samplingrate = 1000; // Hz -const float cutoff_frequency = 5; // Hz -f.setup (samplingrate, cutoff_frequency); -``` -or specify a normalised frequency between 0..1/2: -``` -f.setupN(norm_cutoff_frequency); -``` - -2. Chebyshev Type I -- `ChebyshevI.h` -With permissible passband ripple in dB. -``` -Iir::ChebyshevI::LowPass<order> f; -const float passband_ripple_in_db = 5; -f.setup (samplingrate, - cutoff_frequency, - passband_ripple_in_dB); -``` -or specify a normalised frequency between 0..1/2: -``` -f.setupN(norm_cutoff_frequency,passband_ripple_in_dB); -``` - - -3. Chebyshev Type II -- `ChebyshevII.h` -With worst permissible stopband rejection in dB. -``` -Iir::ChebyshevII::LowPass<order> f; -double stopband_ripple_in_dB = 20; -f.setup (samplingrate, - cutoff_frequency, - stopband_ripple_in_dB); -``` -or specify a normalised frequency between 0..1/2: -``` -f.setupN(norm_cutoff_frequency,stopband_ripple_in_dB); -``` - -4. RBJ -- `RBJ.h` -2nd order filters with cutoff and Q factor. -``` -Iir::RBJ::LowPass f; -const float cutoff_frequency = 100; -const float Q_factor = 5; -f.setup (samplingrate, cutoff_frequency, Q_factor); -``` -or specify a normalised frequency between 0..1/2: -``` -f.setupN(norm_cutoff_frequency, Q_factor); -``` - -5. Designing filters with Python's scipy.signal -- `Custom.h` -``` -######## -# Python -# See "elliptic_design.py" for the complete code. -from scipy import signal -order = 4 -sos = signal.ellip(order, 5, 40, 0.2, 'low', output='sos') -print(sos) # copy/paste the coefficients over & replace [] with {} - -/////// -// C++ -// part of "iirdemo.cpp" -const double coeff[][6] = { - {1.665623674062209972e-02, - -3.924801366970616552e-03, - 1.665623674062210319e-02, - 1.000000000000000000e+00, - -1.715403014004022175e+00, - 8.100474793174089472e-01}, - {1.000000000000000000e+00, - -1.369778997100624895e+00, - 1.000000000000000222e+00, - 1.000000000000000000e+00, - -1.605878925999785656e+00, - 9.538657786383895054e-01} - }; -const int nSOS = sizeof(coeff) / sizeof(coeff[0]); // here: nSOS = 2 = order / 2 -Iir::Custom::SOSCascade<nSOS> cust(coeff); -``` - -### Realtime filtering sample by sample -Samples are processed one by one. In the example below -a sample `x` is processed with the `filter` -command and then saved in `y`. The types of `x` and `y` can either be -float or double -(integer is also allowed but is still processed internally as floating point): -``` -y = f.filter(x); -``` -This is then repeated for every incoming sample in a -loop or event handler. - - -### Error handling -Invalid values provided to `setup()` will throw -an exception. Parameters provided to `setup()` which -result in coefficients being NAN will also -throw an exception. - -You can switch off exeption handling by defining -`IIR1_NO_EXCEPTIONS` via cmake or in your program. - - -## Linking - -### CMake setup -If you use cmake as your build system then just add -to your `CMakeLists.txt` the following lines for the dynamic library: -``` -find_package(iir) -target_link_libraries(... iir::iir) -``` -or for the static one: -``` -find_package(iir) -target_link_libraries(... iir::iir_static) -``` - -### Generic linker setup -Link it against the dynamic library -(Unix/Mac: `-liir`, Windows: `iir.lib`) -or the static library (Unix/Mac: `libiir_static.a`, -Windows: `libiir_static.lib`). - - - -## Packages for Ubuntu LTS: - -If you are using Ubuntu LTS then you can -install this library as a pre-compiled package: - -``` -sudo add-apt-repository ppa:berndporr/dsp -``` - -It's available for 32,64 bit PC and 32,64 bit ARM (Raspberry PI etc). -The documentation and the example programs are in: -``` -/usr/share/doc/iir1-dev/ -``` - -## Package for MacOS - -Make sure you have the homebrew package manager installed: https://brew.sh/ - -Add the homebrew tap: - -``` -brew tap berndporr/dsp -``` - -and then install the iir filter package with: - -``` -brew install iir -``` - - - -## Compilation from source - -The build tool is `cmake` which generates the make- or project -files for the different platforms. `cmake` is available for -Linux, Windows and Mac. It also compiles directly on a -Raspberry PI. - -### Linux / Mac - -Run -``` -cmake . -``` -which generates the Makefile. Then run: -``` -make -sudo make install -``` -which installs it under `/usr/local/lib` and `/usr/local/include`. - -Both gcc and clang have been tested. - -### Windows - -``` -cmake -G "Visual Studio 16 2019" -A x64 . -``` - -See `cmake` for the different build-options. Above is for a 64 bit build. -Then start Visual C++ and open the solution. This will create -the DLL and the LIB files. Under Windows it's highly recommended -to use the static library and link it into the application program. - -### Unit tests - -Run unit tests by typing `make test` or just `ctest`. -These test if after a delta pulse all filters relax to zero, -that their outputs never become NaN and if the Direct Form I&II filters calculate -expected sequences by comparing them from results created -by the output of scipy's `sosfilt`. - -## Documentation - -### Learn from the demos -The easiest way to learn is from the examples which are in the `demo` -directory. A delta pulse as a test signal is sent into the different -filters and saved in a file. With the Python script -`plot_impulse_fresponse.py` you can then plot the frequency responses. - -Also the directory containing the unit tests provides examples for -every filter type. - -### Detailed documentation -A PDF of all classes, methods and in particular `setup` functions -is in the `docs/pdf` directory. - -The online documentation is here: http://berndporr.github.io/iir1 - -## Example filter responses - -These responses have been generated by `iirdemo.cpp` -in the `/demo/` directory and then plotted with `plot_impulse_fresponse.py`. - -![alt tag](demo/1.png) -![alt tag](demo/2.png) -![alt tag](demo/3.png) -![alt tag](demo/4.png) -![alt tag](demo/5.png) -![alt tag](demo/7.png) -![alt tag](demo/8.png) - -## Credits - -This library has been further developed from Vinnie Falco's -great original work which can be found here: - -https://github.com/vinniefalco/DSPFilters - -While the original library processes audio arrays this -library has been adapted to do fast realtime processing sample -by sample. The `setup` -command won't require the filter order and instead remembers -it from the template argument. The class structure has -been simplified and all functions documented for doxygen. -Instead of having assert() statements this libary throws -exceptions in case a parameter is wrong. Any filter design -requiring optimisation (for example Ellipic filters) has -been removed and instead a function has been added which can import easily -coefficients from scipy. - -Bernd Porr -- http://www.berndporr.me.uk diff --git a/src/libs/iir1/iir/Biquad.cpp b/src/libs/iir1/iir/Biquad.cpp deleted file mode 100644 index 7cd23d2ba..000000000 --- a/src/libs/iir1/iir/Biquad.cpp +++ /dev/null @@ -1,221 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "MathSupplement.h" -#include "Biquad.h" - -namespace Iir { - - BiquadPoleState::BiquadPoleState (const Biquad& s) - { - const double a0 = s.getA0 (); - const double a1 = s.getA1 (); - const double a2 = s.getA2 (); - const double b0 = s.getB0 (); - const double b1 = s.getB1 (); - const double b2 = s.getB2 (); - - if (a2 == 0 && b2 == 0) - { - // single pole - poles.first = -a1; - zeros.first = -b0 / b1; - poles.second = 0; - zeros.second = 0; - } - else - { - { - const complex_t c = sqrt (complex_t (a1 * a1 - 4 * a0 * a2, 0)); - double d = 2. * a0; - poles.first = -(a1 + c) / d; - poles.second = (c - a1) / d; - if (poles.is_nan()) throw_invalid_argument("poles are NaN"); - } - - { - const complex_t c = sqrt (complex_t ( - b1 * b1 - 4 * b0 * b2, 0)); - double d = 2. * b0; - zeros.first = -(b1 + c) / d; - zeros.second = (c - b1) / d; - if (zeros.is_nan()) throw_invalid_argument("zeros are NaN"); - } - } - - gain = b0 / a0; - } - -//------------------------------------------------------------------------------ - -/** - * Gets the frequency response of the Biquad - * \param normalizedFrequency Normalised frequency (0 to 0.5) - **/ - complex_t Biquad::response (double normalizedFrequency) const - { - const double a0 = getA0 (); - const double a1 = getA1 (); - const double a2 = getA2 (); - const double b0 = getB0 (); - const double b1 = getB1 (); - const double b2 = getB2 (); - - const double w = 2 * doublePi * normalizedFrequency; - const complex_t czn1 = std::polar (1., -w); - const complex_t czn2 = std::polar (1., -2 * w); - complex_t ch (1); - complex_t cbot (1); - - complex_t ct (b0/a0); - complex_t cb (1); - ct = addmul (ct, b1/a0, czn1); - ct = addmul (ct, b2/a0, czn2); - cb = addmul (cb, a1/a0, czn1); - cb = addmul (cb, a2/a0, czn2); - ch *= ct; - cbot *= cb; - - return ch / cbot; - } - - std::vector<PoleZeroPair> Biquad::getPoleZeros () const - { - std::vector<PoleZeroPair> vpz; - BiquadPoleState bps (*this); - vpz.push_back (bps); - return vpz; - } - - void Biquad::setCoefficients (double a0, double a1, double a2, - double b0, double b1, double b2) - { - if (Iir::is_nan (a0)) throw_invalid_argument("a0 is NaN"); - if (Iir::is_nan (a1)) throw_invalid_argument("a1 is NaN"); - if (Iir::is_nan (a2)) throw_invalid_argument("a2 is NaN"); - if (Iir::is_nan (b0)) throw_invalid_argument("b0 is NaN"); - if (Iir::is_nan (b1)) throw_invalid_argument("b1 is NaN"); - if (Iir::is_nan (b2)) throw_invalid_argument("b2 is NaN"); - - m_a0 = a0; - m_a1 = a1/a0; - m_a2 = a2/a0; - m_b0 = b0/a0; - m_b1 = b1/a0; - m_b2 = b2/a0; - } - - void Biquad::setOnePole (complex_t pole, complex_t zero) - { - if (pole.imag() != 0) throw_invalid_argument("Imaginary part of pole is non-zero."); - if (zero.imag() != 0) throw_invalid_argument("Imaginary part of zero is non-zero."); - - const double a0 = 1; - const double a1 = -pole.real(); - const double a2 = 0; - const double b0 = -zero.real(); - const double b1 = 1; - const double b2 = 0; - - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void Biquad::setTwoPole (complex_t pole1, complex_t zero1, - complex_t pole2, complex_t zero2) - { - const double a0 = 1; - double a1; - double a2; - const char errMsgPole[] = "imaginary parts of both poles need to be 0 or complex conjugate"; - const char errMsgZero[] = "imaginary parts of both zeros need to be 0 or complex conjugate"; - - if (pole1.imag() != 0) - { - if (pole2 != std::conj (pole1)) - throw_invalid_argument(errMsgPole); - a1 = -2 * pole1.real(); - a2 = std::norm (pole1); - } - else - { - if (pole2.imag() != 0) - throw_invalid_argument(errMsgPole); - a1 = -(pole1.real() + pole2.real()); - a2 = pole1.real() * pole2.real(); - } - - const double b0 = 1; - double b1; - double b2; - - if (zero1.imag() != 0) - { - if (zero2 != std::conj (zero1)) - throw_invalid_argument(errMsgZero); - b1 = -2 * zero1.real(); - b2 = std::norm (zero1); - } - else - { - if (zero2.imag() != 0) - throw_invalid_argument(errMsgZero); - - b1 = -(zero1.real() + zero2.real()); - b2 = zero1.real() * zero2.real(); - } - - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void Biquad::setPoleZeroForm (const BiquadPoleState& bps) - { - setPoleZeroPair (bps); - applyScale (bps.gain); - } - - void Biquad::setIdentity () - { - setCoefficients (1, 0, 0, 1, 0, 0); - } - - void Biquad::applyScale (double scale) - { - m_b0 *= scale; - m_b1 *= scale; - m_b2 *= scale; - } - -} diff --git a/src/libs/iir1/iir/Biquad.h b/src/libs/iir1/iir/Biquad.h deleted file mode 100644 index fd31ce5ff..000000000 --- a/src/libs/iir1/iir/Biquad.h +++ /dev/null @@ -1,184 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_BIQUAD_H -#define IIR1_BIQUAD_H - -#include "Common.h" -#include "MathSupplement.h" -#include "Types.h" - -namespace Iir { - - struct DllExport BiquadPoleState; - -/* - * Holds coefficients for a second order Infinite Impulse Response - * digital filter. This is the building block for all IIR filters. - * - */ - class DllExport Biquad - { - public: - /** - * Calculate filter response at the given normalized frequency - * and return the complex response. - **/ - complex_t response (double normalizedFrequency) const; - - /** - * Returns the pole / zero Pairs as a vector. - **/ - std::vector<PoleZeroPair> getPoleZeros () const; - - /** - * Returns 1st IIR coefficient (usually one) - **/ - double getA0 () const { return m_a0; } - - /** - * Returns 2nd IIR coefficient - **/ - double getA1 () const { return m_a1*m_a0; } - - /** - * Returns 3rd IIR coefficient - **/ - double getA2 () const { return m_a2*m_a0; } - - /** - * Returns 1st FIR coefficient - **/ - double getB0 () const { return m_b0*m_a0; } - - /** - * Returns 2nd FIR coefficient - **/ - double getB1 () const { return m_b1*m_a0; } - - /** - * Returns 3rd FIR coefficient - **/ - double getB2 () const { return m_b2*m_a0; } - - /** - * Filter a sample with the coefficients provided here and the State provided as an argument. - * \param s The sample to be filtered. - * \param state The Delay lines (instance of a state from State.h) - * \return The filtered sample. - **/ - template <class StateType> - inline double filter(double s, StateType& state) const - { - return state.filter(s, *this); - } - - public: - /** - * Sets all coefficients - * \param a0 1st IIR coefficient - * \param a1 2nd IIR coefficient - * \param a2 3rd IIR coefficient - * \param b0 1st FIR coefficient - * \param b1 2nd FIR coefficient - * \param b2 3rd FIR coefficient - **/ - void setCoefficients (double a0, double a1, double a2, - double b0, double b1, double b2); - - /** - * Sets one (real) pole and zero. Throws exception if imaginary components. - **/ - void setOnePole (complex_t pole, complex_t zero); - - /** - * Sets two poles/zoes as a pair. Needs to be complex conjugate. - **/ - void setTwoPole (complex_t pole1, complex_t zero1, - complex_t pole2, complex_t zero2); - - /** - * Sets a complex conjugate pair - **/ - void setPoleZeroPair (const PoleZeroPair& pair) - { - if (pair.isSinglePole ()) - setOnePole (pair.poles.first, pair.zeros.first); - else - setTwoPole (pair.poles.first, pair.zeros.first, - pair.poles.second, pair.zeros.second); - } - - void setPoleZeroForm (const BiquadPoleState& bps); - - /** - * Sets the coefficiens as pass through. (b0=1,a0=1, rest zero) - **/ - void setIdentity (); - - /** - * Performs scaling operation on the FIR coefficients - * \param scale Mulitplies the coefficients b0,b1,b2 with the scaling factor scale. - **/ - void applyScale (double scale); - - public: - double m_a0 = 1.0; - double m_a1 = 0.0; - double m_a2 = 0.0; - double m_b1 = 0.0; - double m_b2 = 0.0; - double m_b0 = 1.0; - }; - -//------------------------------------------------------------------------------ - - -/** - * Expresses a biquad as a pair of pole/zeros, with gain - * values so that the coefficients can be reconstructed precisely. - **/ - struct DllExport BiquadPoleState : PoleZeroPair - { - BiquadPoleState () = default; - - explicit BiquadPoleState (const Biquad& s); - - double gain = 1.0; - }; - -} - -#endif diff --git a/src/libs/iir1/iir/Butterworth.cpp b/src/libs/iir1/iir/Butterworth.cpp deleted file mode 100644 index 1a96d0422..000000000 --- a/src/libs/iir1/iir/Butterworth.cpp +++ /dev/null @@ -1,205 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "Butterworth.h" - -namespace Iir { - -namespace Butterworth { - -AnalogLowPass::AnalogLowPass () - : m_numPoles (-1) -{ - setNormal (0, 1); -} - -void AnalogLowPass::design (int numPoles) -{ - if (m_numPoles != numPoles) - { - m_numPoles = numPoles; - - reset (); - - const double n2 = 2 * numPoles; - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - complex_t c = std::polar (1., doublePi_2 + (2 * i + 1) * doublePi / n2); - addPoleZeroConjugatePairs (c, infinity()); - } - - if (numPoles & 1) - add (-1, infinity()); - } -} - -//------------------------------------------------------------------------------ - -AnalogLowShelf::AnalogLowShelf () - : m_numPoles (-1) -{ - setNormal (doublePi, 1); -} - -void AnalogLowShelf::design (int numPoles, double gainDb) -{ - if (m_numPoles != numPoles || - m_gainDb != gainDb) - { - m_numPoles = numPoles; - m_gainDb = gainDb; - - reset (); - - const double n2 = numPoles * 2; - const double g = pow (pow (10., gainDb/20), 1. / n2); - const double gp = -1. / g; - const double gz = -g; - - const int pairs = numPoles / 2; - for (int i = 1; i <= pairs; ++i) - { - const double theta = doublePi * (0.5 - (2 * i - 1) / n2); - addPoleZeroConjugatePairs (std::polar (gp, theta), std::polar (gz, theta)); - } - - if (numPoles & 1) - add (gp, gz); - } -} - -//------------------------------------------------------------------------------ - -void LowPassBase::setup (int order, - double cutoffFrequency) -{ - m_analogProto.design (order); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighPassBase::setup (int order, - double cutoffFrequency) -{ - m_analogProto.design (order); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandPassBase::setup (int order, - double centerFrequency, - double widthFrequency) -{ - m_analogProto.design (order); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandStopBase::setup (int order, - double centerFrequency, - double widthFrequency) -{ - m_analogProto.design (order); - - BandStopTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void LowShelfBase::setup (int order, - double cutoffFrequency, - double gainDb) -{ - m_analogProto.design (order, gainDb); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighShelfBase::setup (int order, - double cutoffFrequency, - double gainDb) -{ - m_analogProto.design (order, gainDb); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandShelfBase::setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb) -{ - m_analogProto.design (order, gainDb); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - // HACK! - m_digitalProto.setNormal ( (centerFrequency < 0.25) ? doublePi : 0, 1); - - Cascade::setLayout (m_digitalProto); -} - -} - -} diff --git a/src/libs/iir1/iir/Butterworth.h b/src/libs/iir1/iir/Butterworth.h deleted file mode 100644 index 37e9c52fd..000000000 --- a/src/libs/iir1/iir/Butterworth.h +++ /dev/null @@ -1,622 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.txt for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_BUTTERWORTH_H -#define IIR1_BUTTERWORTH_H - -#include "Common.h" -#include "Cascade.h" -#include "PoleFilter.h" -#include "State.h" - -namespace Iir { - -/** - * Filters with Butterworth response characteristics. The filter order is usually set - * via the template parameter which reserves the correct space and is then automatically - * passed to the setup function. Optionally one can also provde the filter - * order at setup time to force a lower order than the default one. - **/ -namespace Butterworth { - -/** - * Analogue lowpass prototypes (s-plane) - **/ -class DllExport AnalogLowPass : public LayoutBase -{ -public: - AnalogLowPass (); - - void design (const int numPoles); - -private: - int m_numPoles = 0; -}; - -//------------------------------------------------------------------------------ - -/** - * Analogue low shelf prototypes (s-plane) - **/ -class DllExport AnalogLowShelf : public LayoutBase -{ -public: - AnalogLowShelf (); - - void design (int numPoles, double gainDb); - -private: - int m_numPoles = 0; - double m_gainDb = 0.0; -}; - -//------------------------------------------------------------------------------ - -struct DllExport LowPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency); -}; - -struct DllExport HighPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency); -}; - -struct DllExport BandPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency); -}; - -struct DllExport BandStopBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency); -}; - -struct DllExport LowShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb); -}; - -struct DllExport HighShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb); -}; - -struct DllExport BandShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb); -}; - -//------------------------------------------------------------------------------ - -// -// Filters for the user -// - -/** - * Butterworth Lowpass filter. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport LowPass : PoleFilter <LowPassBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - **/ - void setup (double sampleRate, - double cutoffFrequency) { - LowPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency / sampleRate); - } - - - /** - * Calculates the coefficients - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - **/ - void setupN(double cutoffFrequency) { - LowPassBase::setup (FilterOrder, - cutoffFrequency); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - **/ - void setupN(int reqOrder, - double cutoffFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency); - } -}; - -/** - * Butterworth Highpass filter. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport HighPass : PoleFilter <HighPassBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - **/ - void setup (double sampleRate, - double cutoffFrequency) { - HighPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate); - } - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency / sampleRate); - } - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - **/ - void setupN(double cutoffFrequency) { - HighPassBase::setup (FilterOrder, - cutoffFrequency); - } - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - **/ - void setupN(int reqOrder, - double cutoffFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency); - } -}; - -/** - * Butterworth Bandpass filter. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandPass : PoleFilter <BandPassBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the bandpass - * \param widthFrequency Width of the bandpass - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency) { - BandPassBase::setup(FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the bandpass - * \param widthFrequency Width of the bandpass - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup(reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate); - } - - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass in normalised freq - **/ - void setupN(double centerFrequency, - double widthFrequency) { - BandPassBase::setup(FilterOrder, - centerFrequency, - widthFrequency); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass in normalised freq - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup(reqOrder, - centerFrequency, - widthFrequency); - } -}; - - -/** - * Butterworth Bandstop filter. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandStop : PoleFilter <BandStopBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the bandstop - * \param widthFrequency Width of the bandstop - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency) { - BandStopBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the bandstop - * \param widthFrequency Width of the bandstop - **/ - void setupN(int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate); - } - - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandstop - * \param widthFrequency Normalised width of the bandstop - **/ - void setupN(double centerFrequency, - double widthFrequency) { - BandStopBase::setup (FilterOrder, - centerFrequency, - widthFrequency); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandstop - * \param widthFrequency Normalised width of the bandstop - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency, - widthFrequency); - } - -}; - -/** - * Butterworth low shelf filter: below the cutoff it has - * a specified gain and above the cutoff the gain is 0 dB. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport LowShelf : PoleFilter <LowShelfBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - * \param gainDb Gain in dB of the filter in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - * \param gainDb Gain in dB of the filter in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb); - } - - - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in dB of the filter in the passband - **/ - void setupN(double cutoffFrequency, - double gainDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in dB of the filter in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb); - } - -}; - - -/** - * Butterworth high shelf filter. Above the cutoff the filter has - * a specified gain and below it has 0 dB. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport HighShelf : PoleFilter <HighShelfBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - * \param gainDb Gain in dB of the filter in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff - * \param gainDb Gain in dB of the filter in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb); - } - - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in dB of the filter in the passband - **/ - void setupN(double cutoffFrequency, - double gainDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in dB of the filter in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb); - } -}; - - -/** - * Butterworth Bandshelf filter: it is a bandpass filter which amplifies at a specified - * gain in dB the frequencies in the passband. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandShelf : PoleFilter <BandShelfBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the passband - * \param widthFrequency Width of the passband - * \param gainDb The gain in the passband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Centre frequency of the passband - * \param widthFrequency Width of the passband - * \param gainDb The gain in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb); - } - - - - /** - * Calculates the coefficients with the filter order provided by the instantiation - * \param centerFrequency Normalised centre frequency (0..1/2) of the passband - * \param widthFrequency Width of the passband - * \param gainDb The gain in the passband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double gainDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - gainDb); - } - - /** - * Calculates the coefficients - * \param reqOrder The actual order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the passband - * \param widthFrequency Width of the passband - * \param gainDb The gain in the passband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double gainDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency, - widthFrequency, - gainDb); - } -}; - -} - -} - -#endif - diff --git a/src/libs/iir1/iir/Cascade.cpp b/src/libs/iir1/iir/Cascade.cpp deleted file mode 100644 index a347d498e..000000000 --- a/src/libs/iir1/iir/Cascade.cpp +++ /dev/null @@ -1,125 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "Cascade.h" - -namespace Iir { - - Cascade::Cascade () - : m_numStages (0) - , m_maxStages (0) - , m_stageArray (0) - { - } - - void Cascade::setCascadeStorage (const Storage& storage) - { - m_numStages = 0; - m_maxStages = storage.maxStages; - m_stageArray = storage.stageArray; - } - - complex_t Cascade::response (double normalizedFrequency) const - { - double w = 2 * doublePi * normalizedFrequency; - const complex_t czn1 = std::polar (1., -w); - const complex_t czn2 = std::polar (1., -2 * w); - complex_t ch (1); - complex_t cbot (1); - - const Biquad* stage = m_stageArray; - for (int i = m_numStages; --i >=0; ++stage) - { - complex_t cb (1); - complex_t ct (stage->getB0()/stage->getA0()); - ct = addmul (ct, stage->getB1()/stage->getA0(), czn1); - ct = addmul (ct, stage->getB2()/stage->getA0(), czn2); - cb = addmul (cb, stage->getA1()/stage->getA0(), czn1); - cb = addmul (cb, stage->getA2()/stage->getA0(), czn2); - ch *= ct; - cbot *= cb; - } - - return ch / cbot; - } - - std::vector<PoleZeroPair> Cascade::getPoleZeros () const - { - std::vector<PoleZeroPair> vpz; - vpz.reserve ((unsigned long)m_numStages); - - const Biquad* stage = m_stageArray; - for (int i = m_numStages; --i >=0;) - { - BiquadPoleState bps (*stage++); - vpz.push_back (bps); - } - - return vpz; - } - - void Cascade::applyScale (double scale) - { - if (m_numStages < 1) return; - m_stageArray->applyScale (scale); - } - - - void Cascade::setLayout (const LayoutBase& proto) - { - const int numPoles = proto.getNumPoles(); - m_numStages = (numPoles + 1)/ 2; - if (m_numStages > m_maxStages) - throw_invalid_argument("Number of stages is larger than the max stages."); - - Biquad* stage = m_stageArray; - for (int i = 0; i < m_maxStages; ++i, ++stage) - stage->setIdentity(); - - stage = m_stageArray; - for (int i = 0; i < m_numStages; ++i, ++stage) - stage->setPoleZeroPair (proto[i]); - - applyScale (proto.getNormalGain() / - std::abs (response (proto.getNormalW() / (2 * doublePi)))); - } - - - - - -} - diff --git a/src/libs/iir1/iir/Cascade.h b/src/libs/iir1/iir/Cascade.h deleted file mode 100644 index 586fe3bef..000000000 --- a/src/libs/iir1/iir/Cascade.h +++ /dev/null @@ -1,186 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_CASCADE_H -#define IIR1_CASCADE_H - -#include "Common.h" -#include "Biquad.h" -#include "Layout.h" -#include "MathSupplement.h" - -namespace Iir { - -/** - * Holds coefficients for a cascade of second order sections. - **/ - class DllExport Cascade - { - public: - - /** - * Pointer to an array of Biquads - **/ - struct DllExport Storage - { - /** - * Copy-constructor which receives the pointer to the Biquad array and the number of Biquads - * \param maxStages_ Number of biquads - * \param stageArray_ The array of the Biquads - **/ - Storage (int maxStages_, Biquad* const stageArray_) - : maxStages (maxStages_) - , stageArray (stageArray_) - { - } - - const int maxStages = 0; - Biquad* const stageArray = nullptr; - }; - - /** - * Returns the number of Biquads kept here - **/ - int getNumStages () const - { - return m_numStages; - } - - /** - * Returns a reference to a biquad - **/ - const Biquad& operator[] (int index) - { - if ((index < 0) || (index >= m_numStages)) - throw_invalid_argument("Index out of bounds."); - return m_stageArray[index]; - } - - /** - * Calculate filter response at the given normalized frequency - * \param normalizedFrequency Frequency from 0 to 0.5 (Nyquist) - **/ - complex_t response (double normalizedFrequency) const; - - /** - * Returns a vector with all pole/zero pairs of the whole Biqad cascade - **/ - std::vector<PoleZeroPair> getPoleZeros () const; - - protected: - Cascade (); - - void setCascadeStorage (const Storage& storage); - - void applyScale (double scale); - - void setLayout (const LayoutBase& proto); - - private: - int m_numStages = 0; - int m_maxStages = 0; - Biquad* m_stageArray = nullptr; - }; - - - -//------------------------------------------------------------------------------ - -/** - * Storage for Cascade: This holds a chain of 2nd order filters - * with its coefficients. - **/ - template <int MaxStages,class StateType> - class DllExport CascadeStages { - public: - /** - * Resets all biquads (i.e. the delay lines but not the coefficients) - **/ - void reset () - { - for (auto &state: m_states) - state.reset(); - } - - public: - /** - * Sets the coefficients of the whole chain of - * biquads. - * \param sosCoefficients 2D array in Python style sos ordering: 0-2: FIR, 3-5: IIR coeff. - **/ - void setup (const double (&sosCoefficients)[MaxStages][6]) { - for (int i = 0; i < MaxStages; i++) { - m_stages[i].setCoefficients( - sosCoefficients[i][3], - sosCoefficients[i][4], - sosCoefficients[i][5], - sosCoefficients[i][0], - sosCoefficients[i][1], - sosCoefficients[i][2]); - } - } - - public: - /** - * Filters one sample through the whole chain of biquads and return the result - * \param in Sample to be filtered - * \return filtered sample - **/ - template <typename Sample> - inline Sample filter(const Sample in) - { - double out = in; - StateType* state = m_states; - for (const auto &stage: m_stages) - out = (state++)->filter(out, stage); - return static_cast<Sample> (out); - } - - /** - * Returns the coefficients of the entire Biquad chain - **/ - const Cascade::Storage getCascadeStorage() - { - return Cascade::Storage (MaxStages, m_stages); - } - - private: - Biquad m_stages[MaxStages] = {}; - StateType m_states[MaxStages] = {}; - }; - -} - -#endif diff --git a/src/libs/iir1/iir/ChebyshevI.cpp b/src/libs/iir1/iir/ChebyshevI.cpp deleted file mode 100644 index 23730f4ba..000000000 --- a/src/libs/iir1/iir/ChebyshevI.cpp +++ /dev/null @@ -1,263 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "ChebyshevI.h" - -namespace Iir { - -namespace ChebyshevI { - -AnalogLowPass::AnalogLowPass () - : m_numPoles (-1) -{ -} - -void AnalogLowPass::design (int numPoles, - double rippleDb) -{ - if (m_numPoles != numPoles || - m_rippleDb != rippleDb) - { - m_numPoles = numPoles; - m_rippleDb = rippleDb; - - reset (); - - const double eps = std::sqrt (1. / std::exp (-rippleDb * 0.1 * doubleLn10) - 1); - const double v0 = asinh (1 / eps) / numPoles; - const double sinh_v0 = -sinh (v0); - const double cosh_v0 = cosh (v0); - - const double n2 = 2 * numPoles; - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - const int k = 2 * i + 1 - numPoles; - double a = sinh_v0 * cos (k * doublePi / n2); - double b = cosh_v0 * sin (k * doublePi / n2); - - addPoleZeroConjugatePairs (complex_t (a, b), infinity()); - } - - if (numPoles & 1) - { - add (complex_t (sinh_v0, 0), infinity()); - setNormal (0, 1); - } - else - { - setNormal (0, pow (10, -rippleDb/20.)); - } - } -} - -//------------------------------------------------------------------------------ - -// -// Chebyshev Type I low pass shelf prototype -// From "High-Order Digital Parametric Equalizer Design" -// Sophocles J. Orfanidis -// http://www.ece.rutgers.edu/~orfanidi/ece521/hpeq.pdf -// - -AnalogLowShelf::AnalogLowShelf () -{ - setNormal (doublePi, 1); -} - -void AnalogLowShelf::design (int numPoles, - double gainDb, - double rippleDb) -{ - if (m_numPoles != numPoles || - m_rippleDb != rippleDb || - m_gainDb != gainDb) - { - m_numPoles = numPoles; - m_rippleDb = rippleDb; - m_gainDb = gainDb; - - reset (); - - gainDb = -gainDb; - - if (rippleDb >= fabs(gainDb)) - rippleDb = fabs (gainDb); - if (gainDb<0) - rippleDb = -rippleDb; - - const double G = std::pow (10., gainDb / 20.0 ); - const double Gb = std::pow (10., (gainDb - rippleDb) / 20.0); - const double G0 = 1; - const double g0 = pow (G0 , 1. / numPoles); - - double eps; - if (Gb != G0 ) - eps = sqrt((G*G-Gb*Gb)/(Gb*Gb-G0*G0)); - else - eps = G-1; // This is surely wrong - - const double b = pow (G/eps+Gb*sqrt(1+1/(eps*eps)), 1./numPoles); - const double u = log (b / g0); - const double v = log (pow (1. / eps+sqrt(1+1/(eps*eps)),1./numPoles)); - - const double sinh_u = sinh (u); - const double sinh_v = sinh (v); - const double cosh_u = cosh (u); - const double cosh_v = cosh (v); - const double n2 = 2 * numPoles; - const int pairs = numPoles / 2; - for (int i = 1; i <= pairs; ++i) - { - const double a = doublePi * (2 * i - 1) / n2; - const double sn = sin (a); - const double cs = cos (a); - addPoleZeroConjugatePairs (complex_t (-sn * sinh_u, cs * cosh_u), - complex_t (-sn * sinh_v, cs * cosh_v)); - } - - if (numPoles & 1) - add (-sinh_u, -sinh_v); - } -} - -//------------------------------------------------------------------------------ - -void LowPassBase::setup (int order, - double cutoffFrequency, - double rippleDb) -{ - m_analogProto.design (order, rippleDb); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighPassBase::setup (int order, - double cutoffFrequency, - double rippleDb) -{ - m_analogProto.design (order, rippleDb); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandPassBase::setup (int order, - double centerFrequency, - double widthFrequency, - double rippleDb) -{ - m_analogProto.design (order, rippleDb); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandStopBase::setup (int order, - double centerFrequency, - double widthFrequency, - double rippleDb) -{ - m_analogProto.design (order, rippleDb); - - BandStopTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void LowShelfBase::setup (int order, - double cutoffFrequency, - double gainDb, - double rippleDb) -{ - m_analogProto.design (order, gainDb, rippleDb); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighShelfBase::setup (int order, - double cutoffFrequency, - double gainDb, - double rippleDb) -{ - m_analogProto.design (order, gainDb, rippleDb); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandShelfBase::setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb) -{ - m_analogProto.design (order, gainDb, rippleDb); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - m_digitalProto.setNormal ( (centerFrequency < 0.25) ? doublePi : 0, 1); - - Cascade::setLayout (m_digitalProto); -} - -} - -} diff --git a/src/libs/iir1/iir/ChebyshevI.h b/src/libs/iir1/iir/ChebyshevI.h deleted file mode 100644 index d35d61bd7..000000000 --- a/src/libs/iir1/iir/ChebyshevI.h +++ /dev/null @@ -1,717 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.txt for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_CHEBYSHEVI_H -#define IIR1_CHEBYSHEVI_H - -#include "Common.h" -#include "Cascade.h" -#include "PoleFilter.h" -#include "State.h" - -namespace Iir { - -/** - * Filters with Chebyshev response characteristics. The last parameter - * defines the passband ripple in decibel. - **/ -namespace ChebyshevI { - -/** - * Analog lowpass prototypes (s-plane) - **/ -class DllExport AnalogLowPass : public LayoutBase -{ -public: - AnalogLowPass (); - - void design (const int numPoles, - double rippleDb); - -private: - int m_numPoles = 0; - double m_rippleDb = 0.0; -}; - -/** - * Analog lowpass shelf prototype (s-plane) - **/ -class DllExport AnalogLowShelf : public LayoutBase -{ -public: - AnalogLowShelf (); - - void design (int numPoles, - double gainDb, - double rippleDb); - -private: - int m_numPoles = 0; - double m_rippleDb = 0.0; - double m_gainDb = 0.0; -}; - -//------------------------------------------------------------------------------ - -struct DllExport LowPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency, - double rippleDb); -}; - -struct DllExport HighPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency, - double rippleDb); -}; - -struct DllExport BandPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double rippleDb); -}; - -struct DllExport BandStopBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double rippleDb); -}; - -struct DllExport LowShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb, - double rippleDb); -}; - -struct DllExport HighShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb, - double rippleDb); -}; - -struct DllExport BandShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb); -}; - -//------------------------------------------------------------------------------ - -// -// Userland filters -// - -/** - * ChebyshevI lowpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport LowPass : PoleFilter <LowPassBase, StateType, FilterOrder> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double rippleDb) { - LowPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency / sampleRate, - rippleDb); - } - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double cutoffFrequency, - double rippleDb) { - LowPassBase::setup (FilterOrder, - cutoffFrequency, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency, - rippleDb); - } -}; - -/** - * ChebyshevI highpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport HighPass : PoleFilter <HighPassBase, StateType, FilterOrder> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double rippleDb) { - HighPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency / sampleRate, - rippleDb); - } - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double cutoffFrequency, - double rippleDb) { - HighPassBase::setup (FilterOrder, - cutoffFrequency, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency, - rippleDb); - } -}; - -/** - * ChebyshevI bandpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport BandPass : PoleFilter <BandPassBase, StateType, FilterOrder, FilterOrder*2> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Frequency with of the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double rippleDb) { - BandPassBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Frequency with of the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - rippleDb); - } - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param centerFrequency Normalised center frequency (0..1/2) of the bandpass - * \param widthFrequency Frequency with of the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double rippleDb) { - BandPassBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param centerFrequency Normalised center frequency (0..1/2) of the bandpass - * \param widthFrequency Frequency with of the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup (reqOrder, - centerFrequency, - widthFrequency, - rippleDb); - } -}; - -/** - * ChebyshevI bandstop filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport BandStop : PoleFilter <BandStopBase, StateType, FilterOrder, FilterOrder*2> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the notch - * \param widthFrequency Frequency with of the notch - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double rippleDb) { - BandStopBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the notch - * \param widthFrequency Frequency with of the notch - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - rippleDb); - } - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param centerFrequency Normalised centre frequency (0..1/2) of the notch - * \param widthFrequency Frequency width of the notch - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double rippleDb) { - BandStopBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param centerFrequency Normalised centre frequency (0..1/2) of the notch - * \param widthFrequency Frequency width of the notch - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency, - widthFrequency, - rippleDb); - } - -}; - -/** - * ChebyshevI low shelf filter. Specified gain in the passband. Otherwise 0 dB. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport LowShelf : PoleFilter <LowShelfBase, StateType, FilterOrder> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double rippleDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb, - rippleDb); - } - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double cutoffFrequency, - double gainDb, - double rippleDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb, - rippleDb); - } -}; - -/** - * ChebyshevI high shelf filter. Specified gain in the passband. Otherwise 0 dB. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport HighShelf : PoleFilter <HighShelfBase, StateType, FilterOrder> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double rippleDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb, - rippleDb); - } - - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(double cutoffFrequency, - double gainDb, - double rippleDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb, - rippleDb); - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain in the passband - * \param rippleDb Permitted ripples in dB in the passband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb, - rippleDb); - } - -}; - -/** - * ChebyshevI bandshelf filter. Specified gain in the passband. Otherwise 0 dB. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> - struct DllExport BandShelf : PoleFilter <BandShelfBase, StateType, FilterOrder, FilterOrder*2> - { - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the passband - * \param widthFrequency Width of the passband. - * \param gainDb Gain in the passband. The stopband has 0 dB. - * \param rippleDb Permitted ripples in dB in the passband. - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb, - rippleDb); - - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the passband - * \param widthFrequency Width of the passband. - * \param gainDb Gain in the passband. The stopband has 0 dB. - * \param rippleDb Permitted ripples in dB in the passband. - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb, - rippleDb); - - } - - - - - /** - * Calculates the coefficients of the filter at the order FilterOrder - * \param centerFrequency Normalised centre frequency (0..1/2) of the passband - * \param widthFrequency Width of the passband. - * \param gainDb Gain in the passband. The stopband has 0 dB. - * \param rippleDb Permitted ripples in dB in the passband. - **/ - void setupN(double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - gainDb, - rippleDb); - - } - - /** - * Calculates the coefficients of the filter at specified order - * \param reqOrder Actual order for the filter calculations - * \param centerFrequency Normalised centre frequency (0..1/2) of the passband - * \param widthFrequency Width of the passband. - * \param gainDb Gain in the passband. The stopband has 0 dB. - * \param rippleDb Permitted ripples in dB in the passband. - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double gainDb, - double rippleDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency, - widthFrequency, - gainDb, - rippleDb); - - } - - }; - -} - -} - -#endif diff --git a/src/libs/iir1/iir/ChebyshevII.cpp b/src/libs/iir1/iir/ChebyshevII.cpp deleted file mode 100644 index f9647aba3..000000000 --- a/src/libs/iir1/iir/ChebyshevII.cpp +++ /dev/null @@ -1,264 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "ChebyshevII.h" - -namespace Iir { - -namespace ChebyshevII { - -// "Chebyshev Filter Properties" -// http://cnx.org/content/m16906/latest/ - -AnalogLowPass::AnalogLowPass () - : m_numPoles (-1) -{ - setNormal (0, 1); -} - -void AnalogLowPass::design (int numPoles, - double stopBandDb) -{ - if (m_numPoles != numPoles || - m_stopBandDb != stopBandDb) - { - m_numPoles = numPoles; - m_stopBandDb = stopBandDb; - - reset (); - - const double eps = std::sqrt (1. / (std::exp (stopBandDb * 0.1 * doubleLn10) - 1)); - const double v0 = asinh (1 / eps) / numPoles; - const double sinh_v0 = -sinh (v0); - const double cosh_v0 = cosh (v0); - const double fn = doublePi / (2 * numPoles); - - int k = 1; - for (int i = numPoles / 2; --i >= 0; k+=2) - { - const double a = sinh_v0 * cos ((k - numPoles) * fn); - const double b = cosh_v0 * sin ((k - numPoles) * fn); - const double d2 = a * a + b * b; - const double im = 1 / cos (k * fn); - addPoleZeroConjugatePairs (complex_t (a / d2, b / d2), - complex_t (0, im)); - } - - if (numPoles & 1) - { - add (1 / sinh_v0, infinity()); - } - } -} - -//------------------------------------------------------------------------------ - -// -// Chebyshev Type II low pass shelf prototype -// From "High-Order Digital Parametric Equalizer Design" -// Sophocles J. Orfanidis -// http://www.ece.rutgers.edu/~orfanidi/ece521/hpeq.pdf -// - -AnalogLowShelf::AnalogLowShelf () - : m_numPoles (-1) -{ - setNormal (doublePi, 1); -} - -void AnalogLowShelf::design (int numPoles, - double gainDb, - double stopBandDb) -{ - if (m_numPoles != numPoles || - m_stopBandDb != stopBandDb || - m_gainDb != gainDb) - { - m_numPoles = numPoles; - m_stopBandDb = stopBandDb; - m_gainDb = gainDb; - - reset (); - - gainDb = -gainDb; - - if (stopBandDb >= fabs(gainDb)) - stopBandDb = fabs (gainDb); - if (gainDb<0) - stopBandDb = -stopBandDb; - - const double G = std::pow (10., gainDb / 20.0 ); - const double Gb = std::pow (10., (gainDb - stopBandDb) / 20.0); - const double G0 = 1; - const double g0 = pow (G0 , 1. / numPoles); - - double eps; - if (Gb != G0 ) - eps = sqrt((G*G-Gb*Gb)/(Gb*Gb-G0*G0)); - else - eps = G-1; // This is surely wrong - - const double b = pow (G/eps+Gb*sqrt(1+1/(eps*eps)), 1./numPoles); - const double u = log (b / g0); - const double v = log (pow (1. / eps+sqrt(1+1/(eps*eps)),1./numPoles)); - - const double sinh_u = sinh (u); - const double sinh_v = sinh (v); - const double cosh_u = cosh (u); - const double cosh_v = cosh (v); - const double n2 = 2 * numPoles; - const int pairs = numPoles / 2; - for (int i = 1; i <= pairs; ++i) - { - const double a = doublePi * (2 * i - 1) / n2; - const double sn = sin (a); - const double cs = cos (a); - addPoleZeroConjugatePairs (complex_t (-sn * sinh_u, cs * cosh_u), - complex_t (-sn * sinh_v, cs * cosh_v)); - } - - if (numPoles & 1) - add (-sinh_u, -sinh_v); - } -} - -//------------------------------------------------------------------------------ - -void LowPassBase::setup (int order, - double cutoffFrequency, - double stopBandDb) -{ - m_analogProto.design (order, stopBandDb); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighPassBase::setup (int order, - double cutoffFrequency, - double stopBandDb) -{ - m_analogProto.design (order, stopBandDb); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandPassBase::setup (int order, - double centerFrequency, - double widthFrequency, - double stopBandDb) -{ - m_analogProto.design (order, stopBandDb); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandStopBase::setup (int order, - double centerFrequency, - double widthFrequency, - double stopBandDb) -{ - m_analogProto.design (order, stopBandDb); - - BandStopTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void LowShelfBase::setup (int order, - double cutoffFrequency, - double gainDb, - double stopBandDb) -{ - m_analogProto.design (order, gainDb, stopBandDb); - - LowPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void HighShelfBase::setup (int order, - double cutoffFrequency, - double gainDb, - double stopBandDb) -{ - m_analogProto.design (order, gainDb, stopBandDb); - - HighPassTransform (cutoffFrequency, - m_digitalProto, - m_analogProto); - - Cascade::setLayout (m_digitalProto); -} - -void BandShelfBase::setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb) -{ - m_analogProto.design (order, gainDb, stopBandDb); - - BandPassTransform (centerFrequency, - widthFrequency, - m_digitalProto, - m_analogProto); - - m_digitalProto.setNormal ( (centerFrequency < 0.25) ? doublePi : 0, 1); - - Cascade::setLayout (m_digitalProto); -} - -} - -} diff --git a/src/libs/iir1/iir/ChebyshevII.h b/src/libs/iir1/iir/ChebyshevII.h deleted file mode 100644 index 6eb4d8bce..000000000 --- a/src/libs/iir1/iir/ChebyshevII.h +++ /dev/null @@ -1,734 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.txt for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_CHEBYSHEVII_H -#define IIR1_CHEBYSHEVII_H - -#include "Common.h" -#include "Cascade.h" -#include "PoleFilter.h" -#include "State.h" - -namespace Iir { - -/** - * Filters with ChebyshevII response characteristics. The last parameter - * defines the minimal stopband rejection requested. Generally there will be frequencies where - * the rejection is much better but this parameter guarantees that the rejection is at least - * as specified. - * - **/ -namespace ChebyshevII { - -/** - * Analogue lowpass prototype (s-plane) - **/ -class DllExport AnalogLowPass : public LayoutBase -{ -public: - AnalogLowPass (); - - void design (const int numPoles, - double stopBandDb); - -private: - int m_numPoles = 0; - double m_stopBandDb = 0.0; -}; - - -/** - * Analogue shelf lowpass prototype (s-plane) - **/ -class DllExport AnalogLowShelf : public LayoutBase -{ -public: - AnalogLowShelf (); - - void design (int numPoles, - double gainDb, - double stopBandDb); - -private: - int m_numPoles = 0; - double m_stopBandDb = 0.0; - double m_gainDb = 0.0; -}; - -//------------------------------------------------------------------------------ - -struct DllExport LowPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency, - double stopBandDb); -}; - -struct DllExport HighPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double cutoffFrequency, - double stopBandDb); -}; - -struct DllExport BandPassBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double stopBandDb); -}; - -struct DllExport BandStopBase : PoleFilterBase <AnalogLowPass> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double stopBandDb); -}; - -struct DllExport LowShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb, - double stopBandDb); -}; - -struct DllExport HighShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double cutoffFrequency, - double gainDb, - double stopBandDb); -}; - -struct DllExport BandShelfBase : PoleFilterBase <AnalogLowShelf> -{ - void setup (int order, - double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb); -}; - -//------------------------------------------------------------------------------ - -// -// Userland filters -// - -/** - * ChebyshevII lowpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport LowPass : PoleFilter <LowPassBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double stopBandDb) { - LowPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency / sampleRate, - stopBandDb); - } - - - - - - /** - * Calculates the coefficients of the filter - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double cutoffFrequency, - double stopBandDb) { - LowPassBase::setup (FilterOrder, - cutoffFrequency, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowPassBase::setup (reqOrder, - cutoffFrequency, - stopBandDb); - } - -}; - -/** - * ChebyshevII highpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport HighPass : PoleFilter <HighPassBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double stopBandDb) { - HighPassBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency / sampleRate, - stopBandDb); - } - - - - - /** - * Calculates the coefficients of the filter - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double cutoffFrequency, - double stopBandDb) { - HighPassBase::setup (FilterOrder, - cutoffFrequency, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighPassBase::setup (reqOrder, - cutoffFrequency, - stopBandDb); - } - -}; - -/** - * ChebyshevII bandpass filter - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandPass : PoleFilter <BandPassBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Width of the bandpass - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - BandPassBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Width of the bandpass - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - stopBandDb); - } - - - - - /** - * Calculates the coefficients of the filter - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double stopBandDb) { - BandPassBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandPassBase::setup (reqOrder, - centerFrequency, - widthFrequency, - stopBandDb); - } -}; - -/** - * ChebyshevII bandstop filter. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - */ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandStop : PoleFilter <BandStopBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandstop - * \param widthFrequency Width of the bandstop - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - BandStopBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandstop - * \param widthFrequency Width of the bandstop - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - stopBandDb); - } - - - - - /** - * Calculates the coefficients of the filter - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandstop - * \param widthFrequency Width of the bandstop - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double stopBandDb) { - BandStopBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandstop - * \param widthFrequency Width of the bandstop - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandStopBase::setup (reqOrder, - centerFrequency, - widthFrequency, - stopBandDb); - } -}; - -/** - * ChebyshevII low shelf filter. Specified gain in the passband and 0dB in the stopband. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport LowShelf : PoleFilter <LowShelfBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain of the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param gainDb Gain of the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb, - stopBandDb); - } - - - - - - /** - * Calculates the coefficients of the filter - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain of the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double cutoffFrequency, - double gainDb, - double stopBandDb) { - LowShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - LowShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb, - stopBandDb); - } - -}; - -/** - * ChebyshevII high shelf filter. Specified gain in the passband and 0dB in the stopband. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport HighShelf : PoleFilter <HighShelfBase, StateType, FilterOrder> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency / sampleRate, - gainDb, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency. - * \param gainDb Gain the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency / sampleRate, - gainDb, - stopBandDb); - } - - - - - - - /** - * Calculates the coefficients of the filter - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double cutoffFrequency, - double gainDb, - double stopBandDb) { - HighShelfBase::setup (FilterOrder, - cutoffFrequency, - gainDb, - stopBandDb); - } - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param gainDb Gain the passbard. The stopband has 0 dB gain. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double cutoffFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - HighShelfBase::setup (reqOrder, - cutoffFrequency, - gainDb, - stopBandDb); - } - -}; - -/** - * ChebyshevII bandshelf filter. Bandpass with specified gain and 0 dB gain in the stopband. - * \param FilterOrder Reserves memory for a filter of the order FilterOrder - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int FilterOrder = DEFAULT_FILTER_ORDER, class StateType = DEFAULT_STATE> -struct DllExport BandShelf : PoleFilter <BandShelfBase, StateType, FilterOrder, FilterOrder*2> -{ - /** - * Calculates the coefficients of the filter - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Width of the bandpass - * \param gainDb Gain in the passband. The stopband has always 0dB. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb, - stopBandDb); - } - - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param widthFrequency Width of the bandpass - * \param gainDb Gain in the passband. The stopband has always 0dB. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setup (int reqOrder, - double sampleRate, - double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency / sampleRate, - widthFrequency / sampleRate, - gainDb, - stopBandDb); - } - - - - - - - - /** - * Calculates the coefficients of the filter - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass - * \param gainDb Gain in the passband. The stopband has always 0dB. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb) { - BandShelfBase::setup (FilterOrder, - centerFrequency, - widthFrequency, - gainDb, - stopBandDb); - } - - - /** - * Calculates the coefficients of the filter - * \param reqOrder Requested order which can be less than the instantiated one - * \param centerFrequency Normalised centre frequency (0..1/2) of the bandpass - * \param widthFrequency Width of the bandpass - * \param gainDb Gain in the passband. The stopband has always 0dB. - * \param stopBandDb Permitted ripples in dB in the stopband - **/ - void setupN(int reqOrder, - double centerFrequency, - double widthFrequency, - double gainDb, - double stopBandDb) { - if (reqOrder > FilterOrder) throw_invalid_argument(orderTooHigh); - BandShelfBase::setup (reqOrder, - centerFrequency, - widthFrequency, - gainDb, - stopBandDb); - } - - -}; - -} - -} - -#endif diff --git a/src/libs/iir1/iir/Common.h b/src/libs/iir1/iir/Common.h deleted file mode 100644 index 97ad22b4a..000000000 --- a/src/libs/iir1/iir/Common.h +++ /dev/null @@ -1,89 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_COMMON_H -#define IIR1_COMMON_H - -// -// This must be the first file included in every DspFilters header and source -// - -#ifdef _MSC_VER -# pragma warning (disable: 4100) -#endif - -// This exports the classes/structures to the windows DLL -#ifdef _WIN32 -# define DllExport __declspec( dllexport ) -# ifndef _CRT_SECURE_NO_WARNINGS -# define _CRT_SECURE_NO_WARNINGS -# endif -#else -# define DllExport -#endif - -#include <stdlib.h> - -#include <cassert> -#include <cfloat> -#include <cmath> -#include <complex> -#include <cstring> -#include <string> -#include <limits> -#include <vector> -#include <stdexcept> // for invalid_argument - -static const char orderTooHigh[] = "Requested order is too high. Provide a higher order for the template."; - -#define DEFAULT_FILTER_ORDER 4 - -/** - * @brief Throw invalid argument exception if exceptions are enabled, otherwise abort. - * - * @param msg Error message - */ -inline void throw_invalid_argument(const char* msg) { - -#ifndef IIR1_NO_EXCEPTIONS - throw std::invalid_argument(msg); -#else - (void) msg; // Discard parameter - abort(); -#endif - -} - -#endif diff --git a/src/libs/iir1/iir/Custom.cpp b/src/libs/iir1/iir/Custom.cpp deleted file mode 100644 index e1cebdfd5..000000000 --- a/src/libs/iir1/iir/Custom.cpp +++ /dev/null @@ -1,66 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.txt for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "Custom.h" - -namespace Iir { - -namespace Custom { - -void OnePole::setup (double scale, - double pole, - double zero) -{ - setOnePole (pole, zero); - applyScale (scale); -} - -void TwoPole::setup (double scale, - double poleRho, - double poleTheta, - double zeroRho, - double zeroTheta) -{ - complex_t pole = std::polar (poleRho, poleTheta); - complex_t zero = std::polar (zeroRho, zeroTheta); - - setTwoPole (pole, zero, std::conj(pole), std::conj(zero)); - applyScale (scale); -} - -} - -} diff --git a/src/libs/iir1/iir/Custom.h b/src/libs/iir1/iir/Custom.h deleted file mode 100644 index c4367159f..000000000 --- a/src/libs/iir1/iir/Custom.h +++ /dev/null @@ -1,129 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.txt for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_CUSTOM_H -#define IIR1_CUSTOM_H - -#include "Common.h" -#include "Biquad.h" -#include "Cascade.h" -#include "PoleFilter.h" -#include "State.h" - - -namespace Iir { - -/** - * Single pole, Biquad and cascade of Biquads with parameters allowing - * for directly setting the parameters. - **/ - -namespace Custom { - -/** - * Setting up a filter with with one real pole, real zero and scale it by the scale factor - * \param scale Scale the FIR coefficients by this factor - * \param pole Position of the pole on the real axis - * \param zero Position of the zero on the real axis - **/ -struct OnePole : public Biquad -{ - void setup (double scale, - double pole, - double zero); -}; - -/** - * Set a pole/zero pair in polar coordinates and scale the FIR filter coefficients - * \param poleRho Radius of the pole - * \param poleTheta Angle of the pole - * \param zeroRho Radius of the zero - * \param zeroTheta Angle of the zero - **/ -struct TwoPole : public Biquad -{ - void setup (double scale, - double poleRho, - double poleTheta, - double zeroRho, - double zeroTheta); -}; - -/** - * A custom cascade of 2nd order (SOS / biquads) filters. - * \param NSOS The number of 2nd order filters / biquads. - * \param StateType The filter topology: DirectFormI, DirectFormII, ... - **/ -template <int NSOS, class StateType = DEFAULT_STATE> -struct DllExport SOSCascade : CascadeStages<NSOS,StateType> -{ - /** - * Default constructor which creates a unity gain filter of NSOS biquads. - * Set the filter coefficients later with the setup() method. - **/ - SOSCascade() = default; - /** - * Python scipy.signal-friendly setting of coefficients. - * Initialises the coefficients of the whole chain of - * biquads / SOS. The argument is a 2D array where the 1st - * dimension holds an array of 2nd order biquad / SOS coefficients. - * The six SOS coefficients are ordered "Python" style with first - * the FIR coefficients (B) and then the IIR coefficients (A). - * The 2D const double array needs to have exactly the size [NSOS][6]. - * \param sosCoefficients 2D array Python style sos[NSOS][6]. Indexing: 0-2: FIR-, 3-5: IIR-coefficients. - **/ - SOSCascade(const double (&sosCoefficients)[NSOS][6]) { - CascadeStages<NSOS,StateType>::setup(sosCoefficients); - } - /** - * Python scipy.signal-friendly setting of coefficients. - * Sets the coefficients of the whole chain of - * biquads / SOS. The argument is a 2D array where the 1st - * dimension holds an array of 2nd order biquad / SOS coefficients. - * The six SOS coefficients are ordered "Python" style with first - * the FIR coefficients (B) and then the IIR coefficients (A). - * The 2D const double array needs to have exactly the size [NSOS][6]. - * \param sosCoefficients 2D array Python style sos[NSOS][6]. Indexing: 0-2: FIR-, 3-5: IIR-coefficients. - **/ - void setup (const double (&sosCoefficients)[NSOS][6]) { - CascadeStages<NSOS,StateType>::setup(sosCoefficients); - } -}; - -} - -} - -#endif diff --git a/src/libs/iir1/iir/Layout.h b/src/libs/iir1/iir/Layout.h deleted file mode 100644 index c3de277f0..000000000 --- a/src/libs/iir1/iir/Layout.h +++ /dev/null @@ -1,196 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_LAYOUT_H -#define IIR1_LAYOUT_H - -#include "Common.h" -#include "MathSupplement.h" - -/** - * Describes a filter as a collection of poles and zeros along with - * normalization information to achieve a specified gain at a specified - * frequency. The poles and zeros may lie either in the s or the z plane. - **/ -namespace Iir { - - static const char errPoleisNaN[] = "Pole to add is NaN."; - static const char errZeroisNaN[] = "Zero to add is NaN."; - - static const char errCantAdd2ndOrder[] = "Can't add 2nd order after a 1st order filter."; - - static const char errPolesNotComplexConj[] = "Poles not complex conjugate."; - static const char errZerosNotComplexConj[] = "Zeros not complex conjugate."; - - static const char pairIndexOutOfBounds[] = "Pair index out of bounds."; - -/** - * Base uses pointers to reduce template instantiations - **/ - class DllExport LayoutBase - { - public: - LayoutBase () - : m_numPoles (0) - , m_maxPoles (0) - , m_pair (nullptr) - { - } - - LayoutBase (int maxPoles, PoleZeroPair* pairs) - : m_numPoles (0) - , m_maxPoles (maxPoles) - , m_pair (pairs) - { - } - - void setStorage (const LayoutBase& other) - { - m_numPoles = 0; - m_maxPoles = other.m_maxPoles; - m_pair = other.m_pair; - } - - void reset () - { - m_numPoles = 0; - } - - int getNumPoles () const - { - return m_numPoles; - } - - int getMaxPoles () const - { - return m_maxPoles; - } - - void add (const complex_t& pole, const complex_t& zero) - { - if (m_numPoles&1) - throw_invalid_argument(errCantAdd2ndOrder); - if (Iir::is_nan(pole)) - throw_invalid_argument(errPoleisNaN); - if (Iir::is_nan(zero)) - throw_invalid_argument(errZeroisNaN); - m_pair[m_numPoles/2] = PoleZeroPair (pole, zero); - ++m_numPoles; - } - - void addPoleZeroConjugatePairs (const complex_t& pole, - const complex_t& zero) - { - if (m_numPoles&1) - throw_invalid_argument(errCantAdd2ndOrder); - if (Iir::is_nan(pole)) - throw_invalid_argument(errPoleisNaN); - if (Iir::is_nan(zero)) - throw_invalid_argument(errZeroisNaN); - m_pair[m_numPoles/2] = PoleZeroPair ( - pole, zero, std::conj (pole), std::conj (zero)); - m_numPoles += 2; - } - - void add (const ComplexPair& poles, const ComplexPair& zeros) - { - if (m_numPoles&1) - throw_invalid_argument(errCantAdd2ndOrder); - if (!poles.isMatchedPair ()) - throw_invalid_argument(errPolesNotComplexConj); - if (!zeros.isMatchedPair ()) - throw_invalid_argument(errZerosNotComplexConj); - m_pair[m_numPoles/2] = PoleZeroPair (poles.first, zeros.first, - poles.second, zeros.second); - m_numPoles += 2; - } - - const PoleZeroPair& getPair (int pairIndex) const - { - if ((pairIndex < 0) || (pairIndex >= (m_numPoles+1)/2)) - throw_invalid_argument(pairIndexOutOfBounds); - return m_pair[pairIndex]; - } - - const PoleZeroPair& operator[] (int pairIndex) const - { - return getPair (pairIndex); - } - - double getNormalW () const - { - return m_normalW; - } - - double getNormalGain () const - { - return m_normalGain; - } - - void setNormal (double w, double g) - { - m_normalW = w; - m_normalGain = g; - } - - private: - int m_numPoles = 0; - int m_maxPoles = 0; - PoleZeroPair* m_pair = nullptr; - double m_normalW = 0; - double m_normalGain = 1; - }; - -//------------------------------------------------------------------------------ - -/** - * Storage for Layout - **/ - template <int MaxPoles> - class DllExport Layout - { - public: - operator LayoutBase () - { - return LayoutBase (MaxPoles, m_pairs); - } - - private: - PoleZeroPair m_pairs[(MaxPoles+1)/2] = {}; - }; - -} - -#endif diff --git a/src/libs/iir1/iir/MathSupplement.h b/src/libs/iir1/iir/MathSupplement.h deleted file mode 100644 index 7bc4fbf8b..000000000 --- a/src/libs/iir1/iir/MathSupplement.h +++ /dev/null @@ -1,127 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_MATHSUPPLEMENT_H -#define IIR1_MATHSUPPLEMENT_H - -#include "Common.h" - -#include<complex> - -#ifdef _MSC_VER - // Under Unix these have already default instantiations but not under Vis Studio -template class DllExport std::complex<double>; -template class DllExport std::complex<float>; -#endif - -namespace Iir { - -const double doublePi =3.1415926535897932384626433832795028841971; -const double doublePi_2 =1.5707963267948966192313216916397514420986; -const double doubleLn2 =0.69314718055994530941723212145818; -const double doubleLn10 =2.3025850929940456840179914546844; - -typedef std::complex<double> complex_t; -typedef std::pair<complex_t, complex_t> complex_pair_t; - -template<typename Real> -inline std::complex<Real> solve_quadratic_1 (Real a, Real b, Real c) -{ - return (-b + sqrt (std::complex<Real> (b*b - 4*a*c, 0))) / (2. * a); -} - -template<typename Real> -inline std::complex<Real> solve_quadratic_2 (Real a, Real b, Real c) -{ - return (-b - sqrt (std::complex<Real> (b*b - 4*a*c, 0))) / (2. * a); -} - -inline const complex_t infinity() -{ - return complex_t (std::numeric_limits<double>::infinity()); -} - -inline const complex_t adjust_imag (const complex_t& c) -{ - if (fabs (c.imag()) < 1e-30) - return complex_t (c.real(), 0); - else - return c; -} - -template <typename Ty, typename To> -inline std::complex<Ty> addmul (const std::complex<Ty>& c, - Ty v, - const std::complex<To>& c1) -{ - return std::complex <Ty> ( - c.real() + v * c1.real(), c.imag() + v * c1.imag()); -} - -template <typename Ty> -inline std::complex<Ty> recip (const std::complex<Ty>& c) -{ - Ty n = 1.0 / std::norm (c); - - return std::complex<Ty> (n * c.real(), n * c.imag()); -} - -template <typename Ty> -inline Ty asinh (Ty x) -{ - return log (x + std::sqrt (x * x + 1 )); -} - -template <typename Ty> -inline Ty acosh (Ty x) -{ - return log (x + std::sqrt (x * x - 1)); -} - -template <typename Ty> -inline bool is_nan (Ty v) -{ - return !(v == v); -} - -template <> -inline bool is_nan<complex_t> (complex_t v) -{ - return Iir::is_nan (v.real()) || Iir::is_nan (v.imag()); -} - -} - -#endif diff --git a/src/libs/iir1/iir/PoleFilter.cpp b/src/libs/iir1/iir/PoleFilter.cpp deleted file mode 100644 index d54a5eba5..000000000 --- a/src/libs/iir1/iir/PoleFilter.cpp +++ /dev/null @@ -1,309 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "PoleFilter.h" - -namespace Iir { - -//------------------------------------------------------------------------------ - - -static const char cutoffError[] = "The cutoff frequency needs to be below the Nyquist frequency."; -static const char cutoffNeg[] = "Cutoff frequency is negative."; - -complex_t LowPassTransform::transform (complex_t c) -{ - if (c == infinity()) - return complex_t (-1, 0); - - // frequency transform - c = f * c; - - // bilinear low pass transform - return (1. + c) / (1. - c); -} - -LowPassTransform::LowPassTransform (double fc, - LayoutBase& digital, - LayoutBase const& analog) -{ - - if (!(fc < 0.5)) throw_invalid_argument(cutoffError); - if (fc < 0.0) throw_invalid_argument(cutoffNeg); - - digital.reset (); - - // prewarp - f = tan (doublePi * fc); - - const int numPoles = analog.getNumPoles (); - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - const PoleZeroPair& pair = analog[i]; - digital.addPoleZeroConjugatePairs (transform (pair.poles.first), - transform (pair.zeros.first)); - } - - if (numPoles & 1) - { - const PoleZeroPair& pair = analog[pairs]; - digital.add (transform (pair.poles.first), - transform (pair.zeros.first)); - } - - digital.setNormal (analog.getNormalW(), - analog.getNormalGain()); -} - -//------------------------------------------------------------------------------ - -complex_t HighPassTransform::transform (complex_t c) -{ - if (c == infinity()) - return complex_t (1, 0); - - // frequency transform - c = f * c; - - // bilinear high pass transform - return - (1. + c) / (1. - c); -} - -HighPassTransform::HighPassTransform (double fc, - LayoutBase& digital, - LayoutBase const& analog) -{ - if (!(fc < 0.5)) throw_invalid_argument(cutoffError); - if (fc < 0.0) throw_invalid_argument(cutoffNeg); - - digital.reset (); - - // prewarp - f = 1. / tan (doublePi * fc); - - const int numPoles = analog.getNumPoles (); - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - const PoleZeroPair& pair = analog[i]; - digital.addPoleZeroConjugatePairs (transform (pair.poles.first), - transform (pair.zeros.first)); - } - - if (numPoles & 1) - { - const PoleZeroPair& pair = analog[pairs]; - digital.add (transform (pair.poles.first), - transform (pair.zeros.first)); - } - - digital.setNormal (doublePi - analog.getNormalW(), - analog.getNormalGain()); -} - -//------------------------------------------------------------------------------ - -BandPassTransform::BandPassTransform (double fc, - double fw, - LayoutBase& digital, - LayoutBase const& analog) -{ - if (!(fc < 0.5)) throw_invalid_argument(cutoffError); - if (fc < 0.0) throw_invalid_argument(cutoffNeg); - - digital.reset (); - - const double ww = 2 * doublePi * fw; - - // pre-calcs - wc2 = 2 * doublePi * fc - (ww / 2); - wc = wc2 + ww; - - // what is this crap? - if (wc2 < 1e-8) - wc2 = 1e-8; - if (wc > doublePi-1e-8) - wc = doublePi-1e-8; - - a = cos ((wc + wc2) * 0.5) / - cos ((wc - wc2) * 0.5); - b = 1 / tan ((wc - wc2) * 0.5); - a2 = a * a; - b2 = b * b; - ab = a * b; - ab_2 = 2 * ab; - - const int numPoles = analog.getNumPoles (); - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - const PoleZeroPair& pair = analog[i]; - ComplexPair p1 = transform (pair.poles.first); - ComplexPair z1 = transform (pair.zeros.first); - - digital.addPoleZeroConjugatePairs (p1.first, z1.first); - digital.addPoleZeroConjugatePairs (p1.second, z1.second); - } - - if (numPoles & 1) - { - ComplexPair poles = transform (analog[pairs].poles.first); - ComplexPair zeros = transform (analog[pairs].zeros.first); - - digital.add (poles, zeros); - } - - double wn = analog.getNormalW(); - digital.setNormal (2 * atan (sqrt (tan ((wc + wn)* 0.5) * tan((wc2 + wn)* 0.5))), - analog.getNormalGain()); -} - -ComplexPair BandPassTransform::transform (complex_t c) -{ - if (c == infinity()) - return ComplexPair (-1, 1); - - c = (1. + c) / (1. - c); // bilinear - - complex_t v = 0; - v = addmul (v, 4 * (b2 * (a2 - 1) + 1), c); - v += 8 * (b2 * (a2 - 1) - 1); - v *= c; - v += 4 * (b2 * (a2 - 1) + 1); - v = std::sqrt (v); - - complex_t u = -v; - u = addmul (u, ab_2, c); - u += ab_2; - - v = addmul (v, ab_2, c); - v += ab_2; - - complex_t d = 0; - d = addmul (d, 2 * (b - 1), c) + 2 * (1 + b); - - return ComplexPair (u/d, v/d); -} - -//------------------------------------------------------------------------------ - -BandStopTransform::BandStopTransform (double fc, - double fw, - LayoutBase& digital, - LayoutBase const& analog) -{ - if (!(fc < 0.5)) throw_invalid_argument(cutoffError); - if (fc < 0.0) throw_invalid_argument(cutoffNeg); - - digital.reset (); - - const double ww = 2 * doublePi * fw; - - wc2 = 2 * doublePi * fc - (ww / 2); - wc = wc2 + ww; - - // this is crap - if (wc2 < 1e-8) - wc2 = 1e-8; - if (wc > doublePi-1e-8) - wc = doublePi-1e-8; - - a = cos ((wc + wc2) * .5) / - cos ((wc - wc2) * .5); - b = tan ((wc - wc2) * .5); - a2 = a * a; - b2 = b * b; - - const int numPoles = analog.getNumPoles (); - const int pairs = numPoles / 2; - for (int i = 0; i < pairs; ++i) - { - const PoleZeroPair& pair = analog[i]; - ComplexPair p = transform (pair.poles.first); - ComplexPair z = transform (pair.zeros.first); - - // trick to get the conjugate - if (z.second == z.first) - z.second = std::conj (z.first); - - digital.addPoleZeroConjugatePairs (p.first, z.first); - digital.addPoleZeroConjugatePairs (p.second, z.second); - } - - if (numPoles & 1) - { - ComplexPair poles = transform (analog[pairs].poles.first); - ComplexPair zeros = transform (analog[pairs].zeros.first); - - digital.add (poles, zeros); - } - - if (fc < 0.25) - digital.setNormal (doublePi, analog.getNormalGain()); - else - digital.setNormal (0, analog.getNormalGain()); -} - -ComplexPair BandStopTransform::transform (complex_t c) -{ - if (c == infinity()) - c = -1; - else - c = (1. + c) / (1. - c); // bilinear - - complex_t u (0); - u = addmul (u, 4 * (b2 + a2 - 1), c); - u += 8 * (b2 - a2 + 1); - u *= c; - u += 4 * (a2 + b2 - 1); - u = std::sqrt (u); - - complex_t v = u * -.5; - v += a; - v = addmul (v, -a, c); - - u *= .5; - u += a; - u = addmul (u, -a, c); - - complex_t d (b + 1); - d = addmul (d, b-1, c); - - return ComplexPair (u/d, v/d); -} - -} diff --git a/src/libs/iir1/iir/PoleFilter.h b/src/libs/iir1/iir/PoleFilter.h deleted file mode 100644 index 34452f6cd..000000000 --- a/src/libs/iir1/iir/PoleFilter.h +++ /dev/null @@ -1,228 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_POLEFILTER_H -#define IIR1_POLEFILTER_H - -#include "Common.h" -#include "MathSupplement.h" -#include "Cascade.h" -#include "State.h" - -namespace Iir { - -/*** - * Base for filters designed via algorithmic placement of poles and zeros. - * - * Typically, the filter is first designed as a half-band low pass or - * low shelf analog filter (s-plane). Then, using a transformation such - * as the ones from Constantinides, the poles and zeros of the analog filter - * are calculated in the z-plane. - * - ***/ - -/** - * Factored implementations to reduce template instantiations - **/ -class DllExport PoleFilterBase2 : public Cascade -{ -public: - // This gets the poles/zeros directly from the digital - // prototype. It is used to double check the correctness - // of the recovery of pole/zeros from biquad coefficients. - // - // It can also be used to accelerate the interpolation - // of pole/zeros for parameter modulation, since a pole - // filter already has them calculated - - std::vector<PoleZeroPair> getPoleZeros () const - { - std::vector<PoleZeroPair> vpz; - const int pairs = (m_digitalProto.getNumPoles () + 1) / 2; - for (int i = 0; i < pairs; ++i) - vpz.push_back (m_digitalProto[i]); - return vpz; - } - -protected: - LayoutBase m_digitalProto = {}; -}; - - -/** - * Serves a container to hold the analog prototype - * and the digital pole/zero layout. - **/ -template <class AnalogPrototype> -class DllExport PoleFilterBase : public PoleFilterBase2 -{ -protected: - void setPrototypeStorage (const LayoutBase& analogStorage, - const LayoutBase& digitalStorage) - { - m_analogProto.setStorage (analogStorage); - m_digitalProto = digitalStorage; - } - -protected: - AnalogPrototype m_analogProto = {}; -}; - -//------------------------------------------------------------------------------ - -/** - * Storage for pole filters - **/ -template <class BaseClass, - class StateType, - int MaxAnalogPoles, - int MaxDigitalPoles = MaxAnalogPoles> - struct PoleFilter : BaseClass - , CascadeStages <(MaxDigitalPoles + 1) / 2 , StateType> -{ - PoleFilter () - { - // This glues together the factored base classes - // with the templatized storage classes. - BaseClass::setCascadeStorage (this->getCascadeStorage()); - BaseClass::setPrototypeStorage (m_analogStorage, m_digitalStorage); - } - -private: - Layout <MaxAnalogPoles> m_analogStorage = {}; - Layout <MaxDigitalPoles> m_digitalStorage = {}; -}; - -//------------------------------------------------------------------------------ - -/** - * s-plane to z-plane transforms - * - * For pole filters, an analog prototype is created via placement of - * poles and zeros in the s-plane. The analog prototype is either - * a halfband low pass or a halfband low shelf. The poles, zeros, - * and normalization parameters are transformed into the z-plane - * using variants of the bilinear transformation. - * - **/ - -/** - * low pass to low pass - **/ -class DllExport LowPassTransform -{ -public: - LowPassTransform (double fc, - LayoutBase& digital, - LayoutBase const& analog); - -private: - complex_t transform (complex_t c); - - double f = 0.0; -}; - -//------------------------------------------------------------------------------ - -/** - * low pass to high pass - **/ -class DllExport HighPassTransform -{ -public: - HighPassTransform (double fc, - LayoutBase& digital, - LayoutBase const& analog); - -private: - complex_t transform (complex_t c); - - double f = 0.0; -}; - -//------------------------------------------------------------------------------ - -/** - * low pass to band pass transform - **/ -class DllExport BandPassTransform -{ - -public: - BandPassTransform (double fc, - double fw, - LayoutBase& digital, - LayoutBase const& analog); - -private: - ComplexPair transform (complex_t c); - - double wc = 0.0; - double wc2 = 0.0; - double a = 0.0; - double b = 0.0; - double a2 = 0.0; - double b2 = 0.0; - double ab = 0.0; - double ab_2 = 0.0; -}; - -//------------------------------------------------------------------------------ - -/** - * low pass to band stop transform - **/ -class DllExport BandStopTransform -{ -public: - BandStopTransform (double fc, - double fw, - LayoutBase& digital, - LayoutBase const& analog); - -private: - ComplexPair transform (complex_t c); - - double wc = 0.0; - double wc2 = 0.0; - double a = 0.0; - double b = 0.0; - double a2 = 0.0; - double b2 = 0.0; -}; - -} - -#endif diff --git a/src/libs/iir1/iir/RBJ.cpp b/src/libs/iir1/iir/RBJ.cpp deleted file mode 100644 index b1b80ebe8..000000000 --- a/src/libs/iir1/iir/RBJ.cpp +++ /dev/null @@ -1,216 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#include "Common.h" -#include "RBJ.h" - -namespace Iir { - -namespace RBJ { - - void LowPass::setupN(double cutoffFrequency, - double q) - { - double w0 = 2 * doublePi * cutoffFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / (2 * q); - double b0 = (1 - cs) / 2; - double b1 = 1 - cs; - double b2 = (1 - cs) / 2; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void HighPass::setupN (double cutoffFrequency, - double q) - { - double w0 = 2 * doublePi * cutoffFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / ( 2 * q ); - double b0 = (1 + cs) / 2; - double b1 = -(1 + cs); - double b2 = (1 + cs) / 2; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void BandPass1::setupN (double centerFrequency, - double bandWidth) - { - double w0 = 2 * doublePi * centerFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / ( 2 * bandWidth ); - double b0 = bandWidth * AL;// sn / 2; - double b1 = 0; - double b2 = -bandWidth * AL;//-sn / 2; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void BandPass2::setupN (double centerFrequency, - double bandWidth) - { - double w0 = 2 * doublePi * centerFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / ( 2 * bandWidth ); - double b0 = AL; - double b1 = 0; - double b2 = -AL; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void BandStop::setupN (double centerFrequency, - double bandWidth) - { - double w0 = 2 * doublePi * centerFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / ( 2 * bandWidth ); - double b0 = 1; - double b1 = -2 * cs; - double b2 = 1; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void IIRNotch::setupN (double centerFrequency, - double q_factor) - { - double w0 = 2 * doublePi * centerFrequency; - double cs = cos (w0); - double r = exp(-(w0/2) / q_factor); - double b0 = 1; - double b1 = -2 * cs; - double b2 = 1; - double a0 = 1; - double a1 = -2 * r * cs; - double a2 = r * r; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - void LowShelf::setupN (double cutoffFrequency, - double gainDb, - double shelfSlope) - { - double A = pow (10, gainDb/40); - double w0 = 2 * doublePi * cutoffFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / 2 * ::std::sqrt ((A + 1/A) * (1/shelfSlope - 1) + 2); - double sq = 2 * sqrt(A) * AL; - double b0 = A*( (A+1) - (A-1)*cs + sq ); - double b1 = 2*A*( (A-1) - (A+1)*cs ); - double b2 = A*( (A+1) - (A-1)*cs - sq ); - double a0 = (A+1) + (A-1)*cs + sq; - double a1 = -2*( (A-1) + (A+1)*cs ); - double a2 = (A+1) + (A-1)*cs - sq; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - - void HighShelf::setupN (double cutoffFrequency, - double gainDb, - double shelfSlope) - { - double A = pow (10, gainDb/40); - double w0 = 2 * doublePi * cutoffFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / 2 * ::std::sqrt ((A + 1/A) * (1/shelfSlope - 1) + 2); - double sq = 2 * sqrt(A) * AL; - double b0 = A*( (A+1) + (A-1)*cs + sq ); - double b1 = -2*A*( (A-1) + (A+1)*cs ); - double b2 = A*( (A+1) + (A-1)*cs - sq ); - double a0 = (A+1) - (A-1)*cs + sq; - double a1 = 2*( (A-1) - (A+1)*cs ); - double a2 = (A+1) - (A-1)*cs - sq; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - - - void BandShelf::setupN (double centerFrequency, - double gainDb, - double bandWidth) - { - double A = pow (10, gainDb/40); - double w0 = 2 * doublePi * centerFrequency; - double cs = cos(w0); - double sn = sin(w0); - double AL = sn * sinh( doubleLn2/2 * bandWidth * w0/sn ); - if (Iir::is_nan (AL)) - throw_invalid_argument("No solution available for these parameters.\n"); - double b0 = 1 + AL * A; - double b1 = -2 * cs; - double b2 = 1 - AL * A; - double a0 = 1 + AL / A; - double a1 = -2 * cs; - double a2 = 1 - AL / A; - setCoefficients (a0, a1, a2, b0, b1, b2); - } - -void AllPass::setupN (double phaseFrequency, - double q) -{ - double w0 = 2 * doublePi * phaseFrequency; - double cs = cos (w0); - double sn = sin (w0); - double AL = sn / ( 2 * q ); - double b0 = 1 - AL; - double b1 = -2 * cs; - double b2 = 1 + AL; - double a0 = 1 + AL; - double a1 = -2 * cs; - double a2 = 1 - AL; - setCoefficients (a0, a1, a2, b0, b1, b2); -} - -} - -} diff --git a/src/libs/iir1/iir/RBJ.h b/src/libs/iir1/iir/RBJ.h deleted file mode 100644 index b63e969c9..000000000 --- a/src/libs/iir1/iir/RBJ.h +++ /dev/null @@ -1,364 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011-2021 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_RBJ_H -#define IIR1_RBJ_H - -#include "Common.h" -#include "Biquad.h" -#include "State.h" - -namespace Iir { - -/** - * Filter realizations based on Robert Bristol-Johnson formulae: - * - * http://www.musicdsp.org/files/Audio-EQ-Cookbook.txt - * - * These are all 2nd order filters which are tuned with the Q (or Quality factor). - * The Q factor causes a resonance at the cutoff frequency. The higher the Q - * factor the higher the responance. If 0.5 < Q < 1/sqrt(2) then there is no resonance peak. - * Above 1/sqrt(2) the peak becomes more and more pronounced. For bandpass and stopband - * the Q factor is replaced by the width of the filter. The higher Q the more narrow - * the bandwidth of the notch or bandpass. - * - **/ - -#define ONESQRT2 (1/sqrt(2)) - -namespace RBJ { - - /** - * The base class of all RBJ filters - **/ - struct DllExport RBJbase : Biquad - { - public: - /// filter operation - template <typename Sample> - inline Sample filter(Sample s) { - return static_cast<Sample>(state.filter((double)s,*this)); - } - /// resets the delay lines to zero - void reset() { - state.reset(); - } - /// gets the delay lines (=state) of the filter - const DirectFormI& getState() { - return state; - } - private: - DirectFormI state; - }; - - /** - * Lowpass. - **/ - struct DllExport LowPass : RBJbase - { - /** - * Calculates the coefficients - * \param cutoffFrequency Normalised cutoff frequency - * \param q Q factor determines the resonance peak at the cutoff. - **/ - void setupN(double cutoffFrequency, - double q = ONESQRT2); - - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param q Q factor determines the resonance peak at the cutoff. - **/ - void setup(double sampleRate, - double cutoffFrequency, - double q = ONESQRT2) { - setupN(cutoffFrequency / sampleRate, q); - } - }; - - /** - * Highpass. - **/ - struct DllExport HighPass : RBJbase - { - /** - * Calculates the coefficients - * \param cutoffFrequency Normalised cutoff frequency (0..1/2) - * \param q Q factor determines the resonance peak at the cutoff. - **/ - void setupN(double cutoffFrequency, - double q = ONESQRT2); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param q Q factor determines the resonance peak at the cutoff. - **/ - void setup (double sampleRate, - double cutoffFrequency, - double q = ONESQRT2) { - setupN(cutoffFrequency / sampleRate, q); - } - }; - - /** - * Bandpass with constant skirt gain - **/ - struct DllExport BandPass1 : RBJbase - { - /** - * Calculates the coefficients - * \param centerFrequency Center frequency of the bandpass - * \param bandWidth Bandwidth in octaves - **/ - void setupN(double centerFrequency, - double bandWidth); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param bandWidth Bandwidth in octaves - **/ - void setup (double sampleRate, - double centerFrequency, - double bandWidth) { - setupN(centerFrequency / sampleRate, bandWidth); - } - }; - - /** - * Bandpass with constant 0 dB peak gain - **/ - struct DllExport BandPass2 : RBJbase - { - /** - * Calculates the coefficients - * \param centerFrequency Normalised centre frequency of the bandpass - * \param bandWidth Bandwidth in octaves - **/ - void setupN(double centerFrequency, - double bandWidth); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandpass - * \param bandWidth Bandwidth in octaves - **/ - void setup (double sampleRate, - double centerFrequency, - double bandWidth) { - setupN(centerFrequency / sampleRate, bandWidth); - } - }; - - /** - * Bandstop filter. Warning: the bandwidth might not be accurate - * for narrow notches. - **/ - struct DllExport BandStop : RBJbase - { - /** - * Calculates the coefficients - * \param centerFrequency Normalised Centre frequency of the bandstop - * \param bandWidth Bandwidth in octaves - **/ - void setupN(double centerFrequency, - double bandWidth); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the bandstop - * \param bandWidth Bandwidth in octaves - **/ - void setup (double sampleRate, - double centerFrequency, - double bandWidth) { - setupN(centerFrequency / sampleRate, bandWidth); - } - }; - - /** - * Bandstop with Q factor: the higher the Q factor the more narrow is - * the notch. - * However, a narrow notch has a long impulse response ( = ringing) - * and numerical problems might prevent perfect damping. Practical values - * of the Q factor are about Q = 10 to 20. In terms of the design - * the Q factor defines the radius of the - * poles as r = exp(- pi*(centerFrequency/sampleRate)/q_factor) whereas - * the angles of the poles/zeros define the bandstop frequency. The higher - * Q the closer r moves towards the unit circle. - **/ - struct DllExport IIRNotch : RBJbase - { - /** - * Calculates the coefficients - * \param centerFrequency Normalised centre frequency of the notch - * \param q_factor Q factor of the notch (1 to ~20) - **/ - void setupN(double centerFrequency, - double q_factor = 10); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param centerFrequency Center frequency of the notch - * \param q_factor Q factor of the notch (1 to ~20) - **/ - void setup (double sampleRate, - double centerFrequency, - double q_factor = 10) { - setupN(centerFrequency / sampleRate, q_factor); - } - }; - - /** - * Low shelf: 0db in the stopband and gainDb in the passband. - **/ - struct DllExport LowShelf : RBJbase - { - /** - * Calculates the coefficients - * \param cutoffFrequency Normalised cutoff frequency - * \param gainDb Gain in the passband - * \param shelfSlope Slope between stop/passband. 1 = as steep as it can. - **/ - void setupN(double cutoffFrequency, - double gainDb, - double shelfSlope = 1); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param gainDb Gain in the passband - * \param shelfSlope Slope between stop/passband. 1 = as steep as it can. - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double shelfSlope = 1) { - setupN( cutoffFrequency / sampleRate, gainDb, shelfSlope); - } - }; - - /** - * High shelf: 0db in the stopband and gainDb in the passband. - **/ - struct DllExport HighShelf : RBJbase - { - /** - * Calculates the coefficients - * \param cutoffFrequency Normalised cutoff frequency - * \param gainDb Gain in the passband - * \param shelfSlope Slope between stop/passband. 1 = as steep as it can. - **/ - void setupN(double cutoffFrequency, - double gainDb, - double shelfSlope = 1); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param cutoffFrequency Cutoff frequency - * \param gainDb Gain in the passband - * \param shelfSlope Slope between stop/passband. 1 = as steep as it can. - **/ - void setup (double sampleRate, - double cutoffFrequency, - double gainDb, - double shelfSlope = 1) { - setupN( cutoffFrequency / sampleRate, gainDb, shelfSlope); - } - }; - - /** - * Band shelf: 0db in the stopband and gainDb in the passband. - **/ - struct DllExport BandShelf : RBJbase - { - /** - * Calculates the coefficients - * \param centerFrequency Normalised centre frequency - * \param gainDb Gain in the passband - * \param bandWidth Bandwidth in octaves - **/ - void setupN(double centerFrequency, - double gainDb, - double bandWidth); - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param centerFrequency frequency - * \param gainDb Gain in the passband - * \param bandWidth Bandwidth in octaves - **/ - void setup (double sampleRate, - double centerFrequency, - double gainDb, - double bandWidth) { - setupN(centerFrequency / sampleRate, gainDb, bandWidth); - } - }; - - /** - * Allpass filter - **/ - struct DllExport AllPass : RBJbase - { - /** - * Calculates the coefficients - * \param phaseFrequency Normalised frequency where the phase flips - * \param q Q-factor - **/ - void setupN(double phaseFrequency, - double q = ONESQRT2); - - /** - * Calculates the coefficients - * \param sampleRate Sampling rate - * \param phaseFrequency Frequency where the phase flips - * \param q Q-factor - **/ - void setup (double sampleRate, - double phaseFrequency, - double q = ONESQRT2) { - setupN( phaseFrequency / sampleRate, q); - } - }; - -} - -} - - -#endif diff --git a/src/libs/iir1/iir/State.h b/src/libs/iir1/iir/State.h deleted file mode 100644 index 040dd4c07..000000000 --- a/src/libs/iir1/iir/State.h +++ /dev/null @@ -1,164 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_STATE_H -#define IIR1_STATE_H - -#include "Common.h" -#include "Biquad.h" - - -#define DEFAULT_STATE DirectFormII - -namespace Iir { - -/** - * State for applying a second order section to a sample using Direct Form I - * - * Difference equation: - * - * y[n] = (b0/a0)*x[n] + (b1/a0)*x[n-1] + (b2/a0)*x[n-2] - * - (a1/a0)*y[n-1] - (a2/a0)*y[n-2] - **/ - class DllExport DirectFormI - { - public: - DirectFormI () = default; - - void reset () - { - m_x1 = 0; - m_x2 = 0; - m_y1 = 0; - m_y2 = 0; - } - - inline double filter(const double in, - const Biquad& s) - { - const double out = s.m_b0*in + s.m_b1*m_x1 + s.m_b2*m_x2 - - s.m_a1*m_y1 - s.m_a2*m_y2; - m_x2 = m_x1; - m_y2 = m_y1; - m_x1 = in; - m_y1 = out; - - return out; - } - - protected: - double m_x2 = 0.0; // x[n-2] - double m_y2 = 0.0; // y[n-2] - double m_x1 = 0.0; // x[n-1] - double m_y1 = 0.0; // y[n-1] - }; - -//------------------------------------------------------------------------------ - -/** - * State for applying a second order section to a sample using Direct Form II - * - * Difference equation: - * - * v[n] = x[n] - (a1/a0)*v[n-1] - (a2/a0)*v[n-2] - * y(n) = (b0/a0)*v[n] + (b1/a0)*v[n-1] + (b2/a0)*v[n-2] - * - **/ - class DllExport DirectFormII - { - public: - DirectFormII () = default; - - void reset () - { - m_v1 = 0.0; - m_v2 = 0.0; - } - - inline double filter(const double in, - const Biquad& s) - { - const double w = in - s.m_a1*m_v1 - s.m_a2*m_v2; - const double out = s.m_b0*w + s.m_b1*m_v1 + s.m_b2*m_v2; - - m_v2 = m_v1; - m_v1 = w; - - return out; - } - - private: - double m_v1 = 0.0; // v[-1] - double m_v2 = 0.0; // v[-2] - }; - - -//------------------------------------------------------------------------------ - - class DllExport TransposedDirectFormII - { - public: - TransposedDirectFormII() = default; - - void reset () - { - m_s1 = 0.0; - m_s1_1 = 0.0; - m_s2 = 0.0; - m_s2_1 = 0.0; - } - - inline double filter(const double in, - const Biquad& s) - { - const double out = m_s1_1 + s.m_b0*in; - m_s1 = m_s2_1 + s.m_b1*in - s.m_a1*out; - m_s2 = s.m_b2*in - s.m_a2*out; - m_s1_1 = m_s1; - m_s2_1 = m_s2; - - return out; - } - - private: - double m_s1 = 0.0; - double m_s1_1 = 0.0; - double m_s2 = 0.0; - double m_s2_1 = 0.0; - }; - -} - -#endif diff --git a/src/libs/iir1/iir/Types.h b/src/libs/iir1/iir/Types.h deleted file mode 100644 index 3695e55bb..000000000 --- a/src/libs/iir1/iir/Types.h +++ /dev/null @@ -1,147 +0,0 @@ -/** - * - * "A Collection of Useful C++ Classes for Digital Signal Processing" - * By Vinnie Falco and Bernd Porr - * - * Official project location: - * https://github.com/berndporr/iir1 - * - * See Documentation.cpp for contact information, notes, and bibliography. - * - * ----------------------------------------------------------------- - * - * License: MIT License (http://www.opensource.org/licenses/mit-license.php) - * Copyright (c) 2009 by Vinnie Falco - * Copyright (c) 2011 by Bernd Porr - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - **/ - -#ifndef IIR1_TYPES_H -#define IIR1_TYPES_H - -#include "Common.h" -#include "MathSupplement.h" - -namespace Iir { - -/** - * A conjugate or real pair - **/ - struct DllExport ComplexPair : complex_pair_t - { - ComplexPair() = default; - - explicit ComplexPair (const complex_t& c1) - : complex_pair_t (c1, 0.) - { - if (!isReal()) throw_invalid_argument("A single complex number needs to be real."); - } - - ComplexPair (const complex_t& c1, - const complex_t& c2) - : complex_pair_t (c1, c2) - { - } - - bool isConjugate () const - { - return second == std::conj (first); - } - - bool isReal () const - { - return first.imag() == 0 && second.imag() == 0; - } - - /** - * Returns true if this is either a conjugate pair, - * or a pair of reals where neither is zero. - */ - bool isMatchedPair () const - { - if (first.imag() != 0) - return second == std::conj (first); - else - return second.imag () == 0 && - second.real () != 0 && - first.real () != 0; - } - - bool is_nan () const - { - return Iir::is_nan (first) || Iir::is_nan (second); - } - }; - - -/** - * A pair of pole/zeros. This fits in a biquad (but is missing the gain) - **/ - struct DllExport PoleZeroPair - { - ComplexPair poles = ComplexPair(); - ComplexPair zeros = ComplexPair(); - - PoleZeroPair () = default; - - // single pole/zero - PoleZeroPair (const complex_t& p, const complex_t& z) - : poles (p), zeros (z) - { - } - - // pole/zero pair - PoleZeroPair (const complex_t& p1, const complex_t& z1, - const complex_t& p2, const complex_t& z2) - : poles (p1, p2) - , zeros (z1, z2) - { - } - - bool isSinglePole () const - { - return poles.second == 0. && zeros.second == 0.; - } - - bool is_nan () const - { - return poles.is_nan() || zeros.is_nan(); - } - }; - - -/** - * Identifies the general class of filter - **/ - enum Kind - { - kindLowPass, - kindHighPass, - kindBandPass, - kindBandStop, - kindLowShelf, - kindHighShelf, - kindBandShelf, - kindOther - }; - -} - -#endif diff --git a/src/libs/iir1/meson.build b/src/libs/iir1/meson.build deleted file mode 100644 index a25328647..000000000 --- a/src/libs/iir1/meson.build +++ /dev/null @@ -1,15 +0,0 @@ -libiir1_sources = files([ - 'iir/Biquad.cpp', - 'iir/Butterworth.cpp', - 'iir/Cascade.cpp', - 'iir/ChebyshevI.cpp', - 'iir/ChebyshevII.cpp', - 'iir/Custom.cpp', - 'iir/PoleFilter.cpp', - 'iir/RBJ.cpp', -]) - -libiir1 = static_library('iir1', libiir1_sources) - -libiir1_dep = declare_dependency(link_with : libiir1) - diff --git a/subprojects/iir.wrap b/subprojects/iir.wrap new file mode 100644 index 000000000..2c6b8fdf3 --- /dev/null +++ b/subprojects/iir.wrap @@ -0,0 +1,13 @@ +[wrap-file] +directory = iir1-1.9.2 +source_url = https://github.com/berndporr/iir1/archive/refs/tags/1.9.2.tar.gz +source_filename = 1.9.2.tar.gz +source_hash = b53581a71b0e116c74429ffd936b8a94cd1c3e626b8074f948024d2e23bff161 +patch_filename = iir_1.9.2-2_patch.zip +patch_url = https://wrapdb.mesonbuild.com/v2/iir_1.9.2-2/get_patch +patch_hash = 600f996e8bc4cb1327386a3e9d3795f511b11a336eeca4c0ccaa4fad93e8d90f +wrapdb_version = 1.9.2-2 + +[provide] +iir = libiir_dep + diff --git a/tests/meson.build b/tests/meson.build index cfb425a25..876424ed0 100644 --- a/tests/meson.build +++ b/tests/meson.build @@ -59,7 +59,7 @@ unit_tests = [ {'name' : 'bitops', 'deps' : []}, {'name' : 'iohandler_containers', 'deps' : [libmisc_dep]}, {'name' : 'rwqueue', 'deps' : [libmisc_dep]}, - {'name' : 'soft_limiter', 'deps' : [atomic_dep, libiir1_dep, libmisc_dep]}, + {'name' : 'soft_limiter', 'deps' : [atomic_dep, libiir_dep, libmisc_dep]}, {'name' : 'string_utils', 'deps' : []}, {'name' : 'setup', 'deps' : [libmisc_dep]}, {'name' : 'support', 'deps' : [libmisc_dep]}, diff --git a/vs/dosbox.vcxproj b/vs/dosbox.vcxproj index fc1c6dec8..baeedc0bf 100644 --- a/vs/dosbox.vcxproj +++ b/vs/dosbox.vcxproj @@ -121,7 +121,7 @@ <ObjectFileName>$(IntDir)\$(ProjectName)\$(ConfigurationName)\%(RelativeDir)</ObjectFileName> </ClCompile> <Link> - <AdditionalDependencies>opengl32.lib;SDL2_net.lib;winmm.lib;libpng16d.lib;SDL2maind.lib;SDL2d.lib;odbc32.lib;odbccp32.lib;ws2_32.lib;mt32emu.lib;opusfile.lib;opus.lib;ogg.lib;fluidsynth.lib;speexdsp.lib;%(AdditionalDependencies)</AdditionalDependencies> + <AdditionalDependencies>opengl32.lib;SDL2_net.lib;winmm.lib;libpng16d.lib;SDL2maind.lib;SDL2d.lib;odbc32.lib;odbccp32.lib;ws2_32.lib;mt32emu.lib;opusfile.lib;opus.lib;ogg.lib;fluidsynth.lib;iir1.lib;speexdsp.lib;%(AdditionalDependencies)</AdditionalDependencies> <OutputFile>$(OutDir)\dosbox.exe</OutputFile> <GenerateDebugInformation>true</GenerateDebugInformation> <SubSystem>Console</SubSystem> @@ -164,7 +164,7 @@ <ObjectFileName>$(IntDir)\$(ProjectName)\$(ConfigurationName)\%(RelativeDir)</ObjectFileName> </ClCompile> <Link> - <AdditionalDependencies>opengl32.lib;SDL2_net.lib;winmm.lib;libpng16d.lib;SDL2maind.lib;SDL2d.lib;odbc32.lib;odbccp32.lib;ws2_32.lib;mt32emu.lib;opusfile.lib;opus.lib;ogg.lib;speexdsp.lib;%(AdditionalDependencies)</AdditionalDependencies> + <AdditionalDependencies>opengl32.lib;SDL2_net.lib;winmm.lib;libpng16d.lib;SDL2maind.lib;SDL2d.lib;odbc32.lib;odbccp32.lib;ws2_32.lib;iir1.lib;mt32emu.lib;opusfile.lib;opus.lib;ogg.lib;speexdsp.lib;%(AdditionalDependencies)</AdditionalDependencies> <OutputFile>$(OutDir)\dosbox.exe</OutputFile> <GenerateDebugInformation>true</GenerateDebugInformation> <SubSystem>Console</SubSystem> |