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>
74 #include <ardour/source_factory.h>
77 #include <ardour/osc.h>
83 using namespace ARDOUR;
85 using boost::shared_ptr;
87 const char* Session::_template_suffix = X_(".template");
88 const char* Session::_statefile_suffix = X_(".ardour");
89 const char* Session::_pending_suffix = X_(".pending");
90 const char* Session::sound_dir_name = X_("sounds");
91 const char* Session::tape_dir_name = X_("tapes");
92 const char* Session::peak_dir_name = X_("peaks");
93 const char* Session::dead_sound_dir_name = X_("dead_sounds");
95 Session::compute_peak_t Session::compute_peak = 0;
96 Session::apply_gain_to_buffer_t Session::apply_gain_to_buffer = 0;
97 Session::mix_buffers_with_gain_t Session::mix_buffers_with_gain = 0;
98 Session::mix_buffers_no_gain_t Session::mix_buffers_no_gain = 0;
100 sigc::signal<int> Session::AskAboutPendingState;
101 sigc::signal<void> Session::SMPTEOffsetChanged;
102 sigc::signal<void> Session::SendFeedback;
106 Session::find_session (string str, string& path, string& snapshot, bool& isnew)
109 char buf[PATH_MAX+1];
113 if (!realpath (str.c_str(), buf) && (errno != ENOENT && errno != ENOTDIR)) {
114 error << string_compose (_("Could not resolve path: %1 (%2)"), buf, strerror(errno)) << endmsg;
120 /* check to see if it exists, and what it is */
122 if (stat (str.c_str(), &statbuf)) {
123 if (errno == ENOENT) {
126 error << string_compose (_("cannot check session path %1 (%2)"), str, strerror (errno))
134 /* it exists, so it must either be the name
135 of the directory, or the name of the statefile
139 if (S_ISDIR (statbuf.st_mode)) {
141 string::size_type slash = str.find_last_of ('/');
143 if (slash == string::npos) {
145 /* a subdirectory of cwd, so statefile should be ... */
151 tmp += _statefile_suffix;
155 if (stat (tmp.c_str(), &statbuf)) {
156 error << string_compose (_("cannot check statefile %1 (%2)"), tmp, strerror (errno))
166 /* some directory someplace in the filesystem.
167 the snapshot name is the directory name
172 snapshot = str.substr (slash+1);
176 } else if (S_ISREG (statbuf.st_mode)) {
178 string::size_type slash = str.find_last_of ('/');
179 string::size_type suffix;
181 /* remove the suffix */
183 if (slash != string::npos) {
184 snapshot = str.substr (slash+1);
189 suffix = snapshot.find (_statefile_suffix);
191 if (suffix == string::npos) {
192 error << string_compose (_("%1 is not an Ardour snapshot file"), str) << endmsg;
198 snapshot = snapshot.substr (0, suffix);
200 if (slash == string::npos) {
202 /* we must be in the directory where the
203 statefile lives. get it using cwd().
206 char cwd[PATH_MAX+1];
208 if (getcwd (cwd, sizeof (cwd)) == 0) {
209 error << string_compose (_("cannot determine current working directory (%1)"), strerror (errno))
218 /* full path to the statefile */
220 path = str.substr (0, slash);
225 /* what type of file is it? */
226 error << string_compose (_("unknown file type for session %1"), str) << endmsg;
232 /* its the name of a new directory. get the name
236 string::size_type slash = str.find_last_of ('/');
238 if (slash == string::npos) {
240 /* no slash, just use the name, but clean it up */
242 path = legalize_for_path (str);
248 snapshot = str.substr (slash+1);
255 Session::Session (AudioEngine &eng,
257 string snapshot_name,
258 string* mix_template)
261 _scratch_buffers(new BufferSet()),
262 _silent_buffers(new BufferSet()),
263 _send_buffers(new BufferSet()),
264 _mmc_port (default_mmc_port),
265 _mtc_port (default_mtc_port),
266 _midi_port (default_midi_port),
267 pending_events (2048),
268 //midi_requests (128), // the size of this should match the midi request pool size
269 _send_smpte_update (false),
270 diskstreams (new DiskstreamList),
271 routes (new RouteList),
272 auditioner ((Auditioner*) 0),
278 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << " (1)" << endl;
280 n_physical_outputs = _engine.n_physical_outputs();
281 n_physical_inputs = _engine.n_physical_inputs();
283 first_stage_init (fullpath, snapshot_name);
285 if (create (new_session, mix_template, _engine.frame_rate() * 60 * 5)) {
286 cerr << "create failed\n";
287 throw failed_constructor ();
290 if (second_stage_init (new_session)) {
291 cerr << "2nd state failed\n";
292 throw failed_constructor ();
295 store_recent_sessions(_name, _path);
297 bool was_dirty = dirty();
299 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
302 DirtyChanged (); /* EMIT SIGNAL */
306 Session::Session (AudioEngine &eng,
308 string snapshot_name,
309 AutoConnectOption input_ac,
310 AutoConnectOption output_ac,
311 uint32_t control_out_channels,
312 uint32_t master_out_channels,
313 uint32_t requested_physical_in,
314 uint32_t requested_physical_out,
315 jack_nframes_t initial_length)
318 _scratch_buffers(new BufferSet()),
319 _silent_buffers(new BufferSet()),
320 _send_buffers(new BufferSet()),
321 _mmc_port (default_mmc_port),
322 _mtc_port (default_mtc_port),
323 _midi_port (default_midi_port),
324 pending_events (2048),
325 //midi_requests (16),
326 _send_smpte_update (false),
327 diskstreams (new DiskstreamList),
328 routes (new RouteList),
334 cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << " (2)" << endl;
336 n_physical_outputs = max (requested_physical_out, _engine.n_physical_outputs());
337 n_physical_inputs = max (requested_physical_in, _engine.n_physical_inputs());
339 first_stage_init (fullpath, snapshot_name);
341 if (create (new_session, 0, initial_length)) {
342 throw failed_constructor ();
345 if (control_out_channels) {
346 shared_ptr<Route> r (new Route (*this, _("monitor"), -1, control_out_channels, -1, control_out_channels, Route::ControlOut));
353 if (master_out_channels) {
354 shared_ptr<Route> r (new Route (*this, _("master"), -1, master_out_channels, -1, master_out_channels, Route::MasterOut));
360 /* prohibit auto-connect to master, because there isn't one */
361 output_ac = AutoConnectOption (output_ac & ~AutoConnectMaster);
364 input_auto_connect = input_ac;
365 output_auto_connect = output_ac;
367 if (second_stage_init (new_session)) {
368 throw failed_constructor ();
371 store_recent_sessions(_name, _path);
373 bool was_dirty = dirty ();
375 _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
378 DirtyChanged (); /* EMIT SIGNAL */
384 /* if we got to here, leaving pending capture state around
388 remove_pending_capture_state ();
390 _state_of_the_state = StateOfTheState (CannotSave|Deletion);
391 _engine.remove_session ();
393 GoingAway (); /* EMIT SIGNAL */
399 /* clear history so that no references to objects are held any more */
403 /* clear state tree so that no references to objects are held any more */
409 terminate_butler_thread ();
410 //terminate_midi_thread ();
412 if (click_data && click_data != default_click) {
413 delete [] click_data;
416 if (click_emphasis_data && click_emphasis_data != default_click_emphasis) {
417 delete [] click_emphasis_data;
422 delete _scratch_buffers;
423 delete _silent_buffers;
424 delete _send_buffers;
426 AudioDiskstream::free_working_buffers();
428 #undef TRACK_DESTRUCTION
429 #ifdef TRACK_DESTRUCTION
430 cerr << "delete named selections\n";
431 #endif /* TRACK_DESTRUCTION */
432 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ) {
433 NamedSelectionList::iterator tmp;
442 #ifdef TRACK_DESTRUCTION
443 cerr << "delete playlists\n";
444 #endif /* TRACK_DESTRUCTION */
445 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ) {
446 PlaylistList::iterator tmp;
456 #ifdef TRACK_DESTRUCTION
457 cerr << "delete regions\n";
458 #endif /* TRACK_DESTRUCTION */
460 for (RegionList::iterator i = regions.begin(); i != regions.end(); ++i) {
461 i->second->drop_references ();
466 #ifdef TRACK_DESTRUCTION
467 cerr << "delete routes\n";
468 #endif /* TRACK_DESTRUCTION */
470 RCUWriter<RouteList> writer (routes);
471 boost::shared_ptr<RouteList> r = writer.get_copy ();
472 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
473 (*i)->drop_references ();
476 /* writer goes out of scope and updates master */
481 #ifdef TRACK_DESTRUCTION
482 cerr << "delete diskstreams\n";
483 #endif /* TRACK_DESTRUCTION */
485 RCUWriter<DiskstreamList> dwriter (diskstreams);
486 boost::shared_ptr<DiskstreamList> dsl = dwriter.get_copy();
487 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
488 (*i)->drop_references ();
492 diskstreams.flush ();
494 #ifdef TRACK_DESTRUCTION
495 cerr << "delete audio sources\n";
496 #endif /* TRACK_DESTRUCTION */
497 for (SourceMap::iterator i = sources.begin(); i != sources.end(); ) {
498 SourceMap::iterator tmp;
503 i->second->drop_references ();
510 #ifdef TRACK_DESTRUCTION
511 cerr << "delete mix groups\n";
512 #endif /* TRACK_DESTRUCTION */
513 for (list<RouteGroup *>::iterator i = mix_groups.begin(); i != mix_groups.end(); ) {
514 list<RouteGroup*>::iterator tmp;
524 #ifdef TRACK_DESTRUCTION
525 cerr << "delete edit groups\n";
526 #endif /* TRACK_DESTRUCTION */
527 for (list<RouteGroup *>::iterator i = edit_groups.begin(); i != edit_groups.end(); ) {
528 list<RouteGroup*>::iterator tmp;
538 #ifdef TRACK_DESTRUCTION
539 cerr << "delete connections\n";
540 #endif /* TRACK_DESTRUCTION */
541 for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); ) {
542 ConnectionList::iterator tmp;
552 if (butler_mixdown_buffer) {
553 delete [] butler_mixdown_buffer;
556 if (butler_gain_buffer) {
557 delete [] butler_gain_buffer;
560 Crossfade::set_buffer_size (0);
568 Session::set_worst_io_latencies ()
570 _worst_output_latency = 0;
571 _worst_input_latency = 0;
573 if (!_engine.connected()) {
577 boost::shared_ptr<RouteList> r = routes.reader ();
579 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
580 _worst_output_latency = max (_worst_output_latency, (*i)->output_latency());
581 _worst_input_latency = max (_worst_input_latency, (*i)->input_latency());
586 Session::when_engine_running ()
588 string first_physical_output;
590 /* we don't want to run execute this again */
592 first_time_running.disconnect ();
594 set_block_size (_engine.frames_per_cycle());
595 set_frame_rate (_engine.frame_rate());
597 /* every time we reconnect, recompute worst case output latencies */
599 _engine.Running.connect (mem_fun (*this, &Session::set_worst_io_latencies));
601 if (synced_to_jack()) {
602 _engine.transport_stop ();
605 if (Config->get_jack_time_master()) {
606 _engine.transport_locate (_transport_frame);
614 _click_io.reset (new ClickIO (*this, "click", 0, 0, -1, -1));
616 if (state_tree && (child = find_named_node (*state_tree->root(), "Click")) != 0) {
618 /* existing state for Click */
620 if (_click_io->set_state (*child->children().front()) == 0) {
622 _clicking = click_requested;
626 error << _("could not setup Click I/O") << endmsg;
632 /* default state for Click */
634 first_physical_output = _engine.get_nth_physical_output (DataType::AUDIO, 0);
636 if (first_physical_output.length()) {
637 if (_click_io->add_output_port (first_physical_output, this)) {
638 // relax, even though its an error
640 _clicking = click_requested;
646 catch (failed_constructor& err) {
647 error << _("cannot setup Click I/O") << endmsg;
650 set_worst_io_latencies ();
653 ControlChanged (Clicking); /* EMIT SIGNAL */
656 if (auditioner == 0) {
658 /* we delay creating the auditioner till now because
659 it makes its own connections to ports named
660 in the ARDOUR_RC config file. the engine has
661 to be running for this to work.
665 auditioner.reset (new Auditioner (*this));
668 catch (failed_constructor& err) {
669 warning << _("cannot create Auditioner: no auditioning of regions possible") << endmsg;
673 /* Create a set of Connection objects that map
674 to the physical outputs currently available
679 for (uint32_t np = 0; np < n_physical_outputs; ++np) {
681 snprintf (buf, sizeof (buf), _("out %" PRIu32), np+1);
683 Connection* c = new OutputConnection (buf, true);
686 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
691 for (uint32_t np = 0; np < n_physical_inputs; ++np) {
693 snprintf (buf, sizeof (buf), _("in %" PRIu32), np+1);
695 Connection* c = new InputConnection (buf, true);
698 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
705 for (uint32_t np = 0; np < n_physical_outputs; np +=2) {
707 snprintf (buf, sizeof (buf), _("out %" PRIu32 "+%" PRIu32), np+1, np+2);
709 Connection* c = new OutputConnection (buf, true);
713 c->add_connection (0, _engine.get_nth_physical_output (DataType::AUDIO, np));
714 c->add_connection (1, _engine.get_nth_physical_output (DataType::AUDIO, np+1));
719 for (uint32_t np = 0; np < n_physical_inputs; np +=2) {
721 snprintf (buf, sizeof (buf), _("in %" PRIu32 "+%" PRIu32), np+1, np+2);
723 Connection* c = new InputConnection (buf, true);
727 c->add_connection (0, _engine.get_nth_physical_input (DataType::AUDIO, np));
728 c->add_connection (1, _engine.get_nth_physical_input (DataType::AUDIO, np+1));
737 /* create master/control ports */
742 /* force the master to ignore any later call to this */
744 if (_master_out->pending_state_node) {
745 _master_out->ports_became_legal();
748 /* no panner resets till we are through */
750 _master_out->defer_pan_reset ();
752 while (_master_out->n_inputs().get(DataType::AUDIO)
753 < _master_out->input_maximum().get(DataType::AUDIO)) {
754 if (_master_out->add_input_port ("", this, DataType::AUDIO)) {
755 error << _("cannot setup master inputs")
761 while (_master_out->n_outputs().get(DataType::AUDIO)
762 < _master_out->output_maximum().get(DataType::AUDIO)) {
763 if (_master_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this, DataType::AUDIO)) {
764 error << _("cannot setup master outputs")
771 _master_out->allow_pan_reset ();
775 Connection* c = new OutputConnection (_("Master Out"), true);
777 for (uint32_t n = 0; n < _master_out->n_inputs ().get_total(); ++n) {
779 c->add_connection ((int) n, _master_out->input(n)->name());
786 /* catch up on send+insert cnts */
790 for (list<PortInsert*>::iterator i = _port_inserts.begin(); i != _port_inserts.end(); ++i) {
793 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
794 if (id > insert_cnt) {
802 for (list<Send*>::iterator i = _sends.begin(); i != _sends.end(); ++i) {
805 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
812 _state_of_the_state = StateOfTheState (_state_of_the_state & ~(CannotSave|Dirty));
814 /* hook us up to the engine */
816 _engine.set_session (this);
821 osc->set_session (*this);
824 _state_of_the_state = Clean;
826 DirtyChanged (); /* EMIT SIGNAL */
830 Session::hookup_io ()
832 /* stop graph reordering notifications from
833 causing resorts, etc.
836 _state_of_the_state = StateOfTheState (_state_of_the_state | InitialConnecting);
838 /* Tell all IO objects to create their ports */
845 while (_control_out->n_inputs().get(DataType::AUDIO) < _control_out->input_maximum().get(DataType::AUDIO)) {
846 if (_control_out->add_input_port ("", this)) {
847 error << _("cannot setup control inputs")
853 while (_control_out->n_outputs().get(DataType::AUDIO) < _control_out->output_maximum().get(DataType::AUDIO)) {
854 if (_control_out->add_output_port (_engine.get_nth_physical_output (DataType::AUDIO, n), this)) {
855 error << _("cannot set up master outputs")
863 /* Tell all IO objects to connect themselves together */
865 IO::enable_connecting ();
867 /* Now reset all panners */
869 IO::reset_panners ();
871 /* Anyone who cares about input state, wake up and do something */
873 IOConnectionsComplete (); /* EMIT SIGNAL */
875 _state_of_the_state = StateOfTheState (_state_of_the_state & ~InitialConnecting);
877 /* now handle the whole enchilada as if it was one
883 /* update mixer solo state */
889 Session::playlist_length_changed (Playlist* pl)
891 /* we can't just increase end_location->end() if pl->get_maximum_extent()
892 if larger. if the playlist used to be the longest playlist,
893 and its now shorter, we have to decrease end_location->end(). hence,
894 we have to iterate over all diskstreams and check the
895 playlists currently in use.
901 Session::diskstream_playlist_changed (boost::shared_ptr<Diskstream> dstream)
905 if ((playlist = dstream->playlist()) != 0) {
906 playlist->LengthChanged.connect (sigc::bind (mem_fun (this, &Session::playlist_length_changed), playlist));
909 /* see comment in playlist_length_changed () */
914 Session::record_enabling_legal () const
916 /* this used to be in here, but survey says.... we don't need to restrict it */
917 // if (record_status() == Recording) {
928 Session::set_auto_play (bool yn)
930 if (auto_play != yn) {
933 ControlChanged (AutoPlay);
938 Session::set_auto_return (bool yn)
940 if (auto_return != yn) {
943 ControlChanged (AutoReturn);
948 Session::set_crossfades_active (bool yn)
950 if (crossfades_active != yn) {
951 crossfades_active = yn;
953 ControlChanged (CrossFadesActive);
958 Session::set_do_not_record_plugins (bool yn)
960 if (do_not_record_plugins != yn) {
961 do_not_record_plugins = yn;
963 ControlChanged (RecordingPlugins);
968 Session::set_auto_input (bool yn)
970 if (auto_input != yn) {
973 if (Config->get_use_hardware_monitoring() && transport_rolling()) {
974 /* auto-input only makes a difference if we're rolling */
976 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
978 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
979 if ((*i)->record_enabled ()) {
980 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
981 (*i)->monitor_input (!auto_input);
987 ControlChanged (AutoInput);
992 Session::reset_input_monitor_state ()
994 if (transport_rolling()) {
996 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
998 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
999 if ((*i)->record_enabled ()) {
1000 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
1001 (*i)->monitor_input (Config->get_use_hardware_monitoring() && !auto_input);
1005 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1007 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1008 if ((*i)->record_enabled ()) {
1009 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
1010 (*i)->monitor_input (Config->get_use_hardware_monitoring());
1018 Session::set_input_auto_connect (bool yn)
1021 input_auto_connect = AutoConnectOption (input_auto_connect|AutoConnectPhysical);
1023 input_auto_connect = AutoConnectOption (input_auto_connect|~AutoConnectPhysical);
1029 Session::get_input_auto_connect () const
1031 return (input_auto_connect & AutoConnectPhysical);
1035 Session::set_output_auto_connect (AutoConnectOption aco)
1037 output_auto_connect = aco;
1042 Session::auto_punch_start_changed (Location* location)
1044 replace_event (Event::PunchIn, location->start());
1046 if (get_record_enabled() && get_punch_in()) {
1047 /* capture start has been changed, so save new pending state */
1048 save_state ("", true);
1053 Session::auto_punch_end_changed (Location* location)
1055 jack_nframes_t when_to_stop = location->end();
1056 // when_to_stop += _worst_output_latency + _worst_input_latency;
1057 replace_event (Event::PunchOut, when_to_stop);
1061 Session::auto_punch_changed (Location* location)
1063 jack_nframes_t when_to_stop = location->end();
1065 replace_event (Event::PunchIn, location->start());
1066 //when_to_stop += _worst_output_latency + _worst_input_latency;
1067 replace_event (Event::PunchOut, when_to_stop);
1071 Session::auto_loop_changed (Location* location)
1073 replace_event (Event::AutoLoop, location->end(), location->start());
1075 if (transport_rolling() && get_auto_loop()) {
1077 //if (_transport_frame < location->start() || _transport_frame > location->end()) {
1079 if (_transport_frame > location->end()) {
1080 // relocate to beginning of loop
1081 clear_events (Event::LocateRoll);
1083 request_locate (location->start(), true);
1086 else if (seamless_loop && !loop_changing) {
1088 // schedule a locate-roll to refill the diskstreams at the
1089 // previous loop end
1090 loop_changing = true;
1092 if (location->end() > last_loopend) {
1093 clear_events (Event::LocateRoll);
1094 Event *ev = new Event (Event::LocateRoll, Event::Add, last_loopend, last_loopend, 0, true);
1101 last_loopend = location->end();
1106 Session::set_auto_punch_location (Location* location)
1110 if ((existing = _locations.auto_punch_location()) != 0 && existing != location) {
1111 auto_punch_start_changed_connection.disconnect();
1112 auto_punch_end_changed_connection.disconnect();
1113 auto_punch_changed_connection.disconnect();
1114 existing->set_auto_punch (false, this);
1115 remove_event (existing->start(), Event::PunchIn);
1116 clear_events (Event::PunchOut);
1117 auto_punch_location_changed (0);
1122 if (location == 0) {
1126 if (location->end() <= location->start()) {
1127 error << _("Session: you can't use that location for auto punch (start <= end)") << endmsg;
1131 auto_punch_start_changed_connection.disconnect();
1132 auto_punch_end_changed_connection.disconnect();
1133 auto_punch_changed_connection.disconnect();
1135 auto_punch_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_punch_start_changed));
1136 auto_punch_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_punch_end_changed));
1137 auto_punch_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_punch_changed));
1139 location->set_auto_punch (true, this);
1140 auto_punch_location_changed (location);
1144 Session::set_punch_in (bool yn)
1146 if (punch_in == yn) {
1152 if ((location = _locations.auto_punch_location()) != 0) {
1153 if ((punch_in = yn) == true) {
1154 replace_event (Event::PunchIn, location->start());
1156 remove_event (location->start(), Event::PunchIn);
1161 ControlChanged (PunchIn); /* EMIT SIGNAL */
1165 Session::set_punch_out (bool yn)
1167 if (punch_out == yn) {
1173 if ((location = _locations.auto_punch_location()) != 0) {
1174 if ((punch_out = yn) == true) {
1175 replace_event (Event::PunchOut, location->end());
1177 clear_events (Event::PunchOut);
1182 ControlChanged (PunchOut); /* EMIT SIGNAL */
1186 Session::set_auto_loop_location (Location* location)
1190 if ((existing = _locations.auto_loop_location()) != 0 && existing != location) {
1191 auto_loop_start_changed_connection.disconnect();
1192 auto_loop_end_changed_connection.disconnect();
1193 auto_loop_changed_connection.disconnect();
1194 existing->set_auto_loop (false, this);
1195 remove_event (existing->end(), Event::AutoLoop);
1196 auto_loop_location_changed (0);
1201 if (location == 0) {
1205 if (location->end() <= location->start()) {
1206 error << _("Session: you can't use a mark for auto loop") << endmsg;
1210 last_loopend = location->end();
1212 auto_loop_start_changed_connection.disconnect();
1213 auto_loop_end_changed_connection.disconnect();
1214 auto_loop_changed_connection.disconnect();
1216 auto_loop_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1217 auto_loop_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1218 auto_loop_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_loop_changed));
1220 location->set_auto_loop (true, this);
1221 auto_loop_location_changed (location);
1225 Session::locations_added (Location* ignored)
1231 Session::locations_changed ()
1233 _locations.apply (*this, &Session::handle_locations_changed);
1237 Session::handle_locations_changed (Locations::LocationList& locations)
1239 Locations::LocationList::iterator i;
1241 bool set_loop = false;
1242 bool set_punch = false;
1244 for (i = locations.begin(); i != locations.end(); ++i) {
1248 if (location->is_auto_punch()) {
1249 set_auto_punch_location (location);
1252 if (location->is_auto_loop()) {
1253 set_auto_loop_location (location);
1260 set_auto_loop_location (0);
1263 set_auto_punch_location (0);
1270 Session::enable_record ()
1272 /* XXX really atomic compare+swap here */
1273 if (g_atomic_int_get (&_record_status) != Recording) {
1274 g_atomic_int_set (&_record_status, Recording);
1275 _last_record_location = _transport_frame;
1276 deliver_mmc(MIDI::MachineControl::cmdRecordStrobe, _last_record_location);
1278 if (Config->get_use_hardware_monitoring() && auto_input) {
1279 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1280 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1281 if ((*i)->record_enabled ()) {
1282 (*i)->monitor_input (true);
1287 RecordStateChanged ();
1292 Session::disable_record (bool rt_context, bool force)
1296 if ((rs = (RecordState) g_atomic_int_get (&_record_status)) != Disabled) {
1298 if (!Config->get_latched_record_enable () || force) {
1299 g_atomic_int_set (&_record_status, Disabled);
1301 if (rs == Recording) {
1302 g_atomic_int_set (&_record_status, Enabled);
1306 // FIXME: timestamp correct? [DR]
1307 // FIXME FIXME FIXME: rt_context? this must be called in the process thread.
1308 // does this /need/ to be sent in all cases?
1310 deliver_mmc (MIDI::MachineControl::cmdRecordExit, _transport_frame);
1312 if (Config->get_use_hardware_monitoring() && auto_input) {
1313 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1315 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1316 if ((*i)->record_enabled ()) {
1317 (*i)->monitor_input (false);
1322 RecordStateChanged (); /* emit signal */
1325 remove_pending_capture_state ();
1331 Session::step_back_from_record ()
1333 g_atomic_int_set (&_record_status, Enabled);
1335 if (Config->get_use_hardware_monitoring()) {
1336 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1338 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1339 if (auto_input && (*i)->record_enabled ()) {
1340 //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1341 (*i)->monitor_input (false);
1348 Session::maybe_enable_record ()
1350 g_atomic_int_set (&_record_status, Enabled);
1352 /* XXX this save should really happen in another thread. its needed so that
1353 pending capture state can be recovered if we crash.
1356 save_state ("", true);
1358 if (_transport_speed) {
1363 deliver_mmc (MIDI::MachineControl::cmdRecordPause, _transport_frame);
1364 RecordStateChanged (); /* EMIT SIGNAL */
1371 Session::audible_frame () const
1374 jack_nframes_t offset;
1377 /* the first of these two possible settings for "offset"
1378 mean that the audible frame is stationary until
1379 audio emerges from the latency compensation
1382 the second means that the audible frame is stationary
1383 until audio would emerge from a physical port
1384 in the absence of any plugin latency compensation
1387 offset = _worst_output_latency;
1389 if (offset > current_block_size) {
1390 offset -= current_block_size;
1392 /* XXX is this correct? if we have no external
1393 physical connections and everything is internal
1394 then surely this is zero? still, how
1395 likely is that anyway?
1397 offset = current_block_size;
1400 if (synced_to_jack()) {
1401 tf = _engine.transport_frame();
1403 tf = _transport_frame;
1406 if (_transport_speed == 0) {
1416 if (!non_realtime_work_pending()) {
1420 /* take latency into account */
1429 Session::set_frame_rate (jack_nframes_t frames_per_second)
1431 /** \fn void Session::set_frame_size(jack_nframes_t)
1432 the AudioEngine object that calls this guarantees
1433 that it will not be called while we are also in
1434 ::process(). Its fine to do things that block
1438 _current_frame_rate = frames_per_second;
1439 _frames_per_smpte_frame = (double) _current_frame_rate / (double) smpte_frames_per_second;
1441 Route::set_automation_interval ((jack_nframes_t) ceil ((double) frames_per_second * 0.25));
1443 // XXX we need some equivalent to this, somehow
1444 // DestructiveFileSource::setup_standard_crossfades (frames_per_second);
1448 /* XXX need to reset/reinstantiate all LADSPA plugins */
1452 Session::set_block_size (jack_nframes_t nframes)
1454 /* the AudioEngine guarantees
1455 that it will not be called while we are also in
1456 ::process(). It is therefore fine to do things that block
1462 current_block_size = nframes;
1464 ensure_buffers(_scratch_buffers->available());
1466 if (_gain_automation_buffer) {
1467 delete [] _gain_automation_buffer;
1469 _gain_automation_buffer = new gain_t[nframes];
1471 allocate_pan_automation_buffers (nframes, _npan_buffers, true);
1473 boost::shared_ptr<RouteList> r = routes.reader ();
1475 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1476 (*i)->set_block_size (nframes);
1479 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1480 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1481 (*i)->set_block_size (nframes);
1484 set_worst_io_latencies ();
1489 Session::set_default_fade (float steepness, float fade_msecs)
1492 jack_nframes_t fade_frames;
1494 /* Don't allow fade of less 1 frame */
1496 if (fade_msecs < (1000.0 * (1.0/_current_frame_rate))) {
1503 fade_frames = (jack_nframes_t) floor (fade_msecs * _current_frame_rate * 0.001);
1507 default_fade_msecs = fade_msecs;
1508 default_fade_steepness = steepness;
1511 // jlc, WTF is this!
1512 Glib::RWLock::ReaderLock lm (route_lock);
1513 AudioRegion::set_default_fade (steepness, fade_frames);
1518 /* XXX have to do this at some point */
1519 /* foreach region using default fade, reset, then
1520 refill_all_diskstream_buffers ();
1525 struct RouteSorter {
1526 bool operator() (boost::shared_ptr<Route> r1, boost::shared_ptr<Route> r2) {
1527 if (r1->fed_by.find (r2) != r1->fed_by.end()) {
1529 } else if (r2->fed_by.find (r1) != r2->fed_by.end()) {
1532 if (r1->fed_by.empty()) {
1533 if (r2->fed_by.empty()) {
1534 /* no ardour-based connections inbound to either route. just use signal order */
1535 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1537 /* r2 has connections, r1 does not; run r1 early */
1541 return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1548 trace_terminal (shared_ptr<Route> r1, shared_ptr<Route> rbase)
1550 shared_ptr<Route> r2;
1552 if ((r1->fed_by.find (rbase) != r1->fed_by.end()) && (rbase->fed_by.find (r1) != rbase->fed_by.end())) {
1553 info << string_compose(_("feedback loop setup between %1 and %2"), r1->name(), rbase->name()) << endmsg;
1557 /* make a copy of the existing list of routes that feed r1 */
1559 set<shared_ptr<Route> > existing = r1->fed_by;
1561 /* for each route that feeds r1, recurse, marking it as feeding
1565 for (set<shared_ptr<Route> >::iterator i = existing.begin(); i != existing.end(); ++i) {
1568 /* r2 is a route that feeds r1 which somehow feeds base. mark
1569 base as being fed by r2
1572 rbase->fed_by.insert (r2);
1576 /* 2nd level feedback loop detection. if r1 feeds or is fed by r2,
1580 if ((r1->fed_by.find (r2) != r1->fed_by.end()) && (r2->fed_by.find (r1) != r2->fed_by.end())) {
1584 /* now recurse, so that we can mark base as being fed by
1585 all routes that feed r2
1588 trace_terminal (r2, rbase);
1595 Session::resort_routes ()
1597 /* don't do anything here with signals emitted
1598 by Routes while we are being destroyed.
1601 if (_state_of_the_state & Deletion) {
1608 RCUWriter<RouteList> writer (routes);
1609 shared_ptr<RouteList> r = writer.get_copy ();
1610 resort_routes_using (r);
1611 /* writer goes out of scope and forces update */
1616 Session::resort_routes_using (shared_ptr<RouteList> r)
1618 RouteList::iterator i, j;
1620 for (i = r->begin(); i != r->end(); ++i) {
1622 (*i)->fed_by.clear ();
1624 for (j = r->begin(); j != r->end(); ++j) {
1626 /* although routes can feed themselves, it will
1627 cause an endless recursive descent if we
1628 detect it. so don't bother checking for
1636 if ((*j)->feeds (*i)) {
1637 (*i)->fed_by.insert (*j);
1642 for (i = r->begin(); i != r->end(); ++i) {
1643 trace_terminal (*i, *i);
1650 cerr << "finished route resort\n";
1652 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1653 cerr << " " << (*i)->name() << " signal order = " << (*i)->order_key ("signal") << endl;
1660 list<boost::shared_ptr<MidiTrack> >
1661 Session::new_midi_track (TrackMode mode, uint32_t how_many)
1663 char track_name[32];
1664 uint32_t track_id = 0;
1666 uint32_t channels_used = 0;
1668 RouteList new_routes;
1669 list<boost::shared_ptr<MidiTrack> > ret;
1671 /* count existing audio tracks */
1674 shared_ptr<RouteList> r = routes.reader ();
1676 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1677 if (dynamic_cast<MidiTrack*>((*i).get()) != 0) {
1678 if (!(*i)->hidden()) {
1680 channels_used += (*i)->n_inputs().get(DataType::MIDI);
1688 /* check for duplicate route names, since we might have pre-existing
1689 routes with this name (e.g. create Midi1, Midi2, delete Midi1,
1690 save, close,restart,add new route - first named route is now
1698 snprintf (track_name, sizeof(track_name), "Midi %" PRIu32, track_id);
1700 if (route_by_name (track_name) == 0) {
1704 } while (track_id < (UINT_MAX-1));
1707 shared_ptr<MidiTrack> track (new MidiTrack (*this, track_name, Route::Flag (0), mode));
1709 if (track->ensure_io (ChanCount(DataType::MIDI, 1), ChanCount(DataType::MIDI, 1), false, this)) {
1710 error << "cannot configure 1 in/1 out configuration for new midi track" << endmsg;
1713 channels_used += track->n_inputs ().get(DataType::MIDI);
1715 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1716 track->set_remote_control_id (ntracks());
1718 new_routes.push_back (track);
1719 ret.push_back (track);
1722 catch (failed_constructor &err) {
1723 error << _("Session: could not create new midi track.") << endmsg;
1724 // XXX should we delete the tracks already created?
1732 if (!new_routes.empty()) {
1733 add_routes (new_routes, false);
1734 save_state (_current_snapshot_name);
1741 std::list<boost::shared_ptr<MidiTrack> >
1742 Session::new_midi_track (TrackMode mode)
1744 char track_name[32];
1746 uint32_t channels_used = 0;
1749 /* count existing midi tracks */
1752 shared_ptr<RouteList> r = routes.reader ();
1754 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1755 if (dynamic_cast<MidiTrack*>((*i).get()) != 0) {
1756 if (!(*i)->hidden()) {
1758 channels_used += (*i)->n_inputs().get(DataType::MIDI);
1764 /* check for duplicate route names, since we might have pre-existing
1765 routes with this name (e.g. create Midi1, Midi2, delete Midi1,
1766 save, close,restart,add new route - first named route is now
1771 snprintf (track_name, sizeof(track_name), "Midi %" PRIu32, n+1);
1772 if (route_by_name (track_name) == 0) {
1777 } while (n < (UINT_MAX-1));
1780 shared_ptr<MidiTrack> track (new MidiTrack (*this, track_name, Route::Flag (0), mode));
1782 if (track->ensure_io (1, 1, false, this)) {
1783 error << string_compose (_("cannot configure %1 in/%2 out configuration for new midi track"), track_name)
1787 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
1791 track->set_remote_control_id (ntracks());
1795 catch (failed_constructor &err) {
1796 error << _("Session: could not create new midi track.") << endmsg;
1797 return shared_ptr<MidiTrack> ((MidiTrack*) 0);
1801 boost::shared_ptr<Route>
1802 Session::new_midi_route ()
1808 /* count existing midi busses */
1810 shared_ptr<RouteList> r = routes.reader ();
1812 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1813 if (dynamic_cast<MidiTrack*>((*i).get()) == 0) {
1814 if (!(*i)->hidden()) {
1822 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, n+1);
1823 if (route_by_name (bus_name) == 0) {
1828 } while (n < (UINT_MAX-1));
1831 shared_ptr<Route> bus (new Route (*this, bus_name, -1, -1, -1, -1, Route::Flag(0), DataType::MIDI));
1833 if (bus->ensure_io (1, 1, false, this)) {
1834 error << (_("cannot configure 1 in/1 out configuration for new midi track"))
1838 for (uint32_t x = 0; x < bus->n_inputs(); ++x) {
1842 if (input_auto_connect & AutoConnectPhysical) {
1843 port = _engine.get_nth_physical_input ((n+x)%n_physical_inputs);
1846 if (port.length() && bus->connect_input (bus->input (x), port, this)) {
1851 for (uint32_t x = 0; x < bus->n_outputs(); ++x) {
1855 if (output_auto_connect & AutoConnectPhysical) {
1856 port = _engine.get_nth_physical_input ((n+x)%n_physical_outputs);
1857 } else if (output_auto_connect & AutoConnectMaster) {
1859 port = _master_out->input (x%_master_out->n_inputs())->name();
1863 if (port.length() && bus->connect_output (bus->output (x), port, this)) {
1870 vector<string> cports;
1871 uint32_t ni = _control_out->n_inputs();
1873 for (uint32_t n = 0; n < ni; ++n) {
1874 cports.push_back (_control_out->input(n)->name());
1876 bus->set_control_outs (cports);
1883 catch (failed_constructor &err) {
1884 error << _("Session: could not create new MIDI route.") << endmsg;
1885 return shared_ptr<Route> ((Route*) 0);
1890 list<boost::shared_ptr<AudioTrack> >
1891 Session::new_audio_track (int input_channels, int output_channels, TrackMode mode, uint32_t how_many)
1893 char track_name[32];
1894 uint32_t track_id = 0;
1896 uint32_t channels_used = 0;
1898 RouteList new_routes;
1899 list<boost::shared_ptr<AudioTrack> > ret;
1901 /* count existing audio tracks */
1904 shared_ptr<RouteList> r = routes.reader ();
1906 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1907 if (dynamic_cast<AudioTrack*>((*i).get()) != 0) {
1908 if (!(*i)->hidden()) {
1910 channels_used += (*i)->n_inputs().get(DataType::AUDIO);
1916 vector<string> physinputs;
1917 vector<string> physoutputs;
1918 uint32_t nphysical_in;
1919 uint32_t nphysical_out;
1921 _engine.get_physical_outputs (physoutputs);
1922 _engine.get_physical_inputs (physinputs);
1926 /* check for duplicate route names, since we might have pre-existing
1927 routes with this name (e.g. create Audio1, Audio2, delete Audio1,
1928 save, close,restart,add new route - first named route is now
1936 snprintf (track_name, sizeof(track_name), "Audio %" PRIu32, track_id);
1938 if (route_by_name (track_name) == 0) {
1942 } while (track_id < (UINT_MAX-1));
1944 if (input_auto_connect & AutoConnectPhysical) {
1945 nphysical_in = min (n_physical_inputs, (uint32_t) physinputs.size());
1950 if (output_auto_connect & AutoConnectPhysical) {
1951 nphysical_out = min (n_physical_outputs, (uint32_t) physinputs.size());
1957 shared_ptr<AudioTrack> track (new AudioTrack (*this, track_name, Route::Flag (0), mode));
1959 if (track->ensure_io (input_channels, output_channels, false, this)) {
1960 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1961 input_channels, output_channels)
1966 for (uint32_t x = 0; x < track->n_inputs().get(DataType::AUDIO) && x < nphysical_in; ++x) {
1970 if (input_auto_connect & AutoConnectPhysical) {
1971 port = physinputs[(channels_used+x)%nphysical_in];
1974 if (port.length() && track->connect_input (track->input (x), port, this)) {
1980 for (uint32_t x = 0; x < track->n_outputs().get(DataType::MIDI); ++x) {
1984 if (nphysical_out && (output_auto_connect & AutoConnectPhysical)) {
1985 port = physoutputs[(channels_used+x)%nphysical_out];
1986 } else if (output_auto_connect & AutoConnectMaster) {
1988 port = _master_out->input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
1992 if (port.length() && track->connect_output (track->output (x), port, this)) {
1997 channels_used += track->n_inputs ().get(DataType::AUDIO);
2000 vector<string> cports;
2001 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
2003 for (n = 0; n < ni; ++n) {
2004 cports.push_back (_control_out->input(n)->name());
2007 track->set_control_outs (cports);
2010 track->DiskstreamChanged.connect (mem_fun (this, &Session::resort_routes));
2011 track->set_remote_control_id (ntracks());
2013 new_routes.push_back (track);
2014 ret.push_back (track);
2017 catch (failed_constructor &err) {
2018 error << _("Session: could not create new audio track.") << endmsg;
2019 // XXX should we delete the tracks already created?
2027 if (!new_routes.empty()) {
2028 add_routes (new_routes, false);
2029 save_state (_current_snapshot_name);
2036 Session::new_audio_route (int input_channels, int output_channels, uint32_t how_many)
2039 uint32_t bus_id = 1;
2044 /* count existing audio busses */
2047 shared_ptr<RouteList> r = routes.reader ();
2049 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2050 if (dynamic_cast<AudioTrack*>((*i).get()) == 0) {
2051 if (!(*i)->hidden()) {
2058 vector<string> physinputs;
2059 vector<string> physoutputs;
2061 _engine.get_physical_outputs (physoutputs);
2062 _engine.get_physical_inputs (physinputs);
2069 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, bus_id);
2071 if (route_by_name (bus_name) == 0) {
2075 } while (bus_id < (UINT_MAX-1));
2078 shared_ptr<Route> bus (new Route (*this, bus_name, -1, -1, -1, -1, Route::Flag(0), DataType::AUDIO));
2080 if (bus->ensure_io (input_channels, output_channels, false, this)) {
2081 error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
2082 input_channels, output_channels)
2086 for (uint32_t x = 0; x < bus->n_inputs().get(DataType::AUDIO); ++x) {
2090 if (input_auto_connect & AutoConnectPhysical) {
2091 port = physinputs[((n+x)%n_physical_inputs)];
2094 if (port.length() && bus->connect_input (bus->input (x), port, this)) {
2099 for (uint32_t x = 0; x < bus->n_outputs().get(DataType::AUDIO); ++x) {
2103 if (output_auto_connect & AutoConnectPhysical) {
2104 port = physoutputs[((n+x)%n_physical_outputs)];
2105 } else if (output_auto_connect & AutoConnectMaster) {
2107 port = _master_out->input (x%_master_out->n_inputs().get(DataType::AUDIO))->name();
2111 if (port.length() && bus->connect_output (bus->output (x), port, this)) {
2117 vector<string> cports;
2118 uint32_t ni = _control_out->n_inputs().get(DataType::AUDIO);
2120 for (uint32_t n = 0; n < ni; ++n) {
2121 cports.push_back (_control_out->input(n)->name());
2123 bus->set_control_outs (cports);
2126 ret.push_back (bus);
2130 catch (failed_constructor &err) {
2131 error << _("Session: could not create new audio route.") << endmsg;
2140 add_routes (ret, false);
2141 save_state (_current_snapshot_name);
2149 Session::add_routes (RouteList& new_routes, bool save)
2152 RCUWriter<RouteList> writer (routes);
2153 shared_ptr<RouteList> r = writer.get_copy ();
2154 r->insert (r->end(), new_routes.begin(), new_routes.end());
2155 resort_routes_using (r);
2158 for (RouteList::iterator x = new_routes.begin(); x != new_routes.end(); ++x) {
2159 (*x)->solo_changed.connect (sigc::bind (mem_fun (*this, &Session::route_solo_changed), (*x)));
2160 (*x)->mute_changed.connect (mem_fun (*this, &Session::route_mute_changed));
2161 (*x)->output_changed.connect (mem_fun (*this, &Session::set_worst_io_latencies_x));
2162 (*x)->redirects_changed.connect (mem_fun (*this, &Session::update_latency_compensation_proxy));
2164 if ((*x)->master()) {
2168 if ((*x)->control()) {
2169 _control_out = (*x);
2176 save_state (_current_snapshot_name);
2179 RouteAdded (new_routes); /* EMIT SIGNAL */
2183 Session::add_diskstream (boost::shared_ptr<Diskstream> dstream)
2185 /* need to do this in case we're rolling at the time, to prevent false underruns */
2186 dstream->do_refill_with_alloc();
2189 RCUWriter<DiskstreamList> writer (diskstreams);
2190 boost::shared_ptr<DiskstreamList> ds = writer.get_copy();
2191 ds->push_back (dstream);
2194 dstream->set_block_size (current_block_size);
2196 dstream->PlaylistChanged.connect (sigc::bind (mem_fun (*this, &Session::diskstream_playlist_changed), dstream));
2197 /* this will connect to future changes, and check the current length */
2198 diskstream_playlist_changed (dstream);
2200 dstream->prepare ();
2204 Session::remove_route (shared_ptr<Route> route)
2207 RCUWriter<RouteList> writer (routes);
2208 shared_ptr<RouteList> rs = writer.get_copy ();
2211 /* deleting the master out seems like a dumb
2212 idea, but its more of a UI policy issue
2216 if (route == _master_out) {
2217 _master_out = shared_ptr<Route> ((Route*) 0);
2220 if (route == _control_out) {
2221 _control_out = shared_ptr<Route> ((Route*) 0);
2223 /* cancel control outs for all routes */
2225 vector<string> empty;
2227 for (RouteList::iterator r = rs->begin(); r != rs->end(); ++r) {
2228 (*r)->set_control_outs (empty);
2232 update_route_solo_state ();
2234 /* writer goes out of scope, forces route list update */
2238 boost::shared_ptr<Diskstream> ds;
2240 if ((t = dynamic_cast<Track*>(route.get())) != 0) {
2241 ds = t->diskstream();
2247 RCUWriter<DiskstreamList> dsl (diskstreams);
2248 boost::shared_ptr<DiskstreamList> d = dsl.get_copy();
2253 find_current_end ();
2255 update_latency_compensation (false, false);
2258 /* XXX should we disconnect from the Route's signals ? */
2260 save_state (_current_snapshot_name);
2262 /* try to cause everyone to drop their references */
2264 route->drop_references ();
2268 Session::route_mute_changed (void* src)
2274 Session::route_solo_changed (void* src, shared_ptr<Route> route)
2276 if (solo_update_disabled) {
2283 is_track = (dynamic_cast<Track*>(route.get()) != 0);
2285 shared_ptr<RouteList> r = routes.reader ();
2287 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2289 /* soloing a track mutes all other tracks, soloing a bus mutes all other busses */
2293 /* don't mess with busses */
2295 if (dynamic_cast<Track*>((*i).get()) == 0) {
2301 /* don't mess with tracks */
2303 if (dynamic_cast<Track*>((*i).get()) != 0) {
2308 if ((*i) != route &&
2309 ((*i)->mix_group () == 0 ||
2310 (*i)->mix_group () != route->mix_group () ||
2311 !route->mix_group ()->is_active())) {
2313 if ((*i)->soloed()) {
2315 /* if its already soloed, and solo latching is enabled,
2316 then leave it as it is.
2319 if (_solo_latched) {
2326 solo_update_disabled = true;
2327 (*i)->set_solo (false, src);
2328 solo_update_disabled = false;
2332 bool something_soloed = false;
2333 bool same_thing_soloed = false;
2334 bool signal = false;
2336 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2337 if ((*i)->soloed()) {
2338 something_soloed = true;
2339 if (dynamic_cast<Track*>((*i).get())) {
2341 same_thing_soloed = true;
2346 same_thing_soloed = true;
2354 if (something_soloed != currently_soloing) {
2356 currently_soloing = something_soloed;
2359 modify_solo_mute (is_track, same_thing_soloed);
2362 SoloActive (currently_soloing);
2369 Session::set_solo_latched (bool yn)
2371 if (yn != _solo_latched) {
2374 ControlChanged (SoloLatch);
2379 Session::update_route_solo_state ()
2382 bool is_track = false;
2383 bool signal = false;
2385 /* caller must hold RouteLock */
2387 /* this is where we actually implement solo by changing
2388 the solo mute setting of each track.
2391 shared_ptr<RouteList> r = routes.reader ();
2393 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2394 if ((*i)->soloed()) {
2396 if (dynamic_cast<Track*>((*i).get())) {
2403 if (mute != currently_soloing) {
2405 currently_soloing = mute;
2408 if (!is_track && !mute) {
2410 /* nothing is soloed */
2412 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2413 (*i)->set_solo_mute (false);
2423 modify_solo_mute (is_track, mute);
2426 SoloActive (currently_soloing);
2431 Session::modify_solo_mute (bool is_track, bool mute)
2433 shared_ptr<RouteList> r = routes.reader ();
2435 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2439 /* only alter track solo mute */
2441 if (dynamic_cast<Track*>((*i).get())) {
2442 if ((*i)->soloed()) {
2443 (*i)->set_solo_mute (!mute);
2445 (*i)->set_solo_mute (mute);
2451 /* only alter bus solo mute */
2453 if (!dynamic_cast<Track*>((*i).get())) {
2455 if ((*i)->soloed()) {
2457 (*i)->set_solo_mute (false);
2461 /* don't mute master or control outs
2462 in response to another bus solo
2465 if ((*i) != _master_out &&
2466 (*i) != _control_out) {
2467 (*i)->set_solo_mute (mute);
2478 Session::catch_up_on_solo ()
2480 /* this is called after set_state() to catch the full solo
2481 state, which can't be correctly determined on a per-route
2482 basis, but needs the global overview that only the session
2485 update_route_solo_state();
2489 Session::route_by_name (string name)
2491 shared_ptr<RouteList> r = routes.reader ();
2493 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2494 if ((*i)->name() == name) {
2499 return shared_ptr<Route> ((Route*) 0);
2503 Session::route_by_id (PBD::ID id)
2505 shared_ptr<RouteList> r = routes.reader ();
2507 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2508 if ((*i)->id() == id) {
2513 return shared_ptr<Route> ((Route*) 0);
2517 Session::route_by_remote_id (uint32_t id)
2519 shared_ptr<RouteList> r = routes.reader ();
2521 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
2522 if ((*i)->remote_control_id() == id) {
2527 return shared_ptr<Route> ((Route*) 0);
2531 Session::find_current_end ()
2533 if (_state_of_the_state & Loading) {
2537 jack_nframes_t max = get_maximum_extent ();
2539 if (max > end_location->end()) {
2540 end_location->set_end (max);
2542 DurationChanged(); /* EMIT SIGNAL */
2547 Session::get_maximum_extent () const
2549 jack_nframes_t max = 0;
2552 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2554 for (DiskstreamList::const_iterator i = dsl->begin(); i != dsl->end(); ++i) {
2555 Playlist* pl = (*i)->playlist();
2556 if ((me = pl->get_maximum_extent()) > max) {
2564 boost::shared_ptr<Diskstream>
2565 Session::diskstream_by_name (string name)
2567 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2569 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2570 if ((*i)->name() == name) {
2575 return boost::shared_ptr<Diskstream>((Diskstream*) 0);
2578 boost::shared_ptr<Diskstream>
2579 Session::diskstream_by_id (const PBD::ID& id)
2581 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2583 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2584 if ((*i)->id() == id) {
2589 return boost::shared_ptr<Diskstream>((Diskstream*) 0);
2592 /* Region management */
2595 Session::new_region_name (string old)
2597 string::size_type last_period;
2599 string::size_type len = old.length() + 64;
2602 if ((last_period = old.find_last_of ('.')) == string::npos) {
2604 /* no period present - add one explicitly */
2607 last_period = old.length() - 1;
2612 number = atoi (old.substr (last_period+1).c_str());
2616 while (number < (UINT_MAX-1)) {
2618 RegionList::const_iterator i;
2623 snprintf (buf, len, "%s%" PRIu32, old.substr (0, last_period + 1).c_str(), number);
2626 for (i = regions.begin(); i != regions.end(); ++i) {
2627 if (i->second->name() == sbuf) {
2632 if (i == regions.end()) {
2637 if (number != (UINT_MAX-1)) {
2641 error << string_compose (_("cannot create new name for region \"%1\""), old) << endmsg;
2646 Session::region_name (string& result, string base, bool newlevel) const
2651 assert(base.find("/") == string::npos);
2655 Glib::Mutex::Lock lm (region_lock);
2657 snprintf (buf, sizeof (buf), "%d", (int)regions.size() + 1);
2665 /* XXX this is going to be slow. optimize me later */
2670 string::size_type pos;
2672 pos = base.find_last_of ('.');
2674 /* pos may be npos, but then we just use entire base */
2676 subbase = base.substr (0, pos);
2680 bool name_taken = true;
2683 Glib::Mutex::Lock lm (region_lock);
2685 for (int n = 1; n < 5000; ++n) {
2688 snprintf (buf, sizeof (buf), ".%d", n);
2693 for (RegionList::const_iterator i = regions.begin(); i != regions.end(); ++i) {
2694 if (i->second->name() == result) {
2707 fatal << string_compose(_("too many regions with names like %1"), base) << endmsg;
2715 Session::add_region (boost::shared_ptr<Region> region)
2717 boost::shared_ptr<Region> other;
2721 Glib::Mutex::Lock lm (region_lock);
2723 RegionList::iterator x;
2725 for (x = regions.begin(); x != regions.end(); ++x) {
2729 if (region->region_list_equivalent (other)) {
2734 if (x == regions.end()) {
2736 pair<RegionList::key_type,RegionList::mapped_type> entry;
2738 entry.first = region->id();
2739 entry.second = region;
2741 pair<RegionList::iterator,bool> x = regions.insert (entry);
2753 /* mark dirty because something has changed even if we didn't
2754 add the region to the region list.
2760 region->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_region), region));
2761 region->StateChanged.connect (sigc::bind (mem_fun (*this, &Session::region_changed), region));
2762 RegionAdded (region); /* EMIT SIGNAL */
2767 Session::region_changed (Change what_changed, boost::shared_ptr<Region> region)
2769 if (what_changed & Region::HiddenChanged) {
2770 /* relay hidden changes */
2771 RegionHiddenChange (region);
2776 Session::region_renamed (boost::shared_ptr<Region> region)
2778 add_region (region);
2782 Session::remove_region (boost::shared_ptr<Region> region)
2784 RegionList::iterator i;
2785 bool removed = false;
2788 Glib::Mutex::Lock lm (region_lock);
2790 if ((i = regions.find (region->id())) != regions.end()) {
2796 /* mark dirty because something has changed even if we didn't
2797 remove the region from the region list.
2803 RegionRemoved(region); /* EMIT SIGNAL */
2807 boost::shared_ptr<Region>
2808 Session::find_whole_file_parent (Region& child)
2810 RegionList::iterator i;
2811 boost::shared_ptr<Region> region;
2813 Glib::Mutex::Lock lm (region_lock);
2815 for (i = regions.begin(); i != regions.end(); ++i) {
2819 if (region->whole_file()) {
2821 if (child.source_equivalent (region)) {
2827 return boost::shared_ptr<AudioRegion> ((AudioRegion*) 0);
2831 Session::find_equivalent_playlist_regions (boost::shared_ptr<Region> region, vector<boost::shared_ptr<Region> >& result)
2833 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i)
2834 (*i)->get_region_list_equivalent_regions (region, result);
2838 Session::destroy_region (boost::shared_ptr<Region> region)
2840 boost::shared_ptr<AudioRegion> aregion;
2842 if ((aregion = boost::dynamic_pointer_cast<AudioRegion> (region)) == 0) {
2846 if (aregion->playlist()) {
2847 aregion->playlist()->destroy_region (region);
2850 vector<boost::shared_ptr<Source> > srcs;
2852 for (uint32_t n = 0; n < aregion->n_channels(); ++n) {
2853 srcs.push_back (aregion->source (n));
2856 for (vector<boost::shared_ptr<Source> >::iterator i = srcs.begin(); i != srcs.end(); ++i) {
2858 if ((*i).use_count() == 1) {
2859 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*i);
2862 (afs)->mark_for_remove ();
2865 (*i)->drop_references ();
2873 Session::destroy_regions (list<boost::shared_ptr<Region> > regions)
2875 for (list<boost::shared_ptr<Region> >::iterator i = regions.begin(); i != regions.end(); ++i) {
2876 destroy_region (*i);
2882 Session::remove_last_capture ()
2884 list<boost::shared_ptr<Region> > r;
2886 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
2888 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
2889 list<boost::shared_ptr<Region> >& l = (*i)->last_capture_regions();
2892 r.insert (r.end(), l.begin(), l.end());
2897 destroy_regions (r);
2902 Session::remove_region_from_region_list (boost::shared_ptr<Region> r)
2908 /* Source Management */
2910 Session::add_source (boost::shared_ptr<Source> source)
2912 cerr << "add new source " << source->name() << endl;
2914 pair<SourceMap::key_type, SourceMap::mapped_type> entry;
2915 pair<SourceMap::iterator,bool> result;
2917 entry.first = source->id();
2918 entry.second = source;
2921 Glib::Mutex::Lock lm (source_lock);
2922 result = sources.insert (entry);
2925 if (!result.second) {
2926 cerr << "\tNOT inserted ? " << result.second << endl;
2929 source->GoingAway.connect (sigc::bind (mem_fun (this, &Session::remove_source), boost::weak_ptr<Source> (source)));
2932 SourceAdded (source); /* EMIT SIGNAL */
2936 Session::remove_source (boost::weak_ptr<Source> src)
2938 SourceMap::iterator i;
2939 boost::shared_ptr<Source> source = src.lock();
2942 cerr << "removing a source DEAD\n";
2944 cerr << "removing a source " << source->name () << endl;
2947 Glib::Mutex::Lock lm (source_lock);
2949 if ((i = sources.find (source->id())) != sources.end()) {
2954 if (!_state_of_the_state & InCleanup) {
2956 /* save state so we don't end up with a session file
2957 referring to non-existent sources.
2960 save_state (_current_snapshot_name);
2963 SourceRemoved(source); /* EMIT SIGNAL */
2967 boost::shared_ptr<Source>
2968 Session::source_by_id (const PBD::ID& id)
2970 Glib::Mutex::Lock lm (source_lock);
2971 SourceMap::iterator i;
2972 boost::shared_ptr<Source> source;
2974 if ((i = sources.find (id)) != sources.end()) {
2978 /* XXX search MIDI or other searches here */
2984 Session::peak_path_from_audio_path (string audio_path)
2986 /* XXX hardly bombproof! fix me */
2990 res = Glib::path_get_dirname (audio_path);
2991 res = Glib::path_get_dirname (res);
2993 res += peak_dir_name;
2995 res += PBD::basename_nosuffix (audio_path);
3002 Session::change_audio_path_by_name (string path, string oldname, string newname, bool destructive)
3005 string old_basename = PBD::basename_nosuffix (oldname);
3006 string new_legalized = legalize_for_path (newname);
3008 /* note: we know (or assume) the old path is already valid */
3012 /* destructive file sources have a name of the form:
3014 /path/to/Tnnnn-NAME(%[LR])?.wav
3016 the task here is to replace NAME with the new name.
3019 /* find last slash */
3023 string::size_type slash;
3024 string::size_type dash;
3026 if ((slash = path.find_last_of ('/')) == string::npos) {
3030 dir = path.substr (0, slash+1);
3032 /* '-' is not a legal character for the NAME part of the path */
3034 if ((dash = path.find_last_of ('-')) == string::npos) {
3038 prefix = path.substr (slash+1, dash-(slash+1));
3043 path += new_legalized;
3044 path += ".wav"; /* XXX gag me with a spoon */
3048 /* non-destructive file sources have a name of the form:
3050 /path/to/NAME-nnnnn(%[LR])?.wav
3052 the task here is to replace NAME with the new name.
3057 string::size_type slash;
3058 string::size_type dash;
3059 string::size_type postfix;
3061 /* find last slash */
3063 if ((slash = path.find_last_of ('/')) == string::npos) {
3067 dir = path.substr (0, slash+1);
3069 /* '-' is not a legal character for the NAME part of the path */
3071 if ((dash = path.find_last_of ('-')) == string::npos) {
3075 suffix = path.substr (dash+1);
3077 // Suffix is now everything after the dash. Now we need to eliminate
3078 // the nnnnn part, which is done by either finding a '%' or a '.'
3080 postfix = suffix.find_last_of ("%");
3081 if (postfix == string::npos) {
3082 postfix = suffix.find_last_of ('.');
3085 if (postfix != string::npos) {
3086 suffix = suffix.substr (postfix);
3088 error << "Logic error in Session::change_audio_path_by_name(), please report to the developers" << endl;
3092 const uint32_t limit = 10000;
3093 char buf[PATH_MAX+1];
3095 for (uint32_t cnt = 1; cnt <= limit; ++cnt) {
3097 snprintf (buf, sizeof(buf), "%s%s-%u%s", dir.c_str(), newname.c_str(), cnt, suffix.c_str());
3099 if (access (buf, F_OK) != 0) {
3107 error << "FATAL ERROR! Could not find a " << endl;
3116 Session::audio_path_from_name (string name, uint32_t nchan, uint32_t chan, bool destructive)
3120 char buf[PATH_MAX+1];
3121 const uint32_t limit = 10000;
3125 legalized = legalize_for_path (name);
3127 /* find a "version" of the file name that doesn't exist in
3128 any of the possible directories.
3131 for (cnt = (destructive ? ++destructive_index : 1); cnt <= limit; ++cnt) {
3133 vector<space_and_path>::iterator i;
3134 uint32_t existing = 0;
3136 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3141 spath += tape_dir_name;
3143 spath += sound_dir_name;
3148 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3149 } else if (nchan == 2) {
3151 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%L.wav", spath.c_str(), cnt, legalized.c_str());
3153 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%R.wav", spath.c_str(), cnt, legalized.c_str());
3155 } else if (nchan < 26) {
3156 snprintf (buf, sizeof(buf), "%s/T%04d-%s%%%c.wav", spath.c_str(), cnt, legalized.c_str(), 'a' + chan);
3158 snprintf (buf, sizeof(buf), "%s/T%04d-%s.wav", spath.c_str(), cnt, legalized.c_str());
3166 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3167 } else if (nchan == 2) {
3169 snprintf (buf, sizeof(buf), "%s-%u%%L.wav", spath.c_str(), cnt);
3171 snprintf (buf, sizeof(buf), "%s-%u%%R.wav", spath.c_str(), cnt);
3173 } else if (nchan < 26) {
3174 snprintf (buf, sizeof(buf), "%s-%u%%%c.wav", spath.c_str(), cnt, 'a' + chan);
3176 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
3180 if (access (buf, F_OK) == 0) {
3185 if (existing == 0) {
3190 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3191 throw failed_constructor();
3195 /* we now have a unique name for the file, but figure out where to
3202 spath = tape_dir ();
3204 spath = discover_best_sound_dir ();
3207 string::size_type pos = foo.find_last_of ('/');
3209 if (pos == string::npos) {
3212 spath += foo.substr (pos + 1);
3218 boost::shared_ptr<AudioFileSource>
3219 Session::create_audio_source_for_session (AudioDiskstream& ds, uint32_t chan, bool destructive)
3221 string spath = audio_path_from_name (ds.name(), ds.n_channels().get(DataType::AUDIO), chan, destructive);
3222 return boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (DataType::AUDIO, spath, destructive, frame_rate()));
3226 Session::midi_path_from_name (string name)
3230 char buf[PATH_MAX+1];
3231 const uint32_t limit = 10000;
3235 legalized = legalize_for_path (name);
3237 /* find a "version" of the file name that doesn't exist in
3238 any of the possible directories.
3241 for (cnt = 1; cnt <= limit; ++cnt) {
3243 vector<space_and_path>::iterator i;
3244 uint32_t existing = 0;
3246 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
3248 // FIXME: different directory from audio?
3249 spath = (*i).path + sound_dir_name + "/" + legalized;
3251 snprintf (buf, sizeof(buf), "%s-%u.mid", spath.c_str(), cnt);
3253 if (access (buf, F_OK) == 0) {
3258 if (existing == 0) {
3263 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, name) << endmsg;
3264 throw failed_constructor();
3268 /* we now have a unique name for the file, but figure out where to
3274 // FIXME: different directory than audio?
3275 spath = discover_best_sound_dir ();
3277 string::size_type pos = foo.find_last_of ('/');
3279 if (pos == string::npos) {
3282 spath += foo.substr (pos + 1);
3288 boost::shared_ptr<MidiSource>
3289 Session::create_midi_source_for_session (MidiDiskstream& ds)
3291 string spath = midi_path_from_name (ds.name());
3293 return boost::dynamic_pointer_cast<SMFSource> (SourceFactory::createWritable (DataType::MIDI, spath, false, frame_rate()));
3297 /* Playlist management */
3300 Session::playlist_by_name (string name)
3302 Glib::Mutex::Lock lm (playlist_lock);
3303 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3304 if ((*i)->name() == name) {
3308 for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ++i) {
3309 if ((*i)->name() == name) {
3317 Session::add_playlist (Playlist* playlist)
3319 if (playlist->hidden()) {
3324 Glib::Mutex::Lock lm (playlist_lock);
3325 if (find (playlists.begin(), playlists.end(), playlist) == playlists.end()) {
3326 playlists.insert (playlists.begin(), playlist);
3328 playlist->InUse.connect (mem_fun (*this, &Session::track_playlist));
3329 playlist->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_playlist), playlist));
3335 PlaylistAdded (playlist); /* EMIT SIGNAL */
3339 Session::track_playlist (Playlist* pl, bool inuse)
3341 PlaylistList::iterator x;
3344 Glib::Mutex::Lock lm (playlist_lock);
3347 //cerr << "shifting playlist to unused: " << pl->name() << endl;
3349 unused_playlists.insert (pl);
3351 if ((x = playlists.find (pl)) != playlists.end()) {
3352 playlists.erase (x);
3357 //cerr << "shifting playlist to used: " << pl->name() << endl;
3359 playlists.insert (pl);
3361 if ((x = unused_playlists.find (pl)) != unused_playlists.end()) {
3362 unused_playlists.erase (x);
3369 Session::remove_playlist (Playlist* playlist)
3371 if (_state_of_the_state & Deletion) {
3376 Glib::Mutex::Lock lm (playlist_lock);
3377 // cerr << "removing playlist: " << playlist->name() << endl;
3379 PlaylistList::iterator i;
3381 i = find (playlists.begin(), playlists.end(), playlist);
3383 if (i != playlists.end()) {
3384 playlists.erase (i);
3387 i = find (unused_playlists.begin(), unused_playlists.end(), playlist);
3388 if (i != unused_playlists.end()) {
3389 unused_playlists.erase (i);
3396 PlaylistRemoved (playlist); /* EMIT SIGNAL */
3400 Session::set_audition (boost::shared_ptr<Region> r)
3402 pending_audition_region = r;
3403 post_transport_work = PostTransportWork (post_transport_work | PostTransportAudition);
3404 schedule_butler_transport_work ();
3408 Session::audition_playlist ()
3410 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3411 ev->region.reset ();
3416 Session::non_realtime_set_audition ()
3418 if (!pending_audition_region) {
3419 auditioner->audition_current_playlist ();
3421 auditioner->audition_region (pending_audition_region);
3422 pending_audition_region.reset ();
3424 AuditionActive (true); /* EMIT SIGNAL */
3428 Session::audition_region (boost::shared_ptr<Region> r)
3430 Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
3436 Session::cancel_audition ()
3438 if (auditioner->active()) {
3439 auditioner->cancel_audition ();
3440 AuditionActive (false); /* EMIT SIGNAL */
3445 Session::RoutePublicOrderSorter::operator() (boost::shared_ptr<Route> a, boost::shared_ptr<Route> b)
3447 return a->order_key(N_("signal")) < b->order_key(N_("signal"));
3451 Session::remove_empty_sounds ()
3454 PathScanner scanner;
3459 vector<string *>* possible_audiofiles = scanner (dir, "\\.wav$", false, true);
3461 for (vector<string *>::iterator i = possible_audiofiles->begin(); i != possible_audiofiles->end(); ++i) {
3463 if (AudioFileSource::is_empty (*(*i))) {
3465 unlink ((*i)->c_str());
3467 string peak_path = peak_path_from_audio_path (**i);
3468 unlink (peak_path.c_str());
3474 delete possible_audiofiles;
3478 Session::is_auditioning () const
3480 /* can be called before we have an auditioner object */
3482 return auditioner->active();
3489 Session::set_all_solo (bool yn)
3491 shared_ptr<RouteList> r = routes.reader ();
3493 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3494 if (!(*i)->hidden()) {
3495 (*i)->set_solo (yn, this);
3503 Session::set_all_mute (bool yn)
3505 shared_ptr<RouteList> r = routes.reader ();
3507 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3508 if (!(*i)->hidden()) {
3509 (*i)->set_mute (yn, this);
3517 Session::n_diskstreams () const
3521 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3523 for (DiskstreamList::const_iterator i = dsl->begin(); i != dsl->end(); ++i) {
3524 if (!(*i)->hidden()) {
3532 Session::graph_reordered ()
3534 /* don't do this stuff if we are setting up connections
3535 from a set_state() call.
3538 if (_state_of_the_state & InitialConnecting) {
3544 /* force all diskstreams to update their capture offset values to
3545 reflect any changes in latencies within the graph.
3548 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3550 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
3551 (*i)->set_capture_offset ();
3556 Session::record_disenable_all ()
3558 record_enable_change_all (false);
3562 Session::record_enable_all ()
3564 record_enable_change_all (true);
3568 Session::record_enable_change_all (bool yn)
3570 shared_ptr<RouteList> r = routes.reader ();
3572 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3575 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
3576 at->set_record_enable (yn, this);
3580 /* since we don't keep rec-enable state, don't mark session dirty */
3584 Session::add_redirect (Redirect* redirect)
3588 PortInsert* port_insert;
3589 PluginInsert* plugin_insert;
3591 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3592 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3593 _port_inserts.insert (_port_inserts.begin(), port_insert);
3594 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3595 _plugin_inserts.insert (_plugin_inserts.begin(), plugin_insert);
3597 fatal << _("programming error: unknown type of Insert created!") << endmsg;
3600 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3601 _sends.insert (_sends.begin(), send);
3603 fatal << _("programming error: unknown type of Redirect created!") << endmsg;
3607 redirect->GoingAway.connect (sigc::bind (mem_fun (*this, &Session::remove_redirect), redirect));
3613 Session::remove_redirect (Redirect* redirect)
3617 PortInsert* port_insert;
3618 PluginInsert* plugin_insert;
3620 if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3621 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3622 _port_inserts.remove (port_insert);
3623 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3624 _plugin_inserts.remove (plugin_insert);
3626 fatal << _("programming error: unknown type of Insert deleted!") << endmsg;
3629 } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3630 _sends.remove (send);
3632 fatal << _("programming error: unknown type of Redirect deleted!") << endmsg;
3640 Session::available_capture_duration ()
3642 const double scale = 4096.0 / sizeof (Sample);
3644 if (_total_free_4k_blocks * scale > (double) max_frames) {
3648 return (jack_nframes_t) floor (_total_free_4k_blocks * scale);
3652 Session::add_connection (ARDOUR::Connection* connection)
3655 Glib::Mutex::Lock guard (connection_lock);
3656 _connections.push_back (connection);
3659 ConnectionAdded (connection); /* EMIT SIGNAL */
3665 Session::remove_connection (ARDOUR::Connection* connection)
3667 bool removed = false;
3670 Glib::Mutex::Lock guard (connection_lock);
3671 ConnectionList::iterator i = find (_connections.begin(), _connections.end(), connection);
3673 if (i != _connections.end()) {
3674 _connections.erase (i);
3680 ConnectionRemoved (connection); /* EMIT SIGNAL */
3686 ARDOUR::Connection *
3687 Session::connection_by_name (string name) const
3689 Glib::Mutex::Lock lm (connection_lock);
3691 for (ConnectionList::const_iterator i = _connections.begin(); i != _connections.end(); ++i) {
3692 if ((*i)->name() == name) {
3701 Session::set_edit_mode (EditMode mode)
3706 Glib::Mutex::Lock lm (playlist_lock);
3708 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3709 (*i)->set_edit_mode (mode);
3714 ControlChanged (EditingMode); /* EMIT SIGNAL */
3718 Session::tempo_map_changed (Change ignored)
3724 /** Ensures that all buffers (scratch, send, silent, etc) are allocated for
3725 * the given count with the current block size.
3728 Session::ensure_buffers (ChanCount howmany)
3730 // FIXME: NASTY assumption (midi block size == audio block size)
3731 _scratch_buffers->ensure_buffers(howmany, current_block_size);
3732 _send_buffers->ensure_buffers(howmany, current_block_size);
3733 _silent_buffers->ensure_buffers(howmany, current_block_size);
3735 allocate_pan_automation_buffers (current_block_size, howmany.get(DataType::AUDIO), false);
3739 Session::next_send_name ()
3742 snprintf (buf, sizeof (buf), "send %" PRIu32, ++send_cnt);
3747 Session::next_insert_name ()
3750 snprintf (buf, sizeof (buf), "insert %" PRIu32, ++insert_cnt);
3754 /* Named Selection management */
3757 Session::named_selection_by_name (string name)
3759 Glib::Mutex::Lock lm (named_selection_lock);
3760 for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) {
3761 if ((*i)->name == name) {
3769 Session::add_named_selection (NamedSelection* named_selection)
3772 Glib::Mutex::Lock lm (named_selection_lock);
3773 named_selections.insert (named_selections.begin(), named_selection);
3778 NamedSelectionAdded (); /* EMIT SIGNAL */
3782 Session::remove_named_selection (NamedSelection* named_selection)
3784 bool removed = false;
3787 Glib::Mutex::Lock lm (named_selection_lock);
3789 NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection);
3791 if (i != named_selections.end()) {
3793 named_selections.erase (i);
3800 NamedSelectionRemoved (); /* EMIT SIGNAL */
3805 Session::reset_native_file_format ()
3807 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
3809 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
3810 (*i)->reset_write_sources (false);
3815 Session::route_name_unique (string n) const
3817 shared_ptr<RouteList> r = routes.reader ();
3819 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
3820 if ((*i)->name() == n) {
3829 Session::cleanup_audio_file_source (boost::shared_ptr<AudioFileSource> fs)
3831 return fs->move_to_trash (dead_sound_dir_name);
3835 Session::n_playlists () const
3837 Glib::Mutex::Lock lm (playlist_lock);
3838 return playlists.size();
3842 Session::set_solo_model (SoloModel sm)
3844 if (sm != _solo_model) {
3846 ControlChanged (SoloingModel);
3852 Session::allocate_pan_automation_buffers (jack_nframes_t nframes, uint32_t howmany, bool force)
3854 if (!force && howmany <= _npan_buffers) {
3858 if (_pan_automation_buffer) {
3860 for (uint32_t i = 0; i < _npan_buffers; ++i) {
3861 delete [] _pan_automation_buffer[i];
3864 delete [] _pan_automation_buffer;
3867 _pan_automation_buffer = new pan_t*[howmany];
3869 for (uint32_t i = 0; i < howmany; ++i) {
3870 _pan_automation_buffer[i] = new pan_t[nframes];
3873 _npan_buffers = howmany;
3877 Session::freeze (InterThreadInfo& itt)
3879 shared_ptr<RouteList> r = routes.reader ();
3881 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
3885 if ((at = dynamic_cast<Track*>((*i).get())) != 0) {
3886 /* XXX this is wrong because itt.progress will keep returning to zero at the start
3897 Session::write_one_audio_track (AudioTrack& track, jack_nframes_t start, jack_nframes_t len,
3898 bool overwrite, vector<boost::shared_ptr<Source> >& srcs, InterThreadInfo& itt)
3900 boost::shared_ptr<AudioFileSource> fsource;
3903 Playlist* playlist = 0;
3905 char buf[PATH_MAX+1];
3907 ChanCount nchans(track.audio_diskstream()->n_channels());
3908 jack_nframes_t position;
3909 jack_nframes_t this_chunk;
3910 jack_nframes_t to_do;
3913 // any bigger than this seems to cause stack overflows in called functions
3914 const jack_nframes_t chunk_size = (128 * 1024)/4;
3916 g_atomic_int_set (&processing_prohibited, 1);
3918 /* call tree *MUST* hold route_lock */
3920 if ((playlist = track.diskstream()->playlist()) == 0) {
3924 /* external redirects will be a problem */
3926 if (track.has_external_redirects()) {
3930 dir = discover_best_sound_dir ();
3932 for (uint32_t chan_n=0; chan_n < nchans.get(DataType::AUDIO); ++chan_n) {
3934 for (x = 0; x < 99999; ++x) {
3935 snprintf (buf, sizeof(buf), "%s/%s-%d-bounce-%" PRIu32 ".wav", dir.c_str(), playlist->name().c_str(), chan_n, x+1);
3936 if (access (buf, F_OK) != 0) {
3942 error << string_compose (_("too many bounced versions of playlist \"%1\""), playlist->name()) << endmsg;
3947 fsource = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (DataType::AUDIO, buf, false, frame_rate()));
3950 catch (failed_constructor& err) {
3951 error << string_compose (_("cannot create new audio file \"%1\" for %2"), buf, track.name()) << endmsg;
3955 srcs.push_back (fsource);
3958 /* XXX need to flush all redirects */
3963 /* create a set of reasonably-sized buffers */
3964 buffers.ensure_buffers(nchans, chunk_size);
3965 buffers.set_count(nchans);
3967 while (to_do && !itt.cancel) {
3969 this_chunk = min (to_do, chunk_size);
3971 if (track.export_stuff (buffers, start, this_chunk)) {
3976 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) {
3977 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
3980 if (afs->write (buffers.get_audio(n).data(this_chunk), this_chunk) != this_chunk) {
3986 start += this_chunk;
3987 to_do -= this_chunk;
3989 itt.progress = (float) (1.0 - ((double) to_do / len));
3998 xnow = localtime (&now);
4000 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src) {
4001 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4004 afs->update_header (position, *xnow, now);
4008 /* build peakfile for new source */
4010 for (vector<boost::shared_ptr<Source> >::iterator src=srcs.begin(); src != srcs.end(); ++src) {
4011 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4013 afs->build_peaks ();
4022 for (vector<boost::shared_ptr<Source> >::iterator src = srcs.begin(); src != srcs.end(); ++src) {
4023 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource>(*src);
4026 afs->mark_for_remove ();
4029 (*src)->drop_references ();
4033 g_atomic_int_set (&processing_prohibited, 0);
4041 Session::get_silent_buffers (ChanCount count)
4043 assert(_silent_buffers->available() >= count);
4044 _silent_buffers->set_count(count);
4046 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
4047 for (size_t i=0; i < count.get(*t); ++i) {
4048 _silent_buffers->get(*t, i).clear();
4052 return *_silent_buffers;
4056 Session::get_scratch_buffers (ChanCount count)
4058 assert(_scratch_buffers->available() >= count);
4059 _scratch_buffers->set_count(count);
4060 return *_scratch_buffers;
4064 Session::get_send_buffers (ChanCount count)
4066 assert(_send_buffers->available() >= count);
4067 _send_buffers->set_count(count);
4068 return *_send_buffers;
4072 Session::ntracks () const
4075 shared_ptr<RouteList> r = routes.reader ();
4077 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
4078 if (dynamic_cast<Track*> ((*i).get())) {
4087 Session::nbusses () const
4090 shared_ptr<RouteList> r = routes.reader ();
4092 for (RouteList::const_iterator i = r->begin(); i != r->end(); ++i) {
4093 if (dynamic_cast<Track*> ((*i).get()) == 0) {
4102 Session::set_layer_model (LayerModel lm)
4104 if (lm != layer_model) {
4107 ControlChanged (LayeringModel);
4112 Session::set_xfade_model (CrossfadeModel xm)
4114 if (xm != xfade_model) {
4117 ControlChanged (CrossfadingModel);
4122 Session::add_curve(Curve *curve)
4124 curves[curve->id()] = curve;
4128 Session::add_automation_list(AutomationList *al)
4130 automation_lists[al->id()] = al;