From 4ef3e251853dec5e7e300618c5135ea33af9ff81 Mon Sep 17 00:00:00 2001 From: Robin Gareus Date: Fri, 18 Mar 2016 20:00:44 +0100 Subject: Add some convenient DSP methods for lua scripts --- libs/ardour/ardour/dsp_filter.h | 56 +++++++++++++++++++++++++++++++++++++++++ libs/ardour/dsp_filter.cc | 23 +++++++++++++++++ libs/ardour/luabindings.cc | 31 +++++++++++++++++++++-- 3 files changed, 108 insertions(+), 2 deletions(-) diff --git a/libs/ardour/ardour/dsp_filter.h b/libs/ardour/ardour/dsp_filter.h index ae2928de93..1b4cb6eed8 100644 --- a/libs/ardour/ardour/dsp_filter.h +++ b/libs/ardour/ardour/dsp_filter.h @@ -20,13 +20,69 @@ #define _dsp_filter_h_ #include +#include +#include +#include #include "ardour/libardour_visibility.h" namespace ARDOUR { namespace DSP { + /** a convenience class for lua scripts to use C memory for DSP operations. + * + * It should be allocated during dsp_init() or dsp_configure(). + */ + class DspShm { + public: + DspShm () + : _data (0) + , _size (0) + { + assert (sizeof(float) == sizeof (int32_t)); + assert (sizeof(float) == sizeof (int)); + } + + ~DspShm () { + free (_data); + } + + void allocate (size_t s) { + _data = realloc (_data, sizeof(float) * s); + if (_data) { _size = s; } + } + + void clear () { + memset (_data, 0, sizeof(float) * _size); + } + + float* to_float (size_t off) { + if (off >= _size) { return 0; } + return &(((float*)_data)[off]); + } + + int32_t* to_int (size_t off) { + if (off >= _size) { return 0; } + return &(((int32_t*)_data)[off]); + } + + void atomic_set_int (size_t off, int32_t val) { + g_atomic_int_set (&(((int32_t*)_data)[off]), val); + } + + int32_t atomic_get_int (size_t off) { + return g_atomic_int_get (&(((int32_t*)_data)[off])); + } + + private: + void* _data; + size_t _size; + }; + void memset (float *data, const float val, const uint32_t n_samples); void mmult (float *data, float *mult, const uint32_t n_samples); + void peaks (float *data, float &min, float &max, uint32_t n_samples); + float log_meter (float power); + float log_meter_coeff (float coeff); class LIBARDOUR_API LowPass { public: diff --git a/libs/ardour/dsp_filter.cc b/libs/ardour/dsp_filter.cc index 3026666b79..2678d0008c 100644 --- a/libs/ardour/dsp_filter.cc +++ b/libs/ardour/dsp_filter.cc @@ -19,6 +19,7 @@ #include #include +#include "ardour/dB.h" #include "ardour/dsp_filter.h" #ifndef M_PI @@ -41,6 +42,28 @@ ARDOUR::DSP::mmult (float *data, float *mult, const uint32_t n_samples) { } } +float +ARDOUR::DSP::log_meter (float power) { + // compare to gtk2_ardour/logmeter.h + static const float lower_db = -192.f; + static const float upper_db = 0.f; + static const float non_linearity = 8.0; + return (power < lower_db ? 0.0 : powf ((power - lower_db) / (upper_db - lower_db), non_linearity)); +} + +float +ARDOUR::DSP::log_meter_coeff (float coeff) { + if (coeff <= 0) return 0; + return log_meter (fast_coefficient_to_dB (coeff)); +} + +void +ARDOUR::DSP::peaks (float *data, float &min, float &max, uint32_t n_samples) { + for (uint32_t i = 0; i < n_samples; ++i) { + if (data[i] < min) min = data[i]; + if (data[i] > max) max = data[i]; + } +} LowPass::LowPass (double samplerate, float freq) : _rate (samplerate) diff --git a/libs/ardour/luabindings.cc b/libs/ardour/luabindings.cc index 0fa52c4020..b202649229 100644 --- a/libs/ardour/luabindings.cc +++ b/libs/ardour/luabindings.cc @@ -89,6 +89,19 @@ LuaBindings::stddef (lua_State* L) .registerArray ("FloatArray") .endNamespace (); + // register float array (int32_t*) + luabridge::getGlobalNamespace (L) + .beginNamespace ("ARDOUR") + .registerArray ("IntArray") + .endNamespace (); + + // std::vector + luabridge::getGlobalNamespace (L) + .beginNamespace ("ARDOUR") + .beginStdVector ("DoubleVector") + .endClass () + .endNamespace (); + // TODO std::set } @@ -562,6 +575,10 @@ LuaBindings::dsp (lua_State* L) .addFunction ("accurate_coefficient_to_dB", &accurate_coefficient_to_dB) .addFunction ("memset", &DSP::memset) .addFunction ("mmult", &DSP::mmult) + .addFunction ("log_meter", &DSP::log_meter) + .addFunction ("log_meter_coeff", &DSP::log_meter_coeff) + .addRefFunction ("peaks", &DSP::peaks) + .beginClass ("LowPass") .addConstructor () .addFunction ("proc", &DSP::LowPass::proc) @@ -575,8 +592,18 @@ LuaBindings::dsp (lua_State* L) .addFunction ("compute", &DSP::BiQuad::compute) .addFunction ("reset", &DSP::BiQuad::reset) .endClass () - .endNamespace () - .endNamespace (); + + .beginClass ("DspShm") + .addFunction ("allocate", &DSP::DspShm::allocate) + .addFunction ("clear", &DSP::DspShm::clear) + .addFunction ("to_float", &DSP::DspShm::to_float) + .addFunction ("to_int", &DSP::DspShm::to_int) + .addFunction ("atomic_set_int", &DSP::DspShm::atomic_set_int) + .addFunction ("atomic_get_int", &DSP::DspShm::atomic_get_int) + .endClass () + + .endNamespace () // DSP + .endNamespace (); // ARDOUR } void -- cgit v1.2.3