Fix DSP::process_map() plugin-pin I/O map handing

The previous approach failed in case where PluginInsert
uses no-inplace buffers with a linear map.
Since buffers are replicated up to a total of number of
all (inputs + outputs), the number of output buffers
could not be determined. There was insufficient information
using the I/O map alone.

With a known number of outputs processing and applying
the i/o map is also a lot easier and faster.

This break the API of process_map().
This commit is contained in:
Robin Gareus 2020-02-26 17:50:08 +01:00
parent a5c956883d
commit d27cdb3855
Signed by: rgareus
GPG Key ID: A090BCE02CF57F04
4 changed files with 23 additions and 35 deletions

View File

@ -166,10 +166,10 @@ namespace ARDOUR { namespace DSP {
float log_meter_coeff (float coeff);
void process_map (BufferSet* bufs,
const ChanMapping& in,
const ChanMapping& out,
pframes_t nframes, samplecnt_t offset,
const DataType&);
const ChanCount& n_out,
const ChanMapping& in_map,
const ChanMapping& out_map,
pframes_t nframes, samplecnt_t offset);
/** 1st order Low Pass filter */
class LIBARDOUR_API LowPass {

View File

@ -174,7 +174,7 @@ void
Convolution::run (BufferSet& bufs, ChanMapping const& in_map, ChanMapping const& out_map, pframes_t n_samples, samplecnt_t offset)
{
if (!ready ()) {
process_map (&bufs, in_map, out_map, n_samples, offset, DataType::AUDIO);
process_map (&bufs, ChanCount (DataType::AUDIO, _n_outputs), in_map, out_map, n_samples, offset);
return;
}

View File

@ -75,40 +75,28 @@ ARDOUR::DSP::peaks (const float *data, float &min, float &max, uint32_t n_sample
}
void
ARDOUR::DSP::process_map (BufferSet* bufs, const ChanMapping& in, const ChanMapping& out, pframes_t nframes, samplecnt_t offset, const DataType& dt)
ARDOUR::DSP::process_map (BufferSet* bufs, const ChanCount& n_out, const ChanMapping& in_map, const ChanMapping& out_map, pframes_t nframes, samplecnt_t offset)
{
const ChanMapping::Mappings& im (in.mappings());
const ChanMapping::Mappings& om (out.mappings());
for (ChanMapping::Mappings::const_iterator tm = im.begin(); tm != im.end(); ++tm) {
if (tm->first != dt) { continue; }
for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
/* PluginInsert already handles most, in particular `no-inplace` buffers in case
* or x-over connections, and through connections.
*
* This just fills output buffers, forwarding inputs as needed:
* Input -> plugin-sink == plugin-src -> Output
*/
for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
for (uint32_t out = 0; out < n_out.get (*t); ++out) {
bool valid;
const uint32_t idx = out.get (dt, i->second, &valid);
if (valid && idx != i->first) {
bufs->get_available (dt, idx).read_from (bufs->get_available (dt, i->first), nframes, offset, offset);
}
}
}
for (ChanMapping::Mappings::const_iterator tm = im.begin(); tm != im.end(); ++tm) {
if (tm->first != dt) { continue; }
for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
bool valid;
in.get_src (dt, i->first, &valid);
uint32_t out_idx = out_map.get (*t, out, &valid);
if (!valid) {
bufs->get_available (dt, i->second).silence (nframes, offset);
continue;
}
}
}
/* reverse lookup (in case input map is empty */
for (ChanMapping::Mappings::const_iterator tm = om.begin(); tm != om.end(); ++tm) {
if (tm->first != dt) { continue; }
for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
bool valid;
in.get_src (dt, i->first, &valid);
uint32_t in_idx = in_map.get (*t, out, &valid);
if (!valid) {
bufs->get_available (dt, i->second).silence (nframes, offset);
bufs->get_available (*t, out_idx).silence (nframes, offset);
continue;
}
if (in_idx != out_idx) {
bufs->get_available (*t, out_idx).read_from (bufs->get_available (*t, in_idx), nframes, offset, offset);
}
}
}

View File

@ -571,7 +571,7 @@ LuaProc::configure_io (ChanCount in, ChanCount out)
luabridge::LuaRef lua_dsp_configure = luabridge::getGlobal (L, "dsp_configure");
if (lua_dsp_configure.type () == LUA_TFUNCTION) {
try {
luabridge::LuaRef io = lua_dsp_configure (&in, &out);
luabridge::LuaRef io = lua_dsp_configure (in, out);
if (io.isTable ()) {
ChanCount lin (_selected_in);
ChanCount lout (_selected_out);