2 Copyright (C) 1999-2010 Paul Davis
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
27 #include <cstdio> /* sprintf(3) ... grrr */
33 #include <glibmm/thread.h>
34 #include <glibmm/miscutils.h>
35 #include <glibmm/fileutils.h>
37 #include <boost/algorithm/string/erase.hpp>
39 #include "pbd/error.h"
40 #include "pbd/boost_debug.h"
41 #include "pbd/pathscanner.h"
42 #include "pbd/stl_delete.h"
43 #include "pbd/basename.h"
44 #include "pbd/stacktrace.h"
45 #include "pbd/file_utils.h"
46 #include "pbd/convert.h"
47 #include "pbd/strsplit.h"
49 #include "ardour/amp.h"
50 #include "ardour/analyser.h"
51 #include "ardour/audio_buffer.h"
52 #include "ardour/audio_diskstream.h"
53 #include "ardour/audio_port.h"
54 #include "ardour/audio_track.h"
55 #include "ardour/audioengine.h"
56 #include "ardour/audiofilesource.h"
57 #include "ardour/audioplaylist.h"
58 #include "ardour/audioregion.h"
59 #include "ardour/auditioner.h"
60 #include "ardour/buffer_manager.h"
61 #include "ardour/buffer_set.h"
62 #include "ardour/bundle.h"
63 #include "ardour/butler.h"
64 #include "ardour/click.h"
65 #include "ardour/configuration.h"
66 #include "ardour/crossfade.h"
67 #include "ardour/cycle_timer.h"
68 #include "ardour/data_type.h"
69 #include "ardour/debug.h"
70 #include "ardour/filename_extensions.h"
71 #include "ardour/internal_send.h"
72 #include "ardour/io_processor.h"
73 #include "ardour/midi_diskstream.h"
74 #include "ardour/midi_playlist.h"
75 #include "ardour/midi_region.h"
76 #include "ardour/midi_track.h"
77 #include "ardour/midi_ui.h"
78 #include "ardour/named_selection.h"
79 #include "ardour/process_thread.h"
80 #include "ardour/playlist.h"
81 #include "ardour/plugin_insert.h"
82 #include "ardour/port_insert.h"
83 #include "ardour/processor.h"
84 #include "ardour/rc_configuration.h"
85 #include "ardour/recent_sessions.h"
86 #include "ardour/region_factory.h"
87 #include "ardour/return.h"
88 #include "ardour/route_group.h"
89 #include "ardour/send.h"
90 #include "ardour/session.h"
91 #include "ardour/session_directory.h"
92 #include "ardour/session_directory.h"
93 #include "ardour/session_metadata.h"
94 #include "ardour/session_playlists.h"
95 #include "ardour/slave.h"
96 #include "ardour/smf_source.h"
97 #include "ardour/source_factory.h"
98 #include "ardour/tape_file_matcher.h"
99 #include "ardour/tempo.h"
100 #include "ardour/utils.h"
101 #include "ardour/graph.h"
102 #include "ardour/speakers.h"
103 #include "ardour/operations.h"
105 #include "midi++/port.h"
106 #include "midi++/mmc.h"
107 #include "midi++/manager.h"
112 using namespace ARDOUR;
115 bool Session::_disable_all_loaded_plugins = false;
117 PBD::Signal1<void,std::string> Session::Dialog;
118 PBD::Signal0<int> Session::AskAboutPendingState;
119 PBD::Signal2<int, framecnt_t, framecnt_t> Session::AskAboutSampleRateMismatch;
120 PBD::Signal0<void> Session::SendFeedback;
121 PBD::Signal3<int,Session*,std::string,DataType> Session::MissingFile;
123 PBD::Signal1<void, framepos_t> Session::StartTimeChanged;
124 PBD::Signal1<void, framepos_t> Session::EndTimeChanged;
125 PBD::Signal0<void> Session::AutoBindingOn;
126 PBD::Signal0<void> Session::AutoBindingOff;
127 PBD::Signal2<void,std::string, std::string> Session::Exported;
128 PBD::Signal1<int,boost::shared_ptr<Playlist> > Session::AskAboutPlaylistDeletion;
129 PBD::Signal0<void> Session::Quit;
131 static void clean_up_session_event (SessionEvent* ev) { delete ev; }
132 const SessionEvent::RTeventCallback Session::rt_cleanup (clean_up_session_event);
134 Session::Session (AudioEngine &eng,
135 const string& fullpath,
136 const string& snapshot_name,
137 BusProfile* bus_profile,
140 , _target_transport_speed (0.0)
141 , _requested_return_frame (-1)
142 , _session_dir (new SessionDirectory(fullpath))
144 , _state_of_the_state (Clean)
145 , _butler (new Butler (*this))
146 , _post_transport_work (0)
147 , _send_timecode_update (false)
148 , _all_route_group (new RouteGroup (*this, "all"))
149 , route_graph (new Graph(*this))
150 , routes (new RouteList)
151 , _total_free_4k_blocks (0)
152 , _bundles (new BundleList)
153 , _bundle_xml_node (0)
155 , _click_io ((IO*) 0)
157 , click_emphasis_data (0)
159 , _metadata (new SessionMetadata())
160 , _have_rec_enabled_track (false)
161 , _suspend_timecode_transmission (0)
163 _locations = new Locations (*this);
165 playlists.reset (new SessionPlaylists);
167 _all_route_group->set_active (true, this);
169 interpolation.add_channel_to (0, 0);
171 if (!eng.connected()) {
172 throw failed_constructor();
175 n_physical_outputs = _engine.n_physical_outputs ();
176 n_physical_inputs = _engine.n_physical_inputs ();
178 first_stage_init (fullpath, snapshot_name);
180 _is_new = !Glib::file_test (_path, Glib::FileTest (G_FILE_TEST_EXISTS | G_FILE_TEST_IS_DIR));
183 if (create (mix_template, bus_profile)) {
185 throw failed_constructor ();
189 if (second_stage_init ()) {
191 throw failed_constructor ();
194 store_recent_sessions(_name, _path);
196 bool was_dirty = dirty();
198 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
200 Config->ParameterChanged.connect_same_thread (*this, boost::bind (&Session::config_changed, this, _1, false));
201 config.ParameterChanged.connect_same_thread (*this, boost::bind (&Session::config_changed, this, _1, true));
204 DirtyChanged (); /* EMIT SIGNAL */
207 StartTimeChanged.connect_same_thread (*this, boost::bind (&Session::start_time_changed, this, _1));
208 EndTimeChanged.connect_same_thread (*this, boost::bind (&Session::end_time_changed, this, _1));
221 vector<void*> debug_pointers;
223 /* if we got to here, leaving pending capture state around
227 remove_pending_capture_state ();
229 _state_of_the_state = StateOfTheState (CannotSave|Deletion);
231 _engine.remove_session ();
233 /* clear history so that no references to objects are held any more */
237 /* clear state tree so that no references to objects are held any more */
241 /* remove all stubfiles that might still be lurking */
243 cleanup_stubfiles ();
245 /* reset dynamic state version back to default */
247 Stateful::loading_state_version = 0;
249 _butler->drop_references ();
251 delete midi_control_ui;
252 delete _all_route_group;
254 if (click_data != default_click) {
255 delete [] click_data;
258 if (click_emphasis_data != default_click_emphasis) {
259 delete [] click_emphasis_data;
264 /* clear out any pending dead wood from RCU managed objects */
269 AudioDiskstream::free_working_buffers();
271 /* tell everyone who is still standing that we're about to die */
274 /* tell everyone to drop references and delete objects as we go */
276 DEBUG_TRACE (DEBUG::Destruction, "delete named selections\n");
277 named_selections.clear ();
279 DEBUG_TRACE (DEBUG::Destruction, "delete regions\n");
280 RegionFactory::delete_all_regions ();
282 DEBUG_TRACE (DEBUG::Destruction, "delete routes\n");
284 /* reset these three references to special routes before we do the usual route delete thing */
287 _master_out.reset ();
288 _monitor_out.reset ();
291 RCUWriter<RouteList> writer (routes);
292 boost::shared_ptr<RouteList> r = writer.get_copy ();
294 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
295 DEBUG_TRACE(DEBUG::Destruction, string_compose ("Dropping for route %1 ; pre-ref = %2\n", (*i)->name(), (*i).use_count()));
296 (*i)->drop_references ();
300 /* writer goes out of scope and updates master */
304 boost::shared_ptr<RouteList> r = routes.reader ();
306 DEBUG_TRACE (DEBUG::Destruction, "delete sources\n");
307 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ++i) {
308 DEBUG_TRACE(DEBUG::Destruction, string_compose ("Dropping for source %1 ; pre-ref = %2\n", i->second->path(), i->second.use_count()));
309 i->second->drop_references ();
314 DEBUG_TRACE (DEBUG::Destruction, "delete route groups\n");
315 for (list<RouteGroup *>::iterator i = _route_groups.begin(); i != _route_groups.end(); ++i) {
320 Crossfade::set_buffer_size (0);
322 /* not strictly necessary, but doing it here allows the shared_ptr debugging to work */
328 DEBUG_TRACE (DEBUG::Destruction, "Session::destroy() done\n");
330 #ifdef BOOST_SP_ENABLE_DEBUG_HOOKS
331 boost_debug_list_ptrs ();
336 Session::set_worst_io_latencies ()
338 _worst_output_latency = 0;
339 _worst_input_latency = 0;
341 if (!_engine.connected()) {
345 boost::shared_ptr<RouteList> r = routes.reader ();
347 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
348 _worst_output_latency = max (_worst_output_latency, (*i)->output()->latency());
349 _worst_input_latency = max (_worst_input_latency, (*i)->input()->latency());
354 Session::when_engine_running ()
356 string first_physical_output;
358 BootMessage (_("Set block size and sample rate"));
360 set_block_size (_engine.frames_per_cycle());
361 set_frame_rate (_engine.frame_rate());
363 BootMessage (_("Using configuration"));
365 boost::function<void (std::string)> ff (boost::bind (&Session::config_changed, this, _1, false));
366 boost::function<void (std::string)> ft (boost::bind (&Session::config_changed, this, _1, true));
368 Config->map_parameters (ff);
369 config.map_parameters (ft);
371 /* every time we reconnect, recompute worst case output latencies */
373 _engine.Running.connect_same_thread (*this, boost::bind (&Session::set_worst_io_latencies, this));
375 if (synced_to_jack()) {
376 _engine.transport_stop ();
379 if (config.get_jack_time_master()) {
380 _engine.transport_locate (_transport_frame);
388 _click_io.reset (new ClickIO (*this, "click"));
390 if (state_tree && (child = find_named_node (*state_tree->root(), "Click")) != 0) {
392 /* existing state for Click */
395 if (Stateful::loading_state_version < 3000) {
396 c = _click_io->set_state_2X (*child->children().front(), Stateful::loading_state_version, false);
398 c = _click_io->set_state (*child->children().front(), Stateful::loading_state_version);
403 _clicking = Config->get_clicking ();
407 error << _("could not setup Click I/O") << endmsg;
414 /* default state for Click: dual-mono to first 2 physical outputs */
417 _engine.get_physical_outputs (DataType::AUDIO, outs);
419 for (uint32_t physport = 0; physport < 2; ++physport) {
420 if (outs.size() > physport) {
421 if (_click_io->add_port (outs[physport], this)) {
422 // relax, even though its an error
427 if (_click_io->n_ports () > ChanCount::ZERO) {
428 _clicking = Config->get_clicking ();
433 catch (failed_constructor& err) {
434 error << _("cannot setup Click I/O") << endmsg;
437 BootMessage (_("Compute I/O Latencies"));
439 set_worst_io_latencies ();
442 // XXX HOW TO ALERT UI TO THIS ? DO WE NEED TO?
445 BootMessage (_("Set up standard connections"));
447 vector<string> inputs[DataType::num_types];
448 vector<string> outputs[DataType::num_types];
449 for (uint32_t i = 0; i < DataType::num_types; ++i) {
450 _engine.get_physical_inputs (DataType (DataType::Symbol (i)), inputs[i]);
451 _engine.get_physical_outputs (DataType (DataType::Symbol (i)), outputs[i]);
454 /* Create a set of Bundle objects that map
455 to the physical I/O currently available. We create both
456 mono and stereo bundles, so that the common cases of mono
457 and stereo tracks get bundles to put in their mixer strip
458 in / out menus. There may be a nicer way of achieving that;
459 it doesn't really scale that well to higher channel counts
462 /* mono output bundles */
464 for (uint32_t np = 0; np < outputs[DataType::AUDIO].size(); ++np) {
466 snprintf (buf, sizeof (buf), _("out %" PRIu32), np+1);
468 boost::shared_ptr<Bundle> c (new Bundle (buf, true));
469 c->add_channel (_("mono"), DataType::AUDIO);
470 c->set_port (0, outputs[DataType::AUDIO][np]);
475 /* stereo output bundles */
477 for (uint32_t np = 0; np < outputs[DataType::AUDIO].size(); np += 2) {
478 if (np + 1 < outputs[DataType::AUDIO].size()) {
480 snprintf (buf, sizeof(buf), _("out %" PRIu32 "+%" PRIu32), np + 1, np + 2);
481 boost::shared_ptr<Bundle> c (new Bundle (buf, true));
482 c->add_channel (_("L"), DataType::AUDIO);
483 c->set_port (0, outputs[DataType::AUDIO][np]);
484 c->add_channel (_("R"), DataType::AUDIO);
485 c->set_port (1, outputs[DataType::AUDIO][np + 1]);
491 /* mono input bundles */
493 for (uint32_t np = 0; np < inputs[DataType::AUDIO].size(); ++np) {
495 snprintf (buf, sizeof (buf), _("in %" PRIu32), np+1);
497 boost::shared_ptr<Bundle> c (new Bundle (buf, false));
498 c->add_channel (_("mono"), DataType::AUDIO);
499 c->set_port (0, inputs[DataType::AUDIO][np]);
504 /* stereo input bundles */
506 for (uint32_t np = 0; np < inputs[DataType::AUDIO].size(); np += 2) {
507 if (np + 1 < inputs[DataType::AUDIO].size()) {
509 snprintf (buf, sizeof(buf), _("in %" PRIu32 "+%" PRIu32), np + 1, np + 2);
511 boost::shared_ptr<Bundle> c (new Bundle (buf, false));
512 c->add_channel (_("L"), DataType::AUDIO);
513 c->set_port (0, inputs[DataType::AUDIO][np]);
514 c->add_channel (_("R"), DataType::AUDIO);
515 c->set_port (1, inputs[DataType::AUDIO][np + 1]);
521 /* MIDI input bundles */
523 for (uint32_t np = 0; np < inputs[DataType::MIDI].size(); ++np) {
524 string n = inputs[DataType::MIDI][np];
525 boost::erase_first (n, X_("alsa_pcm:"));
527 boost::shared_ptr<Bundle> c (new Bundle (n, false));
528 c->add_channel ("", DataType::MIDI);
529 c->set_port (0, inputs[DataType::MIDI][np]);
533 /* MIDI output bundles */
535 for (uint32_t np = 0; np < outputs[DataType::MIDI].size(); ++np) {
536 string n = outputs[DataType::MIDI][np];
537 boost::erase_first (n, X_("alsa_pcm:"));
539 boost::shared_ptr<Bundle> c (new Bundle (n, true));
540 c->add_channel ("", DataType::MIDI);
541 c->set_port (0, outputs[DataType::MIDI][np]);
545 BootMessage (_("Setup signal flow and plugins"));
549 if (_is_new && !no_auto_connect()) {
551 Glib::Mutex::Lock lm (AudioEngine::instance()->process_lock());
553 /* don't connect the master bus outputs if there is a monitor bus */
555 if (_master_out && Config->get_auto_connect_standard_busses() && !_monitor_out) {
557 /* if requested auto-connect the outputs to the first N physical ports.
560 uint32_t limit = _master_out->n_outputs().n_total();
562 for (uint32_t n = 0; n < limit; ++n) {
563 Port* p = _master_out->output()->nth (n);
565 if (outputs[p->type()].size() > n) {
566 connect_to = outputs[p->type()][n];
569 if (!connect_to.empty() && p->connected_to (connect_to) == false) {
570 if (_master_out->output()->connect (p, connect_to, this)) {
571 error << string_compose (_("cannot connect master output %1 to %2"), n, connect_to)
581 /* AUDIO ONLY as of june 29th 2009, because listen semantics for anything else
582 are undefined, at best.
585 /* control out listens to master bus (but ignores it
586 under some conditions)
589 uint32_t limit = _monitor_out->n_inputs().n_audio();
592 for (uint32_t n = 0; n < limit; ++n) {
593 AudioPort* p = _monitor_out->input()->ports().nth_audio_port (n);
594 AudioPort* o = _master_out->output()->ports().nth_audio_port (n);
597 string connect_to = o->name();
598 if (_monitor_out->input()->connect (p, connect_to, this)) {
599 error << string_compose (_("cannot connect control input %1 to %2"), n, connect_to)
607 /* if control out is not connected, connect control out to physical outs
610 if (!_monitor_out->output()->connected ()) {
612 if (!Config->get_monitor_bus_preferred_bundle().empty()) {
614 boost::shared_ptr<Bundle> b = bundle_by_name (Config->get_monitor_bus_preferred_bundle());
617 _monitor_out->output()->connect_ports_to_bundle (b, this);
619 warning << string_compose (_("The preferred I/O for the monitor bus (%1) cannot be found"),
620 Config->get_monitor_bus_preferred_bundle())
626 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
627 uint32_t mod = n_physical_outputs.get (*t);
628 uint32_t limit = _monitor_out->n_outputs().get(*t);
630 for (uint32_t n = 0; n < limit; ++n) {
632 Port* p = _monitor_out->output()->ports().port(*t, n);
634 if (outputs[*t].size() > (n % mod)) {
635 connect_to = outputs[*t][n % mod];
638 if (!connect_to.empty()) {
639 if (_monitor_out->output()->connect (p, connect_to, this)) {
640 error << string_compose (
641 _("cannot connect control output %1 to %2"),
654 /* catch up on send+insert cnts */
656 _state_of_the_state = StateOfTheState (_state_of_the_state & ~(CannotSave|Dirty));
658 /* hook us up to the engine */
660 BootMessage (_("Connect to engine"));
662 _engine.set_session (this);
666 Session::hookup_io ()
668 /* stop graph reordering notifications from
669 causing resorts, etc.
672 _state_of_the_state = StateOfTheState (_state_of_the_state | InitialConnecting);
677 /* we delay creating the auditioner till now because
678 it makes its own connections to ports.
682 Auditioner* a = new Auditioner (*this);
685 throw failed_constructor();
687 a->use_new_diskstream ();
688 auditioner.reset (a);
691 catch (failed_constructor& err) {
692 warning << _("cannot create Auditioner: no auditioning of regions possible") << endmsg;
696 /* load bundles, which we may have postponed earlier on */
697 if (_bundle_xml_node) {
698 load_bundles (*_bundle_xml_node);
699 delete _bundle_xml_node;
702 /* Tell all IO objects to connect themselves together */
704 IO::enable_connecting ();
705 MIDI::Port::MakeConnections ();
707 /* Now reset all panners */
709 Delivery::reset_panners ();
711 /* Connect tracks to monitor/listen bus if there is one.
712 Note that in an existing session, the internal sends will
713 already exist, but we want the routes to notice that
714 they connect to the control out specifically.
718 boost::shared_ptr<RouteList> r = routes.reader ();
719 for (RouteList::iterator x = r->begin(); x != r->end(); ++x) {
721 if ((*x)->is_monitor()) {
725 } else if ((*x)->is_master()) {
731 (*x)->listen_via (_monitor_out,
732 (Config->get_listen_position() == AfterFaderListen ? PostFader : PreFader),
738 /* Anyone who cares about input state, wake up and do something */
740 IOConnectionsComplete (); /* EMIT SIGNAL */
742 _state_of_the_state = StateOfTheState (_state_of_the_state & ~InitialConnecting);
744 /* now handle the whole enchilada as if it was one
750 /* update the full solo state, which can't be
751 correctly determined on a per-route basis, but
752 needs the global overview that only the session
756 update_route_solo_state ();
760 Session::track_playlist_changed (boost::weak_ptr<Track> wp)
762 boost::shared_ptr<Track> track = wp.lock ();
767 boost::shared_ptr<Playlist> playlist;
769 if ((playlist = track->playlist()) != 0) {
770 playlist->RegionAdded.connect_same_thread (*this, boost::bind (&Session::playlist_region_added, this, _1));
771 playlist->RangesMoved.connect_same_thread (*this, boost::bind (&Session::playlist_ranges_moved, this, _1));
776 Session::record_enabling_legal () const
778 /* this used to be in here, but survey says.... we don't need to restrict it */
779 // if (record_status() == Recording) {
783 if (Config->get_all_safe()) {
790 Session::reset_input_monitor_state ()
792 if (transport_rolling()) {
794 boost::shared_ptr<RouteList> rl = routes.reader ();
795 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
796 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
797 if (tr && tr->record_enabled ()) {
798 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
799 tr->monitor_input (Config->get_monitoring_model() == HardwareMonitoring && !config.get_auto_input());
805 boost::shared_ptr<RouteList> rl = routes.reader ();
806 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
807 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
808 if (tr && tr->record_enabled ()) {
809 //cerr << "switching to input = " << !Config->get_auto_input() << __FILE__ << __LINE__ << endl << endl;
810 tr->monitor_input (Config->get_monitoring_model() == HardwareMonitoring);
817 Session::auto_punch_start_changed (Location* location)
819 replace_event (SessionEvent::PunchIn, location->start());
821 if (get_record_enabled() && config.get_punch_in()) {
822 /* capture start has been changed, so save new pending state */
823 save_state ("", true);
828 Session::auto_punch_end_changed (Location* location)
830 framepos_t when_to_stop = location->end();
831 // when_to_stop += _worst_output_latency + _worst_input_latency;
832 replace_event (SessionEvent::PunchOut, when_to_stop);
836 Session::auto_punch_changed (Location* location)
838 framepos_t when_to_stop = location->end();
840 replace_event (SessionEvent::PunchIn, location->start());
841 //when_to_stop += _worst_output_latency + _worst_input_latency;
842 replace_event (SessionEvent::PunchOut, when_to_stop);
846 Session::auto_loop_changed (Location* location)
848 replace_event (SessionEvent::AutoLoop, location->end(), location->start());
850 if (transport_rolling() && play_loop) {
853 // if (_transport_frame > location->end()) {
855 if (_transport_frame < location->start() || _transport_frame > location->end()) {
856 // relocate to beginning of loop
857 clear_events (SessionEvent::LocateRoll);
859 request_locate (location->start(), true);
862 else if (Config->get_seamless_loop() && !loop_changing) {
864 // schedule a locate-roll to refill the diskstreams at the
866 loop_changing = true;
868 if (location->end() > last_loopend) {
869 clear_events (SessionEvent::LocateRoll);
870 SessionEvent *ev = new SessionEvent (SessionEvent::LocateRoll, SessionEvent::Add, last_loopend, last_loopend, 0, true);
877 last_loopend = location->end();
881 Session::set_auto_punch_location (Location* location)
885 if ((existing = _locations->auto_punch_location()) != 0 && existing != location) {
886 punch_connections.drop_connections();
887 existing->set_auto_punch (false, this);
888 remove_event (existing->start(), SessionEvent::PunchIn);
889 clear_events (SessionEvent::PunchOut);
890 auto_punch_location_changed (0);
899 if (location->end() <= location->start()) {
900 error << _("Session: you can't use that location for auto punch (start <= end)") << endmsg;
904 punch_connections.drop_connections ();
906 location->start_changed.connect_same_thread (punch_connections, boost::bind (&Session::auto_punch_start_changed, this, _1));
907 location->end_changed.connect_same_thread (punch_connections, boost::bind (&Session::auto_punch_end_changed, this, _1));
908 location->changed.connect_same_thread (punch_connections, boost::bind (&Session::auto_punch_changed, this, _1));
910 location->set_auto_punch (true, this);
912 auto_punch_changed (location);
914 auto_punch_location_changed (location);
918 Session::set_auto_loop_location (Location* location)
922 if ((existing = _locations->auto_loop_location()) != 0 && existing != location) {
923 loop_connections.drop_connections ();
924 existing->set_auto_loop (false, this);
925 remove_event (existing->end(), SessionEvent::AutoLoop);
926 auto_loop_location_changed (0);
935 if (location->end() <= location->start()) {
936 error << _("Session: you can't use a mark for auto loop") << endmsg;
940 last_loopend = location->end();
942 loop_connections.drop_connections ();
944 location->start_changed.connect_same_thread (loop_connections, boost::bind (&Session::auto_loop_changed, this, _1));
945 location->end_changed.connect_same_thread (loop_connections, boost::bind (&Session::auto_loop_changed, this, _1));
946 location->changed.connect_same_thread (loop_connections, boost::bind (&Session::auto_loop_changed, this, _1));
948 location->set_auto_loop (true, this);
950 /* take care of our stuff first */
952 auto_loop_changed (location);
954 /* now tell everyone else */
956 auto_loop_location_changed (location);
960 Session::locations_added (Location *)
966 Session::locations_changed ()
968 _locations->apply (*this, &Session::handle_locations_changed);
972 Session::handle_locations_changed (Locations::LocationList& locations)
974 Locations::LocationList::iterator i;
976 bool set_loop = false;
977 bool set_punch = false;
979 for (i = locations.begin(); i != locations.end(); ++i) {
983 if (location->is_auto_punch()) {
984 set_auto_punch_location (location);
987 if (location->is_auto_loop()) {
988 set_auto_loop_location (location);
992 if (location->is_session_range()) {
993 _session_range_location = location;
998 set_auto_loop_location (0);
1001 set_auto_punch_location (0);
1008 Session::enable_record ()
1011 RecordState rs = (RecordState) g_atomic_int_get (&_record_status);
1013 if (rs == Recording) {
1017 if (g_atomic_int_compare_and_exchange (&_record_status, rs, Recording)) {
1019 _last_record_location = _transport_frame;
1020 MIDI::Manager::instance()->mmc()->send (MIDI::MachineControlCommand (MIDI::MachineControl::cmdRecordStrobe));
1022 if (Config->get_monitoring_model() == HardwareMonitoring && config.get_auto_input()) {
1024 boost::shared_ptr<RouteList> rl = routes.reader ();
1025 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
1026 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
1027 if (tr && tr->record_enabled ()) {
1028 tr->monitor_input (true);
1033 RecordStateChanged ();
1040 Session::disable_record (bool rt_context, bool force)
1044 if ((rs = (RecordState) g_atomic_int_get (&_record_status)) != Disabled) {
1046 if ((!Config->get_latched_record_enable () && !play_loop) || force) {
1047 g_atomic_int_set (&_record_status, Disabled);
1048 MIDI::Manager::instance()->mmc()->send (MIDI::MachineControlCommand (MIDI::MachineControl::cmdRecordExit));
1050 if (rs == Recording) {
1051 g_atomic_int_set (&_record_status, Enabled);
1055 if (Config->get_monitoring_model() == HardwareMonitoring && config.get_auto_input()) {
1057 boost::shared_ptr<RouteList> rl = routes.reader ();
1058 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
1059 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
1060 if (tr && tr->record_enabled ()) {
1061 tr->monitor_input (false);
1066 RecordStateChanged (); /* emit signal */
1069 remove_pending_capture_state ();
1075 Session::step_back_from_record ()
1077 if (g_atomic_int_compare_and_exchange (&_record_status, Recording, Enabled)) {
1079 if (Config->get_monitoring_model() == HardwareMonitoring && config.get_auto_input()) {
1080 boost::shared_ptr<RouteList> rl = routes.reader ();
1081 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
1082 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
1083 if (tr && tr->record_enabled ()) {
1084 //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1085 tr->monitor_input (false);
1093 Session::maybe_enable_record ()
1095 if (_step_editors > 0) {
1099 g_atomic_int_set (&_record_status, Enabled);
1101 /* This function is currently called from somewhere other than an RT thread.
1102 This save_state() call therefore doesn't impact anything. Doing it here
1103 means that we save pending state of which sources the next record will use,
1104 which gives us some chance of recovering from a crash during the record.
1107 save_state ("", true);
1109 if (_transport_speed) {
1110 if (!config.get_punch_in()) {
1114 MIDI::Manager::instance()->mmc()->send (MIDI::MachineControlCommand (MIDI::MachineControl::cmdRecordPause));
1115 RecordStateChanged (); /* EMIT SIGNAL */
1122 Session::audible_frame () const
1128 /* the first of these two possible settings for "offset"
1129 mean that the audible frame is stationary until
1130 audio emerges from the latency compensation
1133 the second means that the audible frame is stationary
1134 until audio would emerge from a physical port
1135 in the absence of any plugin latency compensation
1138 offset = _worst_output_latency;
1140 if (offset > current_block_size) {
1141 offset -= current_block_size;
1143 /* XXX is this correct? if we have no external
1144 physical connections and everything is internal
1145 then surely this is zero? still, how
1146 likely is that anyway?
1148 offset = current_block_size;
1151 if (synced_to_jack()) {
1152 tf = _engine.transport_frame();
1154 tf = _transport_frame;
1159 if (!non_realtime_work_pending()) {
1163 /* Check to see if we have passed the first guaranteed
1164 audible frame past our last start position. if not,
1165 return that last start point because in terms
1166 of audible frames, we have not moved yet.
1168 `Start position' in this context means the time we last
1169 either started or changed transport direction.
1172 if (_transport_speed > 0.0f) {
1174 if (!play_loop || !have_looped) {
1175 if (tf < _last_roll_or_reversal_location + offset) {
1176 return _last_roll_or_reversal_location;
1184 } else if (_transport_speed < 0.0f) {
1186 /* XXX wot? no backward looping? */
1188 if (tf > _last_roll_or_reversal_location - offset) {
1189 return _last_roll_or_reversal_location;
1201 Session::set_frame_rate (framecnt_t frames_per_second)
1203 /** \fn void Session::set_frame_size(framecnt_t)
1204 the AudioEngine object that calls this guarantees
1205 that it will not be called while we are also in
1206 ::process(). Its fine to do things that block
1210 _base_frame_rate = frames_per_second;
1214 Automatable::set_automation_interval (ceil ((double) frames_per_second * (0.001 * Config->get_automation_interval())));
1218 // XXX we need some equivalent to this, somehow
1219 // SndFileSource::setup_standard_crossfades (frames_per_second);
1223 /* XXX need to reset/reinstantiate all LADSPA plugins */
1227 Session::set_block_size (pframes_t nframes)
1229 /* the AudioEngine guarantees
1230 that it will not be called while we are also in
1231 ::process(). It is therefore fine to do things that block
1236 current_block_size = nframes;
1240 boost::shared_ptr<RouteList> r = routes.reader ();
1242 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1243 (*i)->set_block_size (nframes);
1246 boost::shared_ptr<RouteList> rl = routes.reader ();
1247 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
1248 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
1250 tr->set_block_size (nframes);
1254 set_worst_io_latencies ();
1259 Session::set_default_fade (float /*steepness*/, float /*fade_msecs*/)
1262 framecnt_t fade_frames;
1264 /* Don't allow fade of less 1 frame */
1266 if (fade_msecs < (1000.0 * (1.0/_current_frame_rate))) {
1273 fade_frames = (framecnt_t) floor (fade_msecs * _current_frame_rate * 0.001);
1277 default_fade_msecs = fade_msecs;
1278 default_fade_steepness = steepness;
1281 // jlc, WTF is this!
1282 Glib::RWLock::ReaderLock lm (route_lock);
1283 AudioRegion::set_default_fade (steepness, fade_frames);
1288 /* XXX have to do this at some point */
1289 /* foreach region using default fade, reset, then
1290 refill_all_diskstream_buffers ();
1295 struct RouteSorter {
1296 /** @return true to run r1 before r2, otherwise false */
1297 bool operator() (boost::shared_ptr<Route> r1, boost::shared_ptr<Route> r2) {
1298 if (r2->feeds (r1)) {
1299 /* r1 fed by r2; run r2 early */
1301 } else if (r1->feeds (r2)) {
1302 /* r2 fed by r1; run r1 early */
1305 if (r1->not_fed ()) {
1306 if (r2->not_fed ()) {
1307 /* no ardour-based connections inbound to either route. just use signal order */
1308 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1310 /* r2 has connections, r1 does not; run r1 early */
1314 if (r2->not_fed()) {
1315 /* r1 has connections, r2 does not; run r2 early */
1318 /* both r1 and r2 have connections, but not to each other. just use signal order */
1319 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1327 trace_terminal (boost::shared_ptr<Route> r1, boost::shared_ptr<Route> rbase)
1329 boost::shared_ptr<Route> r2;
1331 if (r1->feeds (rbase) && rbase->feeds (r1)) {
1332 info << string_compose(_("feedback loop setup between %1 and %2"), r1->name(), rbase->name()) << endmsg;
1336 /* make a copy of the existing list of routes that feed r1 */
1338 Route::FedBy existing (r1->fed_by());
1340 /* for each route that feeds r1, recurse, marking it as feeding
1344 for (Route::FedBy::iterator i = existing.begin(); i != existing.end(); ++i) {
1345 if (!(r2 = i->r.lock ())) {
1346 /* (*i) went away, ignore it */
1350 /* r2 is a route that feeds r1 which somehow feeds base. mark
1351 base as being fed by r2
1354 rbase->add_fed_by (r2, i->sends_only);
1358 /* 2nd level feedback loop detection. if r1 feeds or is fed by r2,
1362 if (r1->feeds (r2) && r2->feeds (r1)) {
1366 /* now recurse, so that we can mark base as being fed by
1367 all routes that feed r2
1370 trace_terminal (r2, rbase);
1377 Session::resort_routes ()
1379 /* don't do anything here with signals emitted
1380 by Routes while we are being destroyed.
1383 if (_state_of_the_state & Deletion) {
1388 RCUWriter<RouteList> writer (routes);
1389 boost::shared_ptr<RouteList> r = writer.get_copy ();
1390 resort_routes_using (r);
1391 /* writer goes out of scope and forces update */
1394 //route_graph->dump(1);
1397 boost::shared_ptr<RouteList> rl = routes.reader ();
1398 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
1399 DEBUG_TRACE (DEBUG::Graph, string_compose ("%1 fed by ...\n", (*i)->name()));
1401 const Route::FedBy& fb ((*i)->fed_by());
1403 for (Route::FedBy::const_iterator f = fb.begin(); f != fb.end(); ++f) {
1404 boost::shared_ptr<Route> sf = f->r.lock();
1406 DEBUG_TRACE (DEBUG::Graph, string_compose ("\t%1 (sends only ? %2)\n", sf->name(), f->sends_only));
1414 Session::resort_routes_using (boost::shared_ptr<RouteList> r)
1416 RouteList::iterator i, j;
1418 for (i = r->begin(); i != r->end(); ++i) {
1420 (*i)->clear_fed_by ();
1422 for (j = r->begin(); j != r->end(); ++j) {
1424 /* although routes can feed themselves, it will
1425 cause an endless recursive descent if we
1426 detect it. so don't bother checking for
1434 bool via_sends_only;
1436 if ((*j)->direct_feeds (*i, &via_sends_only)) {
1437 (*i)->add_fed_by (*j, via_sends_only);
1442 for (i = r->begin(); i != r->end(); ++i) {
1443 trace_terminal (*i, *i);
1449 route_graph->rechain (r);
1452 DEBUG_TRACE (DEBUG::Graph, "Routes resorted, order follows:\n");
1453 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1454 DEBUG_TRACE (DEBUG::Graph, string_compose ("\t%1 signal order %2\n",
1455 (*i)->name(), (*i)->order_key ("signal")));
1461 /** Find the route name starting with \a base with the lowest \a id.
1463 * Names are constructed like e.g. "Audio 3" for base="Audio" and id=3.
1464 * The available route name with the lowest ID will be used, and \a id
1465 * will be set to the ID.
1467 * \return false if a route name could not be found, and \a track_name
1468 * and \a id do not reflect a free route name.
1471 Session::find_route_name (const char* base, uint32_t& id, char* name, size_t name_len)
1474 snprintf (name, name_len, "%s %" PRIu32, base, id);
1476 if (route_by_name (name) == 0) {
1482 } while (id < (UINT_MAX-1));
1487 /** Count the total ins and outs of all non-hidden routes in the session and return them in in and out */
1489 Session::count_existing_route_channels (ChanCount& in, ChanCount& out)
1491 in = ChanCount::ZERO;
1492 out = ChanCount::ZERO;
1493 boost::shared_ptr<RouteList> r = routes.reader ();
1494 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1495 if (!(*i)->is_hidden()) {
1496 in += (*i)->n_inputs();
1497 out += (*i)->n_outputs();
1502 /** Caller must not hold process lock */
1503 list<boost::shared_ptr<MidiTrack> >
1504 Session::new_midi_track (TrackMode mode, RouteGroup* route_group, uint32_t how_many)
1506 char track_name[32];
1507 uint32_t track_id = 0;
1508 ChanCount existing_inputs;
1509 ChanCount existing_outputs;
1511 RouteList new_routes;
1512 list<boost::shared_ptr<MidiTrack> > ret;
1513 uint32_t control_id;
1515 count_existing_route_channels (existing_inputs, existing_outputs);
1517 control_id = ntracks() + nbusses();
1520 if (!find_route_name ("Midi", ++track_id, track_name, sizeof(track_name))) {
1521 error << "cannot find name for new midi track" << endmsg;
1525 boost::shared_ptr<MidiTrack> track;
1528 MidiTrack* mt = new MidiTrack (*this, track_name, Route::Flag (0), mode);
1535 mt->use_new_diskstream();
1537 #ifdef BOOST_SP_ENABLE_DEBUG_HOOKS
1538 boost_debug_shared_ptr_mark_interesting (mt, "Track");
1540 track = boost::shared_ptr<MidiTrack>(mt);
1543 Glib::Mutex::Lock lm (AudioEngine::instance()->process_lock ());
1544 if (track->input()->ensure_io (ChanCount(DataType::MIDI, 1), false, this)) {
1545 error << "cannot configure 1 in/1 out configuration for new midi track" << endmsg;
1549 if (track->output()->ensure_io (ChanCount(DataType::MIDI, 1), false, this)) {
1550 error << "cannot configure 1 in/1 out configuration for new midi track" << endmsg;
1555 auto_connect_route (track.get(), existing_inputs, existing_outputs);
1557 track->non_realtime_input_change();
1560 route_group->add (track);
1563 track->DiskstreamChanged.connect_same_thread (*this, boost::bind (&Session::resort_routes, this));
1564 track->set_remote_control_id (control_id);
1566 new_routes.push_back (track);
1567 ret.push_back (track);
1570 catch (failed_constructor &err) {
1571 error << _("Session: could not create new midi track.") << endmsg;
1575 catch (AudioEngine::PortRegistrationFailure& pfe) {
1577 error << string_compose (_("No more JACK ports are available. You will need to stop %1 and restart JACK with ports if you need this many tracks."), PROGRAM_NAME) << endmsg;
1585 if (!new_routes.empty()) {
1586 add_routes (new_routes, false);
1587 save_state (_current_snapshot_name);
1593 /** Caller must hold process lock.
1594 * @param connect_inputs true to connect inputs as well as outputs, false to connect just outputs.
1595 * @param input_start Where to start from when auto-connecting inputs; e.g. if this is 0, auto-connect starting from input 0.
1596 * @param output_start As \a input_start, but for outputs.
1599 Session::auto_connect_route (
1600 Route* route, ChanCount& existing_inputs, ChanCount& existing_outputs, bool connect_inputs, ChanCount input_start, ChanCount output_start
1603 /* If both inputs and outputs are auto-connected to physical ports,
1604 use the max of input and output offsets to ensure auto-connected
1605 port numbers always match up (e.g. the first audio input and the
1606 first audio output of the route will have the same physical
1607 port number). Otherwise just use the lowest input or output
1611 const bool in_out_physical =
1612 (Config->get_input_auto_connect() & AutoConnectPhysical)
1613 && (Config->get_output_auto_connect() & AutoConnectPhysical)
1616 const ChanCount in_offset = in_out_physical
1617 ? ChanCount::max(existing_inputs, existing_outputs)
1620 const ChanCount out_offset = in_out_physical
1621 ? ChanCount::max(existing_inputs, existing_outputs)
1624 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1625 vector<string> physinputs;
1626 vector<string> physoutputs;
1628 _engine.get_physical_outputs (*t, physoutputs);
1629 _engine.get_physical_inputs (*t, physinputs);
1631 if (!physinputs.empty() && connect_inputs) {
1632 uint32_t nphysical_in = physinputs.size();
1633 for (uint32_t i = input_start.get(*t); i < route->n_inputs().get(*t) && i < nphysical_in; ++i) {
1636 if (Config->get_input_auto_connect() & AutoConnectPhysical) {
1637 port = physinputs[(in_offset.get(*t) + i) % nphysical_in];
1640 if (!port.empty() && route->input()->connect (
1641 route->input()->ports().port(*t, i), port, this)) {
1647 if (!physoutputs.empty()) {
1648 uint32_t nphysical_out = physoutputs.size();
1649 for (uint32_t i = output_start.get(*t); i < route->n_outputs().get(*t); ++i) {
1652 if (Config->get_output_auto_connect() & AutoConnectPhysical) {
1653 port = physoutputs[(out_offset.get(*t) + i) % nphysical_out];
1654 } else if (Config->get_output_auto_connect() & AutoConnectMaster) {
1655 if (_master_out && _master_out->n_inputs().get(*t) > 0) {
1656 port = _master_out->input()->ports().port(*t,
1657 i % _master_out->input()->n_ports().get(*t))->name();
1661 if (!port.empty() && route->output()->connect (
1662 route->output()->ports().port(*t, i), port, this)) {
1669 existing_inputs += route->n_inputs();
1670 existing_outputs += route->n_outputs();
1673 /** Caller must not hold process lock */
1674 list< boost::shared_ptr<AudioTrack> >
1675 Session::new_audio_track (int input_channels, int output_channels, TrackMode mode, RouteGroup* route_group, uint32_t how_many)
1677 char track_name[32];
1678 uint32_t track_id = 0;
1679 ChanCount existing_inputs;
1680 ChanCount existing_outputs;
1682 RouteList new_routes;
1683 list<boost::shared_ptr<AudioTrack> > ret;
1684 uint32_t control_id;
1686 count_existing_route_channels (existing_inputs, existing_outputs);
1688 control_id = ntracks() + nbusses() + 1;
1691 if (!find_route_name ("Audio", ++track_id, track_name, sizeof(track_name))) {
1692 error << "cannot find name for new audio track" << endmsg;
1696 boost::shared_ptr<AudioTrack> track;
1699 AudioTrack* at = new AudioTrack (*this, track_name, Route::Flag (0), mode);
1706 at->use_new_diskstream();
1708 #ifdef BOOST_SP_ENABLE_DEBUG_HOOKS
1709 boost_debug_shared_ptr_mark_interesting (at, "Track");
1711 track = boost::shared_ptr<AudioTrack>(at);
1714 Glib::Mutex::Lock lm (AudioEngine::instance()->process_lock ());
1716 if (track->input()->ensure_io (ChanCount(DataType::AUDIO, input_channels), false, this)) {
1717 error << string_compose (
1718 _("cannot configure %1 in/%2 out configuration for new audio track"),
1719 input_channels, output_channels)
1724 if (track->output()->ensure_io (ChanCount(DataType::AUDIO, output_channels), false, this)) {
1725 error << string_compose (
1726 _("cannot configure %1 in/%2 out configuration for new audio track"),
1727 input_channels, output_channels)
1732 auto_connect_route (track.get(), existing_inputs, existing_outputs);
1736 route_group->add (track);
1739 track->non_realtime_input_change();
1741 track->DiskstreamChanged.connect_same_thread (*this, boost::bind (&Session::resort_routes, this));
1742 track->set_remote_control_id (control_id);
1745 new_routes.push_back (track);
1746 ret.push_back (track);
1749 catch (failed_constructor &err) {
1750 error << _("Session: could not create new audio track.") << endmsg;
1754 catch (AudioEngine::PortRegistrationFailure& pfe) {
1756 error << pfe.what() << endmsg;
1764 if (!new_routes.empty()) {
1765 add_routes (new_routes, true);
1772 Session::set_remote_control_ids ()
1774 RemoteModel m = Config->get_remote_model();
1775 bool emit_signal = false;
1777 boost::shared_ptr<RouteList> r = routes.reader ();
1779 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1780 if (MixerOrdered == m) {
1781 int32_t order = (*i)->order_key(N_("signal"));
1782 (*i)->set_remote_control_id (order+1, false);
1784 } else if (EditorOrdered == m) {
1785 int32_t order = (*i)->order_key(N_("editor"));
1786 (*i)->set_remote_control_id (order+1, false);
1788 } else if (UserOrdered == m) {
1789 //do nothing ... only changes to remote id's are initiated by user
1794 Route::RemoteControlIDChange();
1798 /** Caller must not hold process lock */
1800 Session::new_audio_route (int input_channels, int output_channels, RouteGroup* route_group, uint32_t how_many)
1803 uint32_t bus_id = 0;
1804 ChanCount existing_inputs;
1805 ChanCount existing_outputs;
1808 uint32_t control_id;
1810 count_existing_route_channels (existing_inputs, existing_outputs);
1812 control_id = ntracks() + nbusses() + 1;
1815 if (!find_route_name ("Bus", ++bus_id, bus_name, sizeof(bus_name))) {
1816 error << "cannot find name for new audio bus" << endmsg;
1821 Route* rt = new Route (*this, bus_name, Route::Flag(0), DataType::AUDIO);
1828 #ifdef BOOST_SP_ENABLE_DEBUG_HOOKS
1829 boost_debug_shared_ptr_mark_interesting (rt, "Route");
1831 boost::shared_ptr<Route> bus (rt);
1834 Glib::Mutex::Lock lm (AudioEngine::instance()->process_lock ());
1836 if (bus->input()->ensure_io (ChanCount(DataType::AUDIO, input_channels), false, this)) {
1837 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1838 input_channels, output_channels)
1844 if (bus->output()->ensure_io (ChanCount(DataType::AUDIO, output_channels), false, this)) {
1845 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1846 input_channels, output_channels)
1851 auto_connect_route (bus.get(), existing_inputs, existing_outputs, false);
1855 route_group->add (bus);
1857 bus->set_remote_control_id (control_id);
1860 bus->add_internal_return ();
1862 ret.push_back (bus);
1866 catch (failed_constructor &err) {
1867 error << _("Session: could not create new audio route.") << endmsg;
1871 catch (AudioEngine::PortRegistrationFailure& pfe) {
1872 error << pfe.what() << endmsg;
1882 add_routes (ret, true);
1890 Session::new_route_from_template (uint32_t how_many, const std::string& template_path)
1894 uint32_t control_id;
1896 uint32_t number = 0;
1898 if (!tree.read (template_path.c_str())) {
1902 XMLNode* node = tree.root();
1904 control_id = ntracks() + nbusses() + 1;
1908 XMLNode node_copy (*node); // make a copy so we can change the name if we need to
1910 std::string node_name = IO::name_from_state (*node_copy.children().front());
1912 /* generate a new name by adding a number to the end of the template name */
1913 if (!find_route_name (node_name.c_str(), ++number, name, sizeof(name))) {
1914 fatal << _("Session: UINT_MAX routes? impossible!") << endmsg;
1918 /* set IO children to use the new name */
1919 XMLNodeList const & children = node_copy.children ();
1920 for (XMLNodeList::const_iterator i = children.begin(); i != children.end(); ++i) {
1921 if ((*i)->name() == IO::state_node_name) {
1922 IO::set_name_in_state (**i, name);
1926 Track::zero_diskstream_id_in_xml (node_copy);
1929 boost::shared_ptr<Route> route (XMLRouteFactory (node_copy, 3000));
1932 error << _("Session: cannot create track/bus from template description") << endmsg;
1936 if (boost::dynamic_pointer_cast<Track>(route)) {
1937 /* force input/output change signals so that the new diskstream
1938 picks up the configuration of the route. During session
1939 loading this normally happens in a different way.
1942 Glib::Mutex::Lock lm (AudioEngine::instance()->process_lock ());
1944 IOChange change (IOChange::Type (IOChange::ConfigurationChanged | IOChange::ConnectionsChanged));
1945 change.after = route->input()->n_ports();
1946 route->input()->changed (change, this);
1947 change.after = route->output()->n_ports();
1948 route->output()->changed (change, this);
1951 route->set_remote_control_id (control_id);
1954 ret.push_back (route);
1957 catch (failed_constructor &err) {
1958 error << _("Session: could not create new route from template") << endmsg;
1962 catch (AudioEngine::PortRegistrationFailure& pfe) {
1963 error << pfe.what() << endmsg;
1972 add_routes (ret, true);
1979 Session::add_routes (RouteList& new_routes, bool save)
1982 RCUWriter<RouteList> writer (routes);
1983 boost::shared_ptr<RouteList> r = writer.get_copy ();
1984 r->insert (r->end(), new_routes.begin(), new_routes.end());
1987 /* if there is no control out and we're not in the middle of loading,
1988 resort the graph here. if there is a control out, we will resort
1989 toward the end of this method. if we are in the middle of loading,
1990 we will resort when done.
1993 if (!_monitor_out && IO::connecting_legal) {
1994 resort_routes_using (r);
1998 for (RouteList::iterator x = new_routes.begin(); x != new_routes.end(); ++x) {
2000 boost::weak_ptr<Route> wpr (*x);
2001 boost::shared_ptr<Route> r (*x);
2003 r->listen_changed.connect_same_thread (*this, boost::bind (&Session::route_listen_changed, this, _1, wpr));
2004 r->solo_changed.connect_same_thread (*this, boost::bind (&Session::route_solo_changed, this, _1, _2, wpr));
2005 r->solo_isolated_changed.connect_same_thread (*this, boost::bind (&Session::route_solo_isolated_changed, this, _1, wpr));
2006 r->mute_changed.connect_same_thread (*this, boost::bind (&Session::route_mute_changed, this, _1));
2007 r->output()->changed.connect_same_thread (*this, boost::bind (&Session::set_worst_io_latencies_x, this, _1, _2));
2008 r->processors_changed.connect_same_thread (*this, boost::bind (&Session::route_processors_changed, this, _1));
2009 r->order_key_changed.connect_same_thread (*this, boost::bind (&Session::route_order_key_changed, this));
2011 if (r->is_master()) {
2015 if (r->is_monitor()) {
2019 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (r);
2021 tr->PlaylistChanged.connect_same_thread (*this, boost::bind (&Session::track_playlist_changed, this, boost::weak_ptr<Track> (tr)));
2022 track_playlist_changed (boost::weak_ptr<Track> (tr));
2023 tr->RecordEnableChanged.connect_same_thread (*this, boost::bind (&Session::update_have_rec_enabled_track, this));
2025 boost::shared_ptr<MidiTrack> mt = boost::dynamic_pointer_cast<MidiTrack> (tr);
2027 mt->StepEditStatusChange.connect_same_thread (*this, boost::bind (&Session::step_edit_status_change, this, _1));
2032 if (_monitor_out && IO::connecting_legal) {
2034 for (RouteList::iterator x = new_routes.begin(); x != new_routes.end(); ++x) {
2035 if ((*x)->is_monitor()) {
2037 } else if ((*x)->is_master()) {
2040 (*x)->listen_via (_monitor_out,
2041 (Config->get_listen_position() == AfterFaderListen ? PostFader : PreFader),
2052 save_state (_current_snapshot_name);
2055 RouteAdded (new_routes); /* EMIT SIGNAL */
2056 Route::RemoteControlIDChange (); /* EMIT SIGNAL */
2060 Session::globally_set_send_gains_to_zero (boost::shared_ptr<Route> dest)
2062 boost::shared_ptr<RouteList> r = routes.reader ();
2063 boost::shared_ptr<Send> s;
2065 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2066 if ((s = (*i)->internal_send_for (dest)) != 0) {
2067 s->amp()->gain_control()->set_value (0.0);
2073 Session::globally_set_send_gains_to_unity (boost::shared_ptr<Route> dest)
2075 boost::shared_ptr<RouteList> r = routes.reader ();
2076 boost::shared_ptr<Send> s;
2078 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2079 if ((s = (*i)->internal_send_for (dest)) != 0) {
2080 s->amp()->gain_control()->set_value (1.0);
2086 Session::globally_set_send_gains_from_track(boost::shared_ptr<Route> dest)
2088 boost::shared_ptr<RouteList> r = routes.reader ();
2089 boost::shared_ptr<Send> s;
2091 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2092 if ((s = (*i)->internal_send_for (dest)) != 0) {
2093 s->amp()->gain_control()->set_value ((*i)->gain_control()->get_value());
2098 /** @param include_buses true to add sends to buses and tracks, false for just tracks */
2100 Session::globally_add_internal_sends (boost::shared_ptr<Route> dest, Placement p, bool include_buses)
2102 boost::shared_ptr<RouteList> r = routes.reader ();
2103 boost::shared_ptr<RouteList> t (new RouteList);
2105 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2106 if (include_buses || boost::dynamic_pointer_cast<Track>(*i)) {
2111 add_internal_sends (dest, p, t);
2115 Session::add_internal_sends (boost::shared_ptr<Route> dest, Placement p, boost::shared_ptr<RouteList> senders)
2117 if (dest->is_monitor() || dest->is_master()) {
2121 if (!dest->internal_return()) {
2122 dest->add_internal_return();
2125 for (RouteList::iterator i = senders->begin(); i != senders->end(); ++i) {
2127 if ((*i)->is_monitor() || (*i)->is_master() || (*i) == dest) {
2131 (*i)->listen_via (dest, p, true, true);
2138 Session::remove_route (boost::shared_ptr<Route> route)
2140 if (((route == _master_out) || (route == _monitor_out)) && !Config->get_allow_special_bus_removal()) {
2144 route->set_solo (false, this);
2147 RCUWriter<RouteList> writer (routes);
2148 boost::shared_ptr<RouteList> rs = writer.get_copy ();
2152 /* deleting the master out seems like a dumb
2153 idea, but its more of a UI policy issue
2157 if (route == _master_out) {
2158 _master_out = boost::shared_ptr<Route> ();
2161 if (route == _monitor_out) {
2163 /* cancel control outs for all routes */
2165 for (RouteList::iterator r = rs->begin(); r != rs->end(); ++r) {
2166 (*r)->drop_listen (_monitor_out);
2169 _monitor_out.reset ();
2172 /* writer goes out of scope, forces route list update */
2175 update_route_solo_state ();
2177 // We need to disconnect the route's inputs and outputs
2179 route->input()->disconnect (0);
2180 route->output()->disconnect (0);
2182 /* if the route had internal sends sending to it, remove them */
2183 if (route->internal_return()) {
2185 boost::shared_ptr<RouteList> r = routes.reader ();
2186 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2187 boost::shared_ptr<Send> s = (*i)->internal_send_for (route);
2189 (*i)->remove_processor (s);
2194 boost::shared_ptr<MidiTrack> mt = boost::dynamic_pointer_cast<MidiTrack> (route);
2195 if (mt && mt->step_editing()) {
2196 if (_step_editors > 0) {
2201 update_latency_compensation (false, false);
2204 /* Re-sort routes to remove the graph's current references to the one that is
2205 * going away, then flush old references out of the graph.
2209 route_graph->clear_other_chain ();
2211 /* get rid of it from the dead wood collection in the route list manager */
2213 /* XXX i think this is unsafe as it currently stands, but i am not sure. (pd, october 2nd, 2006) */
2217 /* try to cause everyone to drop their references */
2219 route->drop_references ();
2221 sync_order_keys (N_("session"));
2223 Route::RemoteControlIDChange(); /* EMIT SIGNAL */
2225 /* save the new state of the world */
2227 if (save_state (_current_snapshot_name)) {
2228 save_history (_current_snapshot_name);
2233 Session::route_mute_changed (void* /*src*/)
2239 Session::route_listen_changed (void* /*src*/, boost::weak_ptr<Route> wpr)
2241 boost::shared_ptr<Route> route = wpr.lock();
2243 error << string_compose (_("programming error: %1"), X_("invalid route weak ptr passed to route_solo_changed")) << endmsg;
2247 if (route->listening()) {
2249 if (Config->get_exclusive_solo()) {
2250 /* new listen: disable all other listen */
2251 boost::shared_ptr<RouteList> r = routes.reader ();
2252 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2253 if ((*i) == route || (*i)->solo_isolated() || (*i)->is_master() || (*i)->is_monitor() || (*i)->is_hidden()) {
2256 (*i)->set_listen (false, this);
2262 } else if (_listen_cnt > 0) {
2268 Session::route_solo_isolated_changed (void* /*src*/, boost::weak_ptr<Route> wpr)
2270 boost::shared_ptr<Route> route = wpr.lock ();
2273 /* should not happen */
2274 error << string_compose (_("programming error: %1"), X_("invalid route weak ptr passed to route_solo_changed")) << endmsg;
2278 bool send_changed = false;
2280 if (route->solo_isolated()) {
2281 if (_solo_isolated_cnt == 0) {
2282 send_changed = true;
2284 _solo_isolated_cnt++;
2285 } else if (_solo_isolated_cnt > 0) {
2286 _solo_isolated_cnt--;
2287 if (_solo_isolated_cnt == 0) {
2288 send_changed = true;
2293 IsolatedChanged (); /* EMIT SIGNAL */
2298 Session::route_solo_changed (bool self_solo_change, void* /*src*/, boost::weak_ptr<Route> wpr)
2300 if (!self_solo_change) {
2301 // session doesn't care about changes to soloed-by-others
2305 if (solo_update_disabled) {
2310 boost::shared_ptr<Route> route = wpr.lock ();
2313 /* should not happen */
2314 error << string_compose (_("programming error: %1"), X_("invalid route weak ptr passed to route_solo_changed")) << endmsg;
2318 boost::shared_ptr<RouteList> r = routes.reader ();
2321 if (route->self_soloed()) {
2327 if (delta == 1 && Config->get_exclusive_solo()) {
2328 /* new solo: disable all other solos */
2329 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2330 if ((*i) == route || (*i)->solo_isolated() || (*i)->is_master() || (*i)->is_monitor() || (*i)->is_hidden()) {
2333 (*i)->set_solo (false, this);
2337 solo_update_disabled = true;
2339 RouteList uninvolved;
2341 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2342 bool via_sends_only;
2343 bool in_signal_flow;
2345 if ((*i) == route || (*i)->solo_isolated() || (*i)->is_master() || (*i)->is_monitor() || (*i)->is_hidden()) {
2349 in_signal_flow = false;
2351 if ((*i)->feeds (route, &via_sends_only)) {
2352 if (!via_sends_only) {
2353 if (!route->soloed_by_others_upstream()) {
2354 (*i)->mod_solo_by_others_downstream (delta);
2356 in_signal_flow = true;
2360 if (route->feeds (*i, &via_sends_only)) {
2361 (*i)->mod_solo_by_others_upstream (delta);
2362 in_signal_flow = true;
2365 if (!in_signal_flow) {
2366 uninvolved.push_back (*i);
2370 solo_update_disabled = false;
2371 update_route_solo_state (r);
2373 /* now notify that the mute state of the routes not involved in the signal
2374 pathway of the just-solo-changed route may have altered.
2377 for (RouteList::iterator i = uninvolved.begin(); i != uninvolved.end(); ++i) {
2378 (*i)->mute_changed (this);
2381 SoloChanged (); /* EMIT SIGNAL */
2386 Session::update_route_solo_state (boost::shared_ptr<RouteList> r)
2388 /* now figure out if anything that matters is soloed (or is "listening")*/
2390 bool something_soloed = false;
2391 uint32_t listeners = 0;
2392 uint32_t isolated = 0;
2395 r = routes.reader();
2398 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2399 if (!(*i)->is_master() && !(*i)->is_monitor() && !(*i)->is_hidden() && (*i)->self_soloed()) {
2400 something_soloed = true;
2403 if (!(*i)->is_hidden() && (*i)->listening()) {
2404 if (Config->get_solo_control_is_listen_control()) {
2407 (*i)->set_listen (false, this);
2411 if ((*i)->solo_isolated()) {
2416 if (something_soloed != _non_soloed_outs_muted) {
2417 _non_soloed_outs_muted = something_soloed;
2418 SoloActive (_non_soloed_outs_muted); /* EMIT SIGNAL */
2421 _listen_cnt = listeners;
2423 if (isolated != _solo_isolated_cnt) {
2424 _solo_isolated_cnt = isolated;
2425 IsolatedChanged (); /* EMIT SIGNAL */
2429 boost::shared_ptr<RouteList>
2430 Session::get_routes_with_internal_returns() const
2432 boost::shared_ptr<RouteList> r = routes.reader ();
2433 boost::shared_ptr<RouteList> rl (new RouteList);
2435 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2436 if ((*i)->internal_return ()) {
2444 Session::io_name_is_legal (const std::string& name)
2446 boost::shared_ptr<RouteList> r = routes.reader ();
2448 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2449 if ((*i)->name() == name) {
2453 if ((*i)->has_io_processor_named (name)) {
2461 boost::shared_ptr<Route>
2462 Session::route_by_name (string name)
2464 boost::shared_ptr<RouteList> r = routes.reader ();
2466 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2467 if ((*i)->name() == name) {
2472 return boost::shared_ptr<Route> ((Route*) 0);
2475 boost::shared_ptr<Route>
2476 Session::route_by_id (PBD::ID id)
2478 boost::shared_ptr<RouteList> r = routes.reader ();
2480 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2481 if ((*i)->id() == id) {
2486 return boost::shared_ptr<Route> ((Route*) 0);
2489 boost::shared_ptr<Route>
2490 Session::route_by_remote_id (uint32_t id)
2492 boost::shared_ptr<RouteList> r = routes.reader ();
2494 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2495 if ((*i)->remote_control_id() == id) {
2500 return boost::shared_ptr<Route> ((Route*) 0);
2504 Session::playlist_region_added (boost::weak_ptr<Region> w)
2506 boost::shared_ptr<Region> r = w.lock ();
2511 /* These are the operations that are currently in progress... */
2512 list<GQuark> curr = _current_trans_quarks;
2515 /* ...and these are the operations during which we want to update
2516 the session range location markers.
2519 ops.push_back (Operations::capture);
2520 ops.push_back (Operations::paste);
2521 ops.push_back (Operations::duplicate_region);
2522 ops.push_back (Operations::insert_file);
2523 ops.push_back (Operations::insert_region);
2524 ops.push_back (Operations::drag_region_brush);
2525 ops.push_back (Operations::region_drag);
2526 ops.push_back (Operations::selection_grab);
2527 ops.push_back (Operations::region_fill);
2528 ops.push_back (Operations::fill_selection);
2529 ops.push_back (Operations::create_region);
2532 /* See if any of the current operations match the ones that we want */
2534 set_intersection (_current_trans_quarks.begin(), _current_trans_quarks.end(), ops.begin(), ops.end(), back_inserter (in));
2536 /* If so, update the session range markers */
2538 maybe_update_session_range (r->position (), r->last_frame ());
2542 /** Update the session range markers if a is before the current start or
2543 * b is after the current end.
2546 Session::maybe_update_session_range (framepos_t a, framepos_t b)
2548 if (_state_of_the_state & Loading) {
2552 if (_session_range_location == 0) {
2554 add_session_range_location (a, b);
2558 if (a < _session_range_location->start()) {
2559 _session_range_location->set_start (a);
2562 if (b > _session_range_location->end()) {
2563 _session_range_location->set_end (b);
2569 Session::playlist_ranges_moved (list<Evoral::RangeMove<framepos_t> > const & ranges)
2571 for (list<Evoral::RangeMove<framepos_t> >::const_iterator i = ranges.begin(); i != ranges.end(); ++i) {
2572 maybe_update_session_range (i->to, i->to + i->length);
2576 /* Region management */
2578 boost::shared_ptr<Region>
2579 Session::find_whole_file_parent (boost::shared_ptr<Region const> child) const
2581 const RegionFactory::RegionMap& regions (RegionFactory::regions());
2582 RegionFactory::RegionMap::const_iterator i;
2583 boost::shared_ptr<Region> region;
2585 Glib::Mutex::Lock lm (region_lock);
2587 for (i = regions.begin(); i != regions.end(); ++i) {
2591 if (region->whole_file()) {
2593 if (child->source_equivalent (region)) {
2599 return boost::shared_ptr<Region> ();
2603 Session::destroy_sources (list<boost::shared_ptr<Source> > srcs)
2605 set<boost::shared_ptr<Region> > relevant_regions;
2607 for (list<boost::shared_ptr<Source> >::iterator s = srcs.begin(); s != srcs.end(); ++s) {
2608 RegionFactory::get_regions_using_source (*s, relevant_regions);
2611 cerr << "There are " << relevant_regions.size() << " using " << srcs.size() << " sources" << endl;
2613 for (set<boost::shared_ptr<Region> >::iterator r = relevant_regions.begin(); r != relevant_regions.end(); ) {
2614 set<boost::shared_ptr<Region> >::iterator tmp;
2619 cerr << "Cleanup " << (*r)->name() << " UC = " << (*r).use_count() << endl;
2621 playlists->destroy_region (*r);
2622 RegionFactory::map_remove (*r);
2624 (*r)->drop_sources ();
2625 (*r)->drop_references ();
2627 cerr << "\tdone UC = " << (*r).use_count() << endl;
2629 relevant_regions.erase (r);
2634 for (list<boost::shared_ptr<Source> >::iterator s = srcs.begin(); s != srcs.end(); ) {
2637 Glib::Mutex::Lock ls (source_lock);
2638 /* remove from the main source list */
2639 sources.erase ((*s)->id());
2642 (*s)->mark_for_remove ();
2643 (*s)->drop_references ();
2652 Session::remove_last_capture ()
2654 list<boost::shared_ptr<Source> > srcs;
2656 boost::shared_ptr<RouteList> rl = routes.reader ();
2657 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
2658 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
2663 list<boost::shared_ptr<Source> >& l = tr->last_capture_sources();
2666 srcs.insert (srcs.end(), l.begin(), l.end());
2671 destroy_sources (srcs);
2673 save_state (_current_snapshot_name);
2678 /* Source Management */
2681 Session::add_source (boost::shared_ptr<Source> source)
2683 pair<SourceMap::key_type, SourceMap::mapped_type> entry;
2684 pair<SourceMap::iterator,bool> result;
2686 entry.first = source->id();
2687 entry.second = source;
2690 Glib::Mutex::Lock lm (source_lock);
2691 result = sources.insert (entry);
2694 if (result.second) {
2696 /* yay, new source */
2700 boost::shared_ptr<AudioFileSource> afs;
2702 if ((afs = boost::dynamic_pointer_cast<AudioFileSource>(source)) != 0) {
2703 if (Config->get_auto_analyse_audio()) {
2704 Analyser::queue_source_for_analysis (source, false);
2711 Session::remove_source (boost::weak_ptr<Source> src)
2713 SourceMap::iterator i;
2714 boost::shared_ptr<Source> source = src.lock();
2721 Glib::Mutex::Lock lm (source_lock);
2723 if ((i = sources.find (source->id())) != sources.end()) {
2724 cerr << "Removing source " << source->name() << endl;
2729 if (!_state_of_the_state & InCleanup) {
2731 /* save state so we don't end up with a session file
2732 referring to non-existent sources.
2735 save_state (_current_snapshot_name);
2739 boost::shared_ptr<Source>
2740 Session::source_by_id (const PBD::ID& id)
2742 Glib::Mutex::Lock lm (source_lock);
2743 SourceMap::iterator i;
2744 boost::shared_ptr<Source> source;
2746 if ((i = sources.find (id)) != sources.end()) {
2753 boost::shared_ptr<Source>
2754 Session::source_by_path_and_channel (const string& path, uint16_t chn)
2756 Glib::Mutex::Lock lm (source_lock);
2758 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ++i) {
2759 boost::shared_ptr<AudioFileSource> afs
2760 = boost::dynamic_pointer_cast<AudioFileSource>(i->second);
2762 if (afs && afs->path() == path && chn == afs->channel()) {
2766 return boost::shared_ptr<Source>();
2770 Session::count_sources_by_origin (const string& path)
2773 Glib::Mutex::Lock lm (source_lock);
2775 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ++i) {
2776 boost::shared_ptr<FileSource> fs
2777 = boost::dynamic_pointer_cast<FileSource>(i->second);
2779 if (fs && fs->origin() == path) {
2789 Session::change_source_path_by_name (string path, string oldname, string newname, bool destructive)
2792 string old_basename = PBD::basename_nosuffix (oldname);
2793 string new_legalized = legalize_for_path (newname);
2795 /* note: we know (or assume) the old path is already valid */
2799 /* destructive file sources have a name of the form:
2801 /path/to/Tnnnn-NAME(%[LR])?.wav
2803 the task here is to replace NAME with the new name.
2808 string::size_type dash;
2810 dir = Glib::path_get_dirname (path);
2811 path = Glib::path_get_basename (path);
2813 /* '-' is not a legal character for the NAME part of the path */
2815 if ((dash = path.find_last_of ('-')) == string::npos) {
2819 prefix = path.substr (0, dash);
2823 path += new_legalized;
2824 path += native_header_format_extension (config.get_native_file_header_format(), DataType::AUDIO);
2825 path = Glib::build_filename (dir, path);
2829 /* non-destructive file sources have a name of the form:
2831 /path/to/NAME-nnnnn(%[LR])?.ext
2833 the task here is to replace NAME with the new name.
2838 string::size_type dash;
2839 string::size_type postfix;
2841 dir = Glib::path_get_dirname (path);
2842 path = Glib::path_get_basename (path);
2844 /* '-' is not a legal character for the NAME part of the path */
2846 if ((dash = path.find_last_of ('-')) == string::npos) {
2850 suffix = path.substr (dash+1);
2852 // Suffix is now everything after the dash. Now we need to eliminate
2853 // the nnnnn part, which is done by either finding a '%' or a '.'
2855 postfix = suffix.find_last_of ("%");
2856 if (postfix == string::npos) {
2857 postfix = suffix.find_last_of ('.');
2860 if (postfix != string::npos) {
2861 suffix = suffix.substr (postfix);
2863 error << "Logic error in Session::change_source_path_by_name(), please report" << endl;
2867 const uint32_t limit = 10000;
2868 char buf[PATH_MAX+1];
2870 for (uint32_t cnt = 1; cnt <= limit; ++cnt) {
2872 snprintf (buf, sizeof(buf), "%s-%u%s", newname.c_str(), cnt, suffix.c_str());
2874 if (!matching_unsuffixed_filename_exists_in (dir, buf)) {
2875 path = Glib::build_filename (dir, buf);
2883 fatal << string_compose (_("FATAL ERROR! Could not find a suitable version of %1 for a rename"),
2892 /** Return the full path (in some session directory) for a new within-session source.
2893 * \a name must be a session-unique name that does not contain slashes
2894 * (e.g. as returned by new_*_source_name)
2897 Session::new_source_path_from_name (DataType type, const string& name, bool as_stub)
2899 assert(name.find("/") == string::npos);
2901 SessionDirectory sdir(get_best_session_directory_for_new_source());
2904 if (type == DataType::AUDIO) {
2905 p = (as_stub ? sdir.sound_stub_path() : sdir.sound_path());
2906 } else if (type == DataType::MIDI) {
2907 p = (as_stub ? sdir.midi_stub_path() : sdir.midi_path());
2909 error << "Unknown source type, unable to create file path" << endmsg;
2914 return p.to_string();
2918 Session::peak_path (string base) const
2920 sys::path peakfile_path(_session_dir->peak_path());
2921 peakfile_path /= base + peakfile_suffix;
2922 return peakfile_path.to_string();
2925 /** Return a unique name based on \a base for a new internal audio source */
2927 Session::new_audio_source_name (const string& base, uint32_t nchan, uint32_t chan, bool destructive)
2930 char buf[PATH_MAX+1];
2931 const uint32_t limit = 10000;
2933 string ext = native_header_format_extension (config.get_native_file_header_format(), DataType::AUDIO);
2936 legalized = legalize_for_path (base);
2938 // Find a "version" of the base name that doesn't exist in any of the possible directories.
2939 for (cnt = (destructive ? ++destructive_index : 1); cnt <= limit; ++cnt) {
2941 vector<space_and_path>::iterator i;
2942 uint32_t existing = 0;
2944 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
2949 snprintf (buf, sizeof(buf), "T%04d-%s%s",
2950 cnt, legalized.c_str(), ext.c_str());
2951 } else if (nchan == 2) {
2953 snprintf (buf, sizeof(buf), "T%04d-%s%%L%s",
2954 cnt, legalized.c_str(), ext.c_str());
2956 snprintf (buf, sizeof(buf), "T%04d-%s%%R%s",
2957 cnt, legalized.c_str(), ext.c_str());
2959 } else if (nchan < 26) {
2960 snprintf (buf, sizeof(buf), "T%04d-%s%%%c%s",
2961 cnt, legalized.c_str(), 'a' + chan, ext.c_str());
2963 snprintf (buf, sizeof(buf), "T%04d-%s%s",
2964 cnt, legalized.c_str(), ext.c_str());
2970 snprintf (buf, sizeof(buf), "%s-%u%s", legalized.c_str(), cnt, ext.c_str());
2971 } else if (nchan == 2) {
2973 snprintf (buf, sizeof(buf), "%s-%u%%L%s", legalized.c_str(), cnt, ext.c_str());
2975 snprintf (buf, sizeof(buf), "%s-%u%%R%s", legalized.c_str(), cnt, ext.c_str());
2977 } else if (nchan < 26) {
2978 snprintf (buf, sizeof(buf), "%s-%u%%%c%s", legalized.c_str(), cnt, 'a' + chan, ext.c_str());
2980 snprintf (buf, sizeof(buf), "%s-%u%s", legalized.c_str(), cnt, ext.c_str());
2984 SessionDirectory sdir((*i).path);
2986 string spath = sdir.sound_path().to_string();
2987 string spath_stubs = sdir.sound_stub_path().to_string();
2989 /* note that we search *without* the extension so that
2990 we don't end up both "Audio 1-1.wav" and "Audio 1-1.caf"
2991 in the event that this new name is required for
2992 a file format change.
2995 if (matching_unsuffixed_filename_exists_in (spath, buf) ||
2996 matching_unsuffixed_filename_exists_in (spath_stubs, buf)) {
3002 if (existing == 0) {
3007 error << string_compose(
3008 _("There are already %1 recordings for %2, which I consider too many."),
3009 limit, base) << endmsg;
3011 throw failed_constructor();
3015 return Glib::path_get_basename (buf);
3018 /** Create a new within-session audio source */
3019 boost::shared_ptr<AudioFileSource>
3020 Session::create_audio_source_for_session (size_t n_chans, string const & n, uint32_t chan, bool destructive, bool as_stub)
3022 const string name = new_audio_source_name (n, n_chans, chan, destructive);
3023 const string path = new_source_path_from_name(DataType::AUDIO, name, as_stub);
3025 return boost::dynamic_pointer_cast<AudioFileSource> (
3026 SourceFactory::createWritable (DataType::AUDIO, *this, path, string(), destructive, frame_rate()));
3029 /** Return a unique name based on \a base for a new internal MIDI source */
3031 Session::new_midi_source_name (const string& base)
3034 char buf[PATH_MAX+1];
3035 const uint32_t limit = 10000;
3039 legalized = legalize_for_path (base);
3041 // Find a "version" of the file name that doesn't exist in any of the possible directories.
3042 for (cnt = 1; cnt <= limit; ++cnt) {
3044 vector<space_and_path>::iterator i;
3045 uint32_t existing = 0;
3047 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3049 SessionDirectory sdir((*i).path);
3051 sys::path p = sdir.midi_path();
3054 snprintf (buf, sizeof(buf), "%s-%u.mid", p.to_string().c_str(), cnt);
3056 if (sys::exists (buf)) {
3061 if (existing == 0) {
3066 error << string_compose(
3067 _("There are already %1 recordings for %2, which I consider too many."),
3068 limit, base) << endmsg;
3070 throw failed_constructor();
3074 return Glib::path_get_basename(buf);
3078 /** Create a new within-session MIDI source */
3079 boost::shared_ptr<MidiSource>
3080 Session::create_midi_source_for_session (Track* track, string const & n, bool as_stub)
3082 /* try to use the existing write source for the track, to keep numbering sane
3086 /*MidiTrack* mt = dynamic_cast<Track*> (track);
3090 list<boost::shared_ptr<Source> > l = track->steal_write_sources ();
3093 assert (boost::dynamic_pointer_cast<MidiSource> (l.front()));
3094 return boost::dynamic_pointer_cast<MidiSource> (l.front());
3098 const string name = new_midi_source_name (n);
3099 const string path = new_source_path_from_name (DataType::MIDI, name, as_stub);
3101 return boost::dynamic_pointer_cast<SMFSource> (
3102 SourceFactory::createWritable (
3103 DataType::MIDI, *this, path, string(), false, frame_rate()));
3108 Session::add_playlist (boost::shared_ptr<Playlist> playlist, bool unused)
3110 if (playlist->hidden()) {
3114 playlists->add (playlist);
3117 playlist->release();
3124 Session::remove_playlist (boost::weak_ptr<Playlist> weak_playlist)
3126 if (_state_of_the_state & Deletion) {
3130 boost::shared_ptr<Playlist> playlist (weak_playlist.lock());
3136 playlists->remove (playlist);
3142 Session::set_audition (boost::shared_ptr<Region> r)
3144 pending_audition_region = r;
3145 add_post_transport_work (PostTransportAudition);
3146 _butler->schedule_transport_work ();
3150 Session::audition_playlist ()
3152 SessionEvent* ev = new SessionEvent (SessionEvent::Audition, SessionEvent::Add, SessionEvent::Immediate, 0, 0.0);
3153 ev->region.reset ();
3158 Session::non_realtime_set_audition ()
3160 if (!pending_audition_region) {
3161 auditioner->audition_current_playlist ();
3163 auditioner->audition_region (pending_audition_region);
3164 pending_audition_region.reset ();
3166 AuditionActive (true); /* EMIT SIGNAL */
3170 Session::audition_region (boost::shared_ptr<Region> r)
3172 SessionEvent* ev = new SessionEvent (SessionEvent::Audition, SessionEvent::Add, SessionEvent::Immediate, 0, 0.0);
3178 Session::cancel_audition ()
3180 if (auditioner->auditioning()) {
3181 auditioner->cancel_audition ();
3182 AuditionActive (false); /* EMIT SIGNAL */
3187 Session::RoutePublicOrderSorter::operator() (boost::shared_ptr<Route> a, boost::shared_ptr<Route> b)
3189 if (a->is_monitor()) {
3192 if (b->is_monitor()) {
3195 return a->order_key(N_("signal")) < b->order_key(N_("signal"));
3199 Session::is_auditioning () const
3201 /* can be called before we have an auditioner object */
3203 return auditioner->auditioning();
3210 Session::graph_reordered ()
3212 /* don't do this stuff if we are setting up connections
3213 from a set_state() call or creating new tracks. Ditto for deletion.
3216 if (_state_of_the_state & (InitialConnecting|Deletion)) {
3220 /* every track/bus asked for this to be handled but it was deferred because
3221 we were connecting. do it now.
3224 request_input_change_handling ();
3228 /* force all diskstreams to update their capture offset values to
3229 reflect any changes in latencies within the graph.
3232 boost::shared_ptr<RouteList> rl = routes.reader ();
3233 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
3234 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
3236 tr->set_capture_offset ();
3242 Session::available_capture_duration ()
3244 float sample_bytes_on_disk = 4.0; // keep gcc happy
3246 switch (config.get_native_file_data_format()) {
3248 sample_bytes_on_disk = 4.0;
3252 sample_bytes_on_disk = 3.0;
3256 sample_bytes_on_disk = 2.0;
3260 /* impossible, but keep some gcc versions happy */
3261 fatal << string_compose (_("programming error: %1"),
3262 X_("illegal native file data format"))
3267 double scale = 4096.0 / sample_bytes_on_disk;
3269 if (_total_free_4k_blocks * scale > (double) max_framecnt) {
3270 return max_framecnt;
3273 return (framecnt_t) floor (_total_free_4k_blocks * scale);
3277 Session::add_bundle (boost::shared_ptr<Bundle> bundle)
3280 RCUWriter<BundleList> writer (_bundles);
3281 boost::shared_ptr<BundleList> b = writer.get_copy ();
3282 b->push_back (bundle);
3285 BundleAdded (bundle); /* EMIT SIGNAL */
3291 Session::remove_bundle (boost::shared_ptr<Bundle> bundle)
3293 bool removed = false;
3296 RCUWriter<BundleList> writer (_bundles);
3297 boost::shared_ptr<BundleList> b = writer.get_copy ();
3298 BundleList::iterator i = find (b->begin(), b->end(), bundle);
3300 if (i != b->end()) {
3307 BundleRemoved (bundle); /* EMIT SIGNAL */
3313 boost::shared_ptr<Bundle>
3314 Session::bundle_by_name (string name) const
3316 boost::shared_ptr<BundleList> b = _bundles.reader ();
3318 for (BundleList::const_iterator i = b->begin(); i != b->end(); ++i) {
3319 if ((*i)->name() == name) {
3324 return boost::shared_ptr<Bundle> ();
3328 Session::tempo_map_changed (const PropertyChange&)
3332 playlists->update_after_tempo_map_change ();
3334 _locations->apply (*this, &Session::update_locations_after_tempo_map_change);
3340 Session::update_locations_after_tempo_map_change (Locations::LocationList& loc)
3342 for (Locations::LocationList::iterator i = loc.begin(); i != loc.end(); ++i) {
3343 (*i)->recompute_frames_from_bbt ();
3347 /** Ensures that all buffers (scratch, send, silent, etc) are allocated for
3348 * the given count with the current block size.
3351 Session::ensure_buffers (ChanCount howmany)
3353 BufferManager::ensure_buffers (howmany);
3357 Session::ensure_buffer_set(BufferSet& buffers, const ChanCount& count)
3359 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
3360 buffers.ensure_buffers(*t, count.get(*t), _engine.raw_buffer_size(*t));
3365 Session::next_insert_id ()
3367 /* this doesn't really loop forever. just think about it */
3370 for (boost::dynamic_bitset<uint32_t>::size_type n = 0; n < insert_bitset.size(); ++n) {
3371 if (!insert_bitset[n]) {
3372 insert_bitset[n] = true;
3378 /* none available, so resize and try again */
3380 insert_bitset.resize (insert_bitset.size() + 16, false);
3385 Session::next_send_id ()
3387 /* this doesn't really loop forever. just think about it */
3390 for (boost::dynamic_bitset<uint32_t>::size_type n = 0; n < send_bitset.size(); ++n) {
3391 if (!send_bitset[n]) {
3392 send_bitset[n] = true;
3398 /* none available, so resize and try again */
3400 send_bitset.resize (send_bitset.size() + 16, false);
3405 Session::next_return_id ()
3407 /* this doesn't really loop forever. just think about it */
3410 for (boost::dynamic_bitset<uint32_t>::size_type n = 0; n < return_bitset.size(); ++n) {
3411 if (!return_bitset[n]) {
3412 return_bitset[n] = true;
3418 /* none available, so resize and try again */
3420 return_bitset.resize (return_bitset.size() + 16, false);
3425 Session::mark_send_id (uint32_t id)
3427 if (id >= send_bitset.size()) {
3428 send_bitset.resize (id+16, false);
3430 if (send_bitset[id]) {
3431 warning << string_compose (_("send ID %1 appears to be in use already"), id) << endmsg;
3433 send_bitset[id] = true;
3437 Session::mark_return_id (uint32_t id)
3439 if (id >= return_bitset.size()) {
3440 return_bitset.resize (id+16, false);
3442 if (return_bitset[id]) {
3443 warning << string_compose (_("return ID %1 appears to be in use already"), id) << endmsg;
3445 return_bitset[id] = true;
3449 Session::mark_insert_id (uint32_t id)
3451 if (id >= insert_bitset.size()) {
3452 insert_bitset.resize (id+16, false);
3454 if (insert_bitset[id]) {
3455 warning << string_compose (_("insert ID %1 appears to be in use already"), id) << endmsg;
3457 insert_bitset[id] = true;
3461 Session::unmark_send_id (uint32_t id)
3463 if (id < send_bitset.size()) {
3464 send_bitset[id] = false;
3469 Session::unmark_return_id (uint32_t id)
3471 if (id < return_bitset.size()) {
3472 return_bitset[id] = false;
3477 Session::unmark_insert_id (uint32_t id)
3479 if (id < insert_bitset.size()) {
3480 insert_bitset[id] = false;
3485 /* Named Selection management */
3487 boost::shared_ptr<NamedSelection>
3488 Session::named_selection_by_name (string name)
3490 Glib::Mutex::Lock lm (named_selection_lock);
3491 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) {
3492 if ((*i)->name == name) {
3496 return boost::shared_ptr<NamedSelection>();
3500 Session::add_named_selection (boost::shared_ptr<NamedSelection> named_selection)
3503 Glib::Mutex::Lock lm (named_selection_lock);
3504 named_selections.insert (named_selections.begin(), named_selection);
3509 NamedSelectionAdded (); /* EMIT SIGNAL */
3513 Session::remove_named_selection (boost::shared_ptr<NamedSelection> named_selection)
3515 bool removed = false;
3518 Glib::Mutex::Lock lm (named_selection_lock);
3520 NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection);
3522 if (i != named_selections.end()) {
3523 named_selections.erase (i);
3530 NamedSelectionRemoved (); /* EMIT SIGNAL */
3535 Session::reset_native_file_format ()
3537 boost::shared_ptr<RouteList> rl = routes.reader ();
3538 for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
3539 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
3541 /* don't save state as we do this, there's no point
3544 _state_of_the_state = StateOfTheState (_state_of_the_state|InCleanup);
3545 tr->reset_write_sources (false);
3546 _state_of_the_state = StateOfTheState (_state_of_the_state & ~InCleanup);
3552 Session::route_name_unique (string n) const
3554 boost::shared_ptr<RouteList> r = routes.reader ();
3556 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3557 if ((*i)->name() == n) {
3566 Session::route_name_internal (string n) const
3568 if (auditioner && auditioner->name() == n) {
3572 if (_click_io && _click_io->name() == n) {
3580 Session::freeze_all (InterThreadInfo& itt)
3582 boost::shared_ptr<RouteList> r = routes.reader ();
3584 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3586 boost::shared_ptr<Track> t;
3588 if ((t = boost::dynamic_pointer_cast<Track>(*i)) != 0) {
3589 /* XXX this is wrong because itt.progress will keep returning to zero at the start
3599 boost::shared_ptr<Region>
3600 Session::write_one_track (AudioTrack& track, framepos_t start, framepos_t end,
3601 bool /*overwrite*/, vector<boost::shared_ptr<Source> >& srcs,
3602 InterThreadInfo& itt, bool enable_processing)
3604 boost::shared_ptr<Region> result;
3605 boost::shared_ptr<Playlist> playlist;
3606 boost::shared_ptr<AudioFileSource> fsource;
3608 char buf[PATH_MAX+1];
3609 ChanCount diskstream_channels (track.n_channels());
3610 framepos_t position;
3611 framecnt_t this_chunk;
3614 SessionDirectory sdir(get_best_session_directory_for_new_source ());
3615 const string sound_dir = sdir.sound_path().to_string();
3616 framepos_t len = end - start;
3617 bool need_block_size_reset = false;
3619 ChanCount const max_proc = track.max_processor_streams ();
3622 error << string_compose (_("Cannot write a range where end <= start (e.g. %1 <= %2)"),
3623 end, start) << endmsg;
3627 const framecnt_t chunk_size = (256 * 1024)/4;
3629 // block all process callback handling
3631 block_processing ();
3633 /* call tree *MUST* hold route_lock */
3635 if ((playlist = track.playlist()) == 0) {
3639 /* external redirects will be a problem */
3641 if (track.has_external_redirects()) {
3645 ext = native_header_format_extension (config.get_native_file_header_format(), DataType::AUDIO);
3647 for (uint32_t chan_n = 0; chan_n < diskstream_channels.n_audio(); ++chan_n) {
3649 for (x = 0; x < 99999; ++x) {
3650 snprintf (buf, sizeof(buf), "%s/%s-%d-bounce-%" PRIu32 "%s", sound_dir.c_str(), playlist->name().c_str(), chan_n, x+1, ext.c_str());
3651 if (access (buf, F_OK) != 0) {
3657 error << string_compose (_("too many bounced versions of playlist \"%1\""), playlist->name()) << endmsg;
3662 fsource = boost::dynamic_pointer_cast<AudioFileSource> (
3663 SourceFactory::createWritable (DataType::AUDIO, *this, buf, string(), false, frame_rate()));
3666 catch (failed_constructor& err) {
3667 error << string_compose (_("cannot create new audio file \"%1\" for %2"), buf, track.name()) << endmsg;
3671 srcs.push_back (fsource);
3674 /* tell redirects that care that we are about to use a much larger blocksize */
3676 need_block_size_reset = true;
3677 track.set_block_size (chunk_size);
3679 /* XXX need to flush all redirects */
3684 /* create a set of reasonably-sized buffers */
3685 buffers.ensure_buffers (DataType::AUDIO, max_proc.n_audio(), chunk_size);
3686 buffers.set_count (max_proc);
3688 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
3689 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3691 afs->prepare_for_peakfile_writes ();
3694 while (to_do && !itt.cancel) {
3696 this_chunk = min (to_do, chunk_size);
3698 if (track.export_stuff (buffers, start, this_chunk, enable_processing)) {
3703 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) {
3704 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3707 if (afs->write (buffers.get_audio(n).data(), this_chunk) != this_chunk) {
3713 start += this_chunk;
3714 to_do -= this_chunk;
3716 itt.progress = (float) (1.0 - ((double) to_do / len));
3725 xnow = localtime (&now);
3727 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3728 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3731 afs->update_header (position, *xnow, now);
3732 afs->flush_header ();
3736 /* construct a region to represent the bounced material */
3740 plist.add (Properties::start, 0);
3741 plist.add (Properties::length, srcs.front()->length(srcs.front()->timeline_position()));
3742 plist.add (Properties::name, region_name_from_path (srcs.front()->name(), true));
3744 result = RegionFactory::create (srcs, plist);
3750 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
3751 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3754 afs->mark_for_remove ();
3757 (*src)->drop_references ();
3761 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
3762 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3765 afs->done_with_peakfile_writes ();
3770 if (need_block_size_reset) {
3771 track.set_block_size (get_block_size());
3774 unblock_processing ();
3780 Session::gain_automation_buffer() const
3782 return ProcessThread::gain_automation_buffer ();
3786 Session::pan_automation_buffer() const
3788 return ProcessThread::pan_automation_buffer ();
3792 Session::get_silent_buffers (ChanCount count)
3794 return ProcessThread::get_silent_buffers (count);
3796 assert(_silent_buffers->available() >= count);
3797 _silent_buffers->set_count(count);
3799 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
3800 for (size_t i= 0; i < count.get(*t); ++i) {
3801 _silent_buffers->get(*t, i).clear();
3805 return *_silent_buffers;
3810 Session::get_scratch_buffers (ChanCount count)
3812 return ProcessThread::get_scratch_buffers (count);
3814 if (count != ChanCount::ZERO) {
3815 assert(_scratch_buffers->available() >= count);
3816 _scratch_buffers->set_count(count);
3818 _scratch_buffers->set_count (_scratch_buffers->available());
3821 return *_scratch_buffers;
3826 Session::get_mix_buffers (ChanCount count)
3828 return ProcessThread::get_mix_buffers (count);
3830 assert(_mix_buffers->available() >= count);
3831 _mix_buffers->set_count(count);
3832 return *_mix_buffers;
3837 Session::ntracks () const
3840 boost::shared_ptr<RouteList> r = routes.reader ();
3842 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3843 if (boost::dynamic_pointer_cast<Track> (*i)) {
3852 Session::nbusses () const
3855 boost::shared_ptr<RouteList> r = routes.reader ();
3857 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3858 if (boost::dynamic_pointer_cast<Track>(*i) == 0) {
3867 Session::add_automation_list(AutomationList *al)
3869 automation_lists[al->id()] = al;
3873 Session::sync_order_keys (std::string const & base)
3875 if (deletion_in_progress()) {
3879 if (!Config->get_sync_all_route_ordering()) {
3880 /* leave order keys as they are */
3884 boost::shared_ptr<RouteList> r = routes.reader ();
3886 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3887 (*i)->sync_order_keys (base);
3890 Route::SyncOrderKeys (base); // EMIT SIGNAL
3892 /* this might not do anything */
3894 set_remote_control_ids ();
3897 /** @return true if there is at least one record-enabled track, otherwise false */
3899 Session::have_rec_enabled_track () const
3901 return g_atomic_int_get (&_have_rec_enabled_track) == 1;
3904 /** Update the state of our rec-enabled tracks flag */
3906 Session::update_have_rec_enabled_track ()
3908 boost::shared_ptr<RouteList> rl = routes.reader ();
3909 RouteList::iterator i = rl->begin();
3910 while (i != rl->end ()) {
3912 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
3913 if (tr && tr->record_enabled ()) {
3920 int const old = g_atomic_int_get (&_have_rec_enabled_track);
3922 g_atomic_int_set (&_have_rec_enabled_track, i != rl->end () ? 1 : 0);
3924 if (g_atomic_int_get (&_have_rec_enabled_track) != old) {
3925 RecordStateChanged (); /* EMIT SIGNAL */
3930 Session::listen_position_changed ()
3934 switch (Config->get_listen_position()) {
3935 case AfterFaderListen:
3939 case PreFaderListen:
3944 boost::shared_ptr<RouteList> r = routes.reader ();
3946 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3947 (*i)->put_monitor_send_at (p);
3952 Session::solo_control_mode_changed ()
3954 /* cancel all solo or all listen when solo control mode changes */
3957 set_solo (get_routes(), false);
3958 } else if (listening()) {
3959 set_listen (get_routes(), false);
3963 /** Called when anything about any of our route groups changes (membership, state etc.) */
3965 Session::route_group_changed ()
3967 RouteGroupChanged (); /* EMIT SIGNAL */
3971 Session::get_available_sync_options () const
3973 vector<SyncSource> ret;
3975 ret.push_back (JACK);
3976 ret.push_back (MTC);
3977 ret.push_back (MIDIClock);
3982 boost::shared_ptr<RouteList>
3983 Session::get_routes_with_regions_at (framepos_t const p) const
3985 boost::shared_ptr<RouteList> r = routes.reader ();
3986 boost::shared_ptr<RouteList> rl (new RouteList);
3988 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3989 boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*i);
3994 boost::shared_ptr<Playlist> pl = tr->playlist ();
3999 if (pl->has_region_at (p)) {
4008 Session::goto_end ()
4010 if (_session_range_location) {
4011 request_locate (_session_range_location->end(), false);
4013 request_locate (0, false);
4018 Session::goto_start ()
4020 if (_session_range_location) {
4021 request_locate (_session_range_location->start(), false);
4023 request_locate (0, false);
4028 Session::current_start_frame () const
4030 return _session_range_location ? _session_range_location->start() : 0;
4034 Session::current_end_frame () const
4036 return _session_range_location ? _session_range_location->end() : 0;
4040 Session::add_session_range_location (framepos_t start, framepos_t end)
4042 _session_range_location = new Location (*this, start, end, _("session"), Location::IsSessionRange);
4043 _locations->add (_session_range_location);
4046 /** Called when one of our routes' order keys has changed */
4048 Session::route_order_key_changed ()
4050 RouteOrderKeyChanged (); /* EMIT SIGNAL */
4054 Session::step_edit_status_change (bool yn)
4060 send = (_step_editors == 0);
4065 send = (_step_editors == 1);
4068 if (_step_editors > 0) {
4074 StepEditStatusChange (val);
4080 Session::start_time_changed (framepos_t old)
4082 /* Update the auto loop range to match the session range
4083 (unless the auto loop range has been changed by the user)
4086 Location* s = _locations->session_range_location ();
4091 Location* l = _locations->auto_loop_location ();
4093 if (l->start() == old) {
4094 l->set_start (s->start(), true);
4099 Session::end_time_changed (framepos_t old)
4101 /* Update the auto loop range to match the session range
4102 (unless the auto loop range has been changed by the user)
4105 Location* s = _locations->session_range_location ();
4110 Location* l = _locations->auto_loop_location ();
4112 if (l->end() == old) {
4113 l->set_end (s->end(), true);
4118 Session::source_search_path (DataType type) const
4122 if (session_dirs.size() == 1) {
4124 case DataType::AUDIO:
4125 search_path = _session_dir->sound_path().to_string();
4127 case DataType::MIDI:
4128 search_path = _session_dir->midi_path().to_string();
4132 for (vector<space_and_path>::const_iterator i = session_dirs.begin(); i != session_dirs.end(); ++i) {
4133 SessionDirectory sdir (i->path);
4134 if (!search_path.empty()) {
4138 case DataType::AUDIO:
4139 search_path += sdir.sound_path().to_string();
4141 case DataType::MIDI:
4142 search_path += sdir.midi_path().to_string();
4148 /* now add user-specified locations
4151 vector<string> dirs;
4154 case DataType::AUDIO:
4155 split (config.get_audio_search_path (), dirs, ':');
4157 case DataType::MIDI:
4158 split (config.get_midi_search_path (), dirs, ':');
4162 for (vector<string>::iterator i = dirs.begin(); i != dirs.end(); ++i) {
4172 Session::ensure_search_path_includes (const string& path, DataType type)
4175 vector<string> dirs;
4182 case DataType::AUDIO:
4183 search_path = config.get_audio_search_path ();
4185 case DataType::MIDI:
4186 search_path = config.get_midi_search_path ();
4190 split (search_path, dirs, ':');
4192 for (vector<string>::iterator i = dirs.begin(); i != dirs.end(); ++i) {
4198 if (!search_path.empty()) {
4202 search_path += path;
4205 case DataType::AUDIO:
4206 config.set_audio_search_path (search_path);
4208 case DataType::MIDI:
4209 config.set_midi_search_path (search_path);
4215 Session::get_speakers()
4221 Session::unknown_processors () const
4225 boost::shared_ptr<RouteList> r = routes.reader ();
4226 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
4227 list<string> t = (*i)->unknown_processors ();
4228 copy (t.begin(), t.end(), back_inserter (p));
4237 #ifdef HAVE_JACK_NEW_LATENCY
4239 Session::update_latency (bool playback)
4241 DEBUG_TRACE (DEBUG::Latency, "JACK latency callback\n");