Collect plugin runtime profile statistics.
[ardour.git] / libs / ardour / audio_track.cc
index 56d82c3a19c7c88e4f9b6b10b97c3eee126f7c26..46aff98122db5735884493edde4a04867d6ef885 100644 (file)
@@ -26,7 +26,6 @@
 
 #include "ardour/amp.h"
 #include "ardour/audio_buffer.h"
-#include "ardour/audio_diskstream.h"
 #include "ardour/audio_track.h"
 #include "ardour/audioplaylist.h"
 #include "ardour/boost_debug.h"
@@ -65,47 +64,72 @@ AudioTrack::~AudioTrack ()
        }
 }
 
-#ifdef XXX_OLD_DESTRUCTIVE_API_XXX
-int
-AudioTrack::set_mode (TrackMode m)
+MonitorState
+AudioTrack::get_auto_monitoring_state () const
 {
-       if (m != _mode) {
+       /* This is an implementation of the truth table in doc/monitor_modes.pdf;
+          I don't think it's ever going to be too pretty too look at.
+       */
 
-               if (!Profile->get_trx() && _diskstream->set_destructive (m == Destructive)) {
-                       return -1;
-               }
+       bool const roll = _session.transport_rolling ();
+       bool const track_rec = _disk_writer->record_enabled ();
+       bool const auto_input = _session.config.get_auto_input ();
+       bool const software_monitor = Config->get_monitoring_model() == SoftwareMonitoring;
+       bool const tape_machine_mode = Config->get_tape_machine_mode ();
+       bool session_rec;
+
+       /* I suspect that just use actively_recording() is good enough all the
+        * time, but just to keep the semantics the same as they were before
+        * sept 26th 2012, we differentiate between the cases where punch is
+        * enabled and those where it is not.
+        *
+        * rg: sept 30 2017: Above is not the case: punch-in/out location is
+        * global session playhead position.
+        * When this method is called from process_output_buffers() we need
+        * to use delay-compensated route's process-position.
+        *
+        * NB. Disk reader/writer may also be offset by a same amount of time.
+        *
+        * Also keep in mind that _session.transport_rolling() is false during
+        * pre-roll but the disk already produces output.
+        *
+        * TODO: FIXME
+        */
+
+       if (_session.config.get_punch_in() || _session.config.get_punch_out()) {
+               session_rec = _session.actively_recording ();
+       } else {
+               session_rec = _session.get_record_enabled();
+       }
 
-               _diskstream->set_non_layered (m == NonLayered);
-               _mode = m;
+       if (track_rec) {
 
-               TrackModeChanged (); /* EMIT SIGNAL */
-       }
+               if (!session_rec && roll && auto_input) {
+                       return MonitoringDisk;
+               } else {
+                       return software_monitor ? MonitoringInput : MonitoringSilence;
+               }
 
-       return 0;
-}
+       } else {
 
-bool
-AudioTrack::can_use_mode (TrackMode m, bool& bounce_required)
-{
-       switch (m) {
-       case NonLayered:
-       case Normal:
-               bounce_required = false;
-               return true;
+               if (tape_machine_mode) {
+
+                       return MonitoringDisk;
 
-       case Destructive:
-               if (Profile->get_trx()) {
-                       return false;
                } else {
-                       return _diskstream->can_become_destructive (bounce_required);
-               }
-               break;
 
-       default:
-               return false;
+                       if (!roll && auto_input) { 
+                               return software_monitor ? MonitoringInput : MonitoringSilence;
+                       } else {
+                               return MonitoringDisk;
+                       }
+
+               }
        }
+
+       abort(); /* NOTREACHED */
+       return MonitoringSilence;
 }
-#endif
 
 int
 AudioTrack::set_state (const XMLNode& node, int version)
@@ -138,9 +162,9 @@ AudioTrack::set_state (const XMLNode& node, int version)
 }
 
 XMLNode&
-AudioTrack::state (bool full_state)
+AudioTrack::state (bool save_template)
 {
-       XMLNode& root (Track::state(full_state));
+       XMLNode& root (Track::state (save_template));
        XMLNode* freeze_node;
 
        if (_freeze_record.playlist) {
@@ -223,50 +247,8 @@ AudioTrack::set_state_part_two ()
        }
 }
 
-/** @param need_butler to be set to true if this track now needs the butler, otherwise it can be left alone
- *  or set to false.
- */
-int
-AudioTrack::roll (pframes_t nframes, framepos_t start_frame, framepos_t end_frame, int declick, bool& need_butler)
-{
-       Glib::Threads::RWLock::ReaderLock lm (_processor_lock, Glib::Threads::TRY_LOCK);
-
-       if (!lm.locked()) {
-               return 0;
-       }
-
-       if (n_outputs().n_total() == 0 && _processors.empty()) {
-               return 0;
-       }
-
-       if (!_active) {
-               silence (nframes);
-               if (_meter_point == MeterInput && ((_monitoring_control->monitoring_choice() & MonitorInput) || _disk_writer->record_enabled())) {
-                       _meter->reset();
-               }
-               return 0;
-       }
-
-       _silent = false;
-       _amp->apply_gain_automation(false);
-
-       BufferSet& bufs = _session.get_route_buffers (n_process_buffers ());
-
-       fill_buffers_with_input (bufs, _input, nframes);
-
-       if (_meter_point == MeterInput && ((_monitoring_control->monitoring_choice() & MonitorInput) || _disk_writer->record_enabled())) {
-               _meter->run (bufs, start_frame, end_frame, 1.0 /*speed()*/, nframes, true);
-       }
-
-       process_output_buffers (bufs, start_frame, end_frame, nframes, declick, (!_disk_writer->record_enabled() && _session.transport_rolling()));
-
-       flush_processor_buffers_locked (nframes);
-
-       return 0;
-}
-
 int
-AudioTrack::export_stuff (BufferSet& buffers, framepos_t start, framecnt_t nframes,
+AudioTrack::export_stuff (BufferSet& buffers, samplepos_t start, samplecnt_t nframes,
                          boost::shared_ptr<Processor> endpoint, bool include_endpoint, bool for_export, bool for_freeze)
 {
        boost::scoped_array<gain_t> gain_buffer (new gain_t[nframes]);
@@ -278,7 +260,7 @@ AudioTrack::export_stuff (BufferSet& buffers, framepos_t start, framecnt_t nfram
 
        assert(apl);
        assert(buffers.count().n_audio() >= 1);
-       assert ((framecnt_t) buffers.get_audio(0).capacity() >= nframes);
+       assert ((samplecnt_t) buffers.get_audio(0).capacity() >= nframes);
 
        if (apl->read (buffers.get_audio(0).data(), mix_buffer.get(), gain_buffer.get(), start, nframes) != nframes) {
                return -1;
@@ -365,11 +347,11 @@ AudioTrack::bounceable (boost::shared_ptr<Processor> endpoint, bool include_endp
 boost::shared_ptr<Region>
 AudioTrack::bounce (InterThreadInfo& itt)
 {
-       return bounce_range (_session.current_start_frame(), _session.current_end_frame(), itt, main_outs(), false);
+       return bounce_range (_session.current_start_sample(), _session.current_end_sample(), itt, main_outs(), false);
 }
 
 boost::shared_ptr<Region>
-AudioTrack::bounce_range (framepos_t start, framepos_t end, InterThreadInfo& itt,
+AudioTrack::bounce_range (samplepos_t start, samplepos_t end, InterThreadInfo& itt,
                          boost::shared_ptr<Processor> endpoint, bool include_endpoint)
 {
        vector<boost::shared_ptr<Source> > srcs;
@@ -415,7 +397,7 @@ AudioTrack::freeze_me (InterThreadInfo& itt)
 
        boost::shared_ptr<Region> res;
 
-       if ((res = _session.write_one_track (*this, _session.current_start_frame(), _session.current_end_frame(),
+       if ((res = _session.write_one_track (*this, _session.current_start_sample(), _session.current_end_sample(),
                                        true, srcs, itt, main_outs(), false, false, true)) == 0) {
                return;
        }
@@ -466,7 +448,7 @@ AudioTrack::freeze_me (InterThreadInfo& itt)
        boost::shared_ptr<Region> region (RegionFactory::create (srcs, plist, false));
 
        new_playlist->set_orig_track_id (id());
-       new_playlist->add_region (region, _session.current_start_frame());
+       new_playlist->add_region (region, _session.current_start_sample());
        new_playlist->set_frozen (true);
        region->set_locked (true);