Date: Monday, July 23, 2018 @ 18:50:48 Author: dvzrv Revision: 363206
archrelease: copy trunk to community-staging-x86_64 Added: zam-plugins/repos/community-staging-x86_64/ zam-plugins/repos/community-staging-x86_64/PKGBUILD (from rev 363205, zam-plugins/trunk/PKGBUILD) zam-plugins/repos/community-staging-x86_64/system-zita-convolver.patch (from rev 363205, zam-plugins/trunk/system-zita-convolver.patch) zam-plugins/repos/community-staging-x86_64/zita-convolver4.patch (from rev 363205, zam-plugins/trunk/zita-convolver4.patch) -----------------------------+ PKGBUILD | 43 system-zita-convolver.patch | 155 +++ zita-convolver4.patch | 1994 ++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 2192 insertions(+) Copied: zam-plugins/repos/community-staging-x86_64/PKGBUILD (from rev 363205, zam-plugins/trunk/PKGBUILD) =================================================================== --- community-staging-x86_64/PKGBUILD (rev 0) +++ community-staging-x86_64/PKGBUILD 2018-07-23 18:50:48 UTC (rev 363206) @@ -0,0 +1,43 @@ +# $Id$ +# Maintainer: David Runge <d...@sleepmap.de> +pkgname=zam-plugins +pkgver=3.10 +pkgrel=5 +pkgdesc="Collection of LADSPA/LV2/VST/JACK audio plugins for high-quality processing" +arch=('x86_64') +url="https://github.com/zamaudio/zam-plugins" +license=('GPL2') +groups=('ladspa-plugins' 'lv2-plugins' 'pro-audio' 'vst-plugins') +depends=('jack' 'libglvnd' 'liblo' 'zita-convolver') +makedepends=('git' 'ladspa' 'libx11' 'libgl' 'lv2') +source=("$pkgname-$pkgver::git+https://github.com/zamaudio/${pkgname}.git#tag=${pkgver}" + "git+https://github.com/distrho/dpf.git" + 'zita-convolver4.patch' + 'system-zita-convolver.patch') +sha512sums=('SKIP' + 'SKIP' + '21bba1704ddf912146e3a6ce58752236f40695f592cffd50814cbc8083e8d97d8ed4791362990883a59f98b538bde32c320059f5db58061dbbcfddad9003ee02' + 'bb3f3f2f0c5ce0c80755016566ffc2ea1436646ab69cd6f8cd82ea1b221d67490599264964edca062a9e3c19861f99d7c8f12cf51829e0432a9658c8adcf63f3') + +prepare() { + cd "$pkgname-$pkgver" + git submodule init + git config submodule.dpf.url "${srcdir}/dpf" + git submodule update + patch -Np1 -i ../zita-convolver4.patch + patch -Np1 -i ../system-zita-convolver.patch +} + +build() { + cd "$pkgname-$pkgver" + export USE_SYSTEM_LIBS=1 + make +} + +package() { + cd "$pkgname-$pkgver" + make DESTDIR="$pkgdir/" PREFIX='/usr' install + # docs + install -t "${pkgdir}/usr/share/doc/${pkgname}/" \ + -vDm 644 {README.md,changelog} +} Copied: zam-plugins/repos/community-staging-x86_64/system-zita-convolver.patch (from rev 363205, zam-plugins/trunk/system-zita-convolver.patch) =================================================================== --- community-staging-x86_64/system-zita-convolver.patch (rev 0) +++ community-staging-x86_64/system-zita-convolver.patch 2018-07-23 18:50:48 UTC (rev 363206) @@ -0,0 +1,155 @@ +From fbdbf082fef6c5e9cd7796c8e6726c8e98c7c040 Mon Sep 17 00:00:00 2001 +From: Guido Aulisi <guido.aul...@gmail.com> +Date: Wed, 28 Feb 2018 12:28:26 +0100 +Subject: [PATCH 3/3] Allow using system provided zita convolver library + +v.2: Rebase onto newer zita-convolver +--- + Makefile.mk | 9 +++++++++ + plugins/ZamHeadX2/Makefile | 12 ++++++++++-- + plugins/ZamHeadX2/convolution.cpp | 1 - + plugins/ZamHeadX2/convolution.hpp | 4 ++++ + plugins/ZamVerb/Makefile | 12 ++++++++++-- + plugins/ZamVerb/convolution.cpp | 1 - + plugins/ZamVerb/convolution.hpp | 4 ++++ + 7 files changed, 37 insertions(+), 6 deletions(-) + +diff --git a/Makefile.mk b/Makefile.mk +index 7588326..b53ca4e 100644 +--- a/Makefile.mk ++++ b/Makefile.mk +@@ -85,6 +85,15 @@ ifeq ($(LINUX),true) + HAVE_DGL = $(shell pkg-config --exists gl x11 && echo true) + HAVE_JACK = $(shell pkg-config --exists jack && echo true) + HAVE_LIBLO = $(shell pkg-config --exists liblo && echo true) ++ ++# Allow to use system provided libs ++ifeq ($(USE_SYSTEM_LIBS),1) ++HAVE_ZITA_CONVOLVER = true ++ZITA_CONVOLVER_LIBS = -lzita-convolver ++BASE_FLAGS += -I/usr/include ++export HAVE_ZITA_CONVOLVER ++endif ++ + endif + + ifeq ($(MACOS),true) +diff --git a/plugins/ZamHeadX2/Makefile b/plugins/ZamHeadX2/Makefile +index 8500534..28e6931 100644 +--- a/plugins/ZamHeadX2/Makefile ++++ b/plugins/ZamHeadX2/Makefile +@@ -12,8 +12,11 @@ NAME = ZamHeadX2 + # -------------------------------------------------------------- + # Files to build + +-OBJS_DSP = \ +- ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o \ ++ifneq ($(HAVE_ZITA_CONVOLVER),true) ++OBJS_DSP = ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o ++endif ++ ++OBJS_DSP += \ + convolution.cpp.o \ + ZamHeadX2Plugin.cpp.o + +@@ -38,6 +41,11 @@ else + TARGETS += lv2_dsp + endif + ++ifeq ($(HAVE_ZITA_CONVOLVER),true) ++BASE_FLAGS += -DHAVE_ZITA_CONVOLVER ++LINK_FLAGS += $(ZITA_CONVOLVER_LIBS) ++endif ++ + TARGETS += vst + + all: $(TARGETS) +diff --git a/plugins/ZamHeadX2/convolution.cpp b/plugins/ZamHeadX2/convolution.cpp +index 0026ba2..8c42acc 100644 +--- a/plugins/ZamHeadX2/convolution.cpp ++++ b/plugins/ZamHeadX2/convolution.cpp +@@ -42,7 +42,6 @@ + #include <pthread.h> + #include <assert.h> + +-#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + #include <samplerate.h> + #include "convolution.hpp" + +diff --git a/plugins/ZamHeadX2/convolution.hpp b/plugins/ZamHeadX2/convolution.hpp +index 80be8e6..8cdcd71 100644 +--- a/plugins/ZamHeadX2/convolution.hpp ++++ b/plugins/ZamHeadX2/convolution.hpp +@@ -19,7 +19,11 @@ + #ifndef CONVOLUTION_H_ + #define CONVOLUTION_H_ + ++#ifdef HAVE_ZITA_CONVOLVER ++#include <zita-convolver.h> ++#else + #include "../../lib/zita-convolver-4.0.0/zita-convolver.h" ++#endif + + #define MAX_CHANNEL_MAPS (4) + #define VERBOSE_printf(x, ...) +diff --git a/plugins/ZamVerb/Makefile b/plugins/ZamVerb/Makefile +index eacc080..a08e334 100644 +--- a/plugins/ZamVerb/Makefile ++++ b/plugins/ZamVerb/Makefile +@@ -15,8 +15,11 @@ NAME = ZamVerb + OBJS_DSP = \ + ZamVerbPlugin.cpp.o \ + ZamVerbImpulses.cpp.o \ +- convolution.cpp.o \ +- ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o ++ convolution.cpp.o ++ ++ifneq ($(HAVE_ZITA_CONVOLVER),true) ++OBJS_DSP += ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o ++endif + + OBJS_UI = \ + ZamVerbArtwork.cpp.o \ +@@ -39,6 +42,11 @@ else + TARGETS += lv2_dsp + endif + ++ifeq ($(HAVE_ZITA_CONVOLVER),true) ++BASE_FLAGS += -DHAVE_ZITA_CONVOLVER ++LINK_FLAGS += $(ZITA_CONVOLVER_LIBS) ++endif ++ + TARGETS += vst + + all: $(TARGETS) +diff --git a/plugins/ZamVerb/convolution.cpp b/plugins/ZamVerb/convolution.cpp +index 27374e0..8357037 100644 +--- a/plugins/ZamVerb/convolution.cpp ++++ b/plugins/ZamVerb/convolution.cpp +@@ -42,7 +42,6 @@ + #include <pthread.h> + #include <assert.h> + +-#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + #include <samplerate.h> + #include "convolution.hpp" + #include "ZamVerbImpulses.hpp" +diff --git a/plugins/ZamVerb/convolution.hpp b/plugins/ZamVerb/convolution.hpp +index 1c89971..cfb3755 100644 +--- a/plugins/ZamVerb/convolution.hpp ++++ b/plugins/ZamVerb/convolution.hpp +@@ -19,7 +19,11 @@ + #ifndef CONVOLUTION_H_ + #define CONVOLUTION_H_ + ++#ifdef HAVE_ZITA_CONVOLVER ++#include <zita-convolver.h> ++#else + #include "../../lib/zita-convolver-4.0.0/zita-convolver.h" ++#endif + + #define MAX_CHANNEL_MAPS (4) + #define VERBOSE_printf(x, ...) +-- +2.18.0 + Copied: zam-plugins/repos/community-staging-x86_64/zita-convolver4.patch (from rev 363205, zam-plugins/trunk/zita-convolver4.patch) =================================================================== --- community-staging-x86_64/zita-convolver4.patch (rev 0) +++ community-staging-x86_64/zita-convolver4.patch 2018-07-23 18:50:48 UTC (rev 363206) @@ -0,0 +1,1994 @@ +From 71d221b7560c53d48bacf77a1624c467d816b413 Mon Sep 17 00:00:00 2001 +From: Damien Zammit <dam...@zamaudio.com> +Date: Sat, 9 Jun 2018 17:27:56 +1000 +Subject: [PATCH 1/3] lib: Update to zita-convolver 4.0.0 + +--- + Makefile | 2 +- + lib/zita-convolver-3.1.0/zita-convolver.h | 471 ----------------- + .../zcsema-osx-win-compat.h | 40 ++ + .../zita-convolver.cpp | 465 +++++++++-------- + lib/zita-convolver-4.0.0/zita-convolver.h | 475 ++++++++++++++++++ + plugins/ZamHeadX2/Makefile | 2 +- + plugins/ZamHeadX2/convolution.cpp | 10 +- + plugins/ZamHeadX2/convolution.hpp | 2 +- + plugins/ZamVerb/Makefile | 2 +- + plugins/ZamVerb/convolution.cpp | 10 +- + plugins/ZamVerb/convolution.hpp | 2 +- + 11 files changed, 783 insertions(+), 698 deletions(-) + delete mode 100644 lib/zita-convolver-3.1.0/zita-convolver.h + create mode 100644 lib/zita-convolver-4.0.0/zcsema-osx-win-compat.h + rename lib/{zita-convolver-3.1.0 => zita-convolver-4.0.0}/zita-convolver.cpp (68%) + create mode 100644 lib/zita-convolver-4.0.0/zita-convolver.h + +diff --git a/Makefile b/Makefile +index fc8991b..3220651 100644 +--- a/Makefile ++++ b/Makefile +@@ -68,7 +68,7 @@ ifeq ($(HAVE_DGL),true) + $(MAKE) clean -C dpf/dgl + endif + $(MAKE) clean -C dpf/utils/lv2-ttl-generator +- rm -f lib/zita-convolver-3.1.0/*.o lib/zita-convolver-3.1.0/*.d ++ rm -f lib/zita-convolver-4.0.0/*.o lib/zita-convolver-4.0.0/*.d + rm -f plugins/ZamSFZ/libsfz/*.o plugins/ZamSFZ/libsfz/*.d + + # -------------------------------------------------------------- +diff --git a/lib/zita-convolver-3.1.0/zita-convolver.h b/lib/zita-convolver-3.1.0/zita-convolver.h +deleted file mode 100644 +index 37f4d03..0000000 +--- a/lib/zita-convolver-3.1.0/zita-convolver.h ++++ /dev/null +@@ -1,471 +0,0 @@ +-// ---------------------------------------------------------------------------- +-// +-// Copyright (C) 2006-2011 Fons Adriaensen <f...@linuxaudio.org> +-// +-// This program is free software; you can redistribute it and/or modify +-// it under the terms of the GNU General Public License as published by +-// the Free Software Foundation; either version 3 of the License, or +-// (at your option) any later version. +-// +-// This program is distributed in the hope that it will be useful, +-// but WITHOUT ANY WARRANTY; without even the implied warranty of +-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +-// GNU General Public License for more details. +-// +-// You should have received a copy of the GNU General Public License +-// along with this program. If not, see <http://www.gnu.org/licenses/>. +-// +-// ---------------------------------------------------------------------------- +- +- +-#ifndef _ZITA_CONVOLVER_H +-#define _ZITA_CONVOLVER_H +- +-#define _POSIX_PTHREAD_SEMANTICS +- +-#include <errno.h> +-#include <pthread.h> +-#include <fftw3.h> +- +- +-#define ZITA_CONVOLVER_MAJOR_VERSION 3 +-#define ZITA_CONVOLVER_MINOR_VERSION 1 +- +- +-extern int zita_convolver_major_version (void); +-extern int zita_convolver_minor_version (void); +- +- +-// ---------------------------------------------------------------------------- +- +- +-#ifdef ZCSEMA_IS_IMPLEMENTED +-#undef ZCSEMA_IS_IMPLEMENTED +-#endif +- +- +-#if defined(__linux__) || defined(__FreeBSD_kernel__) || defined(__GNU__) || defined(__WIN32__) +- +-// NOTE: __FreeBSD_kernel__ and __GNU__ were added by the Debian maintainers +-// (the latter for the HURD version of Debian). Things are reported to work +-// with some applications but probably have not been tested in depth. +-// __WIN32__ was added by DZ for MingW +- +-#include <semaphore.h> +- +-class ZCsema +-{ +-public: +- +- ZCsema (void) { init (0, 0); } +- ~ZCsema (void) { sem_destroy (&_sema); } +- +- ZCsema (const ZCsema&); // disabled +- ZCsema& operator= (const ZCsema&); // disabled +- +- int init (int s, int v) { return sem_init (&_sema, s, v); } +- int post (void) { return sem_post (&_sema); } +- int wait (void) { return sem_wait (&_sema); } +- int trywait (void) { return sem_trywait (&_sema); } +- +-private: +- +- sem_t _sema; +-}; +- +-#define ZCSEMA_IS_IMPLEMENTED +-#endif +- +- +-// ADDED BY DZ TO MAKE IT COMPILE FOR OSX 10.5 or Windows +-#if defined(__APPLE__) || defined(__WIN32__) +-inline int posix_memalign(void **memptr, size_t alignment, size_t size) +-{ +- *memptr = malloc(size); +- if (*memptr == NULL) +- return ENOMEM; +- return 0; +-} +-#endif +- +- +-#ifdef __APPLE__ +- +-// NOTE: ***** I DO NOT REPEAT NOT PROVIDE SUPPORT FOR OSX ***** +-// +-// The following code partially emulates the POSIX sem_t for which +-// OSX has only a crippled implementation. It may or may not compile, +-// and if it compiles it may or may not work correctly. Blame APPLE +-// for not following POSIX standards. +- +-class ZCsema +-{ +-public: +- +- ZCsema (void) : _count (0) +- { +- init (0, 0); +- } +- +- ~ZCsema (void) +- { +- pthread_mutex_destroy (&_mutex); +- pthread_cond_destroy (&_cond); +- } +- +- ZCsema (const ZCsema&); // disabled +- ZCsema& operator= (const ZCsema&); // disabled +- +- int init (int s, int v) +- { +- _count = v; +- return pthread_mutex_init (&_mutex, 0) || pthread_cond_init (&_cond, 0); +- } +- +- int post (void) +- { +- pthread_mutex_lock (&_mutex); +- _count++; +- if (_count == 1) pthread_cond_signal (&_cond); +- pthread_mutex_unlock (&_mutex); +- return 0; +- } +- +- int wait (void) +- { +- pthread_mutex_lock (&_mutex); +- while (_count < 1) pthread_cond_wait (&_cond, &_mutex); +- _count--; +- pthread_mutex_unlock (&_mutex); +- return 0; +- } +- +- int trywait (void) +- { +- if (pthread_mutex_trylock (&_mutex)) return -1; +- if (_count < 1) +- { +- pthread_mutex_unlock (&_mutex); +- return -1; +- } +- _count--; +- pthread_mutex_unlock (&_mutex); +- return 0; +- } +- +-private: +- +- int _count; +- pthread_mutex_t _mutex; +- pthread_cond_t _cond; +-}; +- +-#define ZCSEMA_IS_IMPLEMENTED +-#endif +- +- +-#ifndef ZCSEMA_IS_IMPLEMENTED +-#error "The ZCsema class is not implemented." +-#endif +- +- +-// ---------------------------------------------------------------------------- +- +- +-class Inpnode +-{ +-private: +- +- friend class Convlevel; +- +- Inpnode *_next; +- fftwf_complex **_ffta; +- unsigned int _inp; +-}; +- +- +-class Macnode +-{ +-private: +- +- friend class Convlevel; +- +- Macnode *_next; +- Inpnode *_inpn; +- fftwf_complex **_fftb; +- bool _copy; +-}; +- +- +-class Outnode +-{ +-private: +- +- friend class Convlevel; +- +- Outnode *_next; +- Macnode *_list; +- float *_buff [3]; +- unsigned int _out; +-}; +- +- +-class Converror +-{ +-public: +- +- enum +- { +- BAD_STATE = -1, +- BAD_PARAM = -2, +- MEM_ALLOC = -3 +- }; +- +-private: +- +- friend class Convlevel; +- friend class Convproc; +- +- Converror (int error) : _error (error) {} +- +- int _error; +-}; +- +- +-class Convlevel +-{ +-private: +- +- friend class Convproc; +- +- enum +- { +- OPT_FFTW_MEASURE = 1, +- OPT_VECTOR_MODE = 2 +- }; +- +- enum +- { +- ST_IDLE, +- ST_TERM, +- ST_PROC +- }; +- +- Convlevel (void); +- ~Convlevel (void); +- +- void *alloc_aligned (size_t size); +- +- void configure (int prio, +- unsigned int offs, +- unsigned int npar, +- unsigned int parsize, +- unsigned int options); +- +- void impdata_create (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1); +- +- void impdata_update (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1); +- +- void impdata_copy (unsigned int inp1, +- unsigned int out1, +- unsigned int inp2, +- unsigned int out2); +- +- void reset (unsigned int inpsize, +- unsigned int outsize, +- float **inpbuff, +- float **outbuff); +- +- void start (int absprio, int policy); +- +- void process (bool sync); +- +- int readout (bool sync, unsigned int skipcnt); +- +- void stop (void); +- +- void cleanup (void); +- +- void fftswap (fftwf_complex *p); +- +- void print (FILE *F); +- +- static void *static_main (void *arg); +- +- void main (void); +- +- Macnode *findmacnode (unsigned int inp, unsigned int out, bool create); +- +- volatile unsigned int _stat; // current processing state +- int _prio; // relative priority +- unsigned int _offs; // offset from start of impulse response +- unsigned int _npar; // number of partitions +- unsigned int _parsize; // partition and outbut buffer size +- unsigned int _outsize; // step size for output buffer +- unsigned int _outoffs; // offset into output buffer +- unsigned int _inpsize; // size of shared input buffer +- unsigned int _inpoffs; // offset into input buffer +- unsigned int _options; // various options +- unsigned int _ptind; // rotating partition index +- unsigned int _opind; // rotating output buffer index +- int _bits; // bit identifiying this level +- int _wait; // number of unfinished cycles +- pthread_t _pthr; // posix thread executing this level +- ZCsema _trig; // sema used to trigger a cycle +- ZCsema _done; // sema used to wait for a cycle +- Inpnode *_inp_list; // linked list of active inputs +- Outnode *_out_list; // linked list of active outputs +- fftwf_plan _plan_r2c; // FFTW plan, forward FFT +- fftwf_plan _plan_c2r; // FFTW plan, inverse FFT +- float *_time_data; // workspace +- float *_prep_data; // workspace +- fftwf_complex *_freq_data; // workspace +- float **_inpbuff; // array of shared input buffers +- float **_outbuff; // array of shared output buffers +-}; +- +- +-// ---------------------------------------------------------------------------- +- +- +-class Convproc +-{ +-public: +- +- Convproc (void); +- ~Convproc (void); +- +- enum +- { +- ST_IDLE, +- ST_STOP, +- ST_WAIT, +- ST_PROC +- }; +- +- enum +- { +- FL_LATE = 0x0000FFFF, +- FL_LOAD = 0x01000000 +- }; +- +- enum +- { +- OPT_FFTW_MEASURE = Convlevel::OPT_FFTW_MEASURE, +- OPT_VECTOR_MODE = Convlevel::OPT_VECTOR_MODE +- }; +- +- enum +- { +- MAXINP = 64, +- MAXOUT = 64, +- MAXLEV = 8, +- MINPART = 64, +- MAXPART = 8192, +- MAXDIVIS = 16, +- MINQUANT = 16, +- MAXQUANT = 8192 +- }; +- +- unsigned int state (void) const +- { +- return _state; +- } +- +- float *inpdata (unsigned int inp) const +- { +- return _inpbuff [inp] + _inpoffs; +- } +- +- float *outdata (unsigned int out) const +- { +- return _outbuff [out] + _outoffs; +- } +- +- void set_density (float density); +- +- void set_options (unsigned int options); +- +- void set_skipcnt (unsigned int skipcnt); +- +- int configure (unsigned int ninp, +- unsigned int nout, +- unsigned int maxsize, +- unsigned int quantum, +- unsigned int minpart, +- unsigned int maxpart); +- +- int impdata_create (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1); +- +- int impdata_update (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1); +- +- int impdata_copy (unsigned int inp1, +- unsigned int out1, +- unsigned int inp2, +- unsigned int out2); +- +- int reset (void); +- +- int start_process (int abspri, int policy); +- +- int process (bool sync = false); +- +- int stop_process (void); +- +- bool check_stop (void); +- +- int cleanup (void); +- +- void print (FILE *F = stdout); +- +- static float _mac_cost; +- static float _fft_cost; +- +-private: +- +- unsigned int _state; // current state +- float *_inpbuff [MAXINP]; // input buffers +- float *_outbuff [MAXOUT]; // output buffers +- unsigned int _inpoffs; // current offset in input buffers +- unsigned int _outoffs; // current offset in output buffers +- unsigned int _options; // option bits +- unsigned int _skipcnt; // number of frames to skip +- float _density; // matrix density hint +- unsigned int _ninp; // number of inputs +- unsigned int _nout; // number of outputs +- unsigned int _quantum; // processing block size +- unsigned int _minpart; // smallest partition size +- unsigned int _maxpart; // largest allowed partition size +- unsigned int _nlevels; // number of partition sizes +- unsigned int _inpsize; // size of input buffers +- unsigned int _latecnt; // count of cycles ending too late +- Convlevel *_convlev [MAXLEV]; // array of processors +- void *_dummy [64]; +-}; +- +- +-// ---------------------------------------------------------------------------- +- +- +-#endif +- +diff --git a/lib/zita-convolver-4.0.0/zcsema-osx-win-compat.h b/lib/zita-convolver-4.0.0/zcsema-osx-win-compat.h +new file mode 100644 +index 0000000..807f6b8 +--- /dev/null ++++ b/lib/zita-convolver-4.0.0/zcsema-osx-win-compat.h +@@ -0,0 +1,40 @@ ++#if defined(__WIN32__) ++ ++#include <semaphore.h> ++ ++class ZCsema ++{ ++public: ++ ++ ZCsema (void) { init (0, 0); } ++ ~ZCsema (void) { sem_destroy (&_sema); } ++ ++ ZCsema (const ZCsema&); // disabled ++ ZCsema& operator= (const ZCsema&); // disabled ++ ++ int init (int s, int v) { return sem_init (&_sema, s, v); } ++ int post (void) { return sem_post (&_sema); } ++ int wait (void) { return sem_wait (&_sema); } ++ int trywait (void) { return sem_trywait (&_sema); } ++ ++private: ++ ++ sem_t _sema; ++}; ++ ++#define ZCSEMA_IS_IMPLEMENTED ++#endif ++ ++ ++// ADDED BY DZ TO MAKE IT COMPILE FOR OSX 10.5 or Windows ++#if defined(__APPLE__) || defined(__WIN32__) ++#include <errno.h> ++ ++inline int posix_memalign(void **memptr, size_t alignment, size_t size) ++{ ++ *memptr = malloc(size); ++ if (*memptr == NULL) ++ return ENOMEM; ++ return 0; ++} ++#endif +diff --git a/lib/zita-convolver-3.1.0/zita-convolver.cpp b/lib/zita-convolver-4.0.0/zita-convolver.cpp +similarity index 68% +rename from lib/zita-convolver-3.1.0/zita-convolver.cpp +rename to lib/zita-convolver-4.0.0/zita-convolver.cpp +index a5155de..202533d 100644 +--- a/lib/zita-convolver-3.1.0/zita-convolver.cpp ++++ b/lib/zita-convolver-4.0.0/zita-convolver.cpp +@@ -1,6 +1,6 @@ + // ---------------------------------------------------------------------------- + // +-// Copyright (C) 2006-2011 Fons Adriaensen <f...@linuxaudio.org> ++// Copyright (C) 2006-2018 Fons Adriaensen <f...@linuxaudio.org> + // + // This program is free software; you can redistribute it and/or modify + // it under the terms of the GNU General Public License as published by +@@ -42,11 +42,27 @@ float Convproc::_mac_cost = 1.0f; + float Convproc::_fft_cost = 5.0f; + + ++static float *calloc_real (uint32_t k) ++{ ++ float *p = fftwf_alloc_real (k); ++ if (!p) throw (Converror (Converror::MEM_ALLOC)); ++ memset (p, 0, k * sizeof (float)); ++ return p; ++} ++ ++static fftwf_complex *calloc_complex (uint32_t k) ++{ ++ fftwf_complex *p = fftwf_alloc_complex (k); ++ if (!p) throw (Converror (Converror::MEM_ALLOC)); ++ memset (p, 0, k * sizeof (fftwf_complex)); ++ return p; ++} ++ ++ + Convproc::Convproc (void) : + _state (ST_IDLE), + _options (0), + _skipcnt (0), +- _density (0), + _ninp (0), + _nout (0), + _quantum (0), +@@ -63,41 +79,39 @@ Convproc::Convproc (void) : + + Convproc::~Convproc (void) + { ++ stop_process (); + cleanup (); + } + + +-void Convproc::set_options (unsigned int options) ++void Convproc::set_options (uint32_t options) + { + _options = options; + } + + +-void Convproc::set_density (float density) +-{ +- _density = density; +-} +- +- +-void Convproc::set_skipcnt (unsigned int skipcnt) ++void Convproc::set_skipcnt (uint32_t skipcnt) + { + if ((_quantum == _minpart) && (_quantum == _maxpart)) _skipcnt = skipcnt; + } + + +-int Convproc::configure (unsigned int ninp, +- unsigned int nout, +- unsigned int maxsize, +- unsigned int quantum, +- unsigned int minpart, +- unsigned int maxpart) ++int Convproc::configure (uint32_t ninp, ++ uint32_t nout, ++ uint32_t maxsize, ++ uint32_t quantum, ++ uint32_t minpart, ++ uint32_t maxpart, ++ float density) + { +- unsigned int offs, npar, size, pind, nmin, nmax, step, i; +- int prio, d, r, s; +- float cfft, cmac, t; ++ uint32_t offs, npar, size, pind, nmin, i; ++ int prio, step, d, r, s; ++ float cfft, cmac; + + if (_state != ST_IDLE) return Converror::BAD_STATE; +- if ( (quantum & (quantum - 1)) ++ if ( (ninp < 1) || (ninp > MAXINP) ++ || (nout < 1) || (nout > MAXOUT) ++ || (quantum & (quantum - 1)) + || (quantum < MINQUANT) + || (quantum > MAXQUANT) + || (minpart & (minpart - 1)) +@@ -108,21 +122,12 @@ int Convproc::configure (unsigned int ninp, + || (maxpart > MAXPART) + || (maxpart < minpart)) return Converror::BAD_PARAM; + +- if (ninp < nout) { nmin = ninp; nmax = nout; } +- else { nmin = nout; nmax = ninp; } +- +- if (_density <= 0) _density = 1.0 / nmin; +- else +- { +- t = 1.0f / nmax; +- if (_density < t) _density = t; +- if (_density > 1) _density = 1; +- } +- ++ nmin = (ninp < nout) ? ninp : nout; ++ if (density <= 0.0f) density = 1.0f / nmin; ++ if (density > 1.0f) density = 1.0f; + cfft = _fft_cost * (ninp + nout); +- cmac = _mac_cost * ninp * nout * _density; ++ cmac = _mac_cost * ninp * nout * density; + step = (cfft < 4 * cmac) ? 1 : 2; +- + if (step == 2) + { + r = maxpart / minpart; +@@ -131,7 +136,6 @@ int Convproc::configure (unsigned int ninp, + else s = 1; + nmin = (s == 1) ? 2 : 6; + if (minpart == quantum) nmin++; +- + prio = 0; + size = quantum; + while (size < minpart) +@@ -154,7 +158,6 @@ int Convproc::configure (unsigned int ninp, + } + _convlev [pind] = new Convlevel (); + _convlev [pind]->configure (prio, offs, npar, size, _options); +- + offs += size * npar; + if (offs < maxsize) + { +@@ -188,21 +191,22 @@ int Convproc::configure (unsigned int ninp, + } + + +-int Convproc::impdata_create (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1) ++int Convproc::impdata_create (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t ind0, ++ int32_t ind1) + { +- unsigned int j; ++ uint32_t j; + + if (_state != ST_STOP) return Converror::BAD_STATE; ++ if ((inp >= _ninp) || (out >= _nout)) return Converror::BAD_PARAM; + try + { + for (j = 0; j < _nlevels; j++) + { +- _convlev [j]->impdata_create (inp, out, step, data, ind0, ind1); ++ _convlev [j]->impdata_write (inp, out, step, data, ind0, ind1, true); + } + } + catch (...) +@@ -214,37 +218,51 @@ int Convproc::impdata_create (unsigned int inp, + } + + +-int Convproc::impdata_update (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int ind0, +- int ind1) ++int Convproc::impdata_clear (uint32_t inp, uint32_t out) + { +- unsigned int j; ++ uint32_t k; + + if (_state < ST_STOP) return Converror::BAD_STATE; ++ for (k = 0; k < _nlevels; k++) _convlev [k]->impdata_clear (inp, out); ++ return 0; ++} ++ ++ ++int Convproc::impdata_update (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t ind0, ++ int32_t ind1) ++{ ++ uint32_t j; ++ ++ if (_state < ST_STOP) return Converror::BAD_STATE; ++ if ((inp >= _ninp) || (out >= _nout)) return Converror::BAD_PARAM; + for (j = 0; j < _nlevels; j++) + { +- _convlev [j]->impdata_update (inp, out, step, data, ind0, ind1); ++ _convlev [j]->impdata_write (inp, out, step, data, ind0, ind1, false); + } + return 0; + } + + +-int Convproc::impdata_copy (unsigned int inp1, +- unsigned int out1, +- unsigned int inp2, +- unsigned int out2) ++int Convproc::impdata_link (uint32_t inp1, ++ uint32_t out1, ++ uint32_t inp2, ++ uint32_t out2) + { +- unsigned int j; +- ++ uint32_t j; ++ ++ if ((inp1 >= _ninp) || (out1 >= _nout)) return Converror::BAD_PARAM; ++ if ((inp2 >= _ninp) || (out2 >= _nout)) return Converror::BAD_PARAM; ++ if ((inp1 == inp2) && (out1 == out2)) return Converror::BAD_PARAM; + if (_state != ST_STOP) return Converror::BAD_STATE; + try + { + for (j = 0; j < _nlevels; j++) + { +- _convlev [j]->impdata_copy (inp1, out1, inp2, out2); ++ _convlev [j]->impdata_link (inp1, out1, inp2, out2); + } + } + catch (...) +@@ -258,7 +276,7 @@ int Convproc::impdata_copy (unsigned int inp1, + + int Convproc::reset (void) + { +- unsigned int k; ++ uint32_t k; + + if (_state == ST_IDLE) return Converror::BAD_STATE; + for (k = 0; k < _ninp; k++) memset (_inpbuff [k], 0, _inpsize * sizeof (float)); +@@ -270,17 +288,17 @@ int Convproc::reset (void) + + int Convproc::start_process (int abspri, int policy) + { +- unsigned int k; ++ uint32_t k; + + if (_state != ST_STOP) return Converror::BAD_STATE; +- + _latecnt = 0; + _inpoffs = 0; + _outoffs = 0; + reset (); ++ + for (k = (_minpart == _quantum) ? 1 : 0; k < _nlevels; k++) + { +- _convlev [k]->start (abspri, policy); ++ _convlev [k]->start (abspri, policy); + } + _state = ST_PROC; + return 0; +@@ -289,14 +307,12 @@ int Convproc::start_process (int abspri, int policy) + + int Convproc::process (bool sync) + { +- unsigned int k; +- int f = 0; ++ uint32_t k; ++ int f = 0; + + if (_state != ST_PROC) return 0; +- + _inpoffs += _quantum; + if (_inpoffs == _inpsize) _inpoffs = 0; +- + _outoffs += _quantum; + if (_outoffs == _minpart) + { +@@ -309,7 +325,7 @@ int Convproc::process (bool sync) + { + if (++_latecnt >= 5) + { +- stop_process (); ++ if (~_options & OPT_LATE_CONTIN) stop_process (); + f |= FL_LOAD; + } + } +@@ -321,7 +337,7 @@ int Convproc::process (bool sync) + + int Convproc::stop_process (void) + { +- unsigned int k; ++ uint32_t k; + + if (_state != ST_PROC) return Converror::BAD_STATE; + for (k = 0; k < _nlevels; k++) _convlev [k]->stop (); +@@ -332,17 +348,12 @@ int Convproc::stop_process (void) + + int Convproc::cleanup (void) + { +- unsigned int k; ++ uint32_t k; + + while (! check_stop ()) + { + usleep (100000); + } +- if (_state != ST_STOP) +- { +- return Converror::BAD_STATE; +- } +- + for (k = 0; k < _ninp; k++) + { + delete[] _inpbuff [k]; +@@ -362,7 +373,6 @@ int Convproc::cleanup (void) + _state = ST_IDLE; + _options = 0; + _skipcnt = 0; +- _density = 0; + _ninp = 0; + _nout = 0; + _quantum = 0; +@@ -376,7 +386,7 @@ int Convproc::cleanup (void) + + bool Convproc::check_stop (void) + { +- unsigned int k; ++ uint32_t k; + + for (k = 0; (k < _nlevels) && (_convlev [k]->_stat == Convlevel::ST_IDLE); k++); + if (k == _nlevels) +@@ -390,7 +400,7 @@ bool Convproc::check_stop (void) + + void Convproc::print (FILE *F) + { +- unsigned int k; ++ uint32_t k; + + for (k = 0; k < _nlevels; k++) _convlev [k]->print (F); + } +@@ -424,21 +434,11 @@ Convlevel::~Convlevel (void) + } + + +-void *Convlevel::alloc_aligned (size_t size) +-{ +- void *p; +- +- if (posix_memalign (&p, 16, size)) throw (Converror (Converror::MEM_ALLOC)); +- memset (p, 0, size); +- return p; +-} +- +- +-void Convlevel::configure (int prio, +- unsigned int offs, +- unsigned int npar, +- unsigned int parsize, +- unsigned int options) ++void Convlevel::configure (int prio, ++ uint32_t offs, ++ uint32_t npar, ++ uint32_t parsize, ++ uint32_t options) + { + int fftwopt = (options & OPT_FFTW_MEASURE) ? FFTW_MEASURE : FFTW_ESTIMATE; + +@@ -448,9 +448,9 @@ void Convlevel::configure (int prio, + _parsize = parsize; + _options = options; + +- _time_data = (float *)(alloc_aligned (2 * _parsize * sizeof (float))); +- _prep_data = (float *)(alloc_aligned (2 * _parsize * sizeof (float))); +- _freq_data = (fftwf_complex *)(alloc_aligned ((_parsize + 1) * sizeof (fftwf_complex))); ++ _time_data = calloc_real (2 * _parsize); ++ _prep_data = calloc_real (2 * _parsize); ++ _freq_data = calloc_complex (_parsize + 1); + _plan_r2c = fftwf_plan_dft_r2c_1d (2 * _parsize, _time_data, _freq_data, fftwopt); + _plan_c2r = fftwf_plan_dft_c2r_1d (2 * _parsize, _freq_data, _time_data, fftwopt); + if (_plan_r2c && _plan_c2r) return; +@@ -458,42 +458,49 @@ void Convlevel::configure (int prio, + } + + +-void Convlevel::impdata_create (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int i0, +- int i1) ++void Convlevel::impdata_write (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t i0, ++ int32_t i1, ++ bool create) + { +- unsigned int k; +- int j, j0, j1, n; +- float norm; +- fftwf_complex *fftb; +- Macnode *M; ++ uint32_t k; ++ int32_t j, j0, j1, n; ++ float norm; ++ fftwf_complex *fftb; ++ Macnode *M; + + n = i1 - i0; + i0 = _offs - i0; + i1 = i0 + _npar * _parsize; + if ((i0 >= n) || (i1 <= 0)) return; + +- M = findmacnode (inp, out, true); +- if (! (M->_fftb)) ++ if (create) + { +- M->_fftb = new fftwf_complex * [_npar]; +- memset (M->_fftb, 0, _npar * sizeof (fftwf_complex *)); ++ M = findmacnode (inp, out, true); ++ if (M == 0 || M->_link) return; ++ if (M->_fftb == 0) M->alloc_fftb (_npar); + } +- ++ else ++ { ++ M = findmacnode (inp, out, false); ++ if (M == 0 || M->_link || M->_fftb == 0) return; ++ } ++ + norm = 0.5f / _parsize; + for (k = 0; k < _npar; k++) + { + i1 = i0 + _parsize; + if ((i0 < n) && (i1 > 0)) + { +- if (! (M->_fftb [k])) +- { +- M->_fftb [k] = (fftwf_complex *)(alloc_aligned ((_parsize + 1) * sizeof (fftwf_complex))); ++ fftb = M->_fftb [k]; ++ if (fftb == 0 && create) ++ { ++ M->_fftb [k] = fftb = calloc_complex (_parsize + 1); + } +- if (data) ++ if (fftb && data) + { + memset (_prep_data, 0, 2 * _parsize * sizeof (float)); + j0 = (i0 < 0) ? 0 : i0; +@@ -503,7 +510,6 @@ void Convlevel::impdata_create (unsigned int inp, + #ifdef ENABLE_VECTOR_MODE + if (_options & OPT_VECTOR_MODE) fftswap (_freq_data); + #endif +- fftb = M->_fftb [k]; + for (j = 0; j <= (int)_parsize; j++) + { + fftb [j][0] += _freq_data [j][0]; +@@ -516,52 +522,27 @@ void Convlevel::impdata_create (unsigned int inp, + } + + +-void Convlevel::impdata_update (unsigned int inp, +- unsigned int out, +- unsigned int step, +- float *data, +- int i0, +- int i1) ++void Convlevel::impdata_clear (uint32_t inp, uint32_t out) + { +- unsigned int k; +- int j, j0, j1, n; +- float norm; +- fftwf_complex *fftb; +- Macnode *M; ++ uint32_t i; ++ Macnode *M; + + M = findmacnode (inp, out, false); +- if (! M) return; +- +- n = i1 - i0; +- i0 = _offs - i0; +- i1 = i0 + _npar * _parsize; +- if ((i0 >= n) || (i1 <= 0)) return; +- +- norm = 0.5f / _parsize; +- for (k = 0; k < _npar; k++) ++ if (M == 0 || M->_link || M->_fftb == 0) return; ++ for (i = 0; i < _npar; i++) + { +- i1 = i0 + _parsize; +- fftb = M->_fftb [k]; +- if (fftb && (i0 < n) && (i1 > 0)) +- { +- memset (_prep_data, 0, 2 * _parsize * sizeof (float)); +- j0 = (i0 < 0) ? 0 : i0; +- j1 = (i1 > n) ? n : i1; +- for (j = j0; j < j1; j++) _prep_data [j - i0] = norm * data [j * step]; +- fftwf_execute_dft_r2c (_plan_r2c, _prep_data, fftb); +-#ifdef ENABLE_VECTOR_MODE +- if (_options & OPT_VECTOR_MODE) fftswap (fftb); +-#endif ++ if (M->_fftb [i]) ++ { ++ memset (M->_fftb [i], 0, (_parsize + 1) * sizeof (fftwf_complex)); + } +- i0 = i1; + } + } + + +-void Convlevel::impdata_copy (unsigned int inp1, +- unsigned int out1, +- unsigned int inp2, +- unsigned int out2) ++void Convlevel::impdata_link (uint32_t inp1, ++ uint32_t out1, ++ uint32_t inp2, ++ uint32_t out2) + { + Macnode *M1; + Macnode *M2; +@@ -569,18 +550,17 @@ void Convlevel::impdata_copy (unsigned int inp1, + M1 = findmacnode (inp1, out1, false); + if (! M1) return; + M2 = findmacnode (inp2, out2, true); +- if (M2->_fftb) return; +- M2->_fftb = M1->_fftb; +- M2->_copy = true; ++ M2->free_fftb (); ++ M2->_link = M1; + } + + +-void Convlevel::reset (unsigned int inpsize, +- unsigned int outsize, ++void Convlevel::reset (uint32_t inpsize, ++ uint32_t outsize, + float **inpbuff, + float **outbuff) + { +- unsigned int i; ++ uint32_t i; + Inpnode *X; + Outnode *Y; + +@@ -658,7 +638,6 @@ void Convlevel::stop (void) + + void Convlevel::cleanup (void) + { +- unsigned int i; + Inpnode *X, *X1; + Outnode *Y, *Y1; + Macnode *M, *M1; +@@ -666,8 +645,6 @@ void Convlevel::cleanup (void) + X = _inp_list; + while (X) + { +- for (i = 0; i < _npar; i++) free (X->_ffta [i]); +- delete[] X->_ffta; + X1 = X->_next; + delete X; + X = X1; +@@ -680,19 +657,10 @@ void Convlevel::cleanup (void) + M = Y->_list; + while (M) + { +- if ((M->_fftb) && !(M->_copy)) +- { +- for (i = 0; i < _npar; i++) +- { +- free (M->_fftb [i]); +- } +- delete[] M->_fftb; +- } + M1 = M->_next; + delete M; + M = M1; + } +- for (i = 0; i < 3; i++) free (Y->_buff [i]); + Y1 = Y->_next; + delete Y; + Y = Y1; +@@ -701,9 +669,9 @@ void Convlevel::cleanup (void) + + fftwf_destroy_plan (_plan_r2c); + fftwf_destroy_plan (_plan_c2r); +- free (_time_data); +- free (_prep_data); +- free (_freq_data); ++ fftwf_free (_time_data); ++ fftwf_free (_prep_data); ++ fftwf_free (_freq_data); + _plan_r2c = 0; + _plan_c2r = 0; + _time_data = 0; +@@ -739,9 +707,7 @@ void Convlevel::main (void) + + void Convlevel::process (bool skip) + { +- unsigned int i, j, k; +- unsigned int i1, n1, n2, opi1, opi2; +- ++ uint32_t i, i1, j, k, n1, n2, opi1, opi2; + Inpnode *X; + Macnode *M; + Outnode *Y; +@@ -796,7 +762,7 @@ void Convlevel::process (bool skip) + for (j = 0; j < _npar; j++) + { + ffta = X->_ffta [i]; +- fftb = M->_fftb [j]; ++ fftb = M->_link ? M->_link->_fftb [j] : M->_fftb [j]; + if (fftb) + { + #ifdef ENABLE_VECTOR_MODE +@@ -847,11 +813,11 @@ void Convlevel::process (bool skip) + } + + +-int Convlevel::readout (bool sync, unsigned int skipcnt) ++int Convlevel::readout (bool sync, uint32_t skipcnt) + { +- unsigned int i; +- float *p, *q; +- Outnode *Y; ++ uint32_t i; ++ float *p, *q; ++ Outnode *Y; + + _outoffs += _outsize; + if (_outoffs == _parsize) +@@ -893,58 +859,38 @@ void Convlevel::print (FILE *F) + } + + +-Macnode *Convlevel::findmacnode (unsigned int inp, unsigned int out, bool create) ++Macnode *Convlevel::findmacnode (uint32_t inp, uint32_t out, bool create) + { +- unsigned int i; +- Inpnode *X; +- Outnode *Y; +- Macnode *M; ++ Inpnode *X; ++ Outnode *Y; ++ Macnode *M; + + for (X = _inp_list; X && (X->_inp != inp); X = X->_next); + if (! X) + { + if (! create) return 0; +- X = new Inpnode; ++ X = new Inpnode (inp); + X->_next = _inp_list; + _inp_list = X; +- X->_inp = inp; +- X->_ffta = new fftwf_complex * [_npar]; +- memset (X->_ffta, 0, _npar * sizeof (fftw_complex *)); +- for (i = 0; i < _npar; i++) +- { +- X->_ffta [i] = (fftwf_complex *)(alloc_aligned ((_parsize + 1) * sizeof (fftwf_complex))); +- } ++ X->alloc_ffta (_npar, _parsize); + } + + for (Y = _out_list; Y && (Y->_out != out); Y = Y->_next); + if (! Y) + { + if (! create) return 0; +- Y = new Outnode; ++ Y = new Outnode (out, _parsize); + Y->_next = _out_list; + _out_list = Y; +- Y->_out = out; +- Y->_list = 0; +- for (i = 0; i < 3; i++) +- { +- Y->_buff [i] = 0; +- } +- for (i = 0; i < 3; i++) +- { +- Y->_buff [i] = (float *)(alloc_aligned (_parsize * sizeof (float))); +- } + } + + for (M = Y->_list; M && (M->_inpn != X); M = M->_next); + if (! M) + { + if (! create) return 0; +- M = new Macnode; ++ M = new Macnode (X); + M->_next = Y->_list; + Y->_list = M; +- M->_inpn = X; +- M->_fftb = 0; +- M->_copy = false; + } + + return M; +@@ -955,8 +901,8 @@ Macnode *Convlevel::findmacnode (unsigned int inp, unsigned int out, bool create + + void Convlevel::fftswap (fftwf_complex *p) + { +- unsigned int n = _parsize; +- float a, b; ++ uint32_t n = _parsize; ++ float a, b; + + while (n) + { +@@ -974,3 +920,98 @@ void Convlevel::fftswap (fftwf_complex *p) + #endif + + ++Inpnode::Inpnode (uint16_t inp): ++ _next (0), ++ _ffta (0), ++ _npar (0), ++ _inp (inp) ++{ ++} ++ ++ ++Inpnode::~Inpnode (void) ++{ ++ free_ffta (); ++} ++ ++ ++void Inpnode::alloc_ffta (uint16_t npar, int32_t size) ++{ ++ _npar = npar; ++ _ffta = new fftwf_complex * [_npar]; ++ for (int i = 0; i < _npar; i++) ++ { ++ _ffta [i] = calloc_complex (size + 1); ++ } ++} ++ ++ ++void Inpnode::free_ffta (void) ++{ ++ if (!_ffta) return; ++ for (uint16_t i = 0; i < _npar; i++) ++ { ++ fftwf_free ( _ffta [i]); ++ } ++ delete[] _ffta; ++ _ffta = 0; ++ _npar = 0; ++} ++ ++ ++Macnode::Macnode (Inpnode *inpn): ++ _next (0), ++ _inpn (inpn), ++ _link (0), ++ _fftb (0), ++ _npar (0) ++{} ++ ++ ++Macnode::~Macnode (void) ++{ ++ free_fftb (); ++} ++ ++ ++void Macnode::alloc_fftb (uint16_t npar) ++{ ++ _npar = npar; ++ _fftb = new fftwf_complex * [_npar]; ++ for (uint16_t i = 0; i < _npar; i++) ++ { ++ _fftb [i] = 0; ++ } ++} ++ ++ ++void Macnode::free_fftb (void) ++{ ++ if (!_fftb) return; ++ for (uint16_t i = 0; i < _npar; i++) ++ { ++ fftwf_free ( _fftb [i]); ++ } ++ delete[] _fftb; ++ _fftb = 0; ++ _npar = 0; ++} ++ ++ ++Outnode::Outnode (uint16_t out, int32_t size): ++ _next (0), ++ _list (0), ++ _out (out) ++{ ++ _buff [0] = calloc_real (size); ++ _buff [1] = calloc_real (size); ++ _buff [2] = calloc_real (size); ++} ++ ++ ++Outnode::~Outnode (void) ++{ ++ fftwf_free (_buff [0]); ++ fftwf_free (_buff [1]); ++ fftwf_free (_buff [2]); ++} +diff --git a/lib/zita-convolver-4.0.0/zita-convolver.h b/lib/zita-convolver-4.0.0/zita-convolver.h +new file mode 100644 +index 0000000..0236bc0 +--- /dev/null ++++ b/lib/zita-convolver-4.0.0/zita-convolver.h +@@ -0,0 +1,475 @@ ++// ---------------------------------------------------------------------------- ++// ++// Copyright (C) 2006-2018 Fons Adriaensen <f...@linuxaudio.org> ++// ++// This program is free software; you can redistribute it and/or modify ++// it under the terms of the GNU General Public License as published by ++// the Free Software Foundation; either version 3 of the License, or ++// (at your option) any later version. ++// ++// This program is distributed in the hope that it will be useful, ++// but WITHOUT ANY WARRANTY; without even the implied warranty of ++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++// GNU General Public License for more details. ++// ++// You should have received a copy of the GNU General Public License ++// along with this program. If not, see <http://www.gnu.org/licenses/>. ++// ++// ---------------------------------------------------------------------------- ++ ++ ++#ifndef _ZITA_CONVOLVER_H ++#define _ZITA_CONVOLVER_H ++ ++ ++#include <pthread.h> ++#include <stdint.h> ++#include <fftw3.h> ++ ++ ++#define ZITA_CONVOLVER_MAJOR_VERSION 4 ++#define ZITA_CONVOLVER_MINOR_VERSION 0 ++ ++ ++extern int zita_convolver_major_version (void); ++extern int zita_convolver_minor_version (void); ++ ++ ++// ---------------------------------------------------------------------------- ++ ++ ++#ifdef ZCSEMA_IS_IMPLEMENTED ++#undef ZCSEMA_IS_IMPLEMENTED ++#endif ++ ++//XXX DZ: Hack for windows/osx10.5 ++#include "zcsema-osx-win-compat.h" ++ ++#if defined(__linux__) || defined(__GNU__) || defined(__FreeBSD__) || defined(__FreeBSD_kernel__) ++ ++#include <semaphore.h> ++ ++class ZCsema ++{ ++public: ++ ++ ZCsema (void) { init (0, 0); } ++ ~ZCsema (void) { sem_destroy (&_sema); } ++ ++ ZCsema (const ZCsema&); // disabled ++ ZCsema& operator= (const ZCsema&); // disabled ++ ++ int init (int s, int v) { return sem_init (&_sema, s, v); } ++ int post (void) { return sem_post (&_sema); } ++ int wait (void) { return sem_wait (&_sema); } ++ int trywait (void) { return sem_trywait (&_sema); } ++ ++private: ++ ++ sem_t _sema; ++}; ++ ++#define ZCSEMA_IS_IMPLEMENTED ++#endif ++ ++ ++#ifdef __APPLE__ ++ ++// NOTE: ***** I DO NOT REPEAT NOT PROVIDE SUPPORT FOR OSX ***** ++// ++// The following code partially emulates the POSIX sem_t for which ++// OSX has only a crippled implementation. It may or may not compile, ++// and if it compiles it may or may not work correctly. Blame APPLE ++// for not following POSIX standards. ++ ++class ZCsema ++{ ++public: ++ ++ ZCsema (void) : _count (0) ++ { ++ init (0, 0); ++ } ++ ++ ~ZCsema (void) ++ { ++ pthread_mutex_destroy (&_mutex); ++ pthread_cond_destroy (&_cond); ++ } ++ ++ ZCsema (const ZCsema&); // disabled ++ ZCsema& operator= (const ZCsema&); // disabled ++ ++ int init (int s, int v) ++ { ++ _count = v; ++ return pthread_mutex_init (&_mutex, 0) || pthread_cond_init (&_cond, 0); ++ } ++ ++ int post (void) ++ { ++ pthread_mutex_lock (&_mutex); ++ _count++; ++ if (_count == 1) pthread_cond_signal (&_cond); ++ pthread_mutex_unlock (&_mutex); ++ return 0; ++ } ++ ++ int wait (void) ++ { ++ pthread_mutex_lock (&_mutex); ++ while (_count < 1) pthread_cond_wait (&_cond, &_mutex); ++ _count--; ++ pthread_mutex_unlock (&_mutex); ++ return 0; ++ } ++ ++ int trywait (void) ++ { ++ if (pthread_mutex_trylock (&_mutex)) return -1; ++ if (_count < 1) ++ { ++ pthread_mutex_unlock (&_mutex); ++ return -1; ++ } ++ _count--; ++ pthread_mutex_unlock (&_mutex); ++ return 0; ++ } ++ ++private: ++ ++ int _count; ++ pthread_mutex_t _mutex; ++ pthread_cond_t _cond; ++}; ++ ++#define ZCSEMA_IS_IMPLEMENTED ++#endif ++ ++ ++#ifndef ZCSEMA_IS_IMPLEMENTED ++#error "The ZCsema class is not implemented." ++#endif ++ ++ ++// ---------------------------------------------------------------------------- ++ ++ ++class Inpnode ++{ ++private: ++ ++ friend class Convlevel; ++ ++ Inpnode (uint16_t inp); ++ ~Inpnode (void); ++ void alloc_ffta (uint16_t npar, int32_t size); ++ void free_ffta (void); ++ ++ Inpnode *_next; ++ fftwf_complex **_ffta; ++ uint16_t _npar; ++ uint16_t _inp; ++}; ++ ++ ++class Macnode ++{ ++private: ++ ++ friend class Convlevel; ++ ++ Macnode (Inpnode *inpn); ++ ~Macnode (void); ++ void alloc_fftb (uint16_t npar); ++ void free_fftb (void); ++ ++ Macnode *_next; ++ Inpnode *_inpn; ++ Macnode *_link; ++ fftwf_complex **_fftb; ++ uint16_t _npar; ++}; ++ ++ ++class Outnode ++{ ++private: ++ ++ friend class Convlevel; ++ ++ Outnode (uint16_t out, int32_t size); ++ ~Outnode (void); ++ ++ Outnode *_next; ++ Macnode *_list; ++ float *_buff [3]; ++ uint16_t _out; ++}; ++ ++ ++class Converror ++{ ++public: ++ ++ enum ++ { ++ BAD_STATE = -1, ++ BAD_PARAM = -2, ++ MEM_ALLOC = -3 ++ }; ++ ++ Converror (int error) : _error (error) {} ++ ++private: ++ ++ int _error; ++}; ++ ++ ++class Convlevel ++{ ++private: ++ ++ friend class Convproc; ++ ++ enum ++ { ++ OPT_FFTW_MEASURE = 1, ++ OPT_VECTOR_MODE = 2, ++ OPT_LATE_CONTIN = 4 ++ }; ++ ++ enum ++ { ++ ST_IDLE, ++ ST_TERM, ++ ST_PROC ++ }; ++ ++ Convlevel (void); ++ ~Convlevel (void); ++ ++ void configure (int prio, ++ uint32_t offs, ++ uint32_t npar, ++ uint32_t parsize, ++ uint32_t options); ++ ++ void impdata_write (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t ind0, ++ int32_t ind1, ++ bool create); ++ ++ void impdata_clear (uint32_t inp, ++ uint32_t out); ++ ++ void impdata_link (uint32_t inp1, ++ uint32_t out1, ++ uint32_t inp2, ++ uint32_t out2); ++ ++ void reset (uint32_t inpsize, ++ uint32_t outsize, ++ float **inpbuff, ++ float **outbuff); ++ ++ void start (int absprio, int policy); ++ ++ void process (bool sync); ++ ++ int readout (bool sync, uint32_t skipcnt); ++ ++ void stop (void); ++ ++ void cleanup (void); ++ ++ void fftswap (fftwf_complex *p); ++ ++ void print (FILE *F); ++ ++ static void *static_main (void *arg); ++ ++ void main (void); ++ ++ Macnode *findmacnode (uint32_t inp, uint32_t out, bool create); ++ ++ ++ volatile uint32_t _stat; // current processing state ++ int _prio; // relative priority ++ uint32_t _offs; // offset from start of impulse response ++ uint32_t _npar; // number of partitions ++ uint32_t _parsize; // partition and outbut buffer size ++ uint32_t _outsize; // step size for output buffer ++ uint32_t _outoffs; // offset into output buffer ++ uint32_t _inpsize; // size of shared input buffer ++ uint32_t _inpoffs; // offset into input buffer ++ uint32_t _options; // various options ++ uint32_t _ptind; // rotating partition index ++ uint32_t _opind; // rotating output buffer index ++ int _bits; // bit identifiying this level ++ int _wait; // number of unfinished cycles ++ pthread_t _pthr; // posix thread executing this level ++ ZCsema _trig; // sema used to trigger a cycle ++ ZCsema _done; // sema used to wait for a cycle ++ Inpnode *_inp_list; // linked list of active inputs ++ Outnode *_out_list; // linked list of active outputs ++ fftwf_plan _plan_r2c; // FFTW plan, forward FFT ++ fftwf_plan _plan_c2r; // FFTW plan, inverse FFT ++ float *_time_data; // workspace ++ float *_prep_data; // workspace ++ fftwf_complex *_freq_data; // workspace ++ float **_inpbuff; // array of shared input buffers ++ float **_outbuff; // array of shared output buffers ++}; ++ ++ ++// ---------------------------------------------------------------------------- ++ ++ ++class Convproc ++{ ++public: ++ ++ Convproc (void); ++ ~Convproc (void); ++ ++ enum ++ { ++ ST_IDLE, ++ ST_STOP, ++ ST_WAIT, ++ ST_PROC ++ }; ++ ++ enum ++ { ++ FL_LATE = 0x0000FFFF, ++ FL_LOAD = 0x01000000 ++ }; ++ ++ enum ++ { ++ OPT_FFTW_MEASURE = Convlevel::OPT_FFTW_MEASURE, ++ OPT_VECTOR_MODE = Convlevel::OPT_VECTOR_MODE, ++ OPT_LATE_CONTIN = Convlevel::OPT_LATE_CONTIN ++ }; ++ ++ enum ++ { ++ MAXINP = 64, ++ MAXOUT = 64, ++ MAXLEV = 8, ++ MINPART = 64, ++ MAXPART = 8192, ++ MAXDIVIS = 16, ++ MINQUANT = 16, ++ MAXQUANT = 8192 ++ }; ++ ++ uint32_t state (void) const ++ { ++ return _state; ++ } ++ ++ float *inpdata (uint32_t inp) const ++ { ++ return _inpbuff [inp] + _inpoffs; ++ } ++ ++ float *outdata (uint32_t out) const ++ { ++ return _outbuff [out] + _outoffs; ++ } ++ ++ int configure (uint32_t ninp, ++ uint32_t nout, ++ uint32_t maxsize, ++ uint32_t quantum, ++ uint32_t minpart, ++ uint32_t maxpart, ++ float density); ++ ++ int impdata_create (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t ind0, ++ int32_t ind1); ++ ++ int impdata_clear (uint32_t inp, ++ uint32_t out); ++ ++ int impdata_update (uint32_t inp, ++ uint32_t out, ++ int32_t step, ++ float *data, ++ int32_t ind0, ++ int32_t ind1); ++ ++ int impdata_link (uint32_t inp1, ++ uint32_t out1, ++ uint32_t inp2, ++ uint32_t out2); ++ ++ // Deprecated, use impdata_link() instead. ++ int impdata_copy (uint32_t inp1, ++ uint32_t out1, ++ uint32_t inp2, ++ uint32_t out2) ++ { ++ return impdata_link (inp1, out1, inp2, out2); ++ } ++ ++ void set_options (uint32_t options); ++ ++ void set_skipcnt (uint32_t skipcnt); ++ ++ int reset (void); ++ ++ int start_process (int abspri, int policy); ++ ++ int process (bool sync = false); ++ ++ int stop_process (void); ++ ++ bool check_stop (void); ++ ++ int cleanup (void); ++ ++ void print (FILE *F = stdout); ++ ++private: ++ ++ uint32_t _state; // current state ++ float *_inpbuff [MAXINP]; // input buffers ++ float *_outbuff [MAXOUT]; // output buffers ++ uint32_t _inpoffs; // current offset in input buffers ++ uint32_t _outoffs; // current offset in output buffers ++ uint32_t _options; // option bits ++ uint32_t _skipcnt; // number of frames to skip ++ uint32_t _ninp; // number of inputs ++ uint32_t _nout; // number of outputs ++ uint32_t _quantum; // processing block size ++ uint32_t _minpart; // smallest partition size ++ uint32_t _maxpart; // largest allowed partition size ++ uint32_t _nlevels; // number of partition sizes ++ uint32_t _inpsize; // size of input buffers ++ uint32_t _latecnt; // count of cycles ending too late ++ Convlevel *_convlev [MAXLEV]; // array of processors ++ void *_dummy [64]; ++ ++ static float _mac_cost; ++ static float _fft_cost; ++}; ++ ++ ++// ---------------------------------------------------------------------------- ++ ++ ++#endif ++ +diff --git a/plugins/ZamHeadX2/Makefile b/plugins/ZamHeadX2/Makefile +index c838293..8500534 100644 +--- a/plugins/ZamHeadX2/Makefile ++++ b/plugins/ZamHeadX2/Makefile +@@ -13,7 +13,7 @@ NAME = ZamHeadX2 + # Files to build + + OBJS_DSP = \ +- ../../lib/zita-convolver-3.1.0/zita-convolver.cpp.o \ ++ ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o \ + convolution.cpp.o \ + ZamHeadX2Plugin.cpp.o + +diff --git a/plugins/ZamHeadX2/convolution.cpp b/plugins/ZamHeadX2/convolution.cpp +index 81847e0..0026ba2 100644 +--- a/plugins/ZamHeadX2/convolution.cpp ++++ b/plugins/ZamHeadX2/convolution.cpp +@@ -42,12 +42,12 @@ + #include <pthread.h> + #include <assert.h> + +-#include "../../lib/zita-convolver-3.1.0/zita-convolver.h" ++#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + #include <samplerate.h> + #include "convolution.hpp" + +-#if ZITA_CONVOLVER_MAJOR_VERSION != 3 +-# error "This programs requires zita-convolver 3.x.x" ++#if ZITA_CONVOLVER_MAJOR_VERSION != 4 ++# error "This programs requires zita-convolver 4.x.x" + #endif + + #ifndef SRC_QUALITY +@@ -557,7 +557,6 @@ int LV2convolv::clv_initialize ( + + convproc = new Convproc(); + convproc->set_options (options); +- convproc->set_density (density); + + float fir_coeffs_lr[400] = { 0 }; + for (int i = 0; i < 200; i++) { +@@ -600,7 +599,8 @@ int LV2convolv::clv_initialize ( + /*max-convolution length */ max_size, + /*quantum*/ buffersize, + /*min-part*/ buffersize, +- /*max-part*/ buffersize ++ /*max-part*/ buffersize, ++ density + )) { + fprintf (stderr, "convolution: Cannot initialize convolution engine.\n"); + goto errout; +diff --git a/plugins/ZamHeadX2/convolution.hpp b/plugins/ZamHeadX2/convolution.hpp +index ddf3d08..80be8e6 100644 +--- a/plugins/ZamHeadX2/convolution.hpp ++++ b/plugins/ZamHeadX2/convolution.hpp +@@ -19,7 +19,7 @@ + #ifndef CONVOLUTION_H_ + #define CONVOLUTION_H_ + +-#include "../../lib/zita-convolver-3.1.0/zita-convolver.h" ++#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + + #define MAX_CHANNEL_MAPS (4) + #define VERBOSE_printf(x, ...) +diff --git a/plugins/ZamVerb/Makefile b/plugins/ZamVerb/Makefile +index 82c3bab..eacc080 100644 +--- a/plugins/ZamVerb/Makefile ++++ b/plugins/ZamVerb/Makefile +@@ -16,7 +16,7 @@ OBJS_DSP = \ + ZamVerbPlugin.cpp.o \ + ZamVerbImpulses.cpp.o \ + convolution.cpp.o \ +- ../../lib/zita-convolver-3.1.0/zita-convolver.cpp.o ++ ../../lib/zita-convolver-4.0.0/zita-convolver.cpp.o + + OBJS_UI = \ + ZamVerbArtwork.cpp.o \ +diff --git a/plugins/ZamVerb/convolution.cpp b/plugins/ZamVerb/convolution.cpp +index 517a3cb..27374e0 100644 +--- a/plugins/ZamVerb/convolution.cpp ++++ b/plugins/ZamVerb/convolution.cpp +@@ -42,13 +42,13 @@ + #include <pthread.h> + #include <assert.h> + +-#include "../../lib/zita-convolver-3.1.0/zita-convolver.h" ++#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + #include <samplerate.h> + #include "convolution.hpp" + #include "ZamVerbImpulses.hpp" + +-#if ZITA_CONVOLVER_MAJOR_VERSION != 3 +-# error "This programs requires zita-convolver 3.x.x" ++#if ZITA_CONVOLVER_MAJOR_VERSION != 4 ++# error "This programs requires zita-convolver 4.x.x" + #endif + + #ifndef SRC_QUALITY +@@ -295,7 +295,6 @@ int LV2convolv::clv_initialize ( + + convproc = new Convproc(); + convproc->set_options (options); +- convproc->set_density (density); + /* + if (audiofile_read (ir_fn, sample_rate, &p, &n_chan, &n_frames)) { + fprintf(stderr, "convolution: failed to read IR.\n"); +@@ -337,7 +336,8 @@ int LV2convolv::clv_initialize ( + /*max-convolution length */ max_size, + /*quantum*/ buffersize, + /*min-part*/ buffersize, +- /*max-part*/ buffersize ++ /*max-part*/ buffersize, ++ density + )) { + fprintf (stderr, "convolution: Cannot initialize convolution engine.\n"); + goto errout; +diff --git a/plugins/ZamVerb/convolution.hpp b/plugins/ZamVerb/convolution.hpp +index 4eeada5..1c89971 100644 +--- a/plugins/ZamVerb/convolution.hpp ++++ b/plugins/ZamVerb/convolution.hpp +@@ -19,7 +19,7 @@ + #ifndef CONVOLUTION_H_ + #define CONVOLUTION_H_ + +-#include "../../lib/zita-convolver-3.1.0/zita-convolver.h" ++#include "../../lib/zita-convolver-4.0.0/zita-convolver.h" + + #define MAX_CHANNEL_MAPS (4) + #define VERBOSE_printf(x, ...) +-- +2.18.0 +