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.
26 #include <cstdio> /* sprintf(3) ... grrr */
32 #include <sigc++/bind.h>
33 #include <sigc++/retype.h>
35 #include <glibmm/thread.h>
36 #include <glibmm/miscutils.h>
38 #include <pbd/error.h>
39 #include <glibmm/thread.h>
40 #include <pbd/pathscanner.h>
41 #include <pbd/stl_delete.h>
42 #include <pbd/basename.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/destructive_filesource.h>
57 #include <ardour/auditioner.h>
58 #include <ardour/recent_sessions.h>
59 #include <ardour/redirect.h>
60 #include <ardour/send.h>
61 #include <ardour/insert.h>
62 #include <ardour/connection.h>
63 #include <ardour/slave.h>
64 #include <ardour/tempo.h>
65 #include <ardour/audio_track.h>
66 #include <ardour/midi_track.h>
67 #include <ardour/cycle_timer.h>
68 #include <ardour/named_selection.h>
69 #include <ardour/crossfade.h>
70 #include <ardour/playlist.h>
71 #include <ardour/click.h>
72 #include <ardour/data_type.h>
73 #include <ardour/buffer_set.h>
76 #include <ardour/osc.h>
82 using namespace ARDOUR;
84 using boost::shared_ptr;
86 const char* Session::_template_suffix = X_(".template");
87 const char* Session::_statefile_suffix = X_(".ardour");
88 const char* Session::_pending_suffix = X_(".pending");
89 const char* Session::sound_dir_name = X_("sounds");
90 const char* Session::tape_dir_name = X_("tapes");
91 const char* Session::peak_dir_name = X_("peaks");
92 const char* Session::dead_sound_dir_name = X_("dead_sounds");
94 Session::compute_peak_t Session::compute_peak = 0;
95 Session::apply_gain_to_buffer_t Session::apply_gain_to_buffer = 0;
96 Session::mix_buffers_with_gain_t Session::mix_buffers_with_gain = 0;
97 Session::mix_buffers_no_gain_t Session::mix_buffers_no_gain = 0;
99 sigc::signal<int> Session::AskAboutPendingState;
100 sigc::signal<void> Session::SMPTEOffsetChanged;
101 sigc::signal<void> Session::SendFeedback;
105 Session::find_session (string str, string& path, string& snapshot, bool& isnew)
108 char buf[PATH_MAX+1];
112 if (!realpath (str.c_str(), buf) && (errno != ENOENT && errno != ENOTDIR)) {
113 error << string_compose (_("Could not resolve path: %1 (%2)"), buf, strerror(errno)) << endmsg;
119 /* check to see if it exists, and what it is */
121 if (stat (str.c_str(), &statbuf)) {
122 if (errno == ENOENT) {
125 error << string_compose (_("cannot check session path %1 (%2)"), str, strerror (errno))
133 /* it exists, so it must either be the name
134 of the directory, or the name of the statefile
138 if (S_ISDIR (statbuf.st_mode)) {
140 string::size_type slash = str.find_last_of ('/');
142 if (slash == string::npos) {
144 /* a subdirectory of cwd, so statefile should be ... */
150 tmp += _statefile_suffix;
154 if (stat (tmp.c_str(), &statbuf)) {
155 error << string_compose (_("cannot check statefile %1 (%2)"), tmp, strerror (errno))
165 /* some directory someplace in the filesystem.
166 the snapshot name is the directory name
171 snapshot = str.substr (slash+1);
175 } else if (S_ISREG (statbuf.st_mode)) {
177 string::size_type slash = str.find_last_of ('/');
178 string::size_type suffix;
180 /* remove the suffix */
182 if (slash != string::npos) {
183 snapshot = str.substr (slash+1);
188 suffix = snapshot.find (_statefile_suffix);
190 if (suffix == string::npos) {
191 error << string_compose (_("%1 is not an Ardour snapshot file"), str) << endmsg;
197 snapshot = snapshot.substr (0, suffix);
199 if (slash == string::npos) {
201 /* we must be in the directory where the
202 statefile lives. get it using cwd().
205 char cwd[PATH_MAX+1];
207 if (getcwd (cwd, sizeof (cwd)) == 0) {
208 error << string_compose (_("cannot determine current working directory (%1)"), strerror (errno))
217 /* full path to the statefile */
219 path = str.substr (0, slash);
224 /* what type of file is it? */
225 error << string_compose (_("unknown file type for session %1"), str) << endmsg;
231 /* its the name of a new directory. get the name
235 string::size_type slash = str.find_last_of ('/');
237 if (slash == string::npos) {
239 /* no slash, just use the name, but clean it up */
241 path = legalize_for_path (str);
247 snapshot = str.substr (slash+1);
254 Session::Session (AudioEngine &eng,
256 string snapshot_name,
257 string* mix_template)
260 _scratch_buffers(new BufferSet()),
261 _silent_buffers(new BufferSet()),
262 _send_buffers(new BufferSet()),
263 _mmc_port (default_mmc_port),
264 _mtc_port (default_mtc_port),
265 _midi_port (default_midi_port),
266 pending_events (2048),
267 //midi_requests (128), // the size of this should match the midi request pool size
268 _send_smpte_update (false),
269 routes (new RouteList),
270 auditioner ((Auditioner*) 0),
276 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << endl;
278 n_physical_outputs = _engine.n_physical_outputs();
279 n_physical_inputs = _engine.n_physical_inputs();
281 first_stage_init (fullpath, snapshot_name);
283 if (create (new_session, mix_template, _engine.frame_rate() * 60 * 5)) {
284 throw failed_constructor ();
287 if (second_stage_init (new_session)) {
288 throw failed_constructor ();
291 store_recent_sessions(_name, _path);
293 bool was_dirty = dirty();
295 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
298 DirtyChanged (); /* EMIT SIGNAL */
302 Session::Session (AudioEngine &eng,
304 string snapshot_name,
305 AutoConnectOption input_ac,
306 AutoConnectOption output_ac,
307 uint32_t control_out_channels,
308 uint32_t master_out_channels,
309 uint32_t requested_physical_in,
310 uint32_t requested_physical_out,
311 jack_nframes_t initial_length)
314 _scratch_buffers(new BufferSet()),
315 _silent_buffers(new BufferSet()),
316 _send_buffers(new BufferSet()),
317 _mmc_port (default_mmc_port),
318 _mtc_port (default_mtc_port),
319 _midi_port (default_midi_port),
320 pending_events (2048),
321 //midi_requests (16),
322 _send_smpte_update (false),
323 routes (new RouteList),
329 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << endl;
331 n_physical_outputs = max (requested_physical_out, _engine.n_physical_outputs());
332 n_physical_inputs = max (requested_physical_in, _engine.n_physical_inputs());
334 first_stage_init (fullpath, snapshot_name);
336 if (create (new_session, 0, initial_length)) {
337 throw failed_constructor ();
340 if (control_out_channels) {
341 shared_ptr<Route> r (new Route (*this, _("monitor"), -1, control_out_channels, -1, control_out_channels, Route::ControlOut));
346 if (master_out_channels) {
347 shared_ptr<Route> r (new Route (*this, _("master"), -1, master_out_channels, -1, master_out_channels, Route::MasterOut));
351 /* prohibit auto-connect to master, because there isn't one */
352 output_ac = AutoConnectOption (output_ac & ~AutoConnectMaster);
355 input_auto_connect = input_ac;
356 output_auto_connect = output_ac;
358 if (second_stage_init (new_session)) {
359 throw failed_constructor ();
362 store_recent_sessions(_name, _path);
364 bool was_dirty = dirty ();
366 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
369 DirtyChanged (); /* EMIT SIGNAL */
375 /* if we got to here, leaving pending capture state around
379 remove_pending_capture_state ();
381 _state_of_the_state = StateOfTheState (CannotSave|Deletion);
382 _engine.remove_session ();
384 going_away (); /* EMIT SIGNAL */
386 terminate_butler_thread ();
387 //terminate_midi_thread ();
389 if (click_data && click_data != default_click) {
390 delete [] click_data;
393 if (click_emphasis_data && click_emphasis_data != default_click_emphasis) {
394 delete [] click_emphasis_data;
399 delete _scratch_buffers;
400 delete _silent_buffers;
401 delete _send_buffers;
403 AudioDiskstream::free_working_buffers();
405 #undef TRACK_DESTRUCTION
406 #ifdef TRACK_DESTRUCTION
407 cerr << "delete named selections\n";
408 #endif /* TRACK_DESTRUCTION */
409 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ) {
410 NamedSelectionList::iterator tmp;
419 #ifdef TRACK_DESTRUCTION
420 cerr << "delete playlists\n";
421 #endif /* TRACK_DESTRUCTION */
422 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ) {
423 PlaylistList::iterator tmp;
433 #ifdef TRACK_DESTRUCTION
434 cerr << "delete regions\n";
435 #endif /* TRACK_DESTRUCTION */
436 for (RegionList::iterator i = regions.begin(); i != regions.end(); ) {
437 RegionList::iterator tmp;
447 #ifdef TRACK_DESTRUCTION
448 cerr << "delete diskstreams\n";
449 #endif /* TRACK_DESTRUCTION */
450 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ) {
451 DiskstreamList::iterator tmp;
461 #ifdef TRACK_DESTRUCTION
462 cerr << "delete audio sources\n";
463 #endif /* TRACK_DESTRUCTION */
464 for (SourceList::iterator i = sources.begin(); i != sources.end(); ) {
465 SourceList::iterator tmp;
475 #ifdef TRACK_DESTRUCTION
476 cerr << "delete mix groups\n";
477 #endif /* TRACK_DESTRUCTION */
478 for (list<RouteGroup *>::iterator i = mix_groups.begin(); i != mix_groups.end(); ) {
479 list<RouteGroup*>::iterator tmp;
489 #ifdef TRACK_DESTRUCTION
490 cerr << "delete edit groups\n";
491 #endif /* TRACK_DESTRUCTION */
492 for (list<RouteGroup *>::iterator i = edit_groups.begin(); i != edit_groups.end(); ) {
493 list<RouteGroup*>::iterator tmp;
503 #ifdef TRACK_DESTRUCTION
504 cerr << "delete connections\n";
505 #endif /* TRACK_DESTRUCTION */
506 for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); ) {
507 ConnectionList::iterator tmp;
517 if (butler_mixdown_buffer) {
518 delete [] butler_mixdown_buffer;
521 if (butler_gain_buffer) {
522 delete [] butler_gain_buffer;
525 Crossfade::set_buffer_size (0);
537 Session::set_worst_io_latencies ()
539 _worst_output_latency = 0;
540 _worst_input_latency = 0;
542 if (!_engine.connected()) {
546 boost::shared_ptr<RouteList> r = routes.reader ();
548 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
549 _worst_output_latency = max (_worst_output_latency, (*i)->output_latency());
550 _worst_input_latency = max (_worst_input_latency, (*i)->input_latency());
555 Session::when_engine_running ()
557 string first_physical_output;
559 /* we don't want to run execute this again */
561 first_time_running.disconnect ();
563 set_block_size (_engine.frames_per_cycle());
564 set_frame_rate (_engine.frame_rate());
566 /* every time we reconnect, recompute worst case output latencies */
568 _engine.Running.connect (mem_fun (*this, &Session::set_worst_io_latencies));
570 if (synced_to_jack()) {
571 _engine.transport_stop ();
574 if (Config->get_jack_time_master()) {
575 _engine.transport_locate (_transport_frame);
583 _click_io.reset (new ClickIO (*this, "click", 0, 0, -1, -1));
585 if (state_tree && (child = find_named_node (*state_tree->root(), "Click")) != 0) {
587 /* existing state for Click */
589 if (_click_io->set_state (*child->children().front()) == 0) {
591 _clicking = click_requested;
595 error << _("could not setup Click I/O") << endmsg;
601 /* default state for Click */
603 first_physical_output = _engine.get_nth_physical_output (DataType::AUDIO, 0);
605 if (first_physical_output.length()) {
606 if (_click_io->add_output_port (first_physical_output, this)) {
607 // relax, even though its an error
609 _clicking = click_requested;
615 catch (failed_constructor& err) {
616 error << _("cannot setup Click I/O") << endmsg;
619 set_worst_io_latencies ();
622 ControlChanged (Clicking); /* EMIT SIGNAL */
625 if (auditioner == 0) {
627 /* we delay creating the auditioner till now because
628 it makes its own connections to ports named
629 in the ARDOUR_RC config file. the engine has
630 to be running for this to work.
634 auditioner.reset (new Auditioner (*this));
637 catch (failed_constructor& err) {
638 warning << _("cannot create Auditioner: no auditioning of regions possible") << endmsg;
642 /* Create a set of Connection objects that map
643 to the physical outputs currently available
648 for (uint32_t np = 0; np < n_physical_outputs; ++np) {
650 snprintf (buf, sizeof (buf), _("out %" PRIu32), np+1);
652 Connection* c = new OutputConnection (buf, true);
655 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
660 for (uint32_t np = 0; np < n_physical_inputs; ++np) {
662 snprintf (buf, sizeof (buf), _("in %" PRIu32), np+1);
664 Connection* c = new InputConnection (buf, true);
667 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
674 for (uint32_t np = 0; np < n_physical_outputs; np +=2) {
676 snprintf (buf, sizeof (buf), _("out %" PRIu32 "+%" PRIu32), np+1, np+2);
678 Connection* c = new OutputConnection (buf, true);
682 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
683 c->add_connection (1, _engine.get_nth_physical_output (DataType::AUDIO, np+1));
688 for (uint32_t np = 0; np < n_physical_inputs; np +=2) {
690 snprintf (buf, sizeof (buf), _("in %" PRIu32 "+%" PRIu32), np+1, np+2);
692 Connection* c = new InputConnection (buf, true);
696 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
697 c->add_connection (1, _engine.get_nth_physical_input (DataType::AUDIO, np+1));
706 /* create master/control ports */
711 /* force the master to ignore any later call to this */
713 if (_master_out->pending_state_node) {
714 _master_out->ports_became_legal();
717 /* no panner resets till we are through */
719 _master_out->defer_pan_reset ();
721 while (_master_out->n_inputs().get(DataType::AUDIO)
722 < _master_out->input_maximum().get(DataType::AUDIO)) {
723 if (_master_out->add_input_port ("", this, DataType::AUDIO)) {
724 error << _("cannot setup master inputs")
730 while (_master_out->n_outputs().get(DataType::AUDIO)
731 < _master_out->output_maximum().get(DataType::AUDIO)) {
732 if (_master_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this, DataType::AUDIO)) {
733 error << _("cannot setup master outputs")
740 _master_out->allow_pan_reset ();
744 Connection* c = new OutputConnection (_("Master Out"), true);
746 for (uint32_t n = 0; n < _master_out->n_inputs ().get_total(); ++n) {
748 c->add_connection ((int) n, _master_out->input(n)->name());
755 /* catch up on send+insert cnts */
759 for (list<PortInsert*>::iterator i = _port_inserts.begin(); i != _port_inserts.end(); ++i) {
762 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
763 if (id > insert_cnt) {
771 for (list<Send*>::iterator i = _sends.begin(); i != _sends.end(); ++i) {
774 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
781 _state_of_the_state = StateOfTheState (_state_of_the_state & ~(CannotSave|Dirty));
783 /* hook us up to the engine */
785 _engine.set_session (this);
790 osc->set_session (*this);
793 _state_of_the_state = Clean;
795 DirtyChanged (); /* EMIT SIGNAL */
799 Session::hookup_io ()
801 /* stop graph reordering notifications from
802 causing resorts, etc.
805 _state_of_the_state = StateOfTheState (_state_of_the_state | InitialConnecting);
807 /* Tell all IO objects to create their ports */
814 while (_control_out->n_inputs().get(DataType::AUDIO) < _control_out->input_maximum().get(DataType::AUDIO)) {
815 if (_control_out->add_input_port ("", this)) {
816 error << _("cannot setup control inputs")
822 while (_control_out->n_outputs().get(DataType::AUDIO) < _control_out->output_maximum().get(DataType::AUDIO)) {
823 if (_control_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this)) {
824 error << _("cannot set up master outputs")
832 /* Tell all IO objects to connect themselves together */
834 IO::enable_connecting ();
836 /* Now reset all panners */
838 IO::reset_panners ();
840 /* Anyone who cares about input state, wake up and do something */
842 IOConnectionsComplete (); /* EMIT SIGNAL */
844 _state_of_the_state = StateOfTheState (_state_of_the_state & ~InitialConnecting);
846 /* now handle the whole enchilada as if it was one
852 /* update mixer solo state */
858 Session::playlist_length_changed (Playlist* pl)
860 /* we can't just increase end_location->end() if pl->get_maximum_extent()
861 if larger. if the playlist used to be the longest playlist,
862 and its now shorter, we have to decrease end_location->end(). hence,
863 we have to iterate over all diskstreams and check the
864 playlists currently in use.
870 Session::diskstream_playlist_changed (Diskstream* dstream)
874 if ((playlist = dstream->playlist()) != 0) {
875 playlist->LengthChanged.connect (sigc::bind (mem_fun (this, &Session::playlist_length_changed), playlist));
878 /* see comment in playlist_length_changed () */
883 Session::record_enabling_legal () const
885 /* this used to be in here, but survey says.... we don't need to restrict it */
886 // if (record_status() == Recording) {
897 Session::set_auto_play (bool yn)
899 if (auto_play != yn) {
902 ControlChanged (AutoPlay);
907 Session::set_auto_return (bool yn)
909 if (auto_return != yn) {
912 ControlChanged (AutoReturn);
917 Session::set_crossfades_active (bool yn)
919 if (crossfades_active != yn) {
920 crossfades_active = yn;
922 ControlChanged (CrossFadesActive);
927 Session::set_do_not_record_plugins (bool yn)
929 if (do_not_record_plugins != yn) {
930 do_not_record_plugins = yn;
932 ControlChanged (RecordingPlugins);
937 Session::set_auto_input (bool yn)
939 if (auto_input != yn) {
942 if (Config->get_use_hardware_monitoring() && transport_rolling()) {
943 /* auto-input only makes a difference if we're rolling */
945 /* Even though this can called from RT context we are using
946 a non-tentative rwlock here, because the action must occur.
947 The rarity and short potential lock duration makes this "OK"
949 Glib::RWLock::ReaderLock dsm (diskstream_lock);
950 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
951 if ((*i)->record_enabled ()) {
952 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
953 (*i)->monitor_input (!auto_input);
959 ControlChanged (AutoInput);
964 Session::reset_input_monitor_state ()
966 if (transport_rolling()) {
967 Glib::RWLock::ReaderLock dsm (diskstream_lock);
968 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
969 if ((*i)->record_enabled ()) {
970 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
971 (*i)->monitor_input (Config->get_use_hardware_monitoring() && !auto_input);
975 Glib::RWLock::ReaderLock dsm (diskstream_lock);
976 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
977 if ((*i)->record_enabled ()) {
978 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
979 (*i)->monitor_input (Config->get_use_hardware_monitoring());
987 Session::set_input_auto_connect (bool yn)
990 input_auto_connect = AutoConnectOption (input_auto_connect|AutoConnectPhysical);
992 input_auto_connect = AutoConnectOption (input_auto_connect|~AutoConnectPhysical);
998 Session::get_input_auto_connect () const
1000 return (input_auto_connect & AutoConnectPhysical);
1004 Session::set_output_auto_connect (AutoConnectOption aco)
1006 output_auto_connect = aco;
1011 Session::auto_punch_start_changed (Location* location)
1013 replace_event (Event::PunchIn, location->start());
1015 if (get_record_enabled() && get_punch_in()) {
1016 /* capture start has been changed, so save new pending state */
1017 save_state ("", true);
1023 Session::auto_punch_end_changed (Location* location)
1025 jack_nframes_t when_to_stop = location->end();
1026 // when_to_stop += _worst_output_latency + _worst_input_latency;
1027 replace_event (Event::PunchOut, when_to_stop);
1031 Session::auto_punch_changed (Location* location)
1033 jack_nframes_t when_to_stop = location->end();
1035 replace_event (Event::PunchIn, location->start());
1036 //when_to_stop += _worst_output_latency + _worst_input_latency;
1037 replace_event (Event::PunchOut, when_to_stop);
1041 Session::auto_loop_changed (Location* location)
1043 replace_event (Event::AutoLoop, location->end(), location->start());
1045 if (transport_rolling() && get_auto_loop()) {
1047 //if (_transport_frame < location->start() || _transport_frame > location->end()) {
1049 if (_transport_frame > location->end()) {
1050 // relocate to beginning of loop
1051 clear_events (Event::LocateRoll);
1053 request_locate (location->start(), true);
1056 else if (seamless_loop && !loop_changing) {
1058 // schedule a locate-roll to refill the diskstreams at the
1059 // previous loop end
1060 loop_changing = true;
1062 if (location->end() > last_loopend) {
1063 clear_events (Event::LocateRoll);
1064 Event *ev = new Event (Event::LocateRoll, Event::Add, last_loopend, last_loopend, 0, true);
1071 last_loopend = location->end();
1076 Session::set_auto_punch_location (Location* location)
1080 if ((existing = _locations.auto_punch_location()) != 0 && existing != location) {
1081 auto_punch_start_changed_connection.disconnect();
1082 auto_punch_end_changed_connection.disconnect();
1083 auto_punch_changed_connection.disconnect();
1084 existing->set_auto_punch (false, this);
1085 remove_event (existing->start(), Event::PunchIn);
1086 clear_events (Event::PunchOut);
1087 auto_punch_location_changed (0);
1092 if (location == 0) {
1096 if (location->end() <= location->start()) {
1097 error << _("Session: you can't use that location for auto punch (start <= end)") << endmsg;
1101 auto_punch_start_changed_connection.disconnect();
1102 auto_punch_end_changed_connection.disconnect();
1103 auto_punch_changed_connection.disconnect();
1105 auto_punch_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_punch_start_changed));
1106 auto_punch_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_punch_end_changed));
1107 auto_punch_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_punch_changed));
1109 location->set_auto_punch (true, this);
1110 auto_punch_location_changed (location);
1114 Session::set_punch_in (bool yn)
1116 if (punch_in == yn) {
1122 if ((location = _locations.auto_punch_location()) != 0) {
1123 if ((punch_in = yn) == true) {
1124 replace_event (Event::PunchIn, location->start());
1126 remove_event (location->start(), Event::PunchIn);
1131 ControlChanged (PunchIn); /* EMIT SIGNAL */
1135 Session::set_punch_out (bool yn)
1137 if (punch_out == yn) {
1143 if ((location = _locations.auto_punch_location()) != 0) {
1144 if ((punch_out = yn) == true) {
1145 replace_event (Event::PunchOut, location->end());
1147 clear_events (Event::PunchOut);
1152 ControlChanged (PunchOut); /* EMIT SIGNAL */
1156 Session::set_auto_loop_location (Location* location)
1160 if ((existing = _locations.auto_loop_location()) != 0 && existing != location) {
1161 auto_loop_start_changed_connection.disconnect();
1162 auto_loop_end_changed_connection.disconnect();
1163 auto_loop_changed_connection.disconnect();
1164 existing->set_auto_loop (false, this);
1165 remove_event (existing->end(), Event::AutoLoop);
1166 auto_loop_location_changed (0);
1171 if (location == 0) {
1175 if (location->end() <= location->start()) {
1176 error << _("Session: you can't use a mark for auto loop") << endmsg;
1180 last_loopend = location->end();
1182 auto_loop_start_changed_connection.disconnect();
1183 auto_loop_end_changed_connection.disconnect();
1184 auto_loop_changed_connection.disconnect();
1186 auto_loop_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1187 auto_loop_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1188 auto_loop_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_loop_changed));
1190 location->set_auto_loop (true, this);
1191 auto_loop_location_changed (location);
1195 Session::locations_added (Location* ignored)
1201 Session::locations_changed ()
1203 _locations.apply (*this, &Session::handle_locations_changed);
1207 Session::handle_locations_changed (Locations::LocationList& locations)
1209 Locations::LocationList::iterator i;
1211 bool set_loop = false;
1212 bool set_punch = false;
1214 for (i = locations.begin(); i != locations.end(); ++i) {
1218 if (location->is_auto_punch()) {
1219 set_auto_punch_location (location);
1222 if (location->is_auto_loop()) {
1223 set_auto_loop_location (location);
1230 set_auto_loop_location (0);
1233 set_auto_punch_location (0);
1240 Session::enable_record ()
1242 /* XXX really atomic compare+swap here */
1243 if (g_atomic_int_get (&_record_status) != Recording) {
1244 g_atomic_int_set (&_record_status, Recording);
1245 _last_record_location = _transport_frame;
1246 deliver_mmc(MIDI::MachineControl::cmdRecordStrobe, _last_record_location);
1248 if (Config->get_use_hardware_monitoring() && auto_input) {
1249 /* Even though this can be called from RT context we are using
1250 a non-tentative rwlock here, because the action must occur.
1251 The rarity and short potential lock duration makes this "OK"
1253 Glib::RWLock::ReaderLock dsm (diskstream_lock);
1255 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1256 if ((*i)->record_enabled ()) {
1257 (*i)->monitor_input (true);
1262 RecordStateChanged ();
1267 Session::disable_record (bool rt_context, bool force)
1271 if ((rs = (RecordState) g_atomic_int_get (&_record_status)) != Disabled) {
1273 if (!Config->get_latched_record_enable () || force) {
1274 g_atomic_int_set (&_record_status, Disabled);
1276 if (rs == Recording) {
1277 g_atomic_int_set (&_record_status, Enabled);
1281 // FIXME: timestamp correct? [DR]
1282 // FIXME FIXME FIXME: rt_context? this must be called in the process thread.
1283 // does this /need/ to be sent in all cases?
1285 deliver_mmc (MIDI::MachineControl::cmdRecordExit, _transport_frame);
1287 if (Config->get_use_hardware_monitoring() && auto_input) {
1288 /* Even though this can be called from RT context we are using
1289 a non-tentative rwlock here, because the action must occur.
1290 The rarity and short potential lock duration makes this "OK"
1292 Glib::RWLock::ReaderLock dsm (diskstream_lock);
1294 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1295 if ((*i)->record_enabled ()) {
1296 (*i)->monitor_input (false);
1301 RecordStateChanged (); /* emit signal */
1304 remove_pending_capture_state ();
1310 Session::step_back_from_record ()
1312 g_atomic_int_set (&_record_status, Enabled);
1314 if (Config->get_use_hardware_monitoring()) {
1315 /* Even though this can be called from RT context we are using
1316 a non-tentative rwlock here, because the action must occur.
1317 The rarity and short potential lock duration makes this "OK"
1319 Glib::RWLock::ReaderLock dsm (diskstream_lock);
1321 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1322 if (auto_input && (*i)->record_enabled ()) {
1323 //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1324 (*i)->monitor_input (false);
1331 Session::maybe_enable_record ()
1333 g_atomic_int_set (&_record_status, Enabled);
1335 /* XXX this save should really happen in another thread. its needed so that
1336 pending capture state can be recovered if we crash.
1339 save_state ("", true);
1342 if (_transport_speed) {
1347 deliver_mmc (MIDI::MachineControl::cmdRecordPause, _transport_frame);
1348 RecordStateChanged (); /* EMIT SIGNAL */
1355 Session::audible_frame () const
1358 jack_nframes_t offset;
1361 /* the first of these two possible settings for "offset"
1362 mean that the audible frame is stationary until
1363 audio emerges from the latency compensation
1366 the second means that the audible frame is stationary
1367 until audio would emerge from a physical port
1368 in the absence of any plugin latency compensation
1371 offset = _worst_output_latency;
1373 if (offset > current_block_size) {
1374 offset -= current_block_size;
1376 /* XXX is this correct? if we have no external
1377 physical connections and everything is internal
1378 then surely this is zero? still, how
1379 likely is that anyway?
1381 offset = current_block_size;
1384 if (synced_to_jack()) {
1385 tf = _engine.transport_frame();
1387 tf = _transport_frame;
1390 if (_transport_speed == 0) {
1400 if (!non_realtime_work_pending()) {
1404 /* take latency into account */
1413 Session::set_frame_rate (jack_nframes_t frames_per_second)
1415 /** \fn void Session::set_frame_size(jack_nframes_t)
1416 the AudioEngine object that calls this guarantees
1417 that it will not be called while we are also in
1418 ::process(). Its fine to do things that block
1422 _current_frame_rate = frames_per_second;
1423 _frames_per_smpte_frame = (double) _current_frame_rate / (double) smpte_frames_per_second;
1425 Route::set_automation_interval ((jack_nframes_t) ceil ((double) frames_per_second * 0.25));
1427 // XXX we need some equivalent to this, somehow
1428 // DestructiveFileSource::setup_standard_crossfades (frames_per_second);
1432 /* XXX need to reset/reinstantiate all LADSPA plugins */
1436 Session::set_block_size (jack_nframes_t nframes)
1438 /* the AudioEngine guarantees
1439 that it will not be called while we are also in
1440 ::process(). It is therefore fine to do things that block
1445 Glib::RWLock::ReaderLock dsm (diskstream_lock);
1447 current_block_size = nframes;
1449 ensure_buffers(_scratch_buffers->available());
1451 if (_gain_automation_buffer) {
1452 delete [] _gain_automation_buffer;
1454 _gain_automation_buffer = new gain_t[nframes];
1456 allocate_pan_automation_buffers (nframes, _npan_buffers, true);
1458 boost::shared_ptr<RouteList> r = routes.reader ();
1460 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1461 (*i)->set_block_size (nframes);
1464 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1465 (*i)->set_block_size (nframes);
1468 set_worst_io_latencies ();
1473 Session::set_default_fade (float steepness, float fade_msecs)
1476 jack_nframes_t fade_frames;
1478 /* Don't allow fade of less 1 frame */
1480 if (fade_msecs < (1000.0 * (1.0/_current_frame_rate))) {
1487 fade_frames = (jack_nframes_t) floor (fade_msecs * _current_frame_rate * 0.001);
1491 default_fade_msecs = fade_msecs;
1492 default_fade_steepness = steepness;
1495 // jlc, WTF is this!
1496 Glib::RWLock::ReaderLock lm (route_lock);
1497 AudioRegion::set_default_fade (steepness, fade_frames);
1502 /* XXX have to do this at some point */
1503 /* foreach region using default fade, reset, then
1504 refill_all_diskstream_buffers ();
1509 struct RouteSorter {
1510 bool operator() (boost::shared_ptr<Route> r1, boost::shared_ptr<Route> r2) {
1511 if (r1->fed_by.find (r2) != r1->fed_by.end()) {
1513 } else if (r2->fed_by.find (r1) != r2->fed_by.end()) {
1516 if (r1->fed_by.empty()) {
1517 if (r2->fed_by.empty()) {
1518 /* no ardour-based connections inbound to either route. just use signal order */
1519 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1521 /* r2 has connections, r1 does not; run r1 early */
1525 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1532 trace_terminal (shared_ptr<Route> r1, shared_ptr<Route> rbase)
1534 shared_ptr<Route> r2;
1536 if ((r1->fed_by.find (rbase) != r1->fed_by.end()) && (rbase->fed_by.find (r1) != rbase->fed_by.end())) {
1537 info << string_compose(_("feedback loop setup between %1 and %2"), r1->name(), rbase->name()) << endmsg;
1541 /* make a copy of the existing list of routes that feed r1 */
1543 set<shared_ptr<Route> > existing = r1->fed_by;
1545 /* for each route that feeds r1, recurse, marking it as feeding
1549 for (set<shared_ptr<Route> >::iterator i = existing.begin(); i != existing.end(); ++i) {
1552 /* r2 is a route that feeds r1 which somehow feeds base. mark
1553 base as being fed by r2
1556 rbase->fed_by.insert (r2);
1560 /* 2nd level feedback loop detection. if r1 feeds or is fed by r2,
1564 if ((r1->fed_by.find (r2) != r1->fed_by.end()) && (r2->fed_by.find (r1) != r2->fed_by.end())) {
1568 /* now recurse, so that we can mark base as being fed by
1569 all routes that feed r2
1572 trace_terminal (r2, rbase);
1579 Session::resort_routes ()
1581 /* don't do anything here with signals emitted
1582 by Routes while we are being destroyed.
1585 if (_state_of_the_state & Deletion) {
1592 RCUWriter<RouteList> writer (routes);
1593 shared_ptr<RouteList> r = writer.get_copy ();
1594 resort_routes_using (r);
1595 /* writer goes out of scope and forces update */
1600 Session::resort_routes_using (shared_ptr<RouteList> r)
1602 RouteList::iterator i, j;
1604 for (i = r->begin(); i != r->end(); ++i) {
1606 (*i)->fed_by.clear ();
1608 for (j = r->begin(); j != r->end(); ++j) {
1610 /* although routes can feed themselves, it will
1611 cause an endless recursive descent if we
1612 detect it. so don't bother checking for
1620 if ((*j)->feeds (*i)) {
1621 (*i)->fed_by.insert (*j);
1626 for (i = r->begin(); i != r->end(); ++i) {
1627 trace_terminal (*i, *i);
1634 cerr << "finished route resort\n";
1636 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1637 cerr << " " << (*i)->name() << " signal order = " << (*i)->order_key ("signal") << endl;
1644 boost::shared_ptr<MidiTrack>
1645 Session::new_midi_track (TrackMode mode)
1647 char track_name[32];
1649 uint32_t channels_used = 0;
1652 /* count existing midi tracks */
1655 shared_ptr<RouteList> r = routes.reader ();
1657 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1658 if (dynamic_cast<MidiTrack*>((*i).get()) != 0) {
1659 if (!(*i)->hidden()) {
1661 channels_used += (*i)->n_inputs().get(DataType::MIDI);
1667 /* check for duplicate route names, since we might have pre-existing
1668 routes with this name (e.g. create Midi1, Midi2, delete Midi1,
1669 save, close,restart,add new route - first named route is now
1674 snprintf (track_name, sizeof(track_name), "Midi %" PRIu32, n+1);
1675 if (route_by_name (track_name) == 0) {
1680 } while (n < (UINT_MAX-1));
1683 shared_ptr<MidiTrack> track (new MidiTrack (*this, track_name, Route::Flag (0), mode));
1685 if (track->ensure_io (1, 1, false, this)) {
1686 error << string_compose (_("cannot configure %1 in/%2 out configuration for new midi track"), track_name)
1691 for (uint32_t x = 0; x < track->n_inputs() && x < nphysical_in; ++x) {
1695 if (input_auto_connect & AutoConnectPhysical) {
1696 port = _engine.get_nth_physical_input ((channels_used+x)%nphysical_in);
1699 if (port.length() && track->connect_input (track->input (x), port, this)) {
1705 for (uint32_t x = 0; x < track->n_outputs(); ++x) {
1709 if (nphysical_out && (output_auto_connect & AutoConnectPhysical)) {
1710 port = _engine.get_nth_physical_output ((channels_used+x)%nphysical_out);
1711 } else if (output_auto_connect & AutoConnectMaster) {
1713 port = _master_out->input (x%_master_out->n_inputs())->name();
1717 if (port.length() && track->connect_output (track->output (x), port, this)) {
1723 vector<string> cports;
1724 uint32_t ni = _control_out->n_inputs();
1726 for (n = 0; n < ni; ++n) {
1727 cports.push_back (_control_out->input(n)->name());
1730 track->set_control_outs (cports);
1733 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1737 track->set_remote_control_id (ntracks());
1741 catch (failed_constructor &err) {
1742 error << _("Session: could not create new midi track.") << endmsg;
1743 return shared_ptr<MidiTrack> ((MidiTrack*) 0);
1748 boost::shared_ptr<Route>
1749 Session::new_midi_route ()
1755 /* count existing midi busses */
1757 shared_ptr<RouteList> r = routes.reader ();
1759 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1760 if (dynamic_cast<MidiTrack*>((*i).get()) == 0) {
1761 if (!(*i)->hidden()) {
1769 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, n+1);
1770 if (route_by_name (bus_name) == 0) {
1775 } while (n < (UINT_MAX-1));
1778 shared_ptr<Route> bus (new Route (*this, bus_name, -1, -1, -1, -1, Route::Flag(0), DataType::MIDI));
1780 if (bus->ensure_io (1, 1, false, this)) {
1781 error << (_("cannot configure 1 in/1 out configuration for new midi track"))
1785 for (uint32_t x = 0; x < bus->n_inputs(); ++x) {
1789 if (input_auto_connect & AutoConnectPhysical) {
1790 port = _engine.get_nth_physical_input ((n+x)%n_physical_inputs);
1793 if (port.length() && bus->connect_input (bus->input (x), port, this)) {
1798 for (uint32_t x = 0; x < bus->n_outputs(); ++x) {
1802 if (output_auto_connect & AutoConnectPhysical) {
1803 port = _engine.get_nth_physical_input ((n+x)%n_physical_outputs);
1804 } else if (output_auto_connect & AutoConnectMaster) {
1806 port = _master_out->input (x%_master_out->n_inputs())->name();
1810 if (port.length() && bus->connect_output (bus->output (x), port, this)) {
1817 vector<string> cports;
1818 uint32_t ni = _control_out->n_inputs();
1820 for (uint32_t n = 0; n < ni; ++n) {
1821 cports.push_back (_control_out->input(n)->name());
1823 bus->set_control_outs (cports);
1830 catch (failed_constructor &err) {
1831 error << _("Session: could not create new MIDI route.") << endmsg;
1832 return shared_ptr<Route> ((Route*) 0);
1837 shared_ptr<AudioTrack>
1838 Session::new_audio_track (int input_channels, int output_channels, TrackMode mode)
1840 char track_name[32];
1842 uint32_t channels_used = 0;
1844 uint32_t nphysical_in;
1845 uint32_t nphysical_out;
1847 /* count existing audio tracks */
1850 shared_ptr<RouteList> r = routes.reader ();
1852 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1853 if (dynamic_cast<AudioTrack*>((*i).get()) != 0) {
1854 if (!(*i)->hidden()) {
1856 channels_used += (*i)->n_inputs().get(DataType::AUDIO);
1862 /* check for duplicate route names, since we might have pre-existing
1863 routes with this name (e.g. create Audio1, Audio2, delete Audio1,
1864 save, close,restart,add new route - first named route is now
1869 snprintf (track_name, sizeof(track_name), "Audio %" PRIu32, n+1);
1870 if (route_by_name (track_name) == 0) {
1875 } while (n < (UINT_MAX-1));
1877 if (input_auto_connect & AutoConnectPhysical) {
1878 nphysical_in = n_physical_inputs;
1883 if (output_auto_connect & AutoConnectPhysical) {
1884 nphysical_out = n_physical_outputs;
1890 shared_ptr<AudioTrack> track (new AudioTrack (*this, track_name, Route::Flag (0), mode));
1892 if (track->ensure_io (input_channels, output_channels, false, this)) {
1893 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1894 input_channels, output_channels)
1899 for (uint32_t x = 0; x < track->n_inputs().get(DataType::AUDIO) && x < nphysical_in; ++x) {
1903 if (input_auto_connect & AutoConnectPhysical) {
1904 port = _engine.get_nth_physical_input (DataType::AUDIO, (channels_used+x)%nphysical_in);
1907 if (port.length() && track->connect_input (track->input (x), port, this)) {
1913 for (uint32_t x = 0; x < track->n_outputs().get(DataType::AUDIO); ++x) {
1917 if (nphysical_out && (output_auto_connect & AutoConnectPhysical)) {
1918 port = _engine.get_nth_physical_output (DataType::AUDIO, (channels_used+x)%nphysical_out);
1919 } else if (output_auto_connect & AutoConnectMaster) {
1921 port = _master_out->audio_input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
1925 if (port.length() && track->connect_output (track->output (x), port, this)) {
1931 vector<string> cports;
1932 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
1934 for (n = 0; n < ni; ++n) {
1935 cports.push_back (_control_out->audio_input(n)->name());
1938 track->set_control_outs (cports);
1941 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1945 track->set_remote_control_id (ntracks());
1949 catch (failed_constructor &err) {
1950 error << _("Session: could not create new audio track.") << endmsg;
1951 return shared_ptr<AudioTrack> ((AudioTrack*) 0);
1956 Session::new_audio_route (int input_channels, int output_channels)
1962 /* count existing audio busses */
1965 shared_ptr<RouteList> r = routes.reader ();
1967 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1968 if (dynamic_cast<AudioTrack*>((*i).get()) == 0) {
1969 if (!(*i)->hidden()) {
1977 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, n+1);
1978 if (route_by_name (bus_name) == 0) {
1983 } while (n < (UINT_MAX-1));
1986 shared_ptr<Route> bus (new Route (*this, bus_name, -1, -1, -1, -1, Route::Flag(0), DataType::AUDIO));
1988 if (bus->ensure_io (input_channels, output_channels, false, this)) {
1989 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1990 input_channels, output_channels)
1994 for (uint32_t x = 0; x < bus->n_inputs().get(DataType::AUDIO); ++x) {
1998 if (input_auto_connect & AutoConnectPhysical) {
1999 port = _engine.get_nth_physical_input (DataType::AUDIO, (n+x)%n_physical_inputs);
2002 if (port.length() && bus->connect_input (bus->input (x), port, this)) {
2007 for (uint32_t x = 0; x < bus->n_outputs().get(DataType::AUDIO); ++x) {
2011 if (output_auto_connect & AutoConnectPhysical) {
2012 port = _engine.get_nth_physical_input (DataType::AUDIO, (n+x)%n_physical_outputs);
2013 } else if (output_auto_connect & AutoConnectMaster) {
2015 port = _master_out->audio_input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
2019 if (port.length() && bus->connect_output (bus->output (x), port, this)) {
2025 vector<string> cports;
2026 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
2028 for (uint32_t n = 0; n < ni; ++n) {
2029 cports.push_back (_control_out->input(n)->name());
2031 bus->set_control_outs (cports);
2038 catch (failed_constructor &err) {
2039 error << _("Session: could not create new audio route.") << endmsg;
2040 return shared_ptr<Route> ((Route*) 0);
2045 Session::add_route (shared_ptr<Route> route)
2048 RCUWriter<RouteList> writer (routes);
2049 shared_ptr<RouteList> r = writer.get_copy ();
2050 r->push_front (route);
2051 resort_routes_using (r);
2054 route->solo_changed.connect (sigc::bind (mem_fun (*this, &Session::route_solo_changed), route));
2055 route->mute_changed.connect (mem_fun (*this, &Session::route_mute_changed));
2056 route->output_changed.connect (mem_fun (*this, &Session::set_worst_io_latencies_x));
2057 route->redirects_changed.connect (mem_fun (*this, &Session::update_latency_compensation_proxy));
2059 if (route->master()) {
2060 _master_out = route;
2063 if (route->control()) {
2064 _control_out = route;
2068 save_state (_current_snapshot_name);
2069 save_history (_current_snapshot_name);
2071 RouteAdded (route); /* EMIT SIGNAL */
2075 Session::add_diskstream (Diskstream* dstream)
2077 /* need to do this in case we're rolling at the time, to prevent false underruns */
2078 dstream->do_refill_with_alloc();
2081 Glib::RWLock::WriterLock lm (diskstream_lock);
2082 diskstreams.push_back (dstream);
2085 /* take a reference to the diskstream, preventing it from
2086 ever being deleted until the session itself goes away,
2087 or chooses to remove it for its own purposes.
2091 dstream->set_block_size (current_block_size);
2093 dstream->PlaylistChanged.connect (sigc::bind (mem_fun (*this, &Session::diskstream_playlist_changed), dstream));
2094 /* this will connect to future changes, and check the current length */
2095 diskstream_playlist_changed (dstream);
2097 dstream->prepare ();
2100 save_state (_current_snapshot_name);
2101 save_history (_current_snapshot_name);
2103 DiskstreamAdded (dstream); /* EMIT SIGNAL */
2107 Session::remove_route (shared_ptr<Route> route)
2110 RCUWriter<RouteList> writer (routes);
2111 shared_ptr<RouteList> rs = writer.get_copy ();
2114 /* deleting the master out seems like a dumb
2115 idea, but its more of a UI policy issue
2119 if (route == _master_out) {
2120 _master_out = shared_ptr<Route> ((Route*) 0);
2123 if (route == _control_out) {
2124 _control_out = shared_ptr<Route> ((Route*) 0);
2126 /* cancel control outs for all routes */
2128 vector<string> empty;
2130 for (RouteList::iterator r = rs->begin(); r != rs->end(); ++r) {
2131 (*r)->set_control_outs (empty);
2135 update_route_solo_state ();
2137 /* writer goes out of scope, forces route list update */
2143 if ((t = dynamic_cast<Track*>(route.get())) != 0) {
2144 ds = &t->diskstream();
2150 Glib::RWLock::WriterLock lm (diskstream_lock);
2151 diskstreams.remove (ds);
2157 find_current_end ();
2159 update_latency_compensation (false, false);
2162 /* XXX should we disconnect from the Route's signals ? */
2164 save_state (_current_snapshot_name);
2165 save_history (_current_snapshot_name);
2167 /* all shared ptrs to route should go out of scope here */
2171 Session::route_mute_changed (void* src)
2177 Session::route_solo_changed (void* src, shared_ptr<Route> route)
2179 if (solo_update_disabled) {
2186 is_track = (dynamic_cast<Track*>(route.get()) != 0);
2188 shared_ptr<RouteList> r = routes.reader ();
2190 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2192 /* soloing a track mutes all other tracks, soloing a bus mutes all other busses */
2196 /* don't mess with busses */
2198 if (dynamic_cast<Track*>((*i).get()) == 0) {
2204 /* don't mess with tracks */
2206 if (dynamic_cast<Track*>((*i).get()) != 0) {
2211 if ((*i) != route &&
2212 ((*i)->mix_group () == 0 ||
2213 (*i)->mix_group () != route->mix_group () ||
2214 !route->mix_group ()->is_active())) {
2216 if ((*i)->soloed()) {
2218 /* if its already soloed, and solo latching is enabled,
2219 then leave it as it is.
2222 if (_solo_latched) {
2229 solo_update_disabled = true;
2230 (*i)->set_solo (false, src);
2231 solo_update_disabled = false;
2235 bool something_soloed = false;
2236 bool same_thing_soloed = false;
2237 bool signal = false;
2239 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2240 if ((*i)->soloed()) {
2241 something_soloed = true;
2242 if (dynamic_cast<Track*>((*i).get())) {
2244 same_thing_soloed = true;
2249 same_thing_soloed = true;
2257 if (something_soloed != currently_soloing) {
2259 currently_soloing = something_soloed;
2262 modify_solo_mute (is_track, same_thing_soloed);
2265 SoloActive (currently_soloing);
2272 Session::set_solo_latched (bool yn)
2274 if (yn != _solo_latched) {
2277 ControlChanged (SoloLatch);
2282 Session::update_route_solo_state ()
2285 bool is_track = false;
2286 bool signal = false;
2288 /* caller must hold RouteLock */
2290 /* this is where we actually implement solo by changing
2291 the solo mute setting of each track.
2294 shared_ptr<RouteList> r = routes.reader ();
2296 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2297 if ((*i)->soloed()) {
2299 if (dynamic_cast<Track*>((*i).get())) {
2306 if (mute != currently_soloing) {
2308 currently_soloing = mute;
2311 if (!is_track && !mute) {
2313 /* nothing is soloed */
2315 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2316 (*i)->set_solo_mute (false);
2326 modify_solo_mute (is_track, mute);
2329 SoloActive (currently_soloing);
2334 Session::modify_solo_mute (bool is_track, bool mute)
2336 shared_ptr<RouteList> r = routes.reader ();
2338 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2342 /* only alter track solo mute */
2344 if (dynamic_cast<Track*>((*i).get())) {
2345 if ((*i)->soloed()) {
2346 (*i)->set_solo_mute (!mute);
2348 (*i)->set_solo_mute (mute);
2354 /* only alter bus solo mute */
2356 if (!dynamic_cast<Track*>((*i).get())) {
2358 if ((*i)->soloed()) {
2360 (*i)->set_solo_mute (false);
2364 /* don't mute master or control outs
2365 in response to another bus solo
2368 if ((*i) != _master_out &&
2369 (*i) != _control_out) {
2370 (*i)->set_solo_mute (mute);
2381 Session::catch_up_on_solo ()
2383 /* this is called after set_state() to catch the full solo
2384 state, which can't be correctly determined on a per-route
2385 basis, but needs the global overview that only the session
2388 update_route_solo_state();
2392 Session::route_by_name (string name)
2394 shared_ptr<RouteList> r = routes.reader ();
2396 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2397 if ((*i)->name() == name) {
2402 return shared_ptr<Route> ((Route*) 0);
2406 Session::route_by_remote_id (uint32_t id)
2408 shared_ptr<RouteList> r = routes.reader ();
2410 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2411 if ((*i)->remote_control_id() == id) {
2416 return shared_ptr<Route> ((Route*) 0);
2420 Session::find_current_end ()
2422 if (_state_of_the_state & Loading) {
2426 jack_nframes_t max = get_maximum_extent ();
2428 if (max > end_location->end()) {
2429 end_location->set_end (max);
2431 DurationChanged(); /* EMIT SIGNAL */
2436 Session::get_maximum_extent () const
2438 jack_nframes_t max = 0;
2441 /* Don't take the diskstream lock. Caller must have other ways to
2445 for (DiskstreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2446 Playlist* pl = (*i)->playlist();
2447 if ((me = pl->get_maximum_extent()) > max) {
2456 Session::diskstream_by_name (string name)
2458 Glib::RWLock::ReaderLock lm (diskstream_lock);
2460 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2461 if ((*i)->name() == name) {
2470 Session::diskstream_by_id (const PBD::ID& id)
2472 Glib::RWLock::ReaderLock lm (diskstream_lock);
2474 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2475 if ((*i)->id() == id) {
2483 /* AudioRegion management */
2486 Session::new_region_name (string old)
2488 string::size_type last_period;
2490 string::size_type len = old.length() + 64;
2493 if ((last_period = old.find_last_of ('.')) == string::npos) {
2495 /* no period present - add one explicitly */
2498 last_period = old.length() - 1;
2503 number = atoi (old.substr (last_period+1).c_str());
2507 while (number < (UINT_MAX-1)) {
2509 RegionList::const_iterator i;
2514 snprintf (buf, len, "%s%" PRIu32, old.substr (0, last_period + 1).c_str(), number);
2517 for (i = regions.begin(); i != regions.end(); ++i) {
2518 if (i->second->name() == sbuf) {
2523 if (i == regions.end()) {
2528 if (number != (UINT_MAX-1)) {
2532 error << string_compose (_("cannot create new name for region \"%1\""), old) << endmsg;
2537 Session::region_name (string& result, string base, bool newlevel) const
2544 Glib::Mutex::Lock lm (region_lock);
2546 snprintf (buf, sizeof (buf), "%d", (int)regions.size() + 1);
2554 /* XXX this is going to be slow. optimize me later */
2559 string::size_type pos;
2561 pos = base.find_last_of ('.');
2563 /* pos may be npos, but then we just use entire base */
2565 subbase = base.substr (0, pos);
2569 bool name_taken = true;
2572 Glib::Mutex::Lock lm (region_lock);
2574 for (int n = 1; n < 5000; ++n) {
2577 snprintf (buf, sizeof (buf), ".%d", n);
2582 for (RegionList::const_iterator i = regions.begin(); i != regions.end(); ++i) {
2583 if (i->second->name() == result) {
2596 fatal << string_compose(_("too many regions with names like %1"), base) << endmsg;
2604 Session::add_region (Region* region)
2609 Glib::Mutex::Lock lm (region_lock);
2611 RegionList::iterator x;
2613 for (x = regions.begin(); x != regions.end(); ++x) {
2615 if (region->region_list_equivalent (*x->second)) {
2620 if (x == regions.end()) {
2622 pair<RegionList::key_type,RegionList::mapped_type> entry;
2624 entry.first = region->id();
2625 entry.second = region;
2627 pair<RegionList::iterator,bool> x = regions.insert (entry);
2638 /* mark dirty because something has changed even if we didn't
2639 add the region to the region list.
2645 region->GoingAway.connect (mem_fun (*this, &Session::remove_region));
2646 region->StateChanged.connect (sigc::bind (mem_fun (*this, &Session::region_changed), region));
2647 RegionAdded (region); /* EMIT SIGNAL */
2652 Session::region_changed (Change what_changed, Region* region)
2654 if (what_changed & Region::HiddenChanged) {
2655 /* relay hidden changes */
2656 RegionHiddenChange (region);
2661 Session::region_renamed (Region* region)
2663 add_region (region);
2667 Session::remove_region (Region* region)
2669 RegionList::iterator i;
2670 bool removed = false;
2673 Glib::Mutex::Lock lm (region_lock);
2675 if ((i = regions.find (region->id())) != regions.end()) {
2682 /* mark dirty because something has changed even if we didn't
2683 remove the region from the region list.
2689 RegionRemoved(region); /* EMIT SIGNAL */
2694 Session::find_whole_file_parent (Region& child)
2696 RegionList::iterator i;
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)) {
2716 Session::find_equivalent_playlist_regions (Region& region, vector<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 (Region* region)
2725 AudioRegion* aregion;
2727 if ((aregion = dynamic_cast<AudioRegion*> (region)) == 0) {
2731 if (aregion->playlist()) {
2732 aregion->playlist()->destroy_region (region);
2735 vector<Source*> srcs;
2737 for (uint32_t n = 0; n < aregion->n_channels(); ++n) {
2738 srcs.push_back (&aregion->source (n));
2741 for (vector<Source*>::iterator i = srcs.begin(); i != srcs.end(); ++i) {
2743 if ((*i)->use_cnt() == 0) {
2744 AudioFileSource* afs = dynamic_cast<AudioFileSource*>(*i);
2746 (afs)->mark_for_remove ();
2756 Session::destroy_regions (list<Region*> regions)
2758 for (list<Region*>::iterator i = regions.begin(); i != regions.end(); ++i) {
2759 destroy_region (*i);
2765 Session::remove_last_capture ()
2769 Glib::RWLock::ReaderLock lm (diskstream_lock);
2771 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2772 list<Region*>& l = (*i)->last_capture_regions();
2775 r.insert (r.end(), l.begin(), l.end());
2780 destroy_regions (r);
2785 Session::remove_region_from_region_list (Region& r)
2791 /* Source Management */
2793 Session::add_source (Source* source)
2795 pair<SourceList::key_type, SourceList::mapped_type> entry;
2798 Glib::Mutex::Lock lm (source_lock);
2799 entry.first = source->id();
2800 entry.second = source;
2801 sources.insert (entry);
2804 source->GoingAway.connect (mem_fun (this, &Session::remove_source));
2807 SourceAdded (source); /* EMIT SIGNAL */
2811 Session::remove_source (Source* source)
2813 SourceList::iterator i;
2816 Glib::Mutex::Lock lm (source_lock);
2818 if ((i = sources.find (source->id())) != sources.end()) {
2823 if (!_state_of_the_state & InCleanup) {
2825 /* save state so we don't end up with a session file
2826 referring to non-existent sources.
2829 save_state (_current_snapshot_name);
2830 save_history (_current_snapshot_name);
2833 SourceRemoved(source); /* EMIT SIGNAL */
2837 Session::source_by_id (const PBD::ID& id)
2839 Glib::Mutex::Lock lm (source_lock);
2840 SourceList::iterator i;
2843 if ((i = sources.find (id)) != sources.end()) {
2847 /* XXX search MIDI or other searches here */
2853 Session::peak_path_from_audio_path (string audio_path)
2855 /* XXX hardly bombproof! fix me */
2859 res = Glib::path_get_dirname (audio_path);
2860 res = Glib::path_get_dirname (res);
2862 res += peak_dir_name;
2864 res += PBD::basename_nosuffix (audio_path);
2871 Session::change_audio_path_by_name (string path, string oldname, string newname, bool destructive)
2874 string old_basename = PBD::basename_nosuffix (oldname);
2875 string new_legalized = legalize_for_path (newname);
2877 /* note: we know (or assume) the old path is already valid */
2881 /* destructive file sources have a name of the form:
2883 /path/to/Tnnnn-NAME(%[LR])?.wav
2885 the task here is to replace NAME with the new name.
2888 /* find last slash */
2892 string::size_type slash;
2893 string::size_type dash;
2895 if ((slash = path.find_last_of ('/')) == string::npos) {
2899 dir = path.substr (0, slash+1);
2901 /* '-' is not a legal character for the NAME part of the path */
2903 if ((dash = path.find_last_of ('-')) == string::npos) {
2907 prefix = path.substr (slash+1, dash-(slash+1));
2912 path += new_legalized;
2913 path += ".wav"; /* XXX gag me with a spoon */
2917 /* non-destructive file sources have a name of the form:
2919 /path/to/NAME-nnnnn(%[LR])?.wav
2921 the task here is to replace NAME with the new name.
2926 string::size_type slash;
2927 string::size_type dash;
2928 string::size_type postfix;
2930 /* find last slash */
2932 if ((slash = path.find_last_of ('/')) == string::npos) {
2936 dir = path.substr (0, slash+1);
2938 /* '-' is not a legal character for the NAME part of the path */
2940 if ((dash = path.find_last_of ('-')) == string::npos) {
2944 suffix = path.substr (dash+1);
2946 // Suffix is now everything after the dash. Now we need to eliminate
2947 // the nnnnn part, which is done by either finding a '%' or a '.'
2949 postfix = suffix.find_last_of ("%");
2950 if (postfix == string::npos) {
2951 postfix = suffix.find_last_of ('.');
2954 if (postfix != string::npos) {
2955 suffix = suffix.substr (postfix);
2957 error << "Logic error in Session::change_audio_path_by_name(), please report to the developers" << endl;
2961 const uint32_t limit = 10000;
2962 char buf[PATH_MAX+1];
2964 for (uint32_t cnt = 1; cnt <= limit; ++cnt) {
2966 snprintf (buf, sizeof(buf), "%s%s-%u%s", dir.c_str(), newname.c_str(), cnt, suffix.c_str());
2968 if (access (buf, F_OK) != 0) {
2976 error << "FATAL ERROR! Could not find a " << endl;
2985 Session::audio_path_from_name (string name, uint32_t nchan, uint32_t chan, bool destructive)
2989 char buf[PATH_MAX+1];
2990 const uint32_t limit = 10000;
2994 legalized = legalize_for_path (name);
2996 /* find a "version" of the file name that doesn't exist in
2997 any of the possible directories.
3000 for (cnt = (destructive ? ++destructive_index : 1); cnt <= limit; ++cnt) {
3002 vector<space_and_path>::iterator i;
3003 uint32_t existing = 0;
3005 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3010 spath += tape_dir_name;
3012 spath += sound_dir_name;
3017 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3018 } else if (nchan == 2) {
3020 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%L.wav", spath.c_str(), cnt, legalized.c_str());
3022 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%R.wav", spath.c_str(), cnt, legalized.c_str());
3024 } else if (nchan < 26) {
3025 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%%c.wav", spath.c_str(), cnt, legalized.c_str(), 'a' + chan);
3027 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3035 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3036 } else if (nchan == 2) {
3038 snprintf (buf, sizeof(buf), "%s-%u%%L.wav", spath.c_str(), cnt);
3040 snprintf (buf, sizeof(buf), "%s-%u%%R.wav", spath.c_str(), cnt);
3042 } else if (nchan < 26) {
3043 snprintf (buf, sizeof(buf), "%s-%u%%%c.wav", spath.c_str(), cnt, 'a' + chan);
3045 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3049 if (access (buf, F_OK) == 0) {
3054 if (existing == 0) {
3059 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3060 throw failed_constructor();
3064 /* we now have a unique name for the file, but figure out where to
3071 spath = tape_dir ();
3073 spath = discover_best_sound_dir ();
3076 string::size_type pos = foo.find_last_of ('/');
3078 if (pos == string::npos) {
3081 spath += foo.substr (pos + 1);
3088 Session::create_audio_source_for_session (AudioDiskstream& ds, uint32_t chan, bool destructive)
3090 string spath = audio_path_from_name (ds.name(), ds.n_channels().get(DataType::AUDIO), chan, destructive);
3092 /* this might throw failed_constructor(), which is OK */
3095 return new DestructiveFileSource (spath,
3096 Config->get_native_file_data_format(),
3097 Config->get_native_file_header_format(),
3100 return new SndFileSource (spath,
3101 Config->get_native_file_data_format(),
3102 Config->get_native_file_header_format(),
3108 Session::midi_path_from_name (string name)
3112 char buf[PATH_MAX+1];
3113 const uint32_t limit = 10000;
3117 legalized = legalize_for_path (name);
3119 /* find a "version" of the file name that doesn't exist in
3120 any of the possible directories.
3123 for (cnt = 1; cnt <= limit; ++cnt) {
3125 vector<space_and_path>::iterator i;
3126 uint32_t existing = 0;
3128 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3130 // FIXME: different directory from audio?
3131 spath = (*i).path + sound_dir_name + "/" + legalized;
3133 snprintf (buf, sizeof(buf), "%s-%u.mid", spath.c_str(), cnt);
3135 if (access (buf, F_OK) == 0) {
3140 if (existing == 0) {
3145 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3146 throw failed_constructor();
3150 /* we now have a unique name for the file, but figure out where to
3156 // FIXME: different directory than audio?
3157 spath = discover_best_sound_dir ();
3159 string::size_type pos = foo.find_last_of ('/');
3161 if (pos == string::npos) {
3164 spath += foo.substr (pos + 1);
3171 Session::create_midi_source_for_session (MidiDiskstream& ds)
3173 string spath = midi_path_from_name (ds.name());
3175 /* this might throw failed_constructor(), which is OK */
3176 return new SMFSource (spath);
3180 /* Playlist management */
3183 Session::playlist_by_name (string name)
3185 Glib::Mutex::Lock lm (playlist_lock);
3186 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3187 if ((*i)->name() == name) {
3191 for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ++i) {
3192 if ((*i)->name() == name) {
3200 Session::add_playlist (Playlist* playlist)
3202 if (playlist->hidden()) {
3207 Glib::Mutex::Lock lm (playlist_lock);
3208 if (find (playlists.begin(), playlists.end(), playlist) == playlists.end()) {
3209 playlists.insert (playlists.begin(), playlist);
3211 playlist->InUse.connect (mem_fun (*this, &Session::track_playlist));
3212 playlist->GoingAway.connect (mem_fun (*this, &Session::remove_playlist));
3218 PlaylistAdded (playlist); /* EMIT SIGNAL */
3222 Session::track_playlist (Playlist* pl, bool inuse)
3224 PlaylistList::iterator x;
3227 Glib::Mutex::Lock lm (playlist_lock);
3230 //cerr << "shifting playlist to unused: " << pl->name() << endl;
3232 unused_playlists.insert (pl);
3234 if ((x = playlists.find (pl)) != playlists.end()) {
3235 playlists.erase (x);
3240 //cerr << "shifting playlist to used: " << pl->name() << endl;
3242 playlists.insert (pl);
3244 if ((x = unused_playlists.find (pl)) != unused_playlists.end()) {
3245 unused_playlists.erase (x);
3252 Session::remove_playlist (Playlist* playlist)
3254 if (_state_of_the_state & Deletion) {
3259 Glib::Mutex::Lock lm (playlist_lock);
3260 // cerr << "removing playlist: " << playlist->name() << endl;
3262 PlaylistList::iterator i;
3264 i = find (playlists.begin(), playlists.end(), playlist);
3266 if (i != playlists.end()) {
3267 playlists.erase (i);
3270 i = find (unused_playlists.begin(), unused_playlists.end(), playlist);
3271 if (i != unused_playlists.end()) {
3272 unused_playlists.erase (i);
3279 PlaylistRemoved (playlist); /* EMIT SIGNAL */
3283 Session::set_audition (AudioRegion* r)
3285 pending_audition_region = r;
3286 post_transport_work = PostTransportWork (post_transport_work | PostTransportAudition);
3287 schedule_butler_transport_work ();
3291 Session::non_realtime_set_audition ()
3293 if (pending_audition_region == (AudioRegion*) 0xfeedface) {
3294 auditioner->audition_current_playlist ();
3295 } else if (pending_audition_region) {
3296 auditioner->audition_region (*pending_audition_region);
3298 pending_audition_region = 0;
3299 AuditionActive (true); /* EMIT SIGNAL */
3303 Session::audition_playlist ()
3305 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3306 ev->set_ptr ((void*) 0xfeedface);
3311 Session::audition_region (Region& r)
3313 AudioRegion* ar = dynamic_cast<AudioRegion*>(&r);
3315 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3322 Session::cancel_audition ()
3324 if (auditioner->active()) {
3325 auditioner->cancel_audition ();
3326 AuditionActive (false); /* EMIT SIGNAL */
3331 Session::RoutePublicOrderSorter::operator() (boost::shared_ptr<Route> a, boost::shared_ptr<Route> b)
3333 return a->order_key(N_("signal")) < b->order_key(N_("signal"));
3337 Session::remove_empty_sounds ()
3340 PathScanner scanner;
3345 vector<string *>* possible_audiofiles = scanner (dir, "\\.wav$", false, true);
3347 for (vector<string *>::iterator i = possible_audiofiles->begin(); i != possible_audiofiles->end(); ++i) {
3349 if (AudioFileSource::is_empty (*(*i))) {
3351 unlink ((*i)->c_str());
3353 string peak_path = peak_path_from_audio_path (**i);
3354 unlink (peak_path.c_str());
3360 delete possible_audiofiles;
3364 Session::is_auditioning () const
3366 /* can be called before we have an auditioner object */
3368 return auditioner->active();
3375 Session::set_all_solo (bool yn)
3377 shared_ptr<RouteList> r = routes.reader ();
3379 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3380 if (!(*i)->hidden()) {
3381 (*i)->set_solo (yn, this);
3389 Session::set_all_mute (bool yn)
3391 shared_ptr<RouteList> r = routes.reader ();
3393 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3394 if (!(*i)->hidden()) {
3395 (*i)->set_mute (yn, this);
3403 Session::n_diskstreams () const
3405 Glib::RWLock::ReaderLock lm (diskstream_lock);
3408 for (DiskstreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
3409 if (!(*i)->hidden()) {
3417 Session::graph_reordered ()
3419 /* don't do this stuff if we are setting up connections
3420 from a set_state() call.
3423 if (_state_of_the_state & InitialConnecting) {
3427 Glib::RWLock::ReaderLock lm2 (diskstream_lock);
3431 /* force all diskstreams to update their capture offset values to
3432 reflect any changes in latencies within the graph.
3435 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
3436 (*i)->set_capture_offset ();
3441 Session::record_disenable_all ()
3443 record_enable_change_all (false);
3447 Session::record_enable_all ()
3449 record_enable_change_all (true);
3453 Session::record_enable_change_all (bool yn)
3455 shared_ptr<RouteList> r = routes.reader ();
3457 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3460 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
3461 at->set_record_enable (yn, this);
3465 /* since we don't keep rec-enable state, don't mark session dirty */
3469 Session::add_redirect (Redirect* redirect)
3473 PortInsert* port_insert;
3474 PluginInsert* plugin_insert;
3476 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3477 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3478 _port_inserts.insert (_port_inserts.begin(), port_insert);
3479 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3480 _plugin_inserts.insert (_plugin_inserts.begin(), plugin_insert);
3482 fatal << _("programming error: unknown type of Insert created!") << endmsg;
3485 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3486 _sends.insert (_sends.begin(), send);
3488 fatal << _("programming error: unknown type of Redirect created!") << endmsg;
3492 redirect->GoingAway.connect (mem_fun (*this, &Session::remove_redirect));
3498 Session::remove_redirect (Redirect* redirect)
3502 PortInsert* port_insert;
3503 PluginInsert* plugin_insert;
3505 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3506 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3507 _port_inserts.remove (port_insert);
3508 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3509 _plugin_inserts.remove (plugin_insert);
3511 fatal << _("programming error: unknown type of Insert deleted!") << endmsg;
3514 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3515 _sends.remove (send);
3517 fatal << _("programming error: unknown type of Redirect deleted!") << endmsg;
3525 Session::available_capture_duration ()
3527 const double scale = 4096.0 / sizeof (Sample);
3529 if (_total_free_4k_blocks * scale > (double) max_frames) {
3533 return (jack_nframes_t) floor (_total_free_4k_blocks * scale);
3537 Session::add_connection (ARDOUR::Connection* connection)
3540 Glib::Mutex::Lock guard (connection_lock);
3541 _connections.push_back (connection);
3544 ConnectionAdded (connection); /* EMIT SIGNAL */
3550 Session::remove_connection (ARDOUR::Connection* connection)
3552 bool removed = false;
3555 Glib::Mutex::Lock guard (connection_lock);
3556 ConnectionList::iterator i = find (_connections.begin(), _connections.end(), connection);
3558 if (i != _connections.end()) {
3559 _connections.erase (i);
3565 ConnectionRemoved (connection); /* EMIT SIGNAL */
3571 ARDOUR::Connection *
3572 Session::connection_by_name (string name) const
3574 Glib::Mutex::Lock lm (connection_lock);
3576 for (ConnectionList::const_iterator i = _connections.begin(); i != _connections.end(); ++i) {
3577 if ((*i)->name() == name) {
3586 Session::set_edit_mode (EditMode mode)
3591 Glib::Mutex::Lock lm (playlist_lock);
3593 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3594 (*i)->set_edit_mode (mode);
3599 ControlChanged (EditingMode); /* EMIT SIGNAL */
3603 Session::tempo_map_changed (Change ignored)
3609 /** Ensures that all buffers (scratch, send, silent, etc) are allocated for
3610 * the given count with the current block size.
3613 Session::ensure_buffers (ChanCount howmany)
3615 // FIXME: NASTY assumption (midi block size == audio block size)
3616 _scratch_buffers->ensure_buffers(howmany, current_block_size);
3617 _send_buffers->ensure_buffers(howmany, current_block_size);
3618 _silent_buffers->ensure_buffers(howmany, current_block_size);
3620 allocate_pan_automation_buffers (current_block_size, howmany.get(DataType::AUDIO), false);
3624 Session::next_send_name ()
3627 snprintf (buf, sizeof (buf), "send %" PRIu32, ++send_cnt);
3632 Session::next_insert_name ()
3635 snprintf (buf, sizeof (buf), "insert %" PRIu32, ++insert_cnt);
3639 /* Named Selection management */
3642 Session::named_selection_by_name (string name)
3644 Glib::Mutex::Lock lm (named_selection_lock);
3645 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) {
3646 if ((*i)->name == name) {
3654 Session::add_named_selection (NamedSelection* named_selection)
3657 Glib::Mutex::Lock lm (named_selection_lock);
3658 named_selections.insert (named_selections.begin(), named_selection);
3663 NamedSelectionAdded (); /* EMIT SIGNAL */
3667 Session::remove_named_selection (NamedSelection* named_selection)
3669 bool removed = false;
3672 Glib::Mutex::Lock lm (named_selection_lock);
3674 NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection);
3676 if (i != named_selections.end()) {
3678 named_selections.erase (i);
3685 NamedSelectionRemoved (); /* EMIT SIGNAL */
3690 Session::reset_native_file_format ()
3692 // jlc - WHY take routelock?
3693 //RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__);
3694 Glib::RWLock::ReaderLock lm2 (diskstream_lock);
3696 for (DiskstreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
3697 (*i)->reset_write_sources (false);
3702 Session::route_name_unique (string n) const
3704 shared_ptr<RouteList> r = routes.reader ();
3706 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3707 if ((*i)->name() == n) {
3716 Session::cleanup_audio_file_source (AudioFileSource& fs)
3718 return fs.move_to_trash (dead_sound_dir_name);
3722 Session::n_playlists () const
3724 Glib::Mutex::Lock lm (playlist_lock);
3725 return playlists.size();
3729 Session::set_solo_model (SoloModel sm)
3731 if (sm != _solo_model) {
3733 ControlChanged (SoloingModel);
3739 Session::allocate_pan_automation_buffers (jack_nframes_t nframes, uint32_t howmany, bool force)
3741 if (!force && howmany <= _npan_buffers) {
3745 if (_pan_automation_buffer) {
3747 for (uint32_t i = 0; i < _npan_buffers; ++i) {
3748 delete [] _pan_automation_buffer[i];
3751 delete [] _pan_automation_buffer;
3754 _pan_automation_buffer = new pan_t*[howmany];
3756 for (uint32_t i = 0; i < howmany; ++i) {
3757 _pan_automation_buffer[i] = new pan_t[nframes];
3760 _npan_buffers = howmany;
3764 Session::freeze (InterThreadInfo& itt)
3766 shared_ptr<RouteList> r = routes.reader ();
3768 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3772 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
3773 /* XXX this is wrong because itt.progress will keep returning to zero at the start
3784 Session::write_one_audio_track (AudioTrack& track, jack_nframes_t start, jack_nframes_t len,
3785 bool overwrite, vector<Source*>& srcs, InterThreadInfo& itt)
3788 Playlist* playlist = 0;
3789 AudioFileSource* fsource = 0;
3791 char buf[PATH_MAX+1];
3793 ChanCount nchans(track.audio_diskstream().n_channels());
3794 jack_nframes_t position;
3795 jack_nframes_t this_chunk;
3796 jack_nframes_t to_do;
3799 // any bigger than this seems to cause stack overflows in called functions
3800 const jack_nframes_t chunk_size = (128 * 1024)/4;
3802 g_atomic_int_set (&processing_prohibited, 1);
3804 /* call tree *MUST* hold route_lock */
3806 if ((playlist = track.diskstream().playlist()) == 0) {
3810 /* external redirects will be a problem */
3812 if (track.has_external_redirects()) {
3816 dir = discover_best_sound_dir ();
3818 for (uint32_t chan_n=0; chan_n < nchans.get(DataType::AUDIO); ++chan_n) {
3820 for (x = 0; x < 99999; ++x) {
3821 snprintf (buf, sizeof(buf), "%s/%s-%d-bounce-%" PRIu32 ".wav", dir.c_str(), playlist->name().c_str(), chan_n, x+1);
3822 if (access (buf, F_OK) != 0) {
3828 error << string_compose (_("too many bounced versions of playlist \"%1\""), playlist->name()) << endmsg;
3833 fsource = new SndFileSource (buf,
3834 Config->get_native_file_data_format(),
3835 Config->get_native_file_header_format(),
3840 catch (failed_constructor& err) {
3841 error << string_compose (_("cannot create new audio file \"%1\" for %2"), buf, track.name()) << endmsg;
3845 srcs.push_back(fsource);
3848 /* XXX need to flush all redirects */
3853 /* create a set of reasonably-sized buffers */
3854 buffers.ensure_buffers(nchans, chunk_size);
3855 buffers.set_count(nchans);
3857 while (to_do && !itt.cancel) {
3859 this_chunk = min (to_do, chunk_size);
3861 if (track.export_stuff (buffers, start, this_chunk)) {
3866 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) {
3867 AudioFileSource* afs = dynamic_cast<AudioFileSource*>(*src);
3870 if (afs->write (buffers.get_audio(n).data(this_chunk), this_chunk) != this_chunk) {
3876 start += this_chunk;
3877 to_do -= this_chunk;
3879 itt.progress = (float) (1.0 - ((double) to_do / len));
3888 xnow = localtime (&now);
3890 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3891 AudioFileSource* afs = dynamic_cast<AudioFileSource*>(*src);
3893 afs->update_header (position, *xnow, now);
3897 /* build peakfile for new source */
3899 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3900 AudioFileSource* afs = dynamic_cast<AudioFileSource*>(*src);
3902 afs->build_peaks ();
3911 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3912 AudioFileSource* afs = dynamic_cast<AudioFileSource*>(*src);
3914 afs->mark_for_remove ();
3920 g_atomic_int_set (&processing_prohibited, 0);
3928 Session::get_silent_buffers (ChanCount count)
3930 assert(_silent_buffers->available() >= count);
3931 _silent_buffers->set_count(count);
3933 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
3934 for (size_t i=0; i < count.get(*t); ++i) {
3935 _silent_buffers->get(*t, i).clear();
3939 return *_silent_buffers;
3943 Session::get_scratch_buffers (ChanCount count)
3945 assert(_scratch_buffers->available() >= count);
3946 _scratch_buffers->set_count(count);
3947 return *_scratch_buffers;
3951 Session::get_send_buffers (ChanCount count)
3953 assert(_send_buffers->available() >= count);
3954 _send_buffers->set_count(count);
3955 return *_send_buffers;
3959 Session::ntracks () const
3962 shared_ptr<RouteList> r = routes.reader ();
3964 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3965 if (dynamic_cast<Track*> ((*i).get())) {
3974 Session::nbusses () const
3977 shared_ptr<RouteList> r = routes.reader ();
3979 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3980 if (dynamic_cast<Track*> ((*i).get()) == 0) {
3989 Session::set_layer_model (LayerModel lm)
3991 if (lm != layer_model) {
3994 ControlChanged (LayeringModel);
3999 Session::set_xfade_model (CrossfadeModel xm)
4001 if (xm != xfade_model) {
4004 ControlChanged (CrossfadingModel);