From 665f3bea5a7b145636b6d85bb3623013e38f1819 Mon Sep 17 00:00:00 2001 From: Paul Davis Date: Mon, 7 Mar 2011 19:06:42 +0000 Subject: [PATCH] fix all manner of wrongness with port buffer offsets git-svn-id: svn://localhost/ardour2/branches/3.0@9098 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/ardour/ardour/audio_buffer.h | 6 ++- libs/ardour/ardour/audio_port.h | 18 ++------- libs/ardour/ardour/buffer_set.h | 2 +- libs/ardour/ardour/midi_port.h | 8 ++-- libs/ardour/ardour/port.h | 19 +++++++-- libs/ardour/audio_port.cc | 40 +++---------------- libs/ardour/buffer_set.cc | 4 +- libs/ardour/delivery.cc | 11 ++--- libs/ardour/graph.cc | 1 + libs/ardour/io.cc | 2 +- libs/ardour/midi_port.cc | 16 ++++---- libs/ardour/port.cc | 1 + libs/ardour/route.cc | 11 +++-- libs/ardour/session.cc | 27 ------------- libs/ardour/session_process.cc | 3 +- libs/ardour/session_transport.cc | 2 +- .../generic_midi_control_protocol.cc | 2 - 17 files changed, 61 insertions(+), 112 deletions(-) diff --git a/libs/ardour/ardour/audio_buffer.h b/libs/ardour/ardour/audio_buffer.h index 403a70232f..63eb7d7c20 100644 --- a/libs/ardour/ardour/audio_buffer.h +++ b/libs/ardour/ardour/audio_buffer.h @@ -49,6 +49,9 @@ public: assert(src.type() == DataType::AUDIO); assert(len <= _capacity); memcpy(_data + dst_offset, ((AudioBuffer&)src).data() + src_offset, sizeof(Sample) * len); + if (next_write_addr >= _data + _capacity) { + next_write_addr = _data; + } if (dst_offset == 0 && src_offset == 0 && len == _capacity) { _silent = src.silent(); } else { @@ -169,11 +172,12 @@ public: void prepare () { _written = false; } bool written() const { return _written; } + void set_marked_for_write (bool yn) { mfw = yn; } + private: bool _owns_data; bool _written; Sample* _data; ///< Actual buffer contents - }; diff --git a/libs/ardour/ardour/audio_port.h b/libs/ardour/ardour/audio_port.h index 748ef8263b..ffd1f8d9b0 100644 --- a/libs/ardour/ardour/audio_port.h +++ b/libs/ardour/ardour/audio_port.h @@ -41,22 +41,12 @@ class AudioPort : public Port size_t raw_buffer_size (pframes_t nframes) const; - Buffer& get_buffer (framecnt_t nframes, framecnt_t offset = 0) { - return get_audio_buffer (nframes, offset); + Buffer& get_buffer (framecnt_t nframes) { + return get_audio_buffer (nframes); } - AudioBuffer& get_audio_buffer (framecnt_t nframes, framecnt_t offset = 0); + AudioBuffer& get_audio_buffer (framecnt_t nframes); - static framecnt_t port_offset() { return _port_offset; } - - static void set_port_offset (framecnt_t off) { - _port_offset = off; - } - - static void increment_port_offset (framecnt_t n) { - _port_offset += n; - } - protected: friend class AudioEngine; @@ -64,8 +54,6 @@ class AudioPort : public Port private: AudioBuffer* _buffer; - - static framecnt_t _port_offset; }; } // namespace ARDOUR diff --git a/libs/ardour/ardour/buffer_set.h b/libs/ardour/ardour/buffer_set.h index f5ac1aee61..9ba44e9481 100644 --- a/libs/ardour/ardour/buffer_set.h +++ b/libs/ardour/ardour/buffer_set.h @@ -67,7 +67,7 @@ public: void clear(); void attach_buffers (PortSet& ports); - void get_jack_port_addresses (PortSet &, framecnt_t, framecnt_t); + void get_jack_port_addresses (PortSet &, framecnt_t); /* the capacity here is a size_t and has a different interpretation depending on the DataType of the buffers. for audio, its a frame count. for MIDI diff --git a/libs/ardour/ardour/midi_port.h b/libs/ardour/ardour/midi_port.h index 7a019e5a20..b7c80e0c01 100644 --- a/libs/ardour/ardour/midi_port.h +++ b/libs/ardour/ardour/midi_port.h @@ -41,16 +41,16 @@ class MidiPort : public Port { void cycle_end (pframes_t nframes); void cycle_split (); - void flush_buffers (pframes_t nframes, framepos_t time, framecnt_t offset = 0); + void flush_buffers (pframes_t nframes, framepos_t time); void transport_stopped (); size_t raw_buffer_size (pframes_t nframes) const; - Buffer& get_buffer (framecnt_t nframes, framecnt_t offset = 0) { - return get_midi_buffer (nframes, offset); + Buffer& get_buffer (framecnt_t nframes) { + return get_midi_buffer (nframes); } - MidiBuffer& get_midi_buffer (framecnt_t nframes, framecnt_t offset = 0); + MidiBuffer& get_midi_buffer (framecnt_t nframes); protected: friend class AudioEngine; diff --git a/libs/ardour/ardour/port.h b/libs/ardour/ardour/port.h index 3a45d010c7..300ecc24af 100644 --- a/libs/ardour/ardour/port.h +++ b/libs/ardour/ardour/port.h @@ -113,10 +113,8 @@ public: virtual void cycle_start (pframes_t) = 0; virtual void cycle_end (pframes_t) = 0; virtual void cycle_split () = 0; - virtual Buffer& get_buffer (framecnt_t nframes, framecnt_t offset = 0) = 0; - virtual void flush_buffers (pframes_t nframes, framepos_t /*time*/, framecnt_t offset = 0) { - assert (offset < nframes); - } + virtual Buffer& get_buffer (framecnt_t nframes) = 0; + virtual void flush_buffers (pframes_t nframes, framepos_t /*time*/) {} virtual void transport_stopped () {} bool physically_connected () const; @@ -125,6 +123,17 @@ public: PBD::Signal1 MonitorInputChanged; + + static framecnt_t port_offset() { return _port_offset; } + + static void set_port_offset (framecnt_t off) { + _port_offset = off; + } + + static void increment_port_offset (framecnt_t n) { + _port_offset += n; + } + protected: Port (std::string const &, DataType, Flags); @@ -133,6 +142,7 @@ protected: static pframes_t _buffer_size; static bool _connecting_blocked; + static framecnt_t _port_offset; static AudioEngine* _engine; ///< the AudioEngine @@ -150,6 +160,7 @@ private: /** ports that we are connected to, kept so that we can reconnect to JACK when required */ std::set _connections; + }; } diff --git a/libs/ardour/audio_port.cc b/libs/ardour/audio_port.cc index aad56748c3..f8a1018e29 100644 --- a/libs/ardour/audio_port.cc +++ b/libs/ardour/audio_port.cc @@ -17,6 +17,9 @@ */ #include + +#include "pbd/stacktrace.h" + #include "ardour/audio_port.h" #include "ardour/audioengine.h" #include "ardour/data_type.h" @@ -25,8 +28,6 @@ using namespace ARDOUR; using namespace std; -framecnt_t AudioPort::_port_offset = 0; - AudioPort::AudioPort (const std::string& name, Flags flags) : Port (name, DataType::AUDIO, flags) , _buffer (new AudioBuffer (0)) @@ -44,22 +45,7 @@ AudioPort::cycle_start (pframes_t nframes) { /* caller must hold process lock */ - /* get_buffer() must only be run on outputs here in cycle_start(). - - Inputs must be done in the correct processing order, which - requires interleaving with route processing. that will - happen when Port::get_buffer() is called. - */ - if (sends_output()) { - - /* Notice that cycle_start() is always run with the *entire* process cycle frame count, - so we do not bother to apply _port_offset here - we always want the address of the - entire JACK port buffer. We are not collecting data here - just noting the - address where we will write data later in the process cycle. - */ - - _buffer->set_data ((Sample *) jack_port_get_buffer (_jack_port, nframes), nframes); _buffer->prepare (); } } @@ -67,7 +53,7 @@ AudioPort::cycle_start (pframes_t nframes) void AudioPort::cycle_end (pframes_t nframes) { - if (sends_output() && !_buffer->written()) { + if (sends_output() && !_buffer->written()) { _buffer->silence (nframes); } } @@ -78,24 +64,10 @@ AudioPort::cycle_split () } AudioBuffer& -AudioPort::get_audio_buffer (framecnt_t nframes, framecnt_t offset) +AudioPort::get_audio_buffer (framecnt_t nframes) { /* caller must hold process lock */ - - if (receives_input ()) { - - /* Get a pointer to the audio data @ offset + _port_offset within the JACK port buffer and store - it in our _buffer member. - - Note that offset is expected to be zero in almost all cases. - */ - - _buffer->set_data ((Sample *) jack_port_get_buffer (_jack_port, nframes) + offset + _port_offset, nframes); - } - - /* output ports set their _buffer data information during ::cycle_start() - */ - + _buffer->set_data ((Sample *) jack_port_get_buffer (_jack_port, nframes) + _port_offset, nframes); return *_buffer; } diff --git a/libs/ardour/buffer_set.cc b/libs/ardour/buffer_set.cc index 736c6a386d..b0a89f640d 100644 --- a/libs/ardour/buffer_set.cc +++ b/libs/ardour/buffer_set.cc @@ -113,7 +113,7 @@ BufferSet::attach_buffers (PortSet& ports) * Does not allocate, so RT-safe. */ void -BufferSet::get_jack_port_addresses (PortSet& ports, framecnt_t nframes, framecnt_t offset) +BufferSet::get_jack_port_addresses (PortSet& ports, framecnt_t nframes) { assert (_count == ports.count ()); assert (_available == ports.count ()); @@ -128,7 +128,7 @@ BufferSet::get_jack_port_addresses (PortSet& ports, framecnt_t nframes, framecnt int i = 0; for (PortSet::iterator p = ports.begin(*t); p != ports.end(*t); ++p) { - v[i] = &p->get_buffer (nframes, offset); + v[i] = &p->get_buffer (nframes); ++i; } } diff --git a/libs/ardour/delivery.cc b/libs/ardour/delivery.cc index bc2d7b8081..157d8a285d 100644 --- a/libs/ardour/delivery.cc +++ b/libs/ardour/delivery.cc @@ -27,6 +27,7 @@ #include "ardour/debug.h" #include "ardour/delivery.h" #include "ardour/audio_buffer.h" +#include "ardour/audio_port.h" #include "ardour/amp.h" #include "ardour/buffer_set.h" #include "ardour/configuration.h" @@ -253,7 +254,7 @@ Delivery::run (BufferSet& bufs, framepos_t start_frame, framepos_t end_frame, pf processing pathway that wants to use this->output_buffers() for some reason. */ - output_buffers().get_jack_port_addresses (ports, nframes, _output_offset); + output_buffers().get_jack_port_addresses (ports, nframes); // this Delivery processor is not a derived type, and thus we assume // we really can modify the buffers passed in (it is almost certainly @@ -289,7 +290,7 @@ Delivery::run (BufferSet& bufs, framepos_t start_frame, framepos_t end_frame, pf panner = _panshell->panner(); if (panner && !panner->bypassed()) { - + // Use the panner to distribute audio to output port buffers _panshell->run (bufs, output_buffers(), start_frame, end_frame, nframes); @@ -300,11 +301,11 @@ Delivery::run (BufferSet& bufs, framepos_t start_frame, framepos_t end_frame, pf // Do a 1:1 copy of data to output ports if (bufs.count().n_audio() > 0 && ports.count().n_audio () > 0) { - _output->copy_to_outputs (bufs, DataType::AUDIO, nframes, _output_offset); + _output->copy_to_outputs (bufs, DataType::AUDIO, nframes, 0); } if (bufs.count().n_midi() > 0 && ports.count().n_midi () > 0) { - _output->copy_to_outputs (bufs, DataType::MIDI, nframes, _output_offset); + _output->copy_to_outputs (bufs, DataType::MIDI, nframes, 0); } } @@ -451,7 +452,7 @@ Delivery::flush_buffers (framecnt_t nframes, framepos_t time) PortSet& ports (_output->ports()); for (PortSet::iterator i = ports.begin(); i != ports.end(); ++i) { - (*i).flush_buffers (nframes, time, _output_offset); + (*i).flush_buffers (nframes, time); } } diff --git a/libs/ardour/graph.cc b/libs/ardour/graph.cc index 5c0d41ed17..f52180f98e 100644 --- a/libs/ardour/graph.cc +++ b/libs/ardour/graph.cc @@ -41,6 +41,7 @@ using namespace std; #ifdef DEBUG_RT_ALLOC static Graph* graph = 0; + extern "C" { int alloc_allowed () diff --git a/libs/ardour/io.cc b/libs/ardour/io.cc index 21afdbae56..d6416bca9a 100644 --- a/libs/ardour/io.cc +++ b/libs/ardour/io.cc @@ -1525,7 +1525,7 @@ IO::process_input (boost::shared_ptr proc, framepos_t start_frame, fr { /* don't read the data into new buffers - just use the port buffers directly */ - _buffers.get_jack_port_addresses (_ports, nframes, 0); + _buffers.get_jack_port_addresses (_ports, nframes); proc->run (_buffers, start_frame, end_frame, nframes, true); } diff --git a/libs/ardour/midi_port.cc b/libs/ardour/midi_port.cc index 5f18810122..75fd269cde 100644 --- a/libs/ardour/midi_port.cc +++ b/libs/ardour/midi_port.cc @@ -50,7 +50,7 @@ MidiPort::cycle_start (pframes_t nframes) } MidiBuffer & -MidiPort::get_midi_buffer (framecnt_t nframes, framecnt_t offset) +MidiPort::get_midi_buffer (framecnt_t nframes) { if (_has_been_mixed_down) { return *_buffer; @@ -78,10 +78,10 @@ MidiPort::get_midi_buffer (framecnt_t nframes, framecnt_t offset) continue; } - if (ev.time >= offset && ev.time < (offset + nframes)) { + if (ev.time >= _port_offset && ev.time < (_port_offset + nframes)) { _buffer->push_back (ev); } else { - cerr << "Dropping incoming MIDI at time " << ev.time << "; offset=" << offset << " limit=" << (offset + nframes) << "\n"; + cerr << "Dropping incoming MIDI at time " << ev.time << "; offset=" << _port_offset << " limit=" << (_port_offset + nframes) << "\n"; } } @@ -114,7 +114,7 @@ MidiPort::cycle_split () } void -MidiPort::flush_buffers (pframes_t nframes, framepos_t time, framecnt_t offset) +MidiPort::flush_buffers (pframes_t nframes, framepos_t time) { if (sends_output ()) { @@ -137,14 +137,14 @@ MidiPort::flush_buffers (pframes_t nframes, framepos_t time, framecnt_t offset) // event times are in frames, relative to cycle start - assert (ev.time() < (nframes + offset)); + assert (ev.time() < (nframes + _port_offset)); - if (ev.time() >= offset) { + if (ev.time() >= _port_offset) { if (jack_midi_event_write (jack_buffer, (jack_nframes_t) ev.time(), ev.buffer(), ev.size()) != 0) { - cerr << "write failed, drop flushed note off on the floor, time " << ev.time() << " > " << offset << endl; + cerr << "write failed, drop flushed note off on the floor, time " << ev.time() << " > " << _port_offset << endl; } } else { - cerr << "drop flushed event on the floor, time " << ev.time() << " < " << offset << endl; + cerr << "drop flushed event on the floor, time " << ev.time() << " < " << _port_offset << endl; } } } diff --git a/libs/ardour/port.cc b/libs/ardour/port.cc index 66a3b68b91..c965f0a6f4 100644 --- a/libs/ardour/port.cc +++ b/libs/ardour/port.cc @@ -42,6 +42,7 @@ using namespace PBD; AudioEngine* Port::_engine = 0; pframes_t Port::_buffer_size = 0; bool Port::_connecting_blocked = false; +framecnt_t Port::_port_offset = 0; /** @param n Port short name */ Port::Port (std::string const & n, DataType t, Flags f) diff --git a/libs/ardour/route.cc b/libs/ardour/route.cc index 1a638bb1b1..994844a17f 100644 --- a/libs/ardour/route.cc +++ b/libs/ardour/route.cc @@ -418,10 +418,8 @@ Route::process_output_buffers (BufferSet& bufs, GLOBAL DECLICK (for transport changes etc.) ----------------------------------------------------------------------------------------- */ - if (declick > 0) { - Amp::declick (bufs, nframes, 1); - } else if (declick < 0) { - Amp::declick (bufs, nframes, -1); + if (declick != 0) { + Amp::declick (bufs, nframes, declick); } _pending_declick = 0; @@ -503,7 +501,7 @@ Route::process_output_buffers (BufferSet& bufs, do we catch route != active somewhere higher? */ - (*i)->run (bufs, start_frame, end_frame, nframes, *i != _processors.back()); + (*i)->run (bufs, start_frame, end_frame, nframes, *i != _processors.back()); bufs.set_count ((*i)->output_streams()); } } @@ -2695,7 +2693,7 @@ Route::nonrealtime_handle_transport_stopped (bool /*abort_ignored*/, bool did_lo if (Config->get_plugins_stop_with_transport() && can_flush_processors) { (*i)->flush (); } - + (*i)->transport_stopped (now); } } @@ -2819,6 +2817,7 @@ Route::check_initial_delay (framecnt_t nframes, framecnt_t& transport_frame) output ports, so make a note of that for future reference. */ + _main_outs->increment_output_offset (_roll_delay); transport_frame += _roll_delay; diff --git a/libs/ardour/session.cc b/libs/ardour/session.cc index 89290f5aa6..a83034d784 100644 --- a/libs/ardour/session.cc +++ b/libs/ardour/session.cc @@ -3745,45 +3745,18 @@ BufferSet& Session::get_silent_buffers (ChanCount count) { return ProcessThread::get_silent_buffers (count); -#if 0 - assert(_silent_buffers->available() >= count); - _silent_buffers->set_count(count); - - for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) { - for (size_t i= 0; i < count.get(*t); ++i) { - _silent_buffers->get(*t, i).clear(); - } - } - - return *_silent_buffers; -#endif } BufferSet& Session::get_scratch_buffers (ChanCount count) { return ProcessThread::get_scratch_buffers (count); -#if 0 - if (count != ChanCount::ZERO) { - assert(_scratch_buffers->available() >= count); - _scratch_buffers->set_count(count); - } else { - _scratch_buffers->set_count (_scratch_buffers->available()); - } - - return *_scratch_buffers; -#endif } BufferSet& Session::get_mix_buffers (ChanCount count) { return ProcessThread::get_mix_buffers (count); -#if 0 - assert(_mix_buffers->available() >= count); - _mix_buffers->set_count(count); - return *_mix_buffers; -#endif } uint32_t diff --git a/libs/ardour/session_process.cc b/libs/ardour/session_process.cc index c189afd9e7..5181cfb46a 100644 --- a/libs/ardour/session_process.cc +++ b/libs/ardour/session_process.cc @@ -51,6 +51,7 @@ using namespace std; /** Called by the audio engine when there is work to be done with JACK. * @param nframes Number of frames to process. */ + void Session::process (pframes_t nframes) { @@ -397,7 +398,7 @@ Session::process_with_events (pframes_t nframes) fail_roll (nframes); return; } - + get_track_statistics (); nframes -= this_nframes; diff --git a/libs/ardour/session_transport.cc b/libs/ardour/session_transport.cc index ed0bf647bc..8ce16dff5b 100644 --- a/libs/ardour/session_transport.cc +++ b/libs/ardour/session_transport.cc @@ -819,7 +819,7 @@ Session::locate (framepos_t target_frame, bool with_roll, bool with_flush, bool return; } - if (_transport_speed && (!with_loop || loop_changing)) { + if (_transport_speed) { /* schedule a declick. we'll be called again when its done */ if (!(transport_sub_state & PendingDeclickOut)) { diff --git a/libs/surfaces/generic_midi/generic_midi_control_protocol.cc b/libs/surfaces/generic_midi/generic_midi_control_protocol.cc index 1275eb2222..36a4548a2a 100644 --- a/libs/surfaces/generic_midi/generic_midi_control_protocol.cc +++ b/libs/surfaces/generic_midi/generic_midi_control_protocol.cc @@ -133,8 +133,6 @@ GenericMidiControlProtocol::reload_maps () return; } - cerr << "Found " << midi_maps->size() << " MIDI maps along " << spath.to_string() << endl; - for (vector::iterator i = midi_maps->begin(); i != midi_maps->end(); ++i) { string fullpath = *(*i);