2 Copyright (C) 1999-2004 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.
25 #include <cstdio> /* sprintf(3) ... grrr */
31 #include <sigc++/bind.h>
32 #include <sigc++/retype.h>
34 #include <glibmm/thread.h>
35 #include <glibmm/miscutils.h>
37 #include <pbd/error.h>
38 #include <glibmm/thread.h>
39 #include <pbd/pathscanner.h>
40 #include <pbd/stl_delete.h>
41 #include <pbd/basename.h>
42 #include <pbd/stacktrace.h>
44 #include <ardour/audioengine.h>
45 #include <ardour/configuration.h>
46 #include <ardour/session.h>
47 #include <ardour/utils.h>
48 #include <ardour/audio_diskstream.h>
49 #include <ardour/audioplaylist.h>
50 #include <ardour/audioregion.h>
51 #include <ardour/audiofilesource.h>
52 #include <ardour/midi_diskstream.h>
53 #include <ardour/midi_playlist.h>
54 #include <ardour/midi_region.h>
55 #include <ardour/smf_source.h>
56 #include <ardour/auditioner.h>
57 #include <ardour/recent_sessions.h>
58 #include <ardour/redirect.h>
59 #include <ardour/send.h>
60 #include <ardour/insert.h>
61 #include <ardour/connection.h>
62 #include <ardour/slave.h>
63 #include <ardour/tempo.h>
64 #include <ardour/audio_track.h>
65 #include <ardour/midi_track.h>
66 #include <ardour/cycle_timer.h>
67 #include <ardour/named_selection.h>
68 #include <ardour/crossfade.h>
69 #include <ardour/playlist.h>
70 #include <ardour/click.h>
71 #include <ardour/data_type.h>
72 #include <ardour/buffer_set.h>
73 #include <ardour/source_factory.h>
74 #include <ardour/region_factory.h>
77 #include <ardour/osc.h>
83 using namespace ARDOUR;
85 using boost::shared_ptr;
88 static const int CPU_CACHE_ALIGN = 64;
90 static const int CPU_CACHE_ALIGN = 16; /* arguably 32 on most arches, but it matters less */
93 const char* Session::_template_suffix = X_(".template");
94 const char* Session::_statefile_suffix = X_(".ardour");
95 const char* Session::_pending_suffix = X_(".pending");
96 const char* Session::old_sound_dir_name = X_("sounds");
97 const char* Session::sound_dir_name = X_("audiofiles");
98 const char* Session::peak_dir_name = X_("peaks");
99 const char* Session::dead_sound_dir_name = X_("dead_sounds");
100 const char* Session::interchange_dir_name = X_("interchange");
101 const char* Session::export_dir_name = X_("export");
103 sigc::signal<int> Session::AskAboutPendingState;
104 sigc::signal<void> Session::SendFeedback;
106 sigc::signal<void> Session::SMPTEOffsetChanged;
107 sigc::signal<void> Session::StartTimeChanged;
108 sigc::signal<void> Session::EndTimeChanged;
111 Session::find_session (string str, string& path, string& snapshot, bool& isnew)
114 char buf[PATH_MAX+1];
118 if (!realpath (str.c_str(), buf) && (errno != ENOENT && errno != ENOTDIR)) {
119 error << string_compose (_("Could not resolve path: %1 (%2)"), buf, strerror(errno)) << endmsg;
125 /* check to see if it exists, and what it is */
127 if (stat (str.c_str(), &statbuf)) {
128 if (errno == ENOENT) {
131 error << string_compose (_("cannot check session path %1 (%2)"), str, strerror (errno))
139 /* it exists, so it must either be the name
140 of the directory, or the name of the statefile
144 if (S_ISDIR (statbuf.st_mode)) {
146 string::size_type slash = str.find_last_of ('/');
148 if (slash == string::npos) {
150 /* a subdirectory of cwd, so statefile should be ... */
156 tmp += _statefile_suffix;
160 if (stat (tmp.c_str(), &statbuf)) {
161 error << string_compose (_("cannot check statefile %1 (%2)"), tmp, strerror (errno))
171 /* some directory someplace in the filesystem.
172 the snapshot name is the directory name
177 snapshot = str.substr (slash+1);
181 } else if (S_ISREG (statbuf.st_mode)) {
183 string::size_type slash = str.find_last_of ('/');
184 string::size_type suffix;
186 /* remove the suffix */
188 if (slash != string::npos) {
189 snapshot = str.substr (slash+1);
194 suffix = snapshot.find (_statefile_suffix);
196 if (suffix == string::npos) {
197 error << string_compose (_("%1 is not an Ardour snapshot file"), str) << endmsg;
203 snapshot = snapshot.substr (0, suffix);
205 if (slash == string::npos) {
207 /* we must be in the directory where the
208 statefile lives. get it using cwd().
211 char cwd[PATH_MAX+1];
213 if (getcwd (cwd, sizeof (cwd)) == 0) {
214 error << string_compose (_("cannot determine current working directory (%1)"), strerror (errno))
223 /* full path to the statefile */
225 path = str.substr (0, slash);
230 /* what type of file is it? */
231 error << string_compose (_("unknown file type for session %1"), str) << endmsg;
237 /* its the name of a new directory. get the name
241 string::size_type slash = str.find_last_of ('/');
243 if (slash == string::npos) {
245 /* no slash, just use the name, but clean it up */
247 path = legalize_for_path (str);
253 snapshot = str.substr (slash+1);
260 Session::Session (AudioEngine &eng,
262 string snapshot_name,
263 string* mix_template)
266 _scratch_buffers(new BufferSet()),
267 _silent_buffers(new BufferSet()),
268 _send_buffers(new BufferSet()),
269 _mmc_port (default_mmc_port),
270 _mtc_port (default_mtc_port),
271 _midi_port (default_midi_port),
272 pending_events (2048),
273 //midi_requests (128), // the size of this should match the midi request pool size
274 _send_smpte_update (false),
275 diskstreams (new DiskstreamList),
276 routes (new RouteList),
277 auditioner ((Auditioner*) 0),
283 if (!eng.connected()) {
284 throw failed_constructor();
287 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << " (1)" << endl;
289 n_physical_outputs = _engine.n_physical_outputs();
290 n_physical_inputs = _engine.n_physical_inputs();
292 first_stage_init (fullpath, snapshot_name);
294 new_session = !g_file_test (_path.c_str(), GFileTest (G_FILE_TEST_EXISTS | G_FILE_TEST_IS_DIR));
296 if (create (new_session, mix_template, compute_initial_length())) {
297 cerr << "create failed\n";
299 throw failed_constructor ();
303 if (second_stage_init (new_session)) {
305 throw failed_constructor ();
308 store_recent_sessions(_name, _path);
310 bool was_dirty = dirty();
312 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
314 Config->ParameterChanged.connect (mem_fun (*this, &Session::config_changed));
317 DirtyChanged (); /* EMIT SIGNAL */
321 Session::Session (AudioEngine &eng,
323 string snapshot_name,
324 AutoConnectOption input_ac,
325 AutoConnectOption output_ac,
326 uint32_t control_out_channels,
327 uint32_t master_out_channels,
328 uint32_t requested_physical_in,
329 uint32_t requested_physical_out,
330 nframes_t initial_length)
333 _scratch_buffers(new BufferSet()),
334 _silent_buffers(new BufferSet()),
335 _send_buffers(new BufferSet()),
336 _mmc_port (default_mmc_port),
337 _mtc_port (default_mtc_port),
338 _midi_port (default_midi_port),
339 pending_events (2048),
340 //midi_requests (16),
341 _send_smpte_update (false),
342 diskstreams (new DiskstreamList),
343 routes (new RouteList),
349 if (!eng.connected()) {
350 throw failed_constructor();
353 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << " (2)" << endl;
355 n_physical_outputs = _engine.n_physical_outputs();
356 n_physical_inputs = _engine.n_physical_inputs();
358 if (n_physical_inputs) {
359 n_physical_inputs = max (requested_physical_in, n_physical_inputs);
362 if (n_physical_outputs) {
363 n_physical_outputs = max (requested_physical_out, n_physical_outputs);
366 first_stage_init (fullpath, snapshot_name);
368 new_session = !g_file_test (_path.c_str(), GFileTest (G_FILE_TEST_EXISTS | G_FILE_TEST_IS_DIR));
371 if (create (new_session, 0, initial_length)) {
373 throw failed_constructor ();
378 /* set up Master Out and Control Out if necessary */
383 if (control_out_channels) {
384 shared_ptr<Route> r (new Route (*this, _("monitor"), -1, control_out_channels, -1, control_out_channels, Route::ControlOut));
385 r->set_remote_control_id (control_id++);
390 if (master_out_channels) {
391 shared_ptr<Route> r (new Route (*this, _("master"), -1, master_out_channels, -1, master_out_channels, Route::MasterOut));
392 r->set_remote_control_id (control_id);
396 /* prohibit auto-connect to master, because there isn't one */
397 output_ac = AutoConnectOption (output_ac & ~AutoConnectMaster);
406 Config->set_input_auto_connect (input_ac);
407 Config->set_output_auto_connect (output_ac);
409 if (second_stage_init (new_session)) {
411 throw failed_constructor ();
414 store_recent_sessions(_name, _path);
416 bool was_dirty = dirty ();
418 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
420 Config->ParameterChanged.connect (mem_fun (*this, &Session::config_changed));
423 DirtyChanged (); /* EMIT SIGNAL */
435 /* if we got to here, leaving pending capture state around
439 remove_pending_capture_state ();
441 _state_of_the_state = StateOfTheState (CannotSave|Deletion);
442 _engine.remove_session ();
444 GoingAway (); /* EMIT SIGNAL */
450 /* clear history so that no references to objects are held any more */
454 /* clear state tree so that no references to objects are held any more */
460 terminate_butler_thread ();
461 //terminate_midi_thread ();
463 if (click_data && click_data != default_click) {
464 delete [] click_data;
467 if (click_emphasis_data && click_emphasis_data != default_click_emphasis) {
468 delete [] click_emphasis_data;
473 delete _scratch_buffers;
474 delete _silent_buffers;
475 delete _send_buffers;
477 AudioDiskstream::free_working_buffers();
479 #undef TRACK_DESTRUCTION
480 #ifdef TRACK_DESTRUCTION
481 cerr << "delete named selections\n";
482 #endif /* TRACK_DESTRUCTION */
483 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ) {
484 NamedSelectionList::iterator tmp;
493 #ifdef TRACK_DESTRUCTION
494 cerr << "delete playlists\n";
495 #endif /* TRACK_DESTRUCTION */
496 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ) {
497 PlaylistList::iterator tmp;
502 (*i)->drop_references ();
507 for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ) {
508 PlaylistList::iterator tmp;
513 (*i)->drop_references ();
519 unused_playlists.clear ();
521 #ifdef TRACK_DESTRUCTION
522 cerr << "delete regions\n";
523 #endif /* TRACK_DESTRUCTION */
525 for (RegionList::iterator i = regions.begin(); i != regions.end(); ) {
526 RegionList::iterator tmp;
531 i->second->drop_references ();
538 #ifdef TRACK_DESTRUCTION
539 cerr << "delete routes\n";
540 #endif /* TRACK_DESTRUCTION */
542 RCUWriter<RouteList> writer (routes);
543 boost::shared_ptr<RouteList> r = writer.get_copy ();
544 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
545 (*i)->drop_references ();
548 /* writer goes out of scope and updates master */
553 #ifdef TRACK_DESTRUCTION
554 cerr << "delete diskstreams\n";
555 #endif /* TRACK_DESTRUCTION */
557 RCUWriter<DiskstreamList> dwriter (diskstreams);
558 boost::shared_ptr<DiskstreamList> dsl = dwriter.get_copy();
559 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
560 (*i)->drop_references ();
564 diskstreams.flush ();
566 #ifdef TRACK_DESTRUCTION
567 cerr << "delete audio sources\n";
568 #endif /* TRACK_DESTRUCTION */
569 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ) {
570 SourceMap::iterator tmp;
575 i->second->drop_references ();
582 #ifdef TRACK_DESTRUCTION
583 cerr << "delete mix groups\n";
584 #endif /* TRACK_DESTRUCTION */
585 for (list<RouteGroup *>::iterator i = mix_groups.begin(); i != mix_groups.end(); ) {
586 list<RouteGroup*>::iterator tmp;
596 #ifdef TRACK_DESTRUCTION
597 cerr << "delete edit groups\n";
598 #endif /* TRACK_DESTRUCTION */
599 for (list<RouteGroup *>::iterator i = edit_groups.begin(); i != edit_groups.end(); ) {
600 list<RouteGroup*>::iterator tmp;
610 #ifdef TRACK_DESTRUCTION
611 cerr << "delete connections\n";
612 #endif /* TRACK_DESTRUCTION */
613 for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); ) {
614 ConnectionList::iterator tmp;
624 if (butler_mixdown_buffer) {
625 delete [] butler_mixdown_buffer;
628 if (butler_gain_buffer) {
629 delete [] butler_gain_buffer;
632 Crossfade::set_buffer_size (0);
640 Session::set_worst_io_latencies ()
642 _worst_output_latency = 0;
643 _worst_input_latency = 0;
645 if (!_engine.connected()) {
649 boost::shared_ptr<RouteList> r = routes.reader ();
651 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
652 _worst_output_latency = max (_worst_output_latency, (*i)->output_latency());
653 _worst_input_latency = max (_worst_input_latency, (*i)->input_latency());
658 Session::when_engine_running ()
660 string first_physical_output;
662 /* we don't want to run execute this again */
664 set_block_size (_engine.frames_per_cycle());
665 set_frame_rate (_engine.frame_rate());
667 Config->map_parameters (mem_fun (*this, &Session::config_changed));
669 /* every time we reconnect, recompute worst case output latencies */
671 _engine.Running.connect (mem_fun (*this, &Session::set_worst_io_latencies));
673 if (synced_to_jack()) {
674 _engine.transport_stop ();
677 if (Config->get_jack_time_master()) {
678 _engine.transport_locate (_transport_frame);
686 _click_io.reset (new ClickIO (*this, "click", 0, 0, -1, -1));
688 if (state_tree && (child = find_named_node (*state_tree->root(), "Click")) != 0) {
690 /* existing state for Click */
692 if (_click_io->set_state (*child->children().front()) == 0) {
694 _clicking = Config->get_clicking ();
698 error << _("could not setup Click I/O") << endmsg;
704 /* default state for Click */
706 first_physical_output = _engine.get_nth_physical_output (DataType::AUDIO, 0);
708 if (first_physical_output.length()) {
709 if (_click_io->add_output_port (first_physical_output, this)) {
710 // relax, even though its an error
712 _clicking = Config->get_clicking ();
718 catch (failed_constructor& err) {
719 error << _("cannot setup Click I/O") << endmsg;
722 set_worst_io_latencies ();
725 // XXX HOW TO ALERT UI TO THIS ? DO WE NEED TO?
728 /* Create a set of Connection objects that map
729 to the physical outputs currently available
734 for (uint32_t np = 0; np < n_physical_outputs; ++np) {
736 snprintf (buf, sizeof (buf), _("out %" PRIu32), np+1);
738 Connection* c = new OutputConnection (buf, true);
741 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
746 for (uint32_t np = 0; np < n_physical_inputs; ++np) {
748 snprintf (buf, sizeof (buf), _("in %" PRIu32), np+1);
750 Connection* c = new InputConnection (buf, true);
753 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
760 for (uint32_t np = 0; np < n_physical_outputs; np +=2) {
762 snprintf (buf, sizeof (buf), _("out %" PRIu32 "+%" PRIu32), np+1, np+2);
764 Connection* c = new OutputConnection (buf, true);
768 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
769 c->add_connection (1, _engine.get_nth_physical_output (DataType::AUDIO, np+1));
774 for (uint32_t np = 0; np < n_physical_inputs; np +=2) {
776 snprintf (buf, sizeof (buf), _("in %" PRIu32 "+%" PRIu32), np+1, np+2);
778 Connection* c = new InputConnection (buf, true);
782 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
783 c->add_connection (1, _engine.get_nth_physical_input (DataType::AUDIO, np+1));
792 /* create master/control ports */
797 /* force the master to ignore any later call to this */
799 if (_master_out->pending_state_node) {
800 _master_out->ports_became_legal();
803 /* no panner resets till we are through */
805 _master_out->defer_pan_reset ();
807 while (_master_out->n_inputs().get(DataType::AUDIO)
808 < _master_out->input_maximum().get(DataType::AUDIO)) {
809 if (_master_out->add_input_port ("", this, DataType::AUDIO)) {
810 error << _("cannot setup master inputs")
816 while (_master_out->n_outputs().get(DataType::AUDIO)
817 < _master_out->output_maximum().get(DataType::AUDIO)) {
818 if (_master_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this, DataType::AUDIO)) {
819 error << _("cannot setup master outputs")
826 _master_out->allow_pan_reset ();
830 Connection* c = new OutputConnection (_("Master Out"), true);
832 for (uint32_t n = 0; n < _master_out->n_inputs ().get_total(); ++n) {
834 c->add_connection ((int) n, _master_out->input(n)->name());
841 /* catch up on send+insert cnts */
845 for (list<PortInsert*>::iterator i = _port_inserts.begin(); i != _port_inserts.end(); ++i) {
848 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
849 if (id > insert_cnt) {
857 for (list<Send*>::iterator i = _sends.begin(); i != _sends.end(); ++i) {
860 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
868 _state_of_the_state = StateOfTheState (_state_of_the_state & ~(CannotSave|Dirty));
870 /* hook us up to the engine */
872 _engine.set_session (this);
877 osc->set_session (*this);
880 _state_of_the_state = Clean;
882 DirtyChanged (); /* EMIT SIGNAL */
886 Session::hookup_io ()
888 /* stop graph reordering notifications from
889 causing resorts, etc.
892 _state_of_the_state = StateOfTheState (_state_of_the_state | InitialConnecting);
894 if (auditioner == 0) {
896 /* we delay creating the auditioner till now because
897 it makes its own connections to ports.
898 the engine has to be running for this to work.
902 auditioner.reset (new Auditioner (*this));
905 catch (failed_constructor& err) {
906 warning << _("cannot create Auditioner: no auditioning of regions possible") << endmsg;
910 /* Tell all IO objects to create their ports */
917 while (_control_out->n_inputs().get(DataType::AUDIO) < _control_out->input_maximum().get(DataType::AUDIO)) {
918 if (_control_out->add_input_port ("", this)) {
919 error << _("cannot setup control inputs")
925 while (_control_out->n_outputs().get(DataType::AUDIO) < _control_out->output_maximum().get(DataType::AUDIO)) {
926 if (_control_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this)) {
927 error << _("cannot set up master outputs")
935 /* Tell all IO objects to connect themselves together */
937 IO::enable_connecting ();
939 /* Now reset all panners */
941 IO::reset_panners ();
943 /* Anyone who cares about input state, wake up and do something */
945 IOConnectionsComplete (); /* EMIT SIGNAL */
947 _state_of_the_state = StateOfTheState (_state_of_the_state & ~InitialConnecting);
949 /* now handle the whole enchilada as if it was one
955 /* update mixer solo state */
961 Session::playlist_length_changed ()
963 /* we can't just increase end_location->end() if pl->get_maximum_extent()
964 if larger. if the playlist used to be the longest playlist,
965 and its now shorter, we have to decrease end_location->end(). hence,
966 we have to iterate over all diskstreams and check the
967 playlists currently in use.
973 Session::diskstream_playlist_changed (boost::shared_ptr<Diskstream> dstream)
975 boost::shared_ptr<Playlist> playlist;
977 if ((playlist = dstream->playlist()) != 0) {
978 playlist->LengthChanged.connect (mem_fun (this, &Session::playlist_length_changed));
981 /* see comment in playlist_length_changed () */
986 Session::record_enabling_legal () const
988 /* this used to be in here, but survey says.... we don't need to restrict it */
989 // if (record_status() == Recording) {
993 if (Config->get_all_safe()) {
1000 Session::reset_input_monitor_state ()
1002 if (transport_rolling()) {
1004 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1006 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1007 if ((*i)->record_enabled ()) {
1008 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
1009 (*i)->monitor_input (Config->get_monitoring_model() == HardwareMonitoring && !Config->get_auto_input());
1013 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1015 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1016 if ((*i)->record_enabled ()) {
1017 //cerr << "switching to input = " << !Config->get_auto_input() << __FILE__ << __LINE__ << endl << endl;
1018 (*i)->monitor_input (Config->get_monitoring_model() == HardwareMonitoring);
1025 Session::auto_punch_start_changed (Location* location)
1027 replace_event (Event::PunchIn, location->start());
1029 if (get_record_enabled() && Config->get_punch_in()) {
1030 /* capture start has been changed, so save new pending state */
1031 save_state ("", true);
1036 Session::auto_punch_end_changed (Location* location)
1038 nframes_t when_to_stop = location->end();
1039 // when_to_stop += _worst_output_latency + _worst_input_latency;
1040 replace_event (Event::PunchOut, when_to_stop);
1044 Session::auto_punch_changed (Location* location)
1046 nframes_t when_to_stop = location->end();
1048 replace_event (Event::PunchIn, location->start());
1049 //when_to_stop += _worst_output_latency + _worst_input_latency;
1050 replace_event (Event::PunchOut, when_to_stop);
1054 Session::auto_loop_changed (Location* location)
1056 replace_event (Event::AutoLoop, location->end(), location->start());
1058 if (transport_rolling() && play_loop) {
1060 //if (_transport_frame < location->start() || _transport_frame > location->end()) {
1062 if (_transport_frame > location->end()) {
1063 // relocate to beginning of loop
1064 clear_events (Event::LocateRoll);
1066 request_locate (location->start(), true);
1069 else if (Config->get_seamless_loop() && !loop_changing) {
1071 // schedule a locate-roll to refill the diskstreams at the
1072 // previous loop end
1073 loop_changing = true;
1075 if (location->end() > last_loopend) {
1076 clear_events (Event::LocateRoll);
1077 Event *ev = new Event (Event::LocateRoll, Event::Add, last_loopend, last_loopend, 0, true);
1084 last_loopend = location->end();
1089 Session::set_auto_punch_location (Location* location)
1093 if ((existing = _locations.auto_punch_location()) != 0 && existing != location) {
1094 auto_punch_start_changed_connection.disconnect();
1095 auto_punch_end_changed_connection.disconnect();
1096 auto_punch_changed_connection.disconnect();
1097 existing->set_auto_punch (false, this);
1098 remove_event (existing->start(), Event::PunchIn);
1099 clear_events (Event::PunchOut);
1100 auto_punch_location_changed (0);
1105 if (location == 0) {
1109 if (location->end() <= location->start()) {
1110 error << _("Session: you can't use that location for auto punch (start <= end)") << endmsg;
1114 auto_punch_start_changed_connection.disconnect();
1115 auto_punch_end_changed_connection.disconnect();
1116 auto_punch_changed_connection.disconnect();
1118 auto_punch_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_punch_start_changed));
1119 auto_punch_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_punch_end_changed));
1120 auto_punch_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_punch_changed));
1122 location->set_auto_punch (true, this);
1123 auto_punch_location_changed (location);
1127 Session::set_auto_loop_location (Location* location)
1131 if ((existing = _locations.auto_loop_location()) != 0 && existing != location) {
1132 auto_loop_start_changed_connection.disconnect();
1133 auto_loop_end_changed_connection.disconnect();
1134 auto_loop_changed_connection.disconnect();
1135 existing->set_auto_loop (false, this);
1136 remove_event (existing->end(), Event::AutoLoop);
1137 auto_loop_location_changed (0);
1142 if (location == 0) {
1146 if (location->end() <= location->start()) {
1147 error << _("Session: you can't use a mark for auto loop") << endmsg;
1151 last_loopend = location->end();
1153 auto_loop_start_changed_connection.disconnect();
1154 auto_loop_end_changed_connection.disconnect();
1155 auto_loop_changed_connection.disconnect();
1157 auto_loop_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1158 auto_loop_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1159 auto_loop_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_loop_changed));
1161 location->set_auto_loop (true, this);
1162 auto_loop_location_changed (location);
1166 Session::locations_added (Location* ignored)
1172 Session::locations_changed ()
1174 _locations.apply (*this, &Session::handle_locations_changed);
1178 Session::handle_locations_changed (Locations::LocationList& locations)
1180 Locations::LocationList::iterator i;
1182 bool set_loop = false;
1183 bool set_punch = false;
1185 for (i = locations.begin(); i != locations.end(); ++i) {
1189 if (location->is_auto_punch()) {
1190 set_auto_punch_location (location);
1193 if (location->is_auto_loop()) {
1194 set_auto_loop_location (location);
1201 set_auto_loop_location (0);
1204 set_auto_punch_location (0);
1211 Session::enable_record ()
1213 /* XXX really atomic compare+swap here */
1214 if (g_atomic_int_get (&_record_status) != Recording) {
1215 g_atomic_int_set (&_record_status, Recording);
1216 _last_record_location = _transport_frame;
1217 deliver_mmc(MIDI::MachineControl::cmdRecordStrobe, _last_record_location);
1219 if (Config->get_monitoring_model() == HardwareMonitoring && Config->get_auto_input()) {
1220 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1221 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1222 if ((*i)->record_enabled ()) {
1223 (*i)->monitor_input (true);
1228 RecordStateChanged ();
1233 Session::disable_record (bool rt_context, bool force)
1237 if ((rs = (RecordState) g_atomic_int_get (&_record_status)) != Disabled) {
1239 if (!Config->get_latched_record_enable () || force) {
1240 g_atomic_int_set (&_record_status, Disabled);
1242 if (rs == Recording) {
1243 g_atomic_int_set (&_record_status, Enabled);
1247 // FIXME: timestamp correct? [DR]
1248 // FIXME FIXME FIXME: rt_context? this must be called in the process thread.
1249 // does this /need/ to be sent in all cases?
1251 deliver_mmc (MIDI::MachineControl::cmdRecordExit, _transport_frame);
1253 if (Config->get_monitoring_model() == HardwareMonitoring && Config->get_auto_input()) {
1254 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1256 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1257 if ((*i)->record_enabled ()) {
1258 (*i)->monitor_input (false);
1263 RecordStateChanged (); /* emit signal */
1266 remove_pending_capture_state ();
1272 Session::step_back_from_record ()
1274 g_atomic_int_set (&_record_status, Enabled);
1276 if (Config->get_monitoring_model() == HardwareMonitoring) {
1277 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1279 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1280 if (Config->get_auto_input() && (*i)->record_enabled ()) {
1281 //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1282 (*i)->monitor_input (false);
1289 Session::maybe_enable_record ()
1291 g_atomic_int_set (&_record_status, Enabled);
1293 /* this function is currently called from somewhere other than an RT thread.
1294 this save_state() call therefore doesn't impact anything.
1297 save_state ("", true);
1299 if (_transport_speed) {
1300 if (!Config->get_punch_in()) {
1304 deliver_mmc (MIDI::MachineControl::cmdRecordPause, _transport_frame);
1305 RecordStateChanged (); /* EMIT SIGNAL */
1312 Session::audible_frame () const
1318 /* the first of these two possible settings for "offset"
1319 mean that the audible frame is stationary until
1320 audio emerges from the latency compensation
1323 the second means that the audible frame is stationary
1324 until audio would emerge from a physical port
1325 in the absence of any plugin latency compensation
1328 offset = _worst_output_latency;
1330 if (offset > current_block_size) {
1331 offset -= current_block_size;
1333 /* XXX is this correct? if we have no external
1334 physical connections and everything is internal
1335 then surely this is zero? still, how
1336 likely is that anyway?
1338 offset = current_block_size;
1341 if (synced_to_jack()) {
1342 tf = _engine.transport_frame();
1344 tf = _transport_frame;
1347 if (_transport_speed == 0) {
1357 if (!non_realtime_work_pending()) {
1361 /* take latency into account */
1370 Session::set_frame_rate (nframes_t frames_per_second)
1372 /** \fn void Session::set_frame_size(nframes_t)
1373 the AudioEngine object that calls this guarantees
1374 that it will not be called while we are also in
1375 ::process(). Its fine to do things that block
1379 _base_frame_rate = frames_per_second;
1383 Route::set_automation_interval ((nframes_t) ceil ((double) frames_per_second * 0.25));
1385 // XXX we need some equivalent to this, somehow
1386 // SndFileSource::setup_standard_crossfades (frames_per_second);
1390 /* XXX need to reset/reinstantiate all LADSPA plugins */
1394 Session::set_block_size (nframes_t nframes)
1396 /* the AudioEngine guarantees
1397 that it will not be called while we are also in
1398 ::process(). It is therefore fine to do things that block
1404 current_block_size = nframes;
1406 ensure_buffers(_scratch_buffers->available());
1408 if (_gain_automation_buffer) {
1409 delete [] _gain_automation_buffer;
1411 _gain_automation_buffer = new gain_t[nframes];
1413 allocate_pan_automation_buffers (nframes, _npan_buffers, true);
1415 boost::shared_ptr<RouteList> r = routes.reader ();
1417 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1418 (*i)->set_block_size (nframes);
1421 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1422 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1423 (*i)->set_block_size (nframes);
1426 set_worst_io_latencies ();
1431 Session::set_default_fade (float steepness, float fade_msecs)
1434 nframes_t fade_frames;
1436 /* Don't allow fade of less 1 frame */
1438 if (fade_msecs < (1000.0 * (1.0/_current_frame_rate))) {
1445 fade_frames = (nframes_t) floor (fade_msecs * _current_frame_rate * 0.001);
1449 default_fade_msecs = fade_msecs;
1450 default_fade_steepness = steepness;
1453 // jlc, WTF is this!
1454 Glib::RWLock::ReaderLock lm (route_lock);
1455 AudioRegion::set_default_fade (steepness, fade_frames);
1460 /* XXX have to do this at some point */
1461 /* foreach region using default fade, reset, then
1462 refill_all_diskstream_buffers ();
1467 struct RouteSorter {
1468 bool operator() (boost::shared_ptr<Route> r1, boost::shared_ptr<Route> r2) {
1469 if (r1->fed_by.find (r2) != r1->fed_by.end()) {
1471 } else if (r2->fed_by.find (r1) != r2->fed_by.end()) {
1474 if (r1->fed_by.empty()) {
1475 if (r2->fed_by.empty()) {
1476 /* no ardour-based connections inbound to either route. just use signal order */
1477 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1479 /* r2 has connections, r1 does not; run r1 early */
1483 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1490 trace_terminal (shared_ptr<Route> r1, shared_ptr<Route> rbase)
1492 shared_ptr<Route> r2;
1494 if ((r1->fed_by.find (rbase) != r1->fed_by.end()) && (rbase->fed_by.find (r1) != rbase->fed_by.end())) {
1495 info << string_compose(_("feedback loop setup between %1 and %2"), r1->name(), rbase->name()) << endmsg;
1499 /* make a copy of the existing list of routes that feed r1 */
1501 set<shared_ptr<Route> > existing = r1->fed_by;
1503 /* for each route that feeds r1, recurse, marking it as feeding
1507 for (set<shared_ptr<Route> >::iterator i = existing.begin(); i != existing.end(); ++i) {
1510 /* r2 is a route that feeds r1 which somehow feeds base. mark
1511 base as being fed by r2
1514 rbase->fed_by.insert (r2);
1518 /* 2nd level feedback loop detection. if r1 feeds or is fed by r2,
1522 if ((r1->fed_by.find (r2) != r1->fed_by.end()) && (r2->fed_by.find (r1) != r2->fed_by.end())) {
1526 /* now recurse, so that we can mark base as being fed by
1527 all routes that feed r2
1530 trace_terminal (r2, rbase);
1537 Session::resort_routes ()
1539 /* don't do anything here with signals emitted
1540 by Routes while we are being destroyed.
1543 if (_state_of_the_state & Deletion) {
1550 RCUWriter<RouteList> writer (routes);
1551 shared_ptr<RouteList> r = writer.get_copy ();
1552 resort_routes_using (r);
1553 /* writer goes out of scope and forces update */
1558 Session::resort_routes_using (shared_ptr<RouteList> r)
1560 RouteList::iterator i, j;
1562 for (i = r->begin(); i != r->end(); ++i) {
1564 (*i)->fed_by.clear ();
1566 for (j = r->begin(); j != r->end(); ++j) {
1568 /* although routes can feed themselves, it will
1569 cause an endless recursive descent if we
1570 detect it. so don't bother checking for
1578 if ((*j)->feeds (*i)) {
1579 (*i)->fed_by.insert (*j);
1584 for (i = r->begin(); i != r->end(); ++i) {
1585 trace_terminal (*i, *i);
1592 cerr << "finished route resort\n";
1594 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1595 cerr << " " << (*i)->name() << " signal order = " << (*i)->order_key ("signal") << endl;
1602 list<boost::shared_ptr<MidiTrack> >
1603 Session::new_midi_track (TrackMode mode, uint32_t how_many)
1605 char track_name[32];
1606 uint32_t track_id = 0;
1608 uint32_t channels_used = 0;
1610 RouteList new_routes;
1611 list<boost::shared_ptr<MidiTrack> > ret;
1613 /* count existing midi tracks */
1616 shared_ptr<RouteList> r = routes.reader ();
1618 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1619 if (dynamic_cast<MidiTrack*>((*i).get()) != 0) {
1620 if (!(*i)->hidden()) {
1622 channels_used += (*i)->n_inputs().get(DataType::MIDI);
1630 /* check for duplicate route names, since we might have pre-existing
1631 routes with this name (e.g. create Midi1, Midi2, delete Midi1,
1632 save, close,restart,add new route - first named route is now
1640 snprintf (track_name, sizeof(track_name), "Midi %" PRIu32, track_id);
1642 if (route_by_name (track_name) == 0) {
1646 } while (track_id < (UINT_MAX-1));
1649 shared_ptr<MidiTrack> track (new MidiTrack (*this, track_name, Route::Flag (0), mode));
1651 if (track->ensure_io (ChanCount(DataType::MIDI, 1), ChanCount(DataType::MIDI, 1), false, this)) {
1652 error << "cannot configure 1 in/1 out configuration for new midi track" << endmsg;
1655 channels_used += track->n_inputs ().get(DataType::MIDI);
1657 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1658 track->set_remote_control_id (ntracks());
1660 new_routes.push_back (track);
1661 ret.push_back (track);
1664 catch (failed_constructor &err) {
1665 error << _("Session: could not create new midi track.") << endmsg;
1666 // XXX should we delete the tracks already created?
1674 if (!new_routes.empty()) {
1675 add_routes (new_routes, false);
1676 save_state (_current_snapshot_name);
1682 list<boost::shared_ptr<AudioTrack> >
1683 Session::new_audio_track (int input_channels, int output_channels, TrackMode mode, uint32_t how_many)
1685 char track_name[32];
1686 uint32_t track_id = 0;
1688 uint32_t channels_used = 0;
1690 RouteList new_routes;
1691 list<boost::shared_ptr<AudioTrack> > ret;
1692 uint32_t control_id;
1694 /* count existing audio tracks */
1697 shared_ptr<RouteList> r = routes.reader ();
1699 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1700 if (dynamic_cast<AudioTrack*>((*i).get()) != 0) {
1701 if (!(*i)->hidden()) {
1703 channels_used += (*i)->n_inputs().get(DataType::AUDIO);
1709 vector<string> physinputs;
1710 vector<string> physoutputs;
1711 uint32_t nphysical_in;
1712 uint32_t nphysical_out;
1714 _engine.get_physical_outputs (physoutputs);
1715 _engine.get_physical_inputs (physinputs);
1716 control_id = ntracks() + nbusses() + 1;
1720 /* check for duplicate route names, since we might have pre-existing
1721 routes with this name (e.g. create Audio1, Audio2, delete Audio1,
1722 save, close,restart,add new route - first named route is now
1730 snprintf (track_name, sizeof(track_name), "Audio %" PRIu32, track_id);
1732 if (route_by_name (track_name) == 0) {
1736 } while (track_id < (UINT_MAX-1));
1738 if (Config->get_input_auto_connect() & AutoConnectPhysical) {
1739 nphysical_in = min (n_physical_inputs, (uint32_t) physinputs.size());
1744 if (Config->get_output_auto_connect() & AutoConnectPhysical) {
1745 nphysical_out = min (n_physical_outputs, (uint32_t) physinputs.size());
1750 shared_ptr<AudioTrack> track;
1753 track = boost::shared_ptr<AudioTrack>((new AudioTrack (*this, track_name, Route::Flag (0), mode)));
1755 if (track->ensure_io (ChanCount(DataType::AUDIO, input_channels), ChanCount(DataType::AUDIO, output_channels), false, this)) {
1756 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1757 input_channels, output_channels)
1763 for (uint32_t x = 0; x < track->n_inputs().get(DataType::AUDIO) && x < nphysical_in; ++x) {
1767 if (Config->get_input_auto_connect() & AutoConnectPhysical) {
1768 port = physinputs[(channels_used+x)%nphysical_in];
1771 if (port.length() && track->connect_input (track->input (x), port, this)) {
1777 for (uint32_t x = 0; x < track->n_outputs().get(DataType::MIDI); ++x) {
1781 if (nphysical_out && (Config->get_output_auto_connect() & AutoConnectPhysical)) {
1782 port = physoutputs[(channels_used+x)%nphysical_out];
1783 } else if (Config->get_output_auto_connect() & AutoConnectMaster) {
1785 port = _master_out->input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
1789 if (port.length() && track->connect_output (track->output (x), port, this)) {
1794 channels_used += track->n_inputs ().get(DataType::AUDIO);
1797 vector<string> cports;
1798 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
1800 for (n = 0; n < ni; ++n) {
1801 cports.push_back (_control_out->input(n)->name());
1804 track->set_control_outs (cports);
1807 // assert (current_thread != RT_thread)
1809 track->audio_diskstream()->non_realtime_input_change();
1811 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1812 track->set_remote_control_id (control_id);
1815 new_routes.push_back (track);
1816 ret.push_back (track);
1819 catch (failed_constructor &err) {
1820 error << _("Session: could not create new audio track.") << endmsg;
1823 /* we need to get rid of this, since the track failed to be created */
1824 /* XXX arguably, AudioTrack::AudioTrack should not do the Session::add_diskstream() */
1827 RCUWriter<DiskstreamList> writer (diskstreams);
1828 boost::shared_ptr<DiskstreamList> ds = writer.get_copy();
1829 ds->remove (track->audio_diskstream());
1836 catch (AudioEngine::PortRegistrationFailure& pfe) {
1838 error << _("No more JACK ports are available. You will need to stop Ardour and restart JACK with ports if you need this many tracks.") << endmsg;
1841 /* we need to get rid of this, since the track failed to be created */
1842 /* XXX arguably, AudioTrack::AudioTrack should not do the Session::add_diskstream() */
1845 RCUWriter<DiskstreamList> writer (diskstreams);
1846 boost::shared_ptr<DiskstreamList> ds = writer.get_copy();
1847 ds->remove (track->audio_diskstream());
1858 if (!new_routes.empty()) {
1859 add_routes (new_routes, false);
1860 save_state (_current_snapshot_name);
1867 Session::set_remote_control_ids ()
1869 RemoteModel m = Config->get_remote_model();
1871 shared_ptr<RouteList> r = routes.reader ();
1873 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1874 if ( MixerOrdered == m) {
1875 long order = (*i)->order_key(N_("signal"));
1876 (*i)->set_remote_control_id( order+1 );
1877 } else if ( EditorOrdered == m) {
1878 long order = (*i)->order_key(N_("editor"));
1879 (*i)->set_remote_control_id( order+1 );
1880 } else if ( UserOrdered == m) {
1881 //do nothing ... only changes to remote id's are initiated by user
1888 Session::new_audio_route (int input_channels, int output_channels, uint32_t how_many)
1891 uint32_t bus_id = 1;
1895 uint32_t control_id;
1897 /* count existing audio busses */
1900 shared_ptr<RouteList> r = routes.reader ();
1902 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1903 if (dynamic_cast<AudioTrack*>((*i).get()) == 0) {
1904 if (!(*i)->hidden() && (*i)->name() != _("master")) {
1911 vector<string> physinputs;
1912 vector<string> physoutputs;
1914 _engine.get_physical_outputs (physoutputs);
1915 _engine.get_physical_inputs (physinputs);
1916 control_id = ntracks() + nbusses() + 1;
1921 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, bus_id);
1923 if (route_by_name (bus_name) == 0) {
1927 } while (++bus_id < (UINT_MAX-1));
1930 shared_ptr<Route> bus (new Route (*this, bus_name, -1, -1, -1, -1, Route::Flag(0), DataType::AUDIO));
1932 if (bus->ensure_io (ChanCount(DataType::AUDIO, input_channels), ChanCount(DataType::AUDIO, output_channels), false, this)) {
1933 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1934 input_channels, output_channels)
1939 for (uint32_t x = 0; n_physical_inputs && x < bus->n_inputs().get(DataType::AUDIO); ++x) {
1943 if (Config->get_input_auto_connect() & AutoConnectPhysical) {
1944 port = physinputs[((n+x)%n_physical_inputs)];
1947 if (port.length() && bus->connect_input (bus->input (x), port, this)) {
1952 for (uint32_t x = 0; n_physical_outputs && x < bus->n_outputs().get(DataType::AUDIO); ++x) {
1956 if (Config->get_output_auto_connect() & AutoConnectPhysical) {
1957 port = physoutputs[((n+x)%n_physical_outputs)];
1958 } else if (Config->get_output_auto_connect() & AutoConnectMaster) {
1960 port = _master_out->input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
1964 if (port.length() && bus->connect_output (bus->output (x), port, this)) {
1970 vector<string> cports;
1971 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
1973 for (uint32_t n = 0; n < ni; ++n) {
1974 cports.push_back (_control_out->input(n)->name());
1976 bus->set_control_outs (cports);
1979 bus->set_remote_control_id (control_id);
1982 ret.push_back (bus);
1986 catch (failed_constructor &err) {
1987 error << _("Session: could not create new audio route.") << endmsg;
1991 catch (AudioEngine::PortRegistrationFailure& pfe) {
1992 error << _("No more JACK ports are available. You will need to stop Ardour and restart JACK with ports if you need this many tracks.") << endmsg;
2002 add_routes (ret, false);
2003 save_state (_current_snapshot_name);
2011 Session::add_routes (RouteList& new_routes, bool save)
2014 RCUWriter<RouteList> writer (routes);
2015 shared_ptr<RouteList> r = writer.get_copy ();
2016 r->insert (r->end(), new_routes.begin(), new_routes.end());
2017 resort_routes_using (r);
2020 for (RouteList::iterator x = new_routes.begin(); x != new_routes.end(); ++x) {
2022 boost::weak_ptr<Route> wpr (*x);
2024 (*x)->solo_changed.connect (sigc::bind (mem_fun (*this, &Session::route_solo_changed), wpr));
2025 (*x)->mute_changed.connect (mem_fun (*this, &Session::route_mute_changed));
2026 (*x)->output_changed.connect (mem_fun (*this, &Session::set_worst_io_latencies_x));
2027 (*x)->redirects_changed.connect (mem_fun (*this, &Session::update_latency_compensation_proxy));
2029 if ((*x)->master()) {
2033 if ((*x)->control()) {
2034 _control_out = (*x);
2041 save_state (_current_snapshot_name);
2044 RouteAdded (new_routes); /* EMIT SIGNAL */
2048 Session::add_diskstream (boost::shared_ptr<Diskstream> dstream)
2050 /* need to do this in case we're rolling at the time, to prevent false underruns */
2051 dstream->do_refill_with_alloc ();
2053 dstream->set_block_size (current_block_size);
2056 RCUWriter<DiskstreamList> writer (diskstreams);
2057 boost::shared_ptr<DiskstreamList> ds = writer.get_copy();
2058 ds->push_back (dstream);
2059 /* writer goes out of scope, copies ds back to main */
2062 dstream->PlaylistChanged.connect (sigc::bind (mem_fun (*this, &Session::diskstream_playlist_changed), dstream));
2063 /* this will connect to future changes, and check the current length */
2064 diskstream_playlist_changed (dstream);
2066 dstream->prepare ();
2071 Session::remove_route (shared_ptr<Route> route)
2074 RCUWriter<RouteList> writer (routes);
2075 shared_ptr<RouteList> rs = writer.get_copy ();
2079 /* deleting the master out seems like a dumb
2080 idea, but its more of a UI policy issue
2084 if (route == _master_out) {
2085 _master_out = shared_ptr<Route> ();
2088 if (route == _control_out) {
2089 _control_out = shared_ptr<Route> ();
2091 /* cancel control outs for all routes */
2093 vector<string> empty;
2095 for (RouteList::iterator r = rs->begin(); r != rs->end(); ++r) {
2096 (*r)->set_control_outs (empty);
2100 update_route_solo_state ();
2102 /* writer goes out of scope, forces route list update */
2106 boost::shared_ptr<Diskstream> ds;
2108 if ((t = dynamic_cast<Track*>(route.get())) != 0) {
2109 ds = t->diskstream();
2115 RCUWriter<DiskstreamList> dsl (diskstreams);
2116 boost::shared_ptr<DiskstreamList> d = dsl.get_copy();
2121 find_current_end ();
2123 update_latency_compensation (false, false);
2126 // We need to disconnect the routes inputs and outputs
2127 route->disconnect_inputs(NULL);
2128 route->disconnect_outputs(NULL);
2130 /* get rid of it from the dead wood collection in the route list manager */
2132 /* XXX i think this is unsafe as it currently stands, but i am not sure. (pd, october 2nd, 2006) */
2136 /* try to cause everyone to drop their references */
2138 route->drop_references ();
2140 /* save the new state of the world */
2142 if (save_state (_current_snapshot_name)) {
2143 save_history (_current_snapshot_name);
2148 Session::route_mute_changed (void* src)
2154 Session::route_solo_changed (void* src, boost::weak_ptr<Route> wpr)
2156 if (solo_update_disabled) {
2162 boost::shared_ptr<Route> route = wpr.lock ();
2165 /* should not happen */
2166 error << string_compose (_("programming error: %1"), X_("invalid route weak ptr passed to route_solo_changed")) << endmsg;
2170 is_track = (boost::dynamic_pointer_cast<AudioTrack>(route) != 0);
2172 shared_ptr<RouteList> r = routes.reader ();
2174 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2176 /* soloing a track mutes all other tracks, soloing a bus mutes all other busses */
2180 /* don't mess with busses */
2182 if (dynamic_cast<Track*>((*i).get()) == 0) {
2188 /* don't mess with tracks */
2190 if (dynamic_cast<Track*>((*i).get()) != 0) {
2195 if ((*i) != route &&
2196 ((*i)->mix_group () == 0 ||
2197 (*i)->mix_group () != route->mix_group () ||
2198 !route->mix_group ()->is_active())) {
2200 if ((*i)->soloed()) {
2202 /* if its already soloed, and solo latching is enabled,
2203 then leave it as it is.
2206 if (Config->get_solo_latched()) {
2213 solo_update_disabled = true;
2214 (*i)->set_solo (false, src);
2215 solo_update_disabled = false;
2219 bool something_soloed = false;
2220 bool same_thing_soloed = false;
2221 bool signal = false;
2223 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2224 if ((*i)->soloed()) {
2225 something_soloed = true;
2226 if (dynamic_cast<Track*>((*i).get())) {
2228 same_thing_soloed = true;
2233 same_thing_soloed = true;
2241 if (something_soloed != currently_soloing) {
2243 currently_soloing = something_soloed;
2246 modify_solo_mute (is_track, same_thing_soloed);
2249 SoloActive (currently_soloing); /* EMIT SIGNAL */
2252 SoloChanged (); /* EMIT SIGNAL */
2258 Session::update_route_solo_state ()
2261 bool is_track = false;
2262 bool signal = false;
2264 /* caller must hold RouteLock */
2266 /* this is where we actually implement solo by changing
2267 the solo mute setting of each track.
2270 shared_ptr<RouteList> r = routes.reader ();
2272 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2273 if ((*i)->soloed()) {
2275 if (dynamic_cast<Track*>((*i).get())) {
2282 if (mute != currently_soloing) {
2284 currently_soloing = mute;
2287 if (!is_track && !mute) {
2289 /* nothing is soloed */
2291 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2292 (*i)->set_solo_mute (false);
2302 modify_solo_mute (is_track, mute);
2305 SoloActive (currently_soloing);
2310 Session::modify_solo_mute (bool is_track, bool mute)
2312 shared_ptr<RouteList> r = routes.reader ();
2314 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2318 /* only alter track solo mute */
2320 if (dynamic_cast<Track*>((*i).get())) {
2321 if ((*i)->soloed()) {
2322 (*i)->set_solo_mute (!mute);
2324 (*i)->set_solo_mute (mute);
2330 /* only alter bus solo mute */
2332 if (!dynamic_cast<Track*>((*i).get())) {
2334 if ((*i)->soloed()) {
2336 (*i)->set_solo_mute (false);
2340 /* don't mute master or control outs
2341 in response to another bus solo
2344 if ((*i) != _master_out &&
2345 (*i) != _control_out) {
2346 (*i)->set_solo_mute (mute);
2357 Session::catch_up_on_solo ()
2359 /* this is called after set_state() to catch the full solo
2360 state, which can't be correctly determined on a per-route
2361 basis, but needs the global overview that only the session
2364 update_route_solo_state();
2368 Session::route_by_name (string name)
2370 shared_ptr<RouteList> r = routes.reader ();
2372 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2373 if ((*i)->name() == name) {
2378 return shared_ptr<Route> ((Route*) 0);
2382 Session::route_by_id (PBD::ID id)
2384 shared_ptr<RouteList> r = routes.reader ();
2386 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2387 if ((*i)->id() == id) {
2392 return shared_ptr<Route> ((Route*) 0);
2396 Session::route_by_remote_id (uint32_t id)
2398 shared_ptr<RouteList> r = routes.reader ();
2400 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2401 if ((*i)->remote_control_id() == id) {
2406 return shared_ptr<Route> ((Route*) 0);
2410 Session::find_current_end ()
2412 if (_state_of_the_state & Loading) {
2416 nframes_t max = get_maximum_extent ();
2418 if (max > end_location->end()) {
2419 end_location->set_end (max);
2421 DurationChanged(); /* EMIT SIGNAL */
2426 Session::get_maximum_extent () const
2431 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2433 for (DiskstreamList::const_iterator i = dsl->begin(); i != dsl->end(); ++i) {
2434 boost::shared_ptr<Playlist> pl = (*i)->playlist();
2435 if ((me = pl->get_maximum_extent()) > max) {
2443 boost::shared_ptr<Diskstream>
2444 Session::diskstream_by_name (string name)
2446 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2448 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2449 if ((*i)->name() == name) {
2454 return boost::shared_ptr<Diskstream>((Diskstream*) 0);
2457 boost::shared_ptr<Diskstream>
2458 Session::diskstream_by_id (const PBD::ID& id)
2460 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2462 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2463 if ((*i)->id() == id) {
2468 return boost::shared_ptr<Diskstream>((Diskstream*) 0);
2471 /* Region management */
2474 Session::new_region_name (string old)
2476 string::size_type last_period;
2478 string::size_type len = old.length() + 64;
2481 if ((last_period = old.find_last_of ('.')) == string::npos) {
2483 /* no period present - add one explicitly */
2486 last_period = old.length() - 1;
2491 number = atoi (old.substr (last_period+1).c_str());
2495 while (number < (UINT_MAX-1)) {
2497 RegionList::const_iterator i;
2502 snprintf (buf, len, "%s%" PRIu32, old.substr (0, last_period + 1).c_str(), number);
2505 for (i = regions.begin(); i != regions.end(); ++i) {
2506 if (i->second->name() == sbuf) {
2511 if (i == regions.end()) {
2516 if (number != (UINT_MAX-1)) {
2520 error << string_compose (_("cannot create new name for region \"%1\""), old) << endmsg;
2525 Session::region_name (string& result, string base, bool newlevel) const
2530 assert(base.find("/") == string::npos);
2534 Glib::Mutex::Lock lm (region_lock);
2536 snprintf (buf, sizeof (buf), "%d", (int)regions.size() + 1);
2544 /* XXX this is going to be slow. optimize me later */
2549 string::size_type pos;
2551 pos = base.find_last_of ('.');
2553 /* pos may be npos, but then we just use entire base */
2555 subbase = base.substr (0, pos);
2559 bool name_taken = true;
2562 Glib::Mutex::Lock lm (region_lock);
2564 for (int n = 1; n < 5000; ++n) {
2567 snprintf (buf, sizeof (buf), ".%d", n);
2572 for (RegionList::const_iterator i = regions.begin(); i != regions.end(); ++i) {
2573 if (i->second->name() == result) {
2586 fatal << string_compose(_("too many regions with names like %1"), base) << endmsg;
2594 Session::add_region (boost::shared_ptr<Region> region)
2596 boost::shared_ptr<Region> other;
2600 Glib::Mutex::Lock lm (region_lock);
2602 RegionList::iterator x;
2604 for (x = regions.begin(); x != regions.end(); ++x) {
2608 if (region->region_list_equivalent (other)) {
2613 if (x == regions.end()) {
2615 pair<RegionList::key_type,RegionList::mapped_type> entry;
2617 entry.first = region->id();
2618 entry.second = region;
2620 pair<RegionList::iterator,bool> x = regions.insert (entry);
2632 /* mark dirty because something has changed even if we didn't
2633 add the region to the region list.
2639 region->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_region), boost::weak_ptr<Region>(region)));
2640 region->StateChanged.connect (sigc::bind (mem_fun (*this, &Session::region_changed), boost::weak_ptr<Region>(region)));
2641 RegionAdded (region); /* EMIT SIGNAL */
2646 Session::region_changed (Change what_changed, boost::weak_ptr<Region> weak_region)
2648 boost::shared_ptr<Region> region (weak_region.lock ());
2654 if (what_changed & Region::HiddenChanged) {
2655 /* relay hidden changes */
2656 RegionHiddenChange (region);
2661 Session::remove_region (boost::weak_ptr<Region> weak_region)
2663 RegionList::iterator i;
2664 boost::shared_ptr<Region> region (weak_region.lock ());
2670 bool removed = false;
2673 Glib::Mutex::Lock lm (region_lock);
2675 if ((i = regions.find (region->id())) != regions.end()) {
2681 /* mark dirty because something has changed even if we didn't
2682 remove the region from the region list.
2688 RegionRemoved(region); /* EMIT SIGNAL */
2692 boost::shared_ptr<Region>
2693 Session::find_whole_file_parent (boost::shared_ptr<Region const> child)
2695 RegionList::iterator i;
2696 boost::shared_ptr<Region> region;
2698 Glib::Mutex::Lock lm (region_lock);
2700 for (i = regions.begin(); i != regions.end(); ++i) {
2704 if (region->whole_file()) {
2706 if (child->source_equivalent (region)) {
2712 return boost::shared_ptr<Region> ();
2716 Session::find_equivalent_playlist_regions (boost::shared_ptr<Region> region, vector<boost::shared_ptr<Region> >& result)
2718 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i)
2719 (*i)->get_region_list_equivalent_regions (region, result);
2723 Session::destroy_region (boost::shared_ptr<Region> region)
2725 vector<boost::shared_ptr<Source> > srcs;
2728 boost::shared_ptr<AudioRegion> aregion;
2730 if ((aregion = boost::dynamic_pointer_cast<AudioRegion> (region)) == 0) {
2734 if (aregion->playlist()) {
2735 aregion->playlist()->destroy_region (region);
2738 for (uint32_t n = 0; n < aregion->n_channels(); ++n) {
2739 srcs.push_back (aregion->source (n));
2743 region->drop_references ();
2745 for (vector<boost::shared_ptr<Source> >::iterator i = srcs.begin(); i != srcs.end(); ++i) {
2747 if (!(*i)->used()) {
2748 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*i);
2751 (afs)->mark_for_remove ();
2754 (*i)->drop_references ();
2756 cerr << "source was not used by any playlist\n";
2764 Session::destroy_regions (list<boost::shared_ptr<Region> > regions)
2766 for (list<boost::shared_ptr<Region> >::iterator i = regions.begin(); i != regions.end(); ++i) {
2767 destroy_region (*i);
2773 Session::remove_last_capture ()
2775 list<boost::shared_ptr<Region> > r;
2777 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2779 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2780 list<boost::shared_ptr<Region> >& l = (*i)->last_capture_regions();
2783 r.insert (r.end(), l.begin(), l.end());
2788 destroy_regions (r);
2790 save_state (_current_snapshot_name);
2796 Session::remove_region_from_region_list (boost::shared_ptr<Region> r)
2802 /* Source Management */
2804 Session::add_source (boost::shared_ptr<Source> source)
2806 pair<SourceMap::key_type, SourceMap::mapped_type> entry;
2807 pair<SourceMap::iterator,bool> result;
2809 entry.first = source->id();
2810 entry.second = source;
2813 Glib::Mutex::Lock lm (source_lock);
2814 result = sources.insert (entry);
2817 if (result.second) {
2818 source->GoingAway.connect (sigc::bind (mem_fun (this, &Session::remove_source), boost::weak_ptr<Source> (source)));
2824 Session::remove_source (boost::weak_ptr<Source> src)
2826 SourceMap::iterator i;
2827 boost::shared_ptr<Source> source = src.lock();
2834 Glib::Mutex::Lock lm (source_lock);
2837 Glib::Mutex::Lock lm (source_lock);
2839 if ((i = sources.find (source->id())) != sources.end()) {
2845 if (!_state_of_the_state & InCleanup) {
2847 /* save state so we don't end up with a session file
2848 referring to non-existent sources.
2851 save_state (_current_snapshot_name);
2855 boost::shared_ptr<Source>
2856 Session::source_by_id (const PBD::ID& id)
2858 Glib::Mutex::Lock lm (source_lock);
2859 SourceMap::iterator i;
2860 boost::shared_ptr<Source> source;
2862 if ((i = sources.find (id)) != sources.end()) {
2866 /* XXX search MIDI or other searches here */
2872 boost::shared_ptr<Source>
2873 Session::source_by_path_and_channel (const Glib::ustring& path, uint16_t chn)
2875 Glib::Mutex::Lock lm (source_lock);
2877 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ++i) {
2878 cerr << "comparing " << path << " with " << i->second->name() << endl;
2879 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(i->second);
2881 if (afs && afs->path() == path && chn == afs->channel()) {
2886 return boost::shared_ptr<Source>();
2890 Session::peak_path_from_audio_path (string audio_path) const
2895 res += PBD::basename_nosuffix (audio_path);
2902 Session::change_audio_path_by_name (string path, string oldname, string newname, bool destructive)
2905 string old_basename = PBD::basename_nosuffix (oldname);
2906 string new_legalized = legalize_for_path (newname);
2908 /* note: we know (or assume) the old path is already valid */
2912 /* destructive file sources have a name of the form:
2914 /path/to/Tnnnn-NAME(%[LR])?.wav
2916 the task here is to replace NAME with the new name.
2919 /* find last slash */
2923 string::size_type slash;
2924 string::size_type dash;
2926 if ((slash = path.find_last_of ('/')) == string::npos) {
2930 dir = path.substr (0, slash+1);
2932 /* '-' is not a legal character for the NAME part of the path */
2934 if ((dash = path.find_last_of ('-')) == string::npos) {
2938 prefix = path.substr (slash+1, dash-(slash+1));
2943 path += new_legalized;
2944 path += ".wav"; /* XXX gag me with a spoon */
2948 /* non-destructive file sources have a name of the form:
2950 /path/to/NAME-nnnnn(%[LR])?.wav
2952 the task here is to replace NAME with the new name.
2957 string::size_type slash;
2958 string::size_type dash;
2959 string::size_type postfix;
2961 /* find last slash */
2963 if ((slash = path.find_last_of ('/')) == string::npos) {
2967 dir = path.substr (0, slash+1);
2969 /* '-' is not a legal character for the NAME part of the path */
2971 if ((dash = path.find_last_of ('-')) == string::npos) {
2975 suffix = path.substr (dash+1);
2977 // Suffix is now everything after the dash. Now we need to eliminate
2978 // the nnnnn part, which is done by either finding a '%' or a '.'
2980 postfix = suffix.find_last_of ("%");
2981 if (postfix == string::npos) {
2982 postfix = suffix.find_last_of ('.');
2985 if (postfix != string::npos) {
2986 suffix = suffix.substr (postfix);
2988 error << "Logic error in Session::change_audio_path_by_name(), please report to the developers" << endl;
2992 const uint32_t limit = 10000;
2993 char buf[PATH_MAX+1];
2995 for (uint32_t cnt = 1; cnt <= limit; ++cnt) {
2997 snprintf (buf, sizeof(buf), "%s%s-%u%s", dir.c_str(), newname.c_str(), cnt, suffix.c_str());
2999 if (access (buf, F_OK) != 0) {
3007 error << "FATAL ERROR! Could not find a " << endl;
3016 Session::audio_path_from_name (string name, uint32_t nchan, uint32_t chan, bool destructive)
3020 char buf[PATH_MAX+1];
3021 const uint32_t limit = 10000;
3025 legalized = legalize_for_path (name);
3027 /* find a "version" of the file name that doesn't exist in
3028 any of the possible directories.
3031 for (cnt = (destructive ? ++destructive_index : 1); cnt <= limit; ++cnt) {
3033 vector<space_and_path>::iterator i;
3034 uint32_t existing = 0;
3036 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3040 spath += sound_dir (false);
3044 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3045 } else if (nchan == 2) {
3047 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%L.wav", spath.c_str(), cnt, legalized.c_str());
3049 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%R.wav", spath.c_str(), cnt, legalized.c_str());
3051 } else if (nchan < 26) {
3052 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%%c.wav", spath.c_str(), cnt, legalized.c_str(), 'a' + chan);
3054 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3063 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3064 } else if (nchan == 2) {
3066 snprintf (buf, sizeof(buf), "%s-%u%%L.wav", spath.c_str(), cnt);
3068 snprintf (buf, sizeof(buf), "%s-%u%%R.wav", spath.c_str(), cnt);
3070 } else if (nchan < 26) {
3071 snprintf (buf, sizeof(buf), "%s-%u%%%c.wav", spath.c_str(), cnt, 'a' + chan);
3073 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3077 if (g_file_test (buf, G_FILE_TEST_EXISTS)) {
3083 if (existing == 0) {
3088 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3090 throw failed_constructor();
3094 /* we now have a unique name for the file, but figure out where to
3100 spath = discover_best_sound_dir ();
3103 string::size_type pos = foo.find_last_of ('/');
3105 if (pos == string::npos) {
3108 spath += foo.substr (pos + 1);
3114 boost::shared_ptr<AudioFileSource>
3115 Session::create_audio_source_for_session (AudioDiskstream& ds, uint32_t chan, bool destructive)
3117 string spath = audio_path_from_name (ds.name(), ds.n_channels().get(DataType::AUDIO), chan, destructive);
3118 return boost::dynamic_pointer_cast<AudioFileSource> (
3119 SourceFactory::createWritable (DataType::AUDIO, *this, spath, destructive, frame_rate()));
3122 // FIXME: _terrible_ code duplication
3124 Session::change_midi_path_by_name (string path, string oldname, string newname, bool destructive)
3127 string old_basename = PBD::basename_nosuffix (oldname);
3128 string new_legalized = legalize_for_path (newname);
3130 /* note: we know (or assume) the old path is already valid */
3134 /* destructive file sources have a name of the form:
3136 /path/to/Tnnnn-NAME(%[LR])?.wav
3138 the task here is to replace NAME with the new name.
3141 /* find last slash */
3145 string::size_type slash;
3146 string::size_type dash;
3148 if ((slash = path.find_last_of ('/')) == string::npos) {
3152 dir = path.substr (0, slash+1);
3154 /* '-' is not a legal character for the NAME part of the path */
3156 if ((dash = path.find_last_of ('-')) == string::npos) {
3160 prefix = path.substr (slash+1, dash-(slash+1));
3165 path += new_legalized;
3166 path += ".mid"; /* XXX gag me with a spoon */
3170 /* non-destructive file sources have a name of the form:
3172 /path/to/NAME-nnnnn(%[LR])?.wav
3174 the task here is to replace NAME with the new name.
3179 string::size_type slash;
3180 string::size_type dash;
3181 string::size_type postfix;
3183 /* find last slash */
3185 if ((slash = path.find_last_of ('/')) == string::npos) {
3189 dir = path.substr (0, slash+1);
3191 /* '-' is not a legal character for the NAME part of the path */
3193 if ((dash = path.find_last_of ('-')) == string::npos) {
3197 suffix = path.substr (dash+1);
3199 // Suffix is now everything after the dash. Now we need to eliminate
3200 // the nnnnn part, which is done by either finding a '%' or a '.'
3202 postfix = suffix.find_last_of ("%");
3203 if (postfix == string::npos) {
3204 postfix = suffix.find_last_of ('.');
3207 if (postfix != string::npos) {
3208 suffix = suffix.substr (postfix);
3210 error << "Logic error in Session::change_midi_path_by_name(), please report to the developers" << endl;
3214 const uint32_t limit = 10000;
3215 char buf[PATH_MAX+1];
3217 for (uint32_t cnt = 1; cnt <= limit; ++cnt) {
3219 snprintf (buf, sizeof(buf), "%s%s-%u%s", dir.c_str(), newname.c_str(), cnt, suffix.c_str());
3221 if (access (buf, F_OK) != 0) {
3229 error << "FATAL ERROR! Could not find a " << endl;
3238 Session::midi_path_from_name (string name)
3242 char buf[PATH_MAX+1];
3243 const uint32_t limit = 10000;
3247 legalized = legalize_for_path (name);
3249 /* find a "version" of the file name that doesn't exist in
3250 any of the possible directories.
3253 for (cnt = 1; cnt <= limit; ++cnt) {
3255 vector<space_and_path>::iterator i;
3256 uint32_t existing = 0;
3258 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3262 // FIXME: different directory from audio?
3263 spath += sound_dir(false) + "/" + legalized;
3265 snprintf (buf, sizeof(buf), "%s-%u.mid", spath.c_str(), cnt);
3267 if (g_file_test (buf, G_FILE_TEST_EXISTS)) {
3272 if (existing == 0) {
3277 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3278 throw failed_constructor();
3282 /* we now have a unique name for the file, but figure out where to
3288 // FIXME: different directory than audio?
3289 spath = discover_best_sound_dir ();
3292 string::size_type pos = foo.find_last_of ('/');
3294 if (pos == string::npos) {
3297 spath += foo.substr (pos + 1);
3303 boost::shared_ptr<MidiSource>
3304 Session::create_midi_source_for_session (MidiDiskstream& ds)
3306 string spath = midi_path_from_name (ds.name());
3308 return boost::dynamic_pointer_cast<SMFSource> (SourceFactory::createWritable (DataType::MIDI, *this, spath, false, frame_rate()));
3312 /* Playlist management */
3314 boost::shared_ptr<Playlist>
3315 Session::playlist_by_name (string name)
3317 Glib::Mutex::Lock lm (playlist_lock);
3318 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3319 if ((*i)->name() == name) {
3323 for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ++i) {
3324 if ((*i)->name() == name) {
3329 return boost::shared_ptr<Playlist>();
3333 Session::add_playlist (boost::shared_ptr<Playlist> playlist)
3335 if (playlist->hidden()) {
3340 Glib::Mutex::Lock lm (playlist_lock);
3341 if (find (playlists.begin(), playlists.end(), playlist) == playlists.end()) {
3342 playlists.insert (playlists.begin(), playlist);
3343 playlist->InUse.connect (sigc::bind (mem_fun (*this, &Session::track_playlist), boost::weak_ptr<Playlist>(playlist)));
3344 playlist->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_playlist), boost::weak_ptr<Playlist>(playlist)));
3350 PlaylistAdded (playlist); /* EMIT SIGNAL */
3354 Session::get_playlists (vector<boost::shared_ptr<Playlist> >& s)
3357 Glib::Mutex::Lock lm (playlist_lock);
3358 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3361 for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ++i) {
3368 Session::track_playlist (bool inuse, boost::weak_ptr<Playlist> wpl)
3370 boost::shared_ptr<Playlist> pl(wpl.lock());
3376 PlaylistList::iterator x;
3379 /* its not supposed to be visible */
3384 Glib::Mutex::Lock lm (playlist_lock);
3388 unused_playlists.insert (pl);
3390 if ((x = playlists.find (pl)) != playlists.end()) {
3391 playlists.erase (x);
3397 playlists.insert (pl);
3399 if ((x = unused_playlists.find (pl)) != unused_playlists.end()) {
3400 unused_playlists.erase (x);
3407 Session::remove_playlist (boost::weak_ptr<Playlist> weak_playlist)
3409 if (_state_of_the_state & Deletion) {
3413 boost::shared_ptr<Playlist> playlist (weak_playlist.lock());
3420 Glib::Mutex::Lock lm (playlist_lock);
3422 PlaylistList::iterator i;
3424 i = find (playlists.begin(), playlists.end(), playlist);
3425 if (i != playlists.end()) {
3426 playlists.erase (i);
3429 i = find (unused_playlists.begin(), unused_playlists.end(), playlist);
3430 if (i != unused_playlists.end()) {
3431 unused_playlists.erase (i);
3438 PlaylistRemoved (playlist); /* EMIT SIGNAL */
3442 Session::set_audition (boost::shared_ptr<Region> r)
3444 pending_audition_region = r;
3445 post_transport_work = PostTransportWork (post_transport_work | PostTransportAudition);
3446 schedule_butler_transport_work ();
3450 Session::audition_playlist ()
3452 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3453 ev->region.reset ();
3458 Session::non_realtime_set_audition ()
3460 if (!pending_audition_region) {
3461 auditioner->audition_current_playlist ();
3463 auditioner->audition_region (pending_audition_region);
3464 pending_audition_region.reset ();
3466 AuditionActive (true); /* EMIT SIGNAL */
3470 Session::audition_region (boost::shared_ptr<Region> r)
3472 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3478 Session::cancel_audition ()
3480 if (auditioner->active()) {
3481 auditioner->cancel_audition ();
3482 AuditionActive (false); /* EMIT SIGNAL */
3487 Session::RoutePublicOrderSorter::operator() (boost::shared_ptr<Route> a, boost::shared_ptr<Route> b)
3489 return a->order_key(N_("signal")) < b->order_key(N_("signal"));
3493 Session::remove_empty_sounds ()
3495 PathScanner scanner;
3497 vector<string *>* possible_audiofiles = scanner (sound_dir(), "\\.(wav|aiff|caf|w64)$", false, true);
3499 Glib::Mutex::Lock lm (source_lock);
3501 regex_t compiled_tape_track_pattern;
3504 if ((err = regcomp (&compiled_tape_track_pattern, "/T[0-9][0-9][0-9][0-9]-", REG_EXTENDED|REG_NOSUB))) {
3508 regerror (err, &compiled_tape_track_pattern, msg, sizeof (msg));
3510 error << string_compose (_("Cannot compile tape track regexp for use (%1)"), msg) << endmsg;
3514 for (vector<string *>::iterator i = possible_audiofiles->begin(); i != possible_audiofiles->end(); ++i) {
3516 /* never remove files that appear to be a tape track */
3518 if (regexec (&compiled_tape_track_pattern, (*i)->c_str(), 0, 0, 0) == 0) {
3523 if (AudioFileSource::is_empty (*this, *(*i))) {
3525 unlink ((*i)->c_str());
3527 string peak_path = peak_path_from_audio_path (**i);
3528 unlink (peak_path.c_str());
3534 delete possible_audiofiles;
3538 Session::is_auditioning () const
3540 /* can be called before we have an auditioner object */
3542 return auditioner->active();
3549 Session::set_all_solo (bool yn)
3551 shared_ptr<RouteList> r = routes.reader ();
3553 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3554 if (!(*i)->hidden()) {
3555 (*i)->set_solo (yn, this);
3563 Session::set_all_mute (bool yn)
3565 shared_ptr<RouteList> r = routes.reader ();
3567 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3568 if (!(*i)->hidden()) {
3569 (*i)->set_mute (yn, this);
3577 Session::n_diskstreams () const
3581 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3583 for (DiskstreamList::const_iterator i = dsl->begin(); i != dsl->end(); ++i) {
3584 if (!(*i)->hidden()) {
3592 Session::graph_reordered ()
3594 /* don't do this stuff if we are setting up connections
3595 from a set_state() call or creating new tracks.
3598 if (_state_of_the_state & InitialConnecting) {
3602 /* every track/bus asked for this to be handled but it was deferred because
3603 we were connecting. do it now.
3606 request_input_change_handling ();
3610 /* force all diskstreams to update their capture offset values to
3611 reflect any changes in latencies within the graph.
3614 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3616 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
3617 (*i)->set_capture_offset ();
3622 Session::record_disenable_all ()
3624 record_enable_change_all (false);
3628 Session::record_enable_all ()
3630 record_enable_change_all (true);
3634 Session::record_enable_change_all (bool yn)
3636 shared_ptr<RouteList> r = routes.reader ();
3638 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3641 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
3642 at->set_record_enable (yn, this);
3646 /* since we don't keep rec-enable state, don't mark session dirty */
3650 Session::add_redirect (Redirect* redirect)
3654 PortInsert* port_insert;
3655 PluginInsert* plugin_insert;
3657 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3658 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3659 _port_inserts.insert (_port_inserts.begin(), port_insert);
3660 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3661 _plugin_inserts.insert (_plugin_inserts.begin(), plugin_insert);
3663 fatal << _("programming error: unknown type of Insert created!") << endmsg;
3666 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3667 _sends.insert (_sends.begin(), send);
3669 fatal << _("programming error: unknown type of Redirect created!") << endmsg;
3673 redirect->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_redirect), redirect));
3679 Session::remove_redirect (Redirect* redirect)
3683 PortInsert* port_insert;
3684 PluginInsert* plugin_insert;
3686 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3687 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3688 list<PortInsert*>::iterator x = find (_port_inserts.begin(), _port_inserts.end(), port_insert);
3689 if (x != _port_inserts.end()) {
3690 insert_bitset[port_insert->bit_slot()] = false;
3691 _port_inserts.erase (x);
3693 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3694 _plugin_inserts.remove (plugin_insert);
3696 fatal << string_compose (_("programming error: %1"),
3697 X_("unknown type of Insert deleted!"))
3701 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3702 list<Send*>::iterator x = find (_sends.begin(), _sends.end(), send);
3703 if (x != _sends.end()) {
3704 send_bitset[send->bit_slot()] = false;
3708 fatal << _("programming error: unknown type of Redirect deleted!") << endmsg;
3716 Session::available_capture_duration ()
3718 float sample_bytes_on_disk = 4.0; // keep gcc happy
3720 switch (Config->get_native_file_data_format()) {
3722 sample_bytes_on_disk = 4.0;
3726 sample_bytes_on_disk = 3.0;
3730 /* impossible, but keep some gcc versions happy */
3731 fatal << string_compose (_("programming error: %1"),
3732 X_("illegal native file data format"))
3737 double scale = 4096.0 / sample_bytes_on_disk;
3739 if (_total_free_4k_blocks * scale > (double) max_frames) {
3743 return (nframes_t) floor (_total_free_4k_blocks * scale);
3747 Session::add_connection (ARDOUR::Connection* connection)
3750 Glib::Mutex::Lock guard (connection_lock);
3751 _connections.push_back (connection);
3754 ConnectionAdded (connection); /* EMIT SIGNAL */
3760 Session::remove_connection (ARDOUR::Connection* connection)
3762 bool removed = false;
3765 Glib::Mutex::Lock guard (connection_lock);
3766 ConnectionList::iterator i = find (_connections.begin(), _connections.end(), connection);
3768 if (i != _connections.end()) {
3769 _connections.erase (i);
3775 ConnectionRemoved (connection); /* EMIT SIGNAL */
3781 ARDOUR::Connection *
3782 Session::connection_by_name (string name) const
3784 Glib::Mutex::Lock lm (connection_lock);
3786 for (ConnectionList::const_iterator i = _connections.begin(); i != _connections.end(); ++i) {
3787 if ((*i)->name() == name) {
3796 Session::tempo_map_changed (Change ignored)
3802 /** Ensures that all buffers (scratch, send, silent, etc) are allocated for
3803 * the given count with the current block size.
3806 Session::ensure_buffers (ChanCount howmany)
3808 // FIXME: NASTY assumption (midi block size == audio block size)
3809 _scratch_buffers->ensure_buffers(howmany, current_block_size);
3810 _send_buffers->ensure_buffers(howmany, current_block_size);
3811 _silent_buffers->ensure_buffers(howmany, current_block_size);
3813 allocate_pan_automation_buffers (current_block_size, howmany.get(DataType::AUDIO), false);
3817 Session::next_insert_id ()
3819 /* this doesn't really loop forever. just think about it */
3822 for (boost::dynamic_bitset<uint32_t>::size_type n = 0; n < insert_bitset.size(); ++n) {
3823 if (!insert_bitset[n]) {
3824 insert_bitset[n] = true;
3830 /* none available, so resize and try again */
3832 insert_bitset.resize (insert_bitset.size() + 16, false);
3837 Session::next_send_id ()
3839 /* this doesn't really loop forever. just think about it */
3842 for (boost::dynamic_bitset<uint32_t>::size_type n = 0; n < send_bitset.size(); ++n) {
3843 if (!send_bitset[n]) {
3844 send_bitset[n] = true;
3850 /* none available, so resize and try again */
3852 send_bitset.resize (send_bitset.size() + 16, false);
3857 Session::mark_send_id (uint32_t id)
3859 if (id >= send_bitset.size()) {
3860 send_bitset.resize (id+16, false);
3862 if (send_bitset[id]) {
3863 warning << string_compose (_("send ID %1 appears to be in use already"), id) << endmsg;
3865 send_bitset[id] = true;
3869 Session::mark_insert_id (uint32_t id)
3871 if (id >= insert_bitset.size()) {
3872 insert_bitset.resize (id+16, false);
3874 if (insert_bitset[id]) {
3875 warning << string_compose (_("insert ID %1 appears to be in use already"), id) << endmsg;
3877 insert_bitset[id] = true;
3880 /* Named Selection management */
3883 Session::named_selection_by_name (string name)
3885 Glib::Mutex::Lock lm (named_selection_lock);
3886 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) {
3887 if ((*i)->name == name) {
3895 Session::add_named_selection (NamedSelection* named_selection)
3898 Glib::Mutex::Lock lm (named_selection_lock);
3899 named_selections.insert (named_selections.begin(), named_selection);
3902 for (list<boost::shared_ptr<Playlist> >::iterator i = named_selection->playlists.begin(); i != named_selection->playlists.end(); ++i) {
3908 NamedSelectionAdded (); /* EMIT SIGNAL */
3912 Session::remove_named_selection (NamedSelection* named_selection)
3914 bool removed = false;
3917 Glib::Mutex::Lock lm (named_selection_lock);
3919 NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection);
3921 if (i != named_selections.end()) {
3923 named_selections.erase (i);
3930 NamedSelectionRemoved (); /* EMIT SIGNAL */
3935 Session::reset_native_file_format ()
3937 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3939 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
3940 (*i)->reset_write_sources (false);
3945 Session::route_name_unique (string n) const
3947 shared_ptr<RouteList> r = routes.reader ();
3949 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3950 if ((*i)->name() == n) {
3959 Session::n_playlists () const
3961 Glib::Mutex::Lock lm (playlist_lock);
3962 return playlists.size();
3966 Session::allocate_pan_automation_buffers (nframes_t nframes, uint32_t howmany, bool force)
3968 if (!force && howmany <= _npan_buffers) {
3972 if (_pan_automation_buffer) {
3974 for (uint32_t i = 0; i < _npan_buffers; ++i) {
3975 delete [] _pan_automation_buffer[i];
3978 delete [] _pan_automation_buffer;
3981 _pan_automation_buffer = new pan_t*[howmany];
3983 for (uint32_t i = 0; i < howmany; ++i) {
3984 _pan_automation_buffer[i] = new pan_t[nframes];
3987 _npan_buffers = howmany;
3991 Session::freeze (InterThreadInfo& itt)
3993 shared_ptr<RouteList> r = routes.reader ();
3995 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3999 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
4000 /* XXX this is wrong because itt.progress will keep returning to zero at the start
4011 Session::write_one_audio_track (AudioTrack& track, nframes_t start, nframes_t len,
4012 bool overwrite, vector<boost::shared_ptr<Source> >& srcs, InterThreadInfo& itt)
4015 boost::shared_ptr<Playlist> playlist;
4016 boost::shared_ptr<AudioFileSource> fsource;
4018 char buf[PATH_MAX+1];
4020 ChanCount nchans(track.audio_diskstream()->n_channels());
4022 nframes_t this_chunk;
4026 // any bigger than this seems to cause stack overflows in called functions
4027 const nframes_t chunk_size = (128 * 1024)/4;
4029 g_atomic_int_set (&processing_prohibited, 1);
4031 /* call tree *MUST* hold route_lock */
4033 if ((playlist = track.diskstream()->playlist()) == 0) {
4037 /* external redirects will be a problem */
4039 if (track.has_external_redirects()) {
4043 dir = discover_best_sound_dir ();
4045 for (uint32_t chan_n=0; chan_n < nchans.get(DataType::AUDIO); ++chan_n) {
4047 for (x = 0; x < 99999; ++x) {
4048 snprintf (buf, sizeof(buf), "%s/%s-%d-bounce-%" PRIu32 ".wav", dir.c_str(), playlist->name().c_str(), chan_n, x+1);
4049 if (access (buf, F_OK) != 0) {
4055 error << string_compose (_("too many bounced versions of playlist \"%1\""), playlist->name()) << endmsg;
4060 fsource = boost::dynamic_pointer_cast<AudioFileSource> (
4061 SourceFactory::createWritable (DataType::AUDIO, *this, buf, false, frame_rate()));
4064 catch (failed_constructor& err) {
4065 error << string_compose (_("cannot create new audio file \"%1\" for %2"), buf, track.name()) << endmsg;
4069 srcs.push_back (fsource);
4072 /* XXX need to flush all redirects */
4077 /* create a set of reasonably-sized buffers */
4078 buffers.ensure_buffers(nchans, chunk_size);
4079 buffers.set_count(nchans);
4081 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src) {
4082 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4084 afs->prepare_for_peakfile_writes ();
4087 while (to_do && !itt.cancel) {
4089 this_chunk = min (to_do, chunk_size);
4091 if (track.export_stuff (buffers, start, this_chunk)) {
4096 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) {
4097 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4100 if (afs->write (buffers.get_audio(n).data(), this_chunk) != this_chunk) {
4106 start += this_chunk;
4107 to_do -= this_chunk;
4109 itt.progress = (float) (1.0 - ((double) to_do / len));
4118 xnow = localtime (&now);
4120 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src) {
4121 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4124 afs->update_header (position, *xnow, now);
4125 afs->flush_header ();
4129 /* construct a region to represent the bounced material */
4131 boost::shared_ptr<Region> aregion = RegionFactory::create (srcs, 0, srcs.front()->length(),
4132 region_name_from_path (srcs.front()->name(), true));
4139 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
4140 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4143 afs->mark_for_remove ();
4146 (*src)->drop_references ();
4150 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
4151 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4154 afs->done_with_peakfile_writes ();
4158 g_atomic_int_set (&processing_prohibited, 0);
4166 Session::get_silent_buffers (ChanCount count)
4168 assert(_silent_buffers->available() >= count);
4169 _silent_buffers->set_count(count);
4171 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
4172 for (size_t i=0; i < count.get(*t); ++i) {
4173 _silent_buffers->get(*t, i).clear();
4177 return *_silent_buffers;
4181 Session::get_scratch_buffers (ChanCount count)
4183 assert(_scratch_buffers->available() >= count);
4184 _scratch_buffers->set_count(count);
4185 return *_scratch_buffers;
4189 Session::get_send_buffers (ChanCount count)
4191 assert(_send_buffers->available() >= count);
4192 _send_buffers->set_count(count);
4193 return *_send_buffers;
4197 Session::ntracks () const
4200 shared_ptr<RouteList> r = routes.reader ();
4202 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
4203 if (dynamic_cast<Track*> ((*i).get())) {
4212 Session::nbusses () const
4215 shared_ptr<RouteList> r = routes.reader ();
4217 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
4218 if (dynamic_cast<Track*> ((*i).get()) == 0) {
4227 Session::add_automation_list(AutomationList *al)
4229 automation_lists[al->id()] = al;
4233 Session::compute_initial_length ()
4235 return _engine.frame_rate() * 60 * 5;