don't attempt MIDI playback if there are no MIDI buffers provided for processing
[ardour.git] / libs / ardour / disk_io.cc
index 587ba19ed05a79c1cfaba85ba02ec9ff9aa85b27..58e8790942510fb1310e4f56e5351bebdff5cdd1 100644 (file)
@@ -54,7 +54,6 @@ DiskIOProcessor::DiskIOProcessor (Session& s, string const & str, Flag f)
        , _slaved (false)
        , loop_location (0)
        , in_set_state (false)
-        , file_frame (0)
         , playback_sample (0)
         , wrap_buffer_size (0)
         , speed_buffer_size (0)
@@ -65,6 +64,7 @@ DiskIOProcessor::DiskIOProcessor (Session& s, string const & str, Flag f)
        , _frames_read_from_ringbuffer (0)
 {
        midi_interpolation.add_channel_to (0,0);
+       set_display_to_user (false);
 }
 
 void
@@ -136,10 +136,8 @@ DiskIOProcessor::can_support_io_configuration (const ChanCount& in, ChanCount& o
                return false;
        }
 
-       if (in != out) {
-               /* currently no way to deliver different channels that we receive */
-               return false;
-       }
+       /* currently no way to deliver different channels that we receive */
+       out = in;
 
        return true;
 }
@@ -149,24 +147,35 @@ DiskIOProcessor::configure_io (ChanCount in, ChanCount out)
 {
        DEBUG_TRACE (DEBUG::DiskIO, string_compose ("Configuring %1 for in:%2 out:%3\n", name(), in, out));
 
-       RCUWriter<ChannelList> writer (channels);
-       boost::shared_ptr<ChannelList> c = writer.get_copy();
+       bool changed = false;
 
-       uint32_t n_audio = in.n_audio();
+       {
+               RCUWriter<ChannelList> writer (channels);
+               boost::shared_ptr<ChannelList> c = writer.get_copy();
 
-       if (n_audio > c->size()) {
-               add_channel_to (c, n_audio - c->size());
-       } else if (n_audio < c->size()) {
-               remove_channel_from (c, c->size() - n_audio);
+               uint32_t n_audio = in.n_audio();
+
+               if (n_audio > c->size()) {
+                       add_channel_to (c, n_audio - c->size());
+                       changed = true;
+               } else if (n_audio < c->size()) {
+                       remove_channel_from (c, c->size() - n_audio);
+                       changed = true;
+               }
+
+               /* writer leaves scope, actual channel list is updated */
        }
 
        if (in.n_midi() > 0 && !_midi_buf) {
                const size_t size = _session.butler()->midi_diskstream_buffer_size();
                _midi_buf = new MidiRingBuffer<framepos_t>(size);
                midi_interpolation.add_channel_to (0,0);
+               changed = true;
        }
 
-       seek (_session.transport_frame());
+       if (changed) {
+               seek (_session.transport_frame());
+       }
 
        return Processor::configure_io (in, out);
 }
@@ -332,6 +341,7 @@ DiskIOProcessor::use_playlist (DataType dt, boost::shared_ptr<Playlist> playlist
         DEBUG_TRACE (DEBUG::DiskIO, string_compose ("%1: set to use playlist %2 (%3)\n", name(), playlist->name(), dt.to_string()));
 
         if (playlist == _playlists[dt]) {
+               DEBUG_TRACE (DEBUG::DiskIO, string_compose ("%1: already using that playlist\n", name()));
                return 0;
         }
 
@@ -349,7 +359,7 @@ DiskIOProcessor::use_playlist (DataType dt, boost::shared_ptr<Playlist> playlist
         playlist->DropReferences.connect_same_thread (playlist_connections, boost::bind (&DiskIOProcessor::playlist_deleted, this, boost::weak_ptr<Playlist>(playlist)));
         playlist->RangesMoved.connect_same_thread (playlist_connections, boost::bind (&DiskIOProcessor::playlist_ranges_moved, this, _1, _2));
 
-       DEBUG_TRACE (DEBUG::DiskIO, string_compose ("%1 now use playlist %1 (%2)\n", name(), playlist->name(), playlist->id()));
+       DEBUG_TRACE (DEBUG::DiskIO, string_compose ("%1 now using playlist %1 (%2)\n", name(), playlist->name(), playlist->id()));
 
        PlaylistChanged (dt); /* EMIT SIGNAL */
        _session.set_dirty ();
@@ -388,10 +398,20 @@ DiskIOProcessor::ChannelInfo::~ChannelInfo ()
        capture_transition_buf = 0;
 }
 
+void
+DiskIOProcessor::drop_route ()
+{
+       _route.reset ();
+}
+
 void
 DiskIOProcessor::set_route (boost::shared_ptr<Route> r)
 {
        _route = r;
+
+       if (_route) {
+               _route->DropReferences.connect_same_thread (*this, boost::bind (&DiskIOProcessor::drop_route, this));
+       }
 }
 
 /** Get the start, end, and length of a location "atomically".
@@ -413,3 +433,4 @@ DiskIOProcessor::get_location_times(const Location* location,
                *length = *end - *start;
        }
 }
+