X-Git-Url: https://git.carlh.net/gitweb/?a=blobdiff_plain;ds=sidebyside;f=libs%2Fardour%2Faudio_port.cc;h=1a6c30dcf25b5e6b07c66a27257603d59ad1d76c;hb=b285559767e21aae4467270590f048c3263fd742;hp=f559578e4e366bc3c93978a609e2248c1c9a1d15;hpb=1937c74191468b4e9e4baa251bb6329a3818d8e4;p=ardour.git diff --git a/libs/ardour/audio_port.cc b/libs/ardour/audio_port.cc index f559578e4e..1a6c30dcf2 100644 --- a/libs/ardour/audio_port.cc +++ b/libs/ardour/audio_port.cc @@ -18,6 +18,7 @@ #include +#include "pbd/malign.h" #include "pbd/stacktrace.h" #include "ardour/audio_buffer.h" @@ -29,6 +30,7 @@ using namespace ARDOUR; using namespace std; +#define ENGINE AudioEngine::instance() #define port_engine AudioEngine::instance()->port_engine() AudioPort::AudioPort (const std::string& name, PortFlags flags) @@ -36,10 +38,14 @@ AudioPort::AudioPort (const std::string& name, PortFlags flags) , _buffer (new AudioBuffer (0)) { assert (name.find_first_of (':') == string::npos); + cache_aligned_malloc ((void**) &_data, sizeof (Sample) * 8192); + _src.setup (_resampler_quality); + _src.set_rrfilt (10); } AudioPort::~AudioPort () { + cache_aligned_free (_data); delete _buffer; } @@ -47,11 +53,27 @@ void AudioPort::cycle_start (pframes_t nframes) { /* caller must hold process lock */ - - Port::cycle_start (nframes); + Port::cycle_start (nframes); if (sends_output()) { _buffer->prepare (); + } else if (!externally_connected ()) { + /* ardour internal port, just silence input, don't resample */ + // TODO reset resampler only once + _src.reset (); + memset (_data, 0, _cycle_nframes * sizeof (float)); + } else { + _src.inp_data = (float*)port_engine.get_buffer (_port_handle, nframes); + _src.inp_count = nframes; + _src.out_count = _cycle_nframes; + _src.set_rratio (_cycle_nframes / (double)nframes); + _src.out_data = _data; + _src.process (); + while (_src.out_count > 0) { + *_src.out_data = _src.out_data[-1]; + ++_src.out_data; + --_src.out_count; + } } } @@ -66,6 +88,28 @@ AudioPort::cycle_end (pframes_t nframes) _buffer->silence (nframes); } } + + if (sends_output() && _port_handle) { + + if (!externally_connected ()) { + /* ardour internal port, data goes nowhere, skip resampling */ + // TODO reset resampler only once + _src.reset (); + return; + } + + _src.inp_count = _cycle_nframes; + _src.out_count = nframes; + _src.set_rratio (nframes / (double)_cycle_nframes); + _src.inp_data = _data; + _src.out_data = (float*)port_engine.get_buffer (_port_handle, nframes); + _src.process (); + while (_src.out_count > 0) { + *_src.out_data = _src.out_data[-1]; + ++_src.out_data; + --_src.out_count; + } + } } void @@ -77,8 +121,19 @@ AudioBuffer& AudioPort::get_audio_buffer (pframes_t nframes) { /* caller must hold process lock */ - _buffer->set_data ((Sample *) port_engine.get_buffer (_port_handle, _cycle_nframes) + - _global_port_buffer_offset + _port_buffer_offset, nframes); + assert (_port_handle); + + Sample* addr; + + if (!externally_connected ()) { + addr = (Sample *) port_engine.get_buffer (_port_handle, nframes); + } else { + /* _data was read and resampled as necessary in ::cycle_start */ + addr = &_data[_global_port_buffer_offset]; + } + + _buffer->set_data (addr, nframes); + return *_buffer; } @@ -86,9 +141,6 @@ Sample* AudioPort::engine_get_whole_audio_buffer () { /* caller must hold process lock */ - return (Sample *) port_engine.get_buffer (_port_handle, _cycle_nframes); + assert (_port_handle); + return (Sample *) port_engine.get_buffer (_port_handle, ENGINE->samples_per_cycle()); } - - - -